diff --git a/frontend/src/app/main/ui/workspace/sidebar/options/menus/component.cljs b/frontend/src/app/main/ui/workspace/sidebar/options/menus/component.cljs index a757c579d1..3895154fb2 100644 --- a/frontend/src/app/main/ui/workspace/sidebar/options/menus/component.cljs +++ b/frontend/src/app/main/ui/workspace/sidebar/options/menus/component.cljs @@ -237,22 +237,54 @@ [:div {:class (stl/css :counter)} (str size "/300")])]]))) -(defn- get-variant-error-message - "Generate error message depending on the selected variants" - [errors] +(defn- get-variant-malformed-warning-message + "Receive a list of booleans, one for each selected variant, indicating if that variant + is malformed, and generate a warning message accordingly" + [malformed-map] (cond - (and (= (count errors) 1) (some? (first errors))) + (and (= (count malformed-map) 1) (some? (first malformed-map))) (tr "workspace.options.component.variant.malformed.single.one") - (and (seq errors) (every? some? errors)) + (and (seq malformed-map) (every? some? malformed-map)) (tr "workspace.options.component.variant.malformed.single.all") - (and (seq errors) (some some? errors)) + (and (seq malformed-map) (some some? malformed-map)) (tr "workspace.options.component.variant.malformed.single.some") :else nil)) +(defn- get-variant-duplicated-warning-message + "Receive a list of booleans, one for each selected variant, indicating if that variant + is duplicated, and generate a warning message accordingly" + [duplicated-map] + (cond + (and (= (count duplicated-map) 1) (some? (first duplicated-map))) + (tr "workspace.options.component.variant.duplicated.single.one") + + (and (seq duplicated-map) (every? some? duplicated-map)) + (tr "workspace.options.component.variant.duplicated.single.all") + + (and (seq duplicated-map) (some some? duplicated-map)) + (tr "workspace.options.component.variant.duplicated.single.some") + + :else nil)) + + +(defn- get-component-ids-with-duplicated-variant-props-and-values + "Get a list of component ids whose property names and values are duplicated" + [components] + (let [duplicated-props (->> components + (map :variant-properties) + frequencies + (filter #(> (val %) 1)) + keys + set)] + (->> components + (filter #(duplicated-props (:variant-properties %))) + (map :main-instance-id)))) + + (defn- get-variant-options "Get variant options for a given property name" [prop-name prop-vals] @@ -278,12 +310,20 @@ (ctv/compare-properties properties-map false) (first properties-map)) + malformed-map (mapv :variant-error shapes) + malformed-msg (get-variant-malformed-warning-message malformed-map) + + duplicated-ids (->> (cfv/find-variant-components data objects variant-id) + get-component-ids-with-duplicated-variant-props-and-values + set) + duplicated-map (->> components + (mapv :main-instance-id) + (mapv duplicated-ids)) + duplicated-msg (get-variant-duplicated-warning-message duplicated-map) + prop-vals (mf/with-memo [data objects variant-id] (cfv/extract-properties-values data objects variant-id)) - variant-errors (mapv :variant-error shapes) - variant-error-msg (get-variant-error-message variant-errors) - get-options (mf/use-fn (mf/deps prop-vals) @@ -330,14 +370,21 @@ :max-length ctv/property-max-length :on-change (partial update-property-value pos)}])]])] - (when variant-error-msg - [:div {:class (stl/css :variant-error-wrapper)} + (if malformed-msg + [:div {:class (stl/css :variant-warning-wrapper)} [:> icon* {:icon-id "msg-neutral" - :class (stl/css :variant-error-darken)}] - [:div {:class (stl/css :variant-error-highlight)} - (str variant-error-msg " " (tr "workspace.options.component.variant.malformed.structure.title"))] - [:div {:class (stl/css :variant-error-darken)} - (tr "workspace.options.component.variant.malformed.structure.example")]])])) + :class (stl/css :variant-warning-darken)}] + [:div {:class (stl/css :variant-warning-highlight)} + (str malformed-msg " " (tr "workspace.options.component.variant.malformed.structure.title"))] + [:div {:class (stl/css :variant-warning-darken)} + (tr "workspace.options.component.variant.malformed.structure.example")]] + + (when duplicated-msg + [:div {:class (stl/css :variant-warning-wrapper)} + [:> icon* {:icon-id "msg-neutral" + :class (stl/css :variant-warning-darken)}] + [:div {:class (stl/css :variant-warning-highlight)} + (str duplicated-msg " " "Adjust the values so they can be retrieved.")]]))])) (mf/defc component-variant* @@ -861,13 +908,16 @@ (get :objects)) variants (mapv #(get objects %) (:shapes shape)) + variant-id (:variant-id (first variants)) - object-error-ids (->> variants + malformed-ids (->> variants (filterv #(some? (:variant-error %))) (mapv :id)) - variant-error? (d/not-empty? object-error-ids) + malformed? (d/not-empty? malformed-ids) - variant-id (:variant-id (first variants)) + duplicated-ids (->> (cfv/find-variant-components data objects variant-id) + get-component-ids-with-duplicated-variant-props-and-values) + duplicated? (d/not-empty? duplicated-ids) properties (mf/with-memo [data objects variant-id] (cfv/extract-properties-values data objects (:id shape))) @@ -875,7 +925,6 @@ menu-open* (mf/use-state false) menu-open? (deref menu-open*) - menu-entries [{:title (tr "workspace.shape.menu.add-variant-property") :action #(st/emit! (dwv/add-new-property variant-id))} {:title (tr "workspace.shape.menu.add-variant") @@ -914,10 +963,15 @@ (when (> (count properties) 1) (st/emit! (dwv/remove-property variant-id pos)))))) - select-shape-with-error + select-shapes-with-malformed (mf/use-fn - (mf/deps object-error-ids) - #(st/emit! (dw/select-shapes (into (d/ordered-set) object-error-ids))))] + (mf/deps malformed-ids) + #(st/emit! (dw/select-shapes (into (d/ordered-set) malformed-ids)))) + + select-shapes-with-duplicated + (mf/use-fn + (mf/deps duplicated-ids) + #(st/emit! (dw/select-shapes (into (d/ordered-set) duplicated-ids))))] (when (seq shapes) [:div {:class (stl/css :element-set)} @@ -978,12 +1032,22 @@ :icon "remove" :disabled (<= (count properties) 1)}]]))]) - (when variant-error? - [:div {:class (stl/css :variant-error-wrapper)} + (if malformed? + [:div {:class (stl/css :variant-warning-wrapper)} [:> icon* {:icon-id "msg-neutral" - :class (stl/css :variant-error-darken)}] - [:div {:class (stl/css :variant-error-highlight)} + :class (stl/css :variant-warning-darken)}] + [:div {:class (stl/css :variant-warning-highlight)} (tr "workspace.options.component.variant.malformed.group.title")] - [:button {:class (stl/css :variant-error-button) - :on-click select-shape-with-error} - (tr "workspace.options.component.variant.malformed.group.locate")]])]]))) + [:button {:class (stl/css :variant-warning-button) + :on-click select-shapes-with-malformed} + (tr "workspace.options.component.variant.malformed.group.locate")]] + + (when duplicated? + [:div {:class (stl/css :variant-warning-wrapper)} + [:> icon* {:icon-id "msg-neutral" + :class (stl/css :variant-warning-darken)}] + [:div {:class (stl/css :variant-warning-highlight)} + (tr "workspace.options.component.variant.duplicated.group.title")] + [:button {:class (stl/css :variant-warning-button) + :on-click select-shapes-with-duplicated} + (tr "workspace.options.component.variant.duplicated.group.locate")]]))]]))) diff --git a/frontend/src/app/main/ui/workspace/sidebar/options/menus/component.scss b/frontend/src/app/main/ui/workspace/sidebar/options/menus/component.scss index 167e507481..fcf5ea7ed9 100644 --- a/frontend/src/app/main/ui/workspace/sidebar/options/menus/component.scss +++ b/frontend/src/app/main/ui/workspace/sidebar/options/menus/component.scss @@ -743,7 +743,7 @@ width: $s-104; } -.variant-error-wrapper { +.variant-warning-wrapper { @include bodySmallTypography; border: 1px solid var(--color-background-quaternary); border-radius: $s-8; @@ -753,15 +753,15 @@ gap: $s-8; } -.variant-error-highlight { +.variant-warning-highlight { color: var(--color-foreground-primary); } -.variant-error-darken { +.variant-warning-darken { color: var(--color-foreground-secondary); } -.variant-error-button { +.variant-warning-button { @include bodySmallTypography; background-color: transparent; border: none; diff --git a/frontend/translations/en.po b/frontend/translations/en.po index 884b530044..387a82bbd6 100644 --- a/frontend/translations/en.po +++ b/frontend/translations/en.po @@ -5483,7 +5483,31 @@ msgstr "Unlinked" msgid "workspace.options.component.variant" msgstr "Variant" -#: src/app/main/ui/workspace/sidebar/options/menus/component.cljs:988 +#: src/app/main/ui/workspace/sidebar/options/menus/component.cljs:957 +msgid "workspace.options.component.variant.duplicated.group.locate" +msgstr "Locate duplicated variants" + +#: src/app/main/ui/workspace/sidebar/options/menus/component.cljs:954 +msgid "workspace.options.component.variant.duplicated.group.title" +msgstr "Some variants have identical properties and values" + +#: src/app/main/ui/workspace/sidebar/options/menus/component.cljs:309 +msgid "workspace.options.component.variant.duplicated.single.adjust" +msgstr "Adjust the values so they can be retrieved." + +#: src/app/main/ui/workspace/sidebar/options/menus/component.cljs:309 +msgid "workspace.options.component.variant.duplicated.single.all" +msgstr "These variants have identical properties and values." + +#: src/app/main/ui/workspace/sidebar/options/menus/component.cljs:309 +msgid "workspace.options.component.variant.duplicated.single.one" +msgstr "This variant has identical properties and values to another variant." + +#: src/app/main/ui/workspace/sidebar/options/menus/component.cljs:309 +msgid "workspace.options.component.variant.duplicated.single.some" +msgstr "Some of these variants have identical properties and values." + +#: src/app/main/ui/workspace/sidebar/options/menus/component.cljs:957 msgid "workspace.options.component.variant.malformed.group.locate" msgstr "Locate invalid variants" diff --git a/frontend/translations/es.po b/frontend/translations/es.po index fbe76c8a42..0b8b2f99b9 100644 --- a/frontend/translations/es.po +++ b/frontend/translations/es.po @@ -5507,7 +5507,31 @@ msgstr "Desvinculado" msgid "workspace.options.component.variant" msgstr "Variante" -#: src/app/main/ui/workspace/sidebar/options/menus/component.cljs:988 +#: src/app/main/ui/workspace/sidebar/options/menus/component.cljs:957 +msgid "workspace.options.component.variant.duplicated.group.locate" +msgstr "Localizar variantes duplicadas" + +#: src/app/main/ui/workspace/sidebar/options/menus/component.cljs:954 +msgid "workspace.options.component.variant.duplicated.group.title" +msgstr "Algunas variantes tienen propiedades y valores idénticos" + +#: src/app/main/ui/workspace/sidebar/options/menus/component.cljs:309 +msgid "workspace.options.component.variant.duplicated.single.adjust" +msgstr "Ajusta los valores para que puedan ser encontradas." + +#: src/app/main/ui/workspace/sidebar/options/menus/component.cljs:309 +msgid "workspace.options.component.variant.duplicated.single.all" +msgstr "Estas variantes tienen propiedades y valores idénticos." + +#: src/app/main/ui/workspace/sidebar/options/menus/component.cljs:309 +msgid "workspace.options.component.variant.duplicated.single.one" +msgstr "Esta variante tiene propiedades y valores idénticos a los de otra variante." + +#: src/app/main/ui/workspace/sidebar/options/menus/component.cljs:309 +msgid "workspace.options.component.variant.duplicated.single.some" +msgstr "Algunas de estas variantes tienen propiedades y valores idénticos." + +#: src/app/main/ui/workspace/sidebar/options/menus/component.cljs:957 msgid "workspace.options.component.variant.malformed.group.locate" msgstr "Localizar variantes no válidas"