Better hash management

This commit is contained in:
2026-04-25 17:44:46 +02:00
parent c32998650f
commit dea14acd29
4 changed files with 31 additions and 26 deletions

View File

@@ -40,13 +40,13 @@ export default {
this.user.timezone = Intl.DateTimeFormat().resolvedOptions().timeZone || this.consts.default_timezone; this.user.timezone = Intl.DateTimeFormat().resolvedOptions().timeZone || this.consts.default_timezone;
//Set initial page //Set initial page
let asInitHash = this.getHash(); let asInitHash = this.getBrowserHash();
if(!asInitHash.page) this.hash.page = this.spot.consts.default_page; if(!asInitHash.page) asInitHash.page = this.spot.consts.default_page;
else this.hash = asInitHash; this.setVarHash(asInitHash);
}, },
mounted() { mounted() {
//Catch browser hash change //Catch browser hash change
window.addEventListener('hashchange', this.onHashChange); window.addEventListener('hashchange', this.onBrowserHashChange);
}, },
watch: { watch: {
hashSnapshot(jNewHash, jOldHash) { hashSnapshot(jNewHash, jOldHash) {
@@ -55,8 +55,8 @@ export default {
this.spot.vars('page', this.hash.page); //FIXME remove this.spot.vars('page', this.hash.page); //FIXME remove
//Sync variable -> #hash //Sync variable -> #hash
if(asNewHash != this.getHash()) { if(asNewHash != this.getBrowserHash()) {
this.setHash(asNewHash.page, asNewHash.items); this.setBrowserHash(asNewHash.page, asNewHash.items);
} }
//Same Page change //Same Page change
@@ -66,25 +66,29 @@ export default {
} }
}, },
methods: { methods: {
onHashChange() { //Sync #hash -> variable setVarHash(asHash) {
let asHash = this.getHash(); this.hash.page = asHash.page || '';
if(asHash != this.hash) this.hash = asHash; this.hash.items = Array.isArray(asHash.items) ? [...asHash.items.filter(n => n)] : [];
},
onBrowserHashChange() { //Sync #hash -> variable
let asHash = this.getBrowserHash();
if(asHash != this.hash) this.setVarHash(asHash);
this.spot.vars('page', this.hash.page); //FIXME remove this.spot.vars('page', this.hash.page); //FIXME remove
}, },
getHash() { getBrowserHash() {
let sHash = window.location.hash.slice(1); let sHash = window.location.hash.slice(1);
let asHash = sHash.split(this.spot.consts.hash_sep); let asHash = sHash.split(this.spot.consts.hash_sep).filter(n => n);
let sPage = asHash.shift() || ''; let sPage = asHash.shift() || '';
return {page: sPage, items: asHash}; return {page: sPage, items: asHash};
}, },
setHash(sPage = '', asItems = []) { setBrowserHash(sPage = '', asItems = []) {
if(typeof asItems == 'string' && asItems != '') asItems = [asItems]; if(typeof asItems == 'string' && asItems != '') asItems = [asItems];
const sItems = (asItems.length > 0)?(this.spot.consts.hash_sep + asItems.join(this.spot.consts.hash_sep)):''; const sItems = (asItems.length > 0)?(this.spot.consts.hash_sep + asItems.join(this.spot.consts.hash_sep)):'';
window.location.hash = '#' + sPage + sItems; window.location.hash = '#' + sPage + sItems;
} }
}, },
beforeUnmount() { beforeUnmount() {
window.removeEventListener('hashchange', this.onHashChange) window.removeEventListener('hashchange', this.onBrowserHashChange)
} }
} }
</script> </script>
@@ -93,4 +97,4 @@ export default {
<component :is="route" /> <component :is="route" />
</div> </div>
<div id="mobile"></div> <div id="mobile"></div>
</template> </template>

View File

@@ -91,7 +91,7 @@ export default {
}, },
inject: ['spot', 'hash', 'projects', 'user'], inject: ['spot', 'hash', 'projects', 'user'],
beforeMount() { beforeMount() {
if(this.$parent.hash.items.length == 0) this.$parent.hash.items[0] = this.spot.vars('default_project_codename'); if(this.hash.items.length == 0) this.hash.items[0] = this.spot.vars('default_project_codename');
}, },
mounted() { mounted() {
this.spot.addPage('project', { this.spot.addPage('project', {
@@ -110,7 +110,7 @@ export default {
//Check for project change //Check for project change
if(asNewHash.items[0] != asOldHash.items[0]) { if(asNewHash.items[0] != asOldHash.items[0]) {
this.$parent.hash.items = [asNewHash.items[0]]; this.hash.items = [asNewHash.items[0]];
this.init(); this.init();
} }
}, },
@@ -136,7 +136,7 @@ export default {
]); ]);
//Direct link: Scroll to post //Direct link: Scroll to post
if(this.$parent.hash.items.length == 3) this.findPost({type: this.$parent.hash.items[1], id: this.$parent.hash.items[2]}); if(this.hash.items.length == 3) this.findPost({type: this.hash.items[1], id: this.hash.items[2]});
}, },
quit() { quit() {
lightbox.end(); lightbox.end();
@@ -145,7 +145,7 @@ export default {
this.map.remove(); this.map.remove();
}, },
initProject() { initProject() {
this.currProject = this.projects[this.$parent.hash.items[0]]; this.currProject = this.projects[this.hash.items[0]];
this.modeHisto = (this.currProject.mode == this.spot.consts.modes.histo); this.modeHisto = (this.currProject.mode == this.spot.consts.modes.histo);
this.feed = {loading:false, updatable:true, outOfData:false, refIdFirst:0, refIdLast:0, firstChunk:true}; this.feed = {loading:false, updatable:true, outOfData:false, refIdFirst:0, refIdLast:0, firstChunk:true};
this.posts = []; this.posts = [];
@@ -162,10 +162,10 @@ export default {
resizeDuration: 400, resizeDuration: 400,
hasVideo: true, hasVideo: true,
onMediaChange: (oMedia) => { onMediaChange: (oMedia) => {
this.$parent.hash.items = [this.currProject.codename, 'media', oMedia.id]; this.hash.items = [this.currProject.codename, 'media', oMedia.id];
if(oMedia.set == 'post-medias') this.goToPost({type: 'media', id: oMedia.id}); if(oMedia.set == 'post-medias') this.goToPost({type: 'media', id: oMedia.id});
}, },
onClosing: () => {this.$parent.hash.items = [this.$parent.hash.items[0]];} onClosing: () => {this.hash.items = [this.hash.items[0]];}
}); });
}, },
async initFeed() { async initFeed() {
@@ -332,7 +332,7 @@ export default {
if( //Blog Mode: Fit to last message if( //Blog Mode: Fit to last message
this.currProject.mode == this.spot.consts.modes.blog && this.currProject.mode == this.spot.consts.modes.blog &&
this.markers.messages.length > 0 && this.markers.messages.length > 0 &&
this.$parent.hash.items[2] != 'message' this.hash.items[2] != 'message'
) { ) {
let oLastMsg = this.markers.messages[this.markers.messages.length - 1]; let oLastMsg = this.markers.messages[this.markers.messages.length - 1];
@@ -622,7 +622,7 @@ export default {
- parseFloat(getComputedStyle(this.$refs.feedSimpleBar.$el).paddingTop) - parseFloat(getComputedStyle(this.$refs.feedSimpleBar.$el).paddingTop)
); );
//this.$parent.hash.items = [this.$parent.hash.items[0]]; //this.hash.items = [this.hash.items[0]];
return oRef; return oRef;
} }
@@ -725,4 +725,4 @@ export default {
</div> </div>
</div> </div>
</div> </div>
</template> </template>

View File

@@ -87,6 +87,7 @@
this.focusZoomLevel, this.focusZoomLevel,
() => {this.map.openMarkerPopup(this.options.id_message);} () => {this.map.openMarkerPopup(this.options.id_message);}
); );
this.hash.items = [this.hash.items[0], this.options.type, this.options.id_message];
}, },
openMarkerPopup() { openMarkerPopup() {
if(this.map.isMarkerVisible(this.lngLat)) this.map.openMarkerPopup(this.options.id_message); if(this.map.isMarkerVisible(this.lngLat)) this.map.openMarkerPopup(this.options.id_message);
@@ -160,7 +161,7 @@
<p v-if="timeDiff"> <p v-if="timeDiff">
<projectRelTime :icon="'time'" :iconClasses="'push'" :localTime="absTimeLocal" :siteTime="options.formatted_time" :offset="options.day_offset" /> <projectRelTime :icon="'time'" :iconClasses="'push'" :localTime="absTimeLocal" :siteTime="options.formatted_time" :offset="options.day_offset" />
</p> </p>
<a class="drill" @click.prevent="panMapToMessage"> <a class="drill" @click.prevent="executeMainAction">
<span v-if="options.weather_icon && options.weather_icon!='unknown'" class="weather clickable" :title="spot.lang(options.weather_cond)"> <span v-if="options.weather_icon && options.weather_icon!='unknown'" class="weather clickable" :title="spot.lang(options.weather_cond)">
<spotIcon :icon="options.weather_icon" /> <spotIcon :icon="options.weather_icon" />
<span class="temperature">{{ options.weather_temp+'°C' }}</span> <span class="temperature">{{ options.weather_temp+'°C' }}</span>
@@ -194,4 +195,4 @@
</div> </div>
</div> </div>
</div> </div>
</template> </template>

View File

@@ -80,7 +80,7 @@
.#{variables.$fa-css-prefix}-altitude:before { content: functions.fa-content(variables.$fa-var-mountain); } .#{variables.$fa-css-prefix}-altitude:before { content: functions.fa-content(variables.$fa-var-mountain); }
.#{variables.$fa-css-prefix}-drill-video:before { content: functions.fa-content(variables.$fa-var-play-circle); } .#{variables.$fa-css-prefix}-drill-video:before { content: functions.fa-content(variables.$fa-var-play-circle); }
.#{variables.$fa-css-prefix}-drill-image:before { content: functions.fa-content(variables.$fa-var-search); } .#{variables.$fa-css-prefix}-drill-image:before { content: functions.fa-content(variables.$fa-var-search); }
.#{variables.$fa-css-prefix}-drill-message:before { content: functions.fa-content(variables.$fa-var-search-location); } .#{variables.$fa-css-prefix}-drill-message:before { content: functions.fa-content(variables.$fa-var-magnifying-glass-location); }
.#{variables.$fa-css-prefix}-video-shot:before { content: functions.fa-content(variables.$fa-var-camcorder); } .#{variables.$fa-css-prefix}-video-shot:before { content: functions.fa-content(variables.$fa-var-camcorder); }
.#{variables.$fa-css-prefix}-image-shot:before { content: functions.fa-content(variables.$fa-var-camera-alt); } .#{variables.$fa-css-prefix}-image-shot:before { content: functions.fa-content(variables.$fa-var-camera-alt); }
.#{variables.$fa-css-prefix}-link:before { content: functions.fa-content(variables.$fa-var-link); } .#{variables.$fa-css-prefix}-link:before { content: functions.fa-content(variables.$fa-var-link); }