Propagate waypoint notes through session init, save-to-journal, and Journal display
- use-yjs: seed note from initialWaypoints on session open - api.sessions: include note in initialWaypoints type - SaveToJournalButton: include note in GPX waypoints on save - Journal routes.: map and display waypoint notes Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
This commit is contained in:
parent
353dcb2c13
commit
02f8a8be44
5 changed files with 14 additions and 6 deletions
|
|
@ -35,7 +35,7 @@ export async function action({ params, request }: Route.ActionArgs) {
|
||||||
|
|
||||||
const session = (await sessionResp.json()) as {
|
const session = (await sessionResp.json()) as {
|
||||||
url: string;
|
url: string;
|
||||||
initialWaypoints?: Array<{ lat: number; lon: number; name?: string }>;
|
initialWaypoints?: Array<{ lat: number; lon: number; name?: string; isDayBreak?: boolean; note?: string; osmId?: number; poiTags?: Record<string, string> }>;
|
||||||
initialNoGoAreas?: Array<{ points: Array<{ lat: number; lon: number }> }>;
|
initialNoGoAreas?: Array<{ points: Array<{ lat: number; lon: number }> }>;
|
||||||
initialNotes?: string;
|
initialNotes?: string;
|
||||||
};
|
};
|
||||||
|
|
|
||||||
|
|
@ -32,7 +32,7 @@ export async function loader({ params, request }: Route.LoaderArgs) {
|
||||||
|
|
||||||
// Parse GPX once for day stats and waypoint POI data
|
// Parse GPX once for day stats and waypoint POI data
|
||||||
let dayStats: Array<{ dayNumber: number; startName?: string; endName?: string; distance: number; ascent: number; descent: number }> = [];
|
let dayStats: Array<{ dayNumber: number; startName?: string; endName?: string; distance: number; ascent: number; descent: number }> = [];
|
||||||
let waypoints: Array<{ lat: number; lon: number; name?: string; isDayBreak?: boolean; osmId?: number; poiTags?: Record<string, string> }> = [];
|
let waypoints: Array<{ lat: number; lon: number; name?: string; isDayBreak?: boolean; note?: string; osmId?: number; poiTags?: Record<string, string> }> = [];
|
||||||
if (route.gpx) {
|
if (route.gpx) {
|
||||||
try {
|
try {
|
||||||
const { computeDays, parseGpxAsync } = await import("@trails-cool/gpx");
|
const { computeDays, parseGpxAsync } = await import("@trails-cool/gpx");
|
||||||
|
|
@ -42,6 +42,7 @@ export async function loader({ params, request }: Route.LoaderArgs) {
|
||||||
lon: w.lon,
|
lon: w.lon,
|
||||||
name: w.name,
|
name: w.name,
|
||||||
isDayBreak: w.isDayBreak,
|
isDayBreak: w.isDayBreak,
|
||||||
|
note: w.note,
|
||||||
osmId: w.osmId,
|
osmId: w.osmId,
|
||||||
poiTags: w.poiTags as Record<string, string> | undefined,
|
poiTags: w.poiTags as Record<string, string> | undefined,
|
||||||
}));
|
}));
|
||||||
|
|
@ -398,15 +399,18 @@ export default function RouteDetailPage({ loaderData }: Route.ComponentProps) {
|
||||||
</div>
|
</div>
|
||||||
)}
|
)}
|
||||||
|
|
||||||
{waypoints.some((w) => w.osmId || w.poiTags) && (
|
{waypoints.some((w) => w.osmId || w.poiTags || w.note) && (
|
||||||
<div className="mt-6">
|
<div className="mt-6">
|
||||||
<h2 className="text-lg font-semibold text-gray-900">{t("routes.waypoints")}</h2>
|
<h2 className="text-lg font-semibold text-gray-900">{t("routes.waypoints")}</h2>
|
||||||
<ul className="mt-3 divide-y divide-gray-200 rounded-md border border-gray-200">
|
<ul className="mt-3 divide-y divide-gray-200 rounded-md border border-gray-200">
|
||||||
{waypoints.filter((w) => w.osmId || w.poiTags || w.name).map((w, i) => (
|
{waypoints.filter((w) => w.osmId || w.poiTags || w.note || w.name).map((w, i) => (
|
||||||
<li key={i} className="px-4 py-3">
|
<li key={i} className="px-4 py-3">
|
||||||
<p className="font-medium text-gray-900">
|
<p className="font-medium text-gray-900">
|
||||||
{w.name ?? `${w.lat.toFixed(5)}, ${w.lon.toFixed(5)}`}
|
{w.name ?? `${w.lat.toFixed(5)}, ${w.lon.toFixed(5)}`}
|
||||||
</p>
|
</p>
|
||||||
|
{w.note && (
|
||||||
|
<p className="mt-1 whitespace-pre-wrap text-sm text-gray-600">{w.note}</p>
|
||||||
|
)}
|
||||||
{w.poiTags && (
|
{w.poiTags && (
|
||||||
<dl className="mt-1 space-y-0.5 text-sm text-gray-600">
|
<dl className="mt-1 space-y-0.5 text-sm text-gray-600">
|
||||||
{w.poiTags.phone && (
|
{w.poiTags.phone && (
|
||||||
|
|
|
||||||
|
|
@ -47,6 +47,7 @@ export function SaveToJournalButton({ yjs, callbackUrl, callbackToken, returnUrl
|
||||||
lon: yMap.get("lon") as number,
|
lon: yMap.get("lon") as number,
|
||||||
name: yMap.get("name") as string | undefined,
|
name: yMap.get("name") as string | undefined,
|
||||||
isDayBreak: yMap.get("overnight") === true ? true : undefined,
|
isDayBreak: yMap.get("overnight") === true ? true : undefined,
|
||||||
|
note: yMap.get("note") as string | undefined,
|
||||||
osmId: yMap.get("osmId") as number | undefined,
|
osmId: yMap.get("osmId") as number | undefined,
|
||||||
poiTags: yMap.get("poiTags") as WaypointPoiTags | undefined,
|
poiTags: yMap.get("poiTags") as WaypointPoiTags | undefined,
|
||||||
}));
|
}));
|
||||||
|
|
|
||||||
|
|
@ -42,7 +42,7 @@ export interface YjsState {
|
||||||
|
|
||||||
export function useYjs(
|
export function useYjs(
|
||||||
sessionId: string,
|
sessionId: string,
|
||||||
initialWaypoints?: Array<{ lat: number; lon: number; name?: string; isDayBreak?: boolean }>,
|
initialWaypoints?: Array<{ lat: number; lon: number; name?: string; isDayBreak?: boolean; note?: string; osmId?: number; poiTags?: Record<string, string> }>,
|
||||||
initialNoGoAreas?: Array<{ points: Array<{ lat: number; lon: number }> }>,
|
initialNoGoAreas?: Array<{ points: Array<{ lat: number; lon: number }> }>,
|
||||||
initialNotes?: string,
|
initialNotes?: string,
|
||||||
): YjsState | null {
|
): YjsState | null {
|
||||||
|
|
@ -108,6 +108,9 @@ export function useYjs(
|
||||||
yMap.set("lon", wp.lon);
|
yMap.set("lon", wp.lon);
|
||||||
if (wp.name) yMap.set("name", wp.name);
|
if (wp.name) yMap.set("name", wp.name);
|
||||||
if (wp.isDayBreak) yMap.set("overnight", true);
|
if (wp.isDayBreak) yMap.set("overnight", true);
|
||||||
|
if (wp.note) yMap.set("note", wp.note);
|
||||||
|
if (wp.osmId !== undefined) yMap.set("osmId", wp.osmId);
|
||||||
|
if (wp.poiTags) yMap.set("poiTags", wp.poiTags);
|
||||||
waypoints.push([yMap]);
|
waypoints.push([yMap]);
|
||||||
}
|
}
|
||||||
if (initialNoGoAreas?.length && noGoAreas.length === 0) {
|
if (initialNoGoAreas?.length && noGoAreas.length === 0) {
|
||||||
|
|
|
||||||
|
|
@ -19,7 +19,7 @@ export async function action({ request }: Route.ActionArgs) {
|
||||||
return withDb(async () => {
|
return withDb(async () => {
|
||||||
const session = await createSession({ callbackUrl, callbackToken });
|
const session = await createSession({ callbackUrl, callbackToken });
|
||||||
|
|
||||||
let initialWaypoints: Array<{ lat: number; lon: number; name?: string; isDayBreak?: boolean }> | undefined;
|
let initialWaypoints: Array<{ lat: number; lon: number; name?: string; isDayBreak?: boolean; note?: string; osmId?: number; poiTags?: Record<string, string> }> | undefined;
|
||||||
let initialNoGoAreas: Array<{ points: Array<{ lat: number; lon: number }> }> | undefined;
|
let initialNoGoAreas: Array<{ points: Array<{ lat: number; lon: number }> }> | undefined;
|
||||||
let initialNotes: string | undefined;
|
let initialNotes: string | undefined;
|
||||||
if (gpx) {
|
if (gpx) {
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue