3

デフォルトで非表示になっている html 要素 (クエリの結果を含む) のリストを作成したいのですが、ユーザーはその状態を切り替えることができます。おもちゃの例として、以下のいくつかの異なる方法を試しましたが、どちらも機能しません。

このコードは 3 つのボタンを正しく作成します。これらは exps 状態を正しく変更しますが、コンテンツを非表示にすることはありません。

(:require  [reagent.core :as r] )
(def exps (r/atom [true true true]))
(defn like-component []
  [:div   
   (for [ [i r] (map-indexed vector  ["A" "B" "C"])] 
     [:div
       [:button {:on-click #(swap! exps update-in [i] not)}]
       (when (nth @exps i)
          [:pre (str i r)])])])

(r/render [like-component]
      (js/document.getElementById "app")) 

一方、以下のコードは 1 つの要素しか作成しませんが、正しく機能します。

(defn expandable-view [e bool]
  (let [expanded (r/atom bool)]
          (fn []
            [:li
            [:div.expandable
              [:div.header {:on-click #(swap! expanded not)}
               "Click me to expand and collapse"]
              (if @expanded
                [:div.body  (allow-html :pre e)])]])))


(defn like-component []
  [:ul
    (vec
      (for [ e  ["A" "B" "C"]]
        (expandable-view e true ))) ])

(r/render [like-component]
          (js/document.getElementById "app"))

編集: おそらく関連: https://github.com/reagent-project/reagent/wiki/Beware-Event-Handlers-Returning-False

4

2 に答える 2

4

for怠け者なので、最初のコード スニペットでreagent逆参照しているとは言えません。exps

アトムを明示的に逆参照することで回避できます。

(defn like-component []
  (apply str @exps) ;; because @exps is a vector, and reagent
                    ;; treat vectors as hiccup component
                    ;; we can't just put `@exps` here.
  [:div   
   (for [ [i r] (map-indexed vector  ["A" "B" "C"])] 
     [:div
       [:button {:on-click #(swap! exps update-in [i] not)}]
       (when (nth @exps i)
          [:pre (str i r)])])])

または、遅延シーケンスを でラップするだけdoallです。

(defn like-component []
  [:div   
   (doall (for [ [i r] (map-indexed vector  ["A" "B" "C"])] 
     [:div
       [:button {:on-click #(swap! exps update-in [i] not)}]
       (when (nth @exps i)
          [:pre (str i r)])]))])

参考までに、関連する議論

私が投稿した2番目のブロックが1つの要素しか作成しない理由は何ですか?

ベクトルは Reagent の特別な市民であり、hiccup/React コンポーネントとして扱われます。

実際の例について

(defn like-component []
  [:ul
    (doall
      (for [ e ["A" "B" "C"]]
        [expandable-view e true]))])

[expandable-view e true]また、試薬コンポーネントを適切に構築するためにを使用していることにも注意してください。詳細については、 () の代わりに [] を使用するおよび試薬コンポーネントの作成を読むことを強くお勧めします。

于 2015-10-03T02:42:38.903 に答える
0

ブートストラップを使用して、このタイプの動作を実現しました。すべてのハッシュマップである状態アトムにレコードのリストがあります。レコードに適切なブートストラップ クラスを設定するために使用される各マップに :visible キーを追加します。has マップの :visible 設定を切り替える関数があります。コンポーネントは、地図の :visible 値を変更して可視性を切り替えるボタンでレコードをレンダリングし、コンポーネントを再レンダリングします。

(defn toggle-visibility [k h]
  (let [new-v (if (= "show" (:visible h))
            "hidden"
            "show")]
    (state/set-value-in! [(state/this-page) :host-list k :visible] new-v)))

(defn host-component [k]
  (let [host (state/value-in [(state/this-page) :host-list k])]
    ^{:key k} [:div.panel.panel-default
               [:div {:class "panel-heading show"}
                [:div {:class (condp = (:status host)
                                "Active" "text-success"
                                "Inactive" "text-info"
                                "Unknown" "text-warning"
                                :else "text-danger")}
                 [:button {:type "button" :class "btn btn-default"
                           :aria-label "Expand"
                           :on-click #(toggle-visibility k host)}
                  [:span {:class (str "glyphicon "
                                      (if (= "show" (:visible host))
                                        "glyphicon-minus"
                                        "glyphicon-plus"))}]]
                 [:strong " IPv4 Address: "] (:ipv4 host)
                 [:strong " Hostname: "] (:hostname host)
                 [:div.pull-right (str "Host ID: " (:host-id host))]]]
               [:div {:class (str "panel-body " (:visible host))}
                [:ul.list-group
                 [:li.list-group-item
                  [:strong "Host Status: "] (:status host)]
                 [:li.list-group-item
                  [:strong "MAC Address: "] (:mac host)]
                 [:li.list-group-item
                  [:strong "IPv6 Address: "] (:ipv6 host)]
                 [:li.list-group-item
                  [:strong "Operating System: "] (:os host)]
                 [:li.list-group-item
                  [:strong "DHCP Client: "] (:dhcp host)
                  [:strong " DNS Entry: "] (:dns host)
                  [:strong " Revers DNS Entry: "] (:reverse-dns host)]
                 [:li.list-group-item
                 [:strong "Host Type: "] (:host-type host)]
                 [:li.list-group-item
                  [:strong "Network Group: "]
                  (str (:network-group host) " / " (:subgroup-name host))]
                 [:li.list-group-item
                  [:strong "Managed By: "] (:management-group host)]
                 [:li.list-group-item
                  [:strong "Creation Date: "] (:created-dt host)]
                 [:li.list-group-item
                  [:strong "Last Modified Date: "] (:last-modified-dt host)]
                 [:li.list-group-item
                  [:strong "Last Seen Date: "] (:last-seen-dt host)]]]]))

基本的に、ブートストラップにコンテンツの表示/非表示を処理させ、コードは表示/非表示の状態を切り替えるだけです。完全なコードは、 theophilusx/Arcisの私の github ページにあります。

于 2015-10-03T08:03:33.720 に答える