From 1c8503485131cbec7153e2fafdcbd6c8f5a0a1c1 Mon Sep 17 00:00:00 2001 From: Varun Patil Date: Mon, 24 Oct 2022 18:58:49 -0700 Subject: [PATCH] Improve settings experience --- src/components/Settings.vue | 58 ++++++++++++++++++++++++------------- src/components/Timeline.vue | 17 ++++++----- src/mixins/UserConfig.ts | 26 ++++++++++++----- 3 files changed, 66 insertions(+), 35 deletions(-) diff --git a/src/components/Settings.vue b/src/components/Settings.vue index ff0f34b8..3cb9689a 100644 --- a/src/components/Settings.vue +++ b/src/components/Settings.vue @@ -24,27 +24,27 @@
{{ t('memories', 'Show hidden folders') }} {{ t('memories', 'Square grid mode') }} - -
@@ -58,7 +58,7 @@ input[type=text] { import { Component, Mixins } from 'vue-property-decorator'; import GlobalMixin from '../mixins/GlobalMixin'; -import { showError } from '@nextcloud/dialogs' +import { getFilePickerBuilder } from '@nextcloud/dialogs' import UserConfig from '../mixins/UserConfig' import { NcCheckboxRadioSwitch } from '@nextcloud/vue' @@ -69,24 +69,42 @@ import { NcCheckboxRadioSwitch } from '@nextcloud/vue' }, }) export default class Settings extends Mixins(UserConfig, GlobalMixin) { - async updateAll() { - // Update localStorage - localStorage.setItem('memories_squareThumbs', this.config_squareThumbs ? '1' : '0'); + async chooseFolder(title: string, initial: string) { + const picker = getFilePickerBuilder(title) + .setMultiSelect(false) + .setModal(true) + .setType(1) + .addMimeTypeFilter('httpd/unix-directory') + .allowDirectories() + .startAt(initial) + .build() - // Settings list - const settings = ['showHidden', 'timelinePath', 'foldersPath']; + return await picker.pick(); + } - // Update all - try { - const p = await Promise.all(settings.map(async (setting) => this.updateSetting(setting))); - if (p.some((r) => !r || r.status !== 200)) { - showError(this.t('memories', 'Error updating settings')); - } else { - window.location.reload(); - } - } catch (e) { - showError(e?.response?.data?.message || this.t('memories', 'Error updating settings')); + async chooseTimelinePath() { + const newPath = await this.chooseFolder(this.t('memories', 'Choose the root of your timeline'), this.config_timelinePath); + if (newPath !== this.config_timelinePath) { + this.config_timelinePath = newPath; + await this.updateSetting('timelinePath'); } } + + async chooseFoldersPath() { + const newPath = await this.chooseFolder(this.t('memories', 'Choose the root for the folders view'), this.config_foldersPath); + if (newPath !== this.config_foldersPath) { + this.config_foldersPath = newPath; + await this.updateSetting('foldersPath'); + } + } + + async updateSquareThumbs() { + console.error('updateSquareThumbs', this.config_squareThumbs); + await this.updateSetting('squareThumbs'); + } + + async updateShowHidden() { + await this.updateSetting('showHidden'); + } } \ No newline at end of file diff --git a/src/components/Timeline.vue b/src/components/Timeline.vue index 5dd8efb8..f857e658 100644 --- a/src/components/Timeline.vue +++ b/src/components/Timeline.vue @@ -104,6 +104,7 @@ import { IDay, IFolder, IHeadRow, IPhoto, IRow, IRowType } from "../types"; import { generateUrl } from '@nextcloud/router' import { showError } from '@nextcloud/dialogs' import { NcEmptyContent } from '@nextcloud/vue'; +import { subscribe, unsubscribe } from '@nextcloud/event-bus' import GlobalMixin from '../mixins/GlobalMixin'; import UserConfig from "../mixins/UserConfig"; @@ -153,8 +154,6 @@ export default class Timeline extends Mixins(GlobalMixin, UserConfig) { private list: IRow[] = []; /** Computed number of columns */ private numCols = 0; - /** Keep all images square */ - private squareMode = false; /** Header rows for dayId key */ private heads: { [dayid: number]: IHeadRow } = {}; @@ -208,10 +207,12 @@ export default class Timeline extends Mixins(GlobalMixin, UserConfig) { } beforeDestroy() { + unsubscribe(this.config_eventName, this.refresh); this.resetState(); } created() { + subscribe(this.config_eventName, this.refresh); window.addEventListener("resize", this.handleResizeWithDelay); } @@ -326,12 +327,9 @@ export default class Timeline extends Mixins(GlobalMixin, UserConfig) { // Mobile this.numCols = MOBILE_NUM_COLS; this.rowHeight = Math.floor(this.rowWidth / this.numCols); - this.squareMode = true; } else { // Desktop - this.squareMode = this.config_squareThumbs; - - if (this.squareMode) { + if (this.config_squareThumbs) { // Set columns first, then height this.numCols = Math.max(3, Math.floor(this.rowWidth / DESKTOP_ROW_HEIGHT)); this.rowHeight = Math.floor(this.rowWidth / this.numCols); @@ -814,6 +812,9 @@ export default class Timeline extends Mixins(GlobalMixin, UserConfig) { row.photos = []; } + // Force all to square + const squareMode = this.isMobile() || this.config_squareThumbs; + // Create justified layout with correct params const justify = getLayout(day.detail.map(p => { return { @@ -824,7 +825,7 @@ export default class Timeline extends Mixins(GlobalMixin, UserConfig) { }), { rowWidth: this.rowWidth, rowHeight: this.rowHeight, - squareMode: this.squareMode, + squareMode: squareMode, numCols: this.numCols, allowBreakout: this.allowBreakout(), seed: dayId, @@ -900,7 +901,7 @@ export default class Timeline extends Mixins(GlobalMixin, UserConfig) { const setPos = () => { photo.dispW = utils.roundHalf(jbox.width); photo.dispX = utils.roundHalf(jbox.left); - photo.dispH = this.squareMode ? utils.roundHalf(jbox.height) : 0; + photo.dispH = squareMode ? utils.roundHalf(jbox.height) : 0; photo.dispY = 0; photo.dispRowNum = row.num; }; diff --git a/src/mixins/UserConfig.ts b/src/mixins/UserConfig.ts index 570a84c3..a5db7c3c 100644 --- a/src/mixins/UserConfig.ts +++ b/src/mixins/UserConfig.ts @@ -27,6 +27,7 @@ import { loadState } from '@nextcloud/initial-state' import axios from '@nextcloud/axios' const eventName = 'memories:user-config-changed' +const localSettings = ['squareThumbs', 'showFaceRect']; @Component export default class UserConfig extends Vue { @@ -39,6 +40,8 @@ export default class UserConfig extends Vue { config_squareThumbs = localStorage.getItem('memories_squareThumbs') === '1'; config_showFaceRect = localStorage.getItem('memories_showFaceRect') === '1'; + config_eventName = eventName; + created() { subscribe(eventName, this.updateLocalSetting) } @@ -48,17 +51,26 @@ export default class UserConfig extends Vue { } updateLocalSetting({ setting, value }) { - this[setting] = value + this['config_' + setting] = value } async updateSetting(setting: string) { const value = this['config_' + setting] - // Long time save setting - const res = await axios.put(generateUrl('apps/memories/api/config/' + setting), { - value: value.toString(), - }) + + if (localSettings.includes(setting)) { + if (typeof value === 'boolean') { + localStorage.setItem('memories_' + setting, value ? '1' : '0') + } else { + localStorage.setItem('memories_' + setting, value) + } + } else { + // Long time save setting + await axios.put(generateUrl('apps/memories/api/config/' + setting), { + value: value.toString(), + }); + } + // Visible elements update setting - emit(eventName, { setting, value }) - return res; + emit(eventName, { setting, value }); } } \ No newline at end of file