[feat] solution: 추천 일정 카드에 출발지(업소명·출발 시각) 한 줄을 얹는다

This commit is contained in:
김성경 2026-09-11 14:07:17 +09:00
parent 6760b38fec
commit 8a2964ebf7
2 changed files with 26 additions and 1 deletions

View File

@ -18,6 +18,7 @@ import {
type PlannedStop,
} from '@o2o/shared';
import {useLocalGuide} from '@/hooks/useLocalGuide';
import {useBuilderStore} from '@/stores/builder';
import {SectionBody, SectionFrame, Rail} from '../../primitives';
import type {SectionRenderProps} from '../../types';
import {
@ -36,6 +37,7 @@ export function ItineraryTickets(props: SectionRenderProps) {
const {section, isSelected, onSelect} = props;
const parsed = parseSectionData<ItineraryItem>(section.type, section.data);
const guide = useLocalGuide();
const placeName = useBuilderStore((s) => s.storeName);
// 사장님이 적은 것이 언제나 이긴다 — 서버가 만든 건 비었을 때의 기본값이다.
const items = parsed.items.length > 0 ? parsed.items : guide.itineraries;
const live = currentSeasons();
@ -105,6 +107,13 @@ export function ItineraryTickets(props: SectionRenderProps) {
{itineraryDays(item).map((entry, dayIndex) => (
<div key={`${entry.label}-${dayIndex}`} className="space-y-1.5">
{/* . (
) . */}
{dayIndex === 0 && placeName && (
<p className="text-[11px] opacity-50">
{placeName} · {entry.day.from}
</p>
)}
{entry.label && (
<p className="text-[11px] font-bold" style={{color: ITEM_ACCENT}}>
{entry.label}

View File

@ -51,12 +51,15 @@ function DayCard({
startTime,
stops,
first,
placeName,
}: {
item: ItineraryItem;
badge: string;
startTime?: string;
stops: PlannerStop[];
first: boolean;
/** 업소 상호명 — 출발지 표시용. 일정 데이터에는 없다(프롬프트가 정거장으로 못 넣게 막는다). */
placeName: string;
}) {
const day = planDay({name: item.name, startTime, stops});
@ -102,6 +105,9 @@ function DayCard({
{/* ★ why·audience 는 첫 장만 — 다 채우면 같은 문구가 이틀·사흘 반복된다. */}
{first && item.audience && <p className="text-[12px] opacity-60">{item.audience}</p>}
{first && item.why && <p className="text-[13px] leading-relaxed opacity-80">{item.why}</p>}
{/* ( audience·why ). day.from planDay
(item.startTime) . */}
{first && <p className="text-[11px] opacity-50">{placeName} · {day.from}</p>}
</div>
<RouteMap stops={day.stops.map((planned) => planned.stop)} />
@ -231,6 +237,7 @@ export function ItinerarySection() {
key={active}
tab={tab}
items={items.filter((item) => (item.duration?.trim() || NO_DURATION) === tab)}
placeName={payload.place.name}
/>
</div>
))}
@ -254,7 +261,15 @@ export function ItinerarySection() {
* `audience`("차 없이 오는 손님") .
* , .
*/
function DurationRail({tab, items}: {tab: string; items: ItineraryItem[]}) {
function DurationRail({
tab,
items,
placeName,
}: {
tab: string;
items: ItineraryItem[];
placeName: string;
}) {
/** 코스별 시작 위치와 길이. 레일 인덱스 ↔ 코스를 잇는 유일한 표다. */
const courses = useMemo(() => {
let cursor = 0;
@ -311,6 +326,7 @@ function DurationRail({tab, items}: {tab: string; items: ItineraryItem[]}) {
startTime={day.startTime}
stops={day.stops}
first={dayIndex === 0}
placeName={placeName}
/>
)),
)}