added privacy switches and documents, assets and local storage for already visited POIs
This commit is contained in:
+79
-7
@@ -9,13 +9,61 @@
|
||||
routeState: 'idle',
|
||||
activePage: null,
|
||||
routeProgressIndex: null,
|
||||
deviceHeading: null
|
||||
deviceHeading: null,
|
||||
viewed: new Set(),
|
||||
playedAudio: new Set(),
|
||||
activePoiId: null,
|
||||
persistTimer: null
|
||||
};
|
||||
|
||||
function escapeHtml(value) {
|
||||
return $('<div>').text(value ?? '').html();
|
||||
}
|
||||
|
||||
|
||||
function persistRouteProgress() {
|
||||
if (!state.route) return;
|
||||
if (state.persistTimer != null) {
|
||||
globalThis.clearTimeout(state.persistTimer);
|
||||
state.persistTimer = null;
|
||||
}
|
||||
|
||||
ns.PrivacyStorage.saveRouteState(
|
||||
state.route,
|
||||
state.routeState,
|
||||
state.routeProgressIndex,
|
||||
[...state.triggered],
|
||||
[...state.viewed],
|
||||
[...state.playedAudio]
|
||||
);
|
||||
}
|
||||
|
||||
function scheduleRouteProgressPersist() {
|
||||
if (!state.route || state.persistTimer != null) return;
|
||||
state.persistTimer = globalThis.setTimeout(persistRouteProgress, 1200);
|
||||
}
|
||||
|
||||
function restoreRouteProgress(route) {
|
||||
const saved = ns.PrivacyStorage.activateRoute(route);
|
||||
state.triggered = new Set(saved?.visitedPoiIds ?? []);
|
||||
state.viewed = new Set(saved?.viewedPoiIds ?? []);
|
||||
state.playedAudio = new Set(saved?.playedAudioPoiIds ?? []);
|
||||
state.routeProgressIndex = Number.isInteger(saved?.routeProgressIndex)
|
||||
? saved.routeProgressIndex
|
||||
: null;
|
||||
state.routeState = saved?.routeState === 'running' || saved?.routeState === 'paused'
|
||||
? 'paused'
|
||||
: 'idle';
|
||||
|
||||
if (state.routeState === 'paused') {
|
||||
$('#tracking-status')
|
||||
.prop('hidden', false)
|
||||
.text('Gespeicherter Streckenfortschritt gefunden. Die Route kann fortgesetzt werden.');
|
||||
} else {
|
||||
$('#tracking-status').prop('hidden', true).text('');
|
||||
}
|
||||
}
|
||||
|
||||
function activate(selector, handler) {
|
||||
$(document)
|
||||
.on('pointerup', selector, function (event) {
|
||||
@@ -185,8 +233,12 @@
|
||||
function endRoute({ announce = true, returnToRoutes = false } = {}) {
|
||||
const wasActive = state.routeState !== 'idle';
|
||||
state.routeState = 'idle';
|
||||
persistRouteProgress();
|
||||
state.routeProgressIndex = null;
|
||||
state.triggered.clear();
|
||||
state.viewed.clear();
|
||||
state.playedAudio.clear();
|
||||
state.activePoiId = null;
|
||||
stopRouteSensors();
|
||||
ns.AudioPlayer.unload();
|
||||
setActivePoi(null);
|
||||
@@ -210,6 +262,7 @@
|
||||
if (state.routeState !== 'running') return;
|
||||
|
||||
state.routeState = 'paused';
|
||||
persistRouteProgress();
|
||||
stopRouteSensors();
|
||||
ns.AudioPlayer.pause();
|
||||
$('#tracking-status')
|
||||
@@ -223,15 +276,14 @@
|
||||
if (state.routeState !== 'idle') endRoute({ announce: false });
|
||||
|
||||
state.route = route;
|
||||
state.triggered.clear();
|
||||
state.routeProgressIndex = null;
|
||||
state.activePoiId = null;
|
||||
restoreRouteProgress(route);
|
||||
setActivePoi(null);
|
||||
$('#route-title').text(route.name);
|
||||
$('#route-description').text(route.description || '');
|
||||
$('#route-distance').text(ns.Distance.format(route.distanceM));
|
||||
$('#route-elevation').text(`${Math.round(route.elevationGainM)} m`);
|
||||
$('#route-poi-count').text(route.pois.length);
|
||||
$('#tracking-status').prop('hidden', true).text('');
|
||||
updateRouteControls();
|
||||
|
||||
const list = $('#poi-list').empty();
|
||||
@@ -261,6 +313,9 @@
|
||||
}
|
||||
|
||||
function showPoi(poi) {
|
||||
state.activePoiId = Number(poi.id);
|
||||
state.viewed.add(state.activePoiId);
|
||||
persistRouteProgress();
|
||||
setActivePoi(poi.id);
|
||||
$('#poi-title').text(poi.title);
|
||||
$('#poi-description').text(poi.description || '');
|
||||
@@ -345,6 +400,7 @@
|
||||
}
|
||||
|
||||
function updateRouteProgress(position) {
|
||||
const previousProgressIndex = state.routeProgressIndex;
|
||||
const points = state.route?.points || [];
|
||||
if (!points.length) return null;
|
||||
|
||||
@@ -370,9 +426,11 @@
|
||||
|
||||
if (targetIndex === lastIndex && distance <= reachedRadius) {
|
||||
state.routeProgressIndex = lastIndex;
|
||||
if (state.routeProgressIndex !== previousProgressIndex) scheduleRouteProgressPersist();
|
||||
return { reached: true, target, distance: 0 };
|
||||
}
|
||||
|
||||
if (state.routeProgressIndex !== previousProgressIndex) scheduleRouteProgressPersist();
|
||||
return { reached: false, target, distance };
|
||||
}
|
||||
|
||||
@@ -464,6 +522,7 @@
|
||||
|
||||
if (nearest && nearest.distance <= nearest.poi.triggerRadiusM) {
|
||||
state.triggered.add(nearest.poi.id);
|
||||
persistRouteProgress();
|
||||
ns.Vibration.start(ns.Vibration.Patterns.ACTIVE_POI);
|
||||
showPoi(nearest.poi);
|
||||
updateNavigation(position);
|
||||
@@ -481,6 +540,7 @@
|
||||
|
||||
state.routeState = 'running';
|
||||
state.deviceHeading = null;
|
||||
persistRouteProgress();
|
||||
updateRouteControls();
|
||||
$('#tracking-status')
|
||||
.prop('hidden', false)
|
||||
@@ -505,9 +565,9 @@
|
||||
|
||||
function routesFromResponse(response) {
|
||||
if (!Array.isArray(response?.routes)) {
|
||||
throw new Error('Die Routen-API hat keine gültige Routenliste geliefert.');
|
||||
throw new TypeError('Die Routen-API hat keine gültige Routenliste geliefert.');
|
||||
}
|
||||
return response.routes.filter(route => route && route.id != null && route.name != null);
|
||||
return response.routes.filter(route => route?.id != null && route?.name != null);
|
||||
}
|
||||
|
||||
function updateRouteProximity(position) {
|
||||
@@ -584,6 +644,17 @@
|
||||
endRoute({ returnToRoutes: true });
|
||||
});
|
||||
|
||||
$('#poi-audio').on('play', function () {
|
||||
if (!state.route || state.activePoiId == null) return;
|
||||
state.playedAudio.add(state.activePoiId);
|
||||
persistRouteProgress();
|
||||
});
|
||||
|
||||
document.addEventListener('wegwichtel:progress-storage-changed', event => {
|
||||
if (event.detail?.enabled) persistRouteProgress();
|
||||
});
|
||||
|
||||
globalThis.addEventListener('pagehide', persistRouteProgress);
|
||||
globalThis.addEventListener('popstate', event => {
|
||||
const page = event.state?.page || '#routes-page';
|
||||
navigate(page, { updateHistory: false, instant: true });
|
||||
@@ -592,6 +663,7 @@
|
||||
globalThis.addEventListener('pageshow', restoreRouteLists);
|
||||
document.addEventListener('visibilitychange', () => {
|
||||
if (document.visibilityState === 'visible') restoreRouteLists();
|
||||
else persistRouteProgress();
|
||||
});
|
||||
}
|
||||
|
||||
@@ -612,7 +684,7 @@
|
||||
updateRouteControls();
|
||||
hideNavigation();
|
||||
|
||||
void initializeLocation(context);
|
||||
await initializeLocation(context);
|
||||
}
|
||||
};
|
||||
}(globalThis.Wegwichtel, globalThis.jQuery));
|
||||
|
||||
Reference in New Issue
Block a user