首页 > 解决方案 > Reagent/ClojureScript - 多组件方面更新

问题描述

我有一个显示标签和相关选项的选择组件。有一个单独的“语言”选择应该选择显示的语言。在更改时,它会同时更新@language选择标签语言和@search-language-options提供选择选项的选项。标签按预期更新,但选项列表没有 - 它保持最初的初始化状态。

;; search-languages -> vector
;; return the languages referenced in the data for options use

(defn search-languages []
  (let [options (list (tr {:dict ld} [@language :en] [:choice-any]))]
  (if (= @language :or) (concat options (vec (set (map (partial get-field "lang") parsed-json))))
    (concat options (vec (set (map (partial get-field "langTranslated") parsed-json)))))))

(def search-language-options (r/atom (search-languages)))

;; filter component -> component
;; create a select
(defn select-filter-component [label value options]
  [:div {:class "form-group"}
  [:label {:class "control-label" :for label} label]
  [:select {:id label :class "form-control" :value @value :on-change #(reset! value (-> % .-target .-value))}
    (for [opt options]
      ^{:key opt} [:option {:value opt} opt])]])

;; lang-select -> component
;; choose display language 
(defn lang-select []
[:div {:class "form-control" }
  [:select {:id :en :value @language :on-change (fn [e]
    (reset! language (.. e -target -value))
    (reset! search-language-options (search-languages)))
    }
  ^{:key :en} [:option {:value :en} "English"]
  ^{:key :fr} [:option {:value :fr} "Français"]
  ^{:key :es} [:option {:value :es} "Español"]
  ^{:key :or} [:option {:value :or} "Original language"]
  ]])

;; filter form
;; filter the results
(defn filter-form []

[:form {:class "form-inline"}
[search-filter-component (tr {:dict ld} [@language :en] [:search] ) search-text]

[select-filter-component (tr {:dict ld} [@language :en] [:language] ) search-language @search-language-options]
[select-filter-component (tr {:dict ld} [@language :en] [:gender] ) gender ["Any" "M" "F"]]
[select-filter-component (tr {:dict ld} [@language :en] [:continent/title] ) continent ["Any" "Europe"]]
[select-filter-component (tr {:dict ld} [@language :en] [:country] ) placeTranslated ["Any" "Austria" "Switzerland" "Germany"]]
[select-filter-component (tr {:dict ld} [@language :en] [:literaryForm] ) literaryForm ["Any" "Drama" "Poetry" "Prose: fiction" "Prose: non-fiction" ]]
[select-filter-component (tr {:dict ld} [@language :en] [:genre] ) genre ["Any" "Short story" "Novella" "Graphic Novel"]]
[reset-button]]

)

标签: clojurescriptreagent

解决方案


Do you mean that the [:option...] elements in select-filter-component don't change? If that's what you mean, it is hard to tell from the code posted why they don't change because those options are rendered based on the props passed into select-filter-component, and you haven't shown how you are calling select-filter-component. Specifically this code is completely dependent on the options prop passed in:

(for [opt options]
   ^{:key opt} [:option {:value opt} opt])

(Side note: though it doesn't matter here, note that for is lazy, so if you ever reference an atom in a for note that you'll have to wrap it in a doall or the atom won't be referenced during rendering and your component won't update when the atom updates.)

If you mean that selecting different options with the mouse doesn't work, then that is because you have commented out the on-change handler.


推荐阅读