From 9165cc1efcf7791f78b61b2c51a9de651b1b09aa Mon Sep 17 00:00:00 2001
From: Zero~Informatique
Date: Fri, 2 Jul 2021 22:53:16 +0200
Subject: viewer: types normalization - gallery.d.ts

GitHub: closes #301
---
 viewer/src/components/LdProposition.vue | 9 +++++----
 1 file changed, 5 insertions(+), 4 deletions(-)

(limited to 'viewer/src/components/LdProposition.vue')

diff --git a/viewer/src/components/LdProposition.vue b/viewer/src/components/LdProposition.vue
index aa44943..2396d1f 100644
--- a/viewer/src/components/LdProposition.vue
+++ b/viewer/src/components/LdProposition.vue
@@ -54,8 +54,9 @@
 </template>
 
 <script lang="ts">
-import { Component, Vue, Prop, PropSync, Watch } from "vue-property-decorator";
+import { Item, RawTag } from "@/@types/gallery";
 import { Operation } from "@/@types/Operation";
+import { Component, Prop, PropSync, Vue, Watch } from "vue-property-decorator";
 
 @Component
 export default class LdProposition extends Vue {
@@ -118,16 +119,16 @@ export default class LdProposition extends Vue {
     return this.category?.tag ?? this.$t("panelLeft.propositions.other");
   }
 
-  extractDistinctItems(currentTags: Tag.Search[]): Gallery.Item[] {
+  extractDistinctItems(currentTags: Tag.Search[]): Item[] {
     return [...new Set(currentTags.flatMap(tag => tag.items))];
   }
 
-  rightmost(tag: Gallery.RawTag): Gallery.RawTag {
+  rightmost(tag: RawTag): RawTag {
     const dot = tag.lastIndexOf(":");
     return dot <= 0 ? tag : tag.substr(dot + 1);
   }
 
-  add(operation: Operation, rawTag: Gallery.RawTag) {
+  add(operation: Operation, rawTag: RawTag) {
     const node = this.tagsIndex[rawTag];
     const display = this.category ? `${operation}${this.category.tag}:${node.tag}` : `${operation}${node.tag}`;
     this.model.push({ ...node, parent: this.category, operation, display });
-- 
cgit v1.2.3


From 92cb34b719b481faf417760f307241e8f6d777a9 Mon Sep 17 00:00:00 2001
From: Zero~Informatique
Date: Fri, 2 Jul 2021 22:59:56 +0200
Subject: viewer: types normalization - tag.d.ts

GitHub: closes #301
---
 viewer/src/components/LdProposition.vue | 9 +++++----
 1 file changed, 5 insertions(+), 4 deletions(-)

(limited to 'viewer/src/components/LdProposition.vue')

diff --git a/viewer/src/components/LdProposition.vue b/viewer/src/components/LdProposition.vue
index 2396d1f..088e249 100644
--- a/viewer/src/components/LdProposition.vue
+++ b/viewer/src/components/LdProposition.vue
@@ -56,15 +56,16 @@
 <script lang="ts">
 import { Item, RawTag } from "@/@types/gallery";
 import { Operation } from "@/@types/Operation";
+import { TagIndex, TagNode, TagSearch } from "@/@types/tag";
 import { Component, Prop, PropSync, Vue, Watch } from "vue-property-decorator";
 
 @Component
 export default class LdProposition extends Vue {
-  @Prop() readonly category?: Tag.Node;
+  @Prop() readonly category?: TagNode;
   @Prop({ type: Boolean, required: true }) readonly showCategory!: boolean;
   @Prop({ type: Array, required: true }) readonly currentTags!: string[];
-  @Prop({ required: true }) readonly tagsIndex!: Tag.Index;
-  @PropSync("searchFilters", { type: Array, required: true }) model!: Tag.Search[];
+  @Prop({ required: true }) readonly tagsIndex!: TagIndex;
+  @PropSync("searchFilters", { type: Array, required: true }) model!: TagSearch[];
 
   readonly INITIAL_TAG_DISPLAY_LIMIT = this.getInitialTagDisplayLimit();
 
@@ -119,7 +120,7 @@ export default class LdProposition extends Vue {
     return this.category?.tag ?? this.$t("panelLeft.propositions.other");
   }
 
-  extractDistinctItems(currentTags: Tag.Search[]): Item[] {
+  extractDistinctItems(currentTags: TagSearch[]): Item[] {
     return [...new Set(currentTags.flatMap(tag => tag.items))];
   }
 
-- 
cgit v1.2.3


From dfa1c6e2f2977c32f75c1d93d9e7eb44fbed28c0 Mon Sep 17 00:00:00 2001
From: Zero~Informatique
Date: Sun, 4 Jul 2021 02:22:39 +0200
Subject: viewer: use CSS modules

GitHub: closes #196
---
 viewer/src/components/LdProposition.vue | 23 ++++++++++++++---------
 1 file changed, 14 insertions(+), 9 deletions(-)

(limited to 'viewer/src/components/LdProposition.vue')

diff --git a/viewer/src/components/LdProposition.vue b/viewer/src/components/LdProposition.vue
index 088e249..07b27f5 100644
--- a/viewer/src/components/LdProposition.vue
+++ b/viewer/src/components/LdProposition.vue
@@ -19,11 +19,14 @@
 -->
 
 <template>
-  <div class="proposition">
-    <h2 v-if="showCategory && Object.keys(propositions).length" class="subtitle category">{{ title }}</h2>
+  <div :class="$style.proposition">
+    <h2 v-if="showCategory && Object.keys(propositions).length" :class="[$style.subtitle, $style.category]">
+      {{ title }}
+    </h2>
     <div v-for="proposed in proposedTags" :key="proposed.rawTag">
       <a
-        class="operation-btns link"
+        class="link"
+        :class="$style.operationBtns"
         :title="$t('tag-propositions.substraction')"
         @click="add(Operation.SUBSTRACTION, proposed.rawTag)"
       >
@@ -31,7 +34,8 @@
       </a>
 
       <a
-        class="operation-btns link"
+        class="link"
+        :class="$style.operationBtns"
         :title="$t('tag-propositions.addition')"
         @click="add(Operation.ADDITION, proposed.rawTag)"
       >
@@ -39,7 +43,8 @@
       </a>
 
       <a
-        class="operation-tag link"
+        class="link"
+        :class="$style.operationTag"
         :title="$t('tag-propositions.intersection')"
         @click="add(Operation.INTERSECTION, proposed.rawTag)"
         >{{ proposed.rawTag }}</a
@@ -47,7 +52,7 @@
 
       <div class="disabled" :title="$t('tag-propositions.item-count')">{{ proposed.count }}</div>
     </div>
-    <div v-if="showMoreCount > 0" class="showmore" @click="limit += showMoreCount">
+    <div v-if="showMoreCount > 0" :class="$style.showmore" @click="limit += showMoreCount">
       {{ $t("tag-propositions.showmore", [showMoreCount]) }}<fa-icon icon="angle-double-down" />
     </div>
   </div>
@@ -137,7 +142,7 @@ export default class LdProposition extends Vue {
 }
 </script>
 
-<style lang="scss">
+<style lang="scss" module>
 @import "~@/assets/scss/theme.scss";
 
 .proposition {
@@ -153,14 +158,14 @@ export default class LdProposition extends Vue {
     display: flex;
     align-items: center;
     padding-right: 7px;
-    .operation-tag {
+    .operationTag {
       text-overflow: ellipsis;
       white-space: nowrap;
       overflow: hidden;
       flex-grow: 1;
       cursor: pointer;
     }
-    .operation-btns {
+    .operationBtns {
       padding: 2px 7px;
       cursor: pointer;
     }
-- 
cgit v1.2.3


From 00510820a2794efcadbc83f7f8b54318fe198ecb Mon Sep 17 00:00:00 2001
From: Zéro~Informatique
Date: Tue, 26 Jul 2022 08:44:34 +0200
Subject: viewer: migrate to vue 3, general refactoring and cleanup

Non-exhaustive list of fixes and improvements done at the same time:

- html default background to grey (avoids white flash during init)
- unified links behavior
- added more theme variables
- removed the flex-expand transition (it wasn't working) and replaced it
  with a slide
- fixed LdLoading not centered on the content
- title on removable tags
- fixed an issue with encoded URI from vue-router
- unified Item resource URLs
- removed the iframe for PlainTextViewer (it wasn't working properly)
  and replaced it with a pre
- fixed clear and search buttons tabindex
- fixed the information panel bumping up during the fade animation of
  tag's dropdown
- fixed some focus outlines not appearing correctly
- moved CSS variables to the :root context
- Code cleaning

GitHub: closes #217
GitHub: closes #300
GitHub: closes #297
GitHub: closes #105
GitHub: closes #267
GitHub: closes #275
GitHub: closes #228
GitHub: closes #215
GitHub: closes #112
---
 viewer/src/components/LdProposition.vue | 186 --------------------------------
 1 file changed, 186 deletions(-)
 delete mode 100644 viewer/src/components/LdProposition.vue

(limited to 'viewer/src/components/LdProposition.vue')

diff --git a/viewer/src/components/LdProposition.vue b/viewer/src/components/LdProposition.vue
deleted file mode 100644
index 07b27f5..0000000
--- a/viewer/src/components/LdProposition.vue
+++ /dev/null
@@ -1,186 +0,0 @@
-<!-- ldgallery - A static generator which turns a collection of tagged
---             pictures into a searchable web gallery.
---
--- Copyright (C) 2019-2020  Guillaume FOUET
---               2020       Pacien TRAN-GIRARD
---
--- This program is free software: you can redistribute it and/or modify
--- it under the terms of the GNU Affero General Public License as
--- published by the Free Software Foundation, either version 3 of the
--- License, or (at your option) any later version.
---
--- This program is distributed in the hope that it will be useful,
--- but WITHOUT ANY WARRANTY; without even the implied warranty of
--- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
--- GNU Affero General Public License for more details.
---
--- You should have received a copy of the GNU Affero General Public License
--- along with this program.  If not, see <https://www.gnu.org/licenses/>.
--->
-
-<template>
-  <div :class="$style.proposition">
-    <h2 v-if="showCategory && Object.keys(propositions).length" :class="[$style.subtitle, $style.category]">
-      {{ title }}
-    </h2>
-    <div v-for="proposed in proposedTags" :key="proposed.rawTag">
-      <a
-        class="link"
-        :class="$style.operationBtns"
-        :title="$t('tag-propositions.substraction')"
-        @click="add(Operation.SUBSTRACTION, proposed.rawTag)"
-      >
-        <fa-icon icon="minus" alt="[-]" />
-      </a>
-
-      <a
-        class="link"
-        :class="$style.operationBtns"
-        :title="$t('tag-propositions.addition')"
-        @click="add(Operation.ADDITION, proposed.rawTag)"
-      >
-        <fa-icon icon="plus" alt="[+]" />
-      </a>
-
-      <a
-        class="link"
-        :class="$style.operationTag"
-        :title="$t('tag-propositions.intersection')"
-        @click="add(Operation.INTERSECTION, proposed.rawTag)"
-        >{{ proposed.rawTag }}</a
-      >
-
-      <div class="disabled" :title="$t('tag-propositions.item-count')">{{ proposed.count }}</div>
-    </div>
-    <div v-if="showMoreCount > 0" :class="$style.showmore" @click="limit += showMoreCount">
-      {{ $t("tag-propositions.showmore", [showMoreCount]) }}<fa-icon icon="angle-double-down" />
-    </div>
-  </div>
-</template>
-
-<script lang="ts">
-import { Item, RawTag } from "@/@types/gallery";
-import { Operation } from "@/@types/Operation";
-import { TagIndex, TagNode, TagSearch } from "@/@types/tag";
-import { Component, Prop, PropSync, Vue, Watch } from "vue-property-decorator";
-
-@Component
-export default class LdProposition extends Vue {
-  @Prop() readonly category?: TagNode;
-  @Prop({ type: Boolean, required: true }) readonly showCategory!: boolean;
-  @Prop({ type: Array, required: true }) readonly currentTags!: string[];
-  @Prop({ required: true }) readonly tagsIndex!: TagIndex;
-  @PropSync("searchFilters", { type: Array, required: true }) model!: TagSearch[];
-
-  readonly INITIAL_TAG_DISPLAY_LIMIT = this.getInitialTagDisplayLimit();
-
-  limit: number = this.INITIAL_TAG_DISPLAY_LIMIT;
-
-  getInitialTagDisplayLimit() {
-    const limit = this.$galleryStore.config?.initialTagDisplayLimit ?? 10;
-    return limit >= 0 ? limit : 1000;
-  }
-
-  @Watch("$route")
-  onRouteChange() {
-    this.limit = this.INITIAL_TAG_DISPLAY_LIMIT;
-  }
-
-  get Operation() {
-    return Operation;
-  }
-
-  get propositions(): Record<string, number> {
-    const propositions: Record<string, number> = {};
-    if (this.model.length > 0) {
-      // Tags count from current search
-      this.extractDistinctItems(this.model)
-        .flatMap(item => item.tags)
-        .map(this.rightmost)
-        .filter(rawTag => this.tagsIndex[rawTag] && !this.model.find(search => search.tag === rawTag))
-        .forEach(rawTag => (propositions[rawTag] = (propositions[rawTag] ?? 0) + 1));
-    } else {
-      // Tags count from the current directory
-      this.currentTags
-        .flatMap(tag => tag.split(":"))
-        .map(tag => this.tagsIndex[tag])
-        .filter(Boolean)
-        .forEach(tagindex => (propositions[tagindex.tag] = tagindex.items.length));
-    }
-    return propositions;
-  }
-
-  get proposedTags() {
-    return Object.entries(this.propositions)
-      .sort((a, b) => b[1] - a[1])
-      .slice(0, this.limit)
-      .map(entry => ({ rawTag: entry[0], count: entry[1] }));
-  }
-
-  get showMoreCount(): number {
-    return Object.keys(this.propositions).length - Object.keys(this.proposedTags).length;
-  }
-
-  get title() {
-    return this.category?.tag ?? this.$t("panelLeft.propositions.other");
-  }
-
-  extractDistinctItems(currentTags: TagSearch[]): Item[] {
-    return [...new Set(currentTags.flatMap(tag => tag.items))];
-  }
-
-  rightmost(tag: RawTag): RawTag {
-    const dot = tag.lastIndexOf(":");
-    return dot <= 0 ? tag : tag.substr(dot + 1);
-  }
-
-  add(operation: Operation, rawTag: RawTag) {
-    const node = this.tagsIndex[rawTag];
-    const display = this.category ? `${operation}${this.category.tag}:${node.tag}` : `${operation}${node.tag}`;
-    this.model.push({ ...node, parent: this.category, operation, display });
-  }
-}
-</script>
-
-<style lang="scss" module>
-@import "~@/assets/scss/theme.scss";
-
-.proposition {
-  .subtitle {
-    background-color: $proposed-category-bgcolor;
-    width: 100%;
-    padding: 0 0 6px 0;
-    margin: 0;
-    text-align: center;
-    font-variant: small-caps;
-  }
-  > div {
-    display: flex;
-    align-items: center;
-    padding-right: 7px;
-    .operationTag {
-      text-overflow: ellipsis;
-      white-space: nowrap;
-      overflow: hidden;
-      flex-grow: 1;
-      cursor: pointer;
-    }
-    .operationBtns {
-      padding: 2px 7px;
-      cursor: pointer;
-    }
-  }
-  .showmore {
-    display: block;
-    text-align: right;
-    color: $palette-300;
-    cursor: pointer;
-    > svg {
-      margin-left: 10px;
-    }
-    &:hover {
-      color: $link-hover;
-    }
-  }
-}
-</style>
-- 
cgit v1.2.3

