Skip to content

Instantly share code, notes, and snippets.

@currentoor
Last active January 26, 2019 00:36
Show Gist options
  • Select an option

  • Save currentoor/afc5d60856063afff9fdeca8087cda87 to your computer and use it in GitHub Desktop.

Select an option

Save currentoor/afc5d60856063afff9fdeca8087cda87 to your computer and use it in GitHub Desktop.

Revisions

  1. currentoor revised this gist Jan 26, 2019. No changes.
  2. currentoor revised this gist Jan 26, 2019. 1 changed file with 35 additions and 6 deletions.
    41 changes: 35 additions & 6 deletions mixed-router.cljs
    Original file line number Diff line number Diff line change
    @@ -1,6 +1,31 @@
    (ns ucv.ui.pos-config.tax-master-detail
    (:require
    [fulcro-css.css :as css]
    [fulcro.client.dom :as dom :refer [div]]
    [fulcro.client.mutations :as m]
    [fulcro.client.primitives :as prim :refer [defsc]]
    [fulcro.client.routing :as r :refer [defsc-router]]
    [fulcro.incubator.ui-state-machines :as uism :refer-macros [defstatemachine]]
    [fulcro.ui.form-state :as fs]
    [taoensso.timbre :as log]
    [ucv.ui.form-helper :as form-helper]
    [ucv.ui.pos-config.state-machine :as sm]
    [ucv.ui.menus :as u.menus]
    [ucv.ui.pos-config.master-detail :as imd]
    [ucv.ui.shared-css :refer [SharedCss]]
    [ucv.ui.crud-machine :as crud]
    [ucv.util :as util :refer [Defn =>]]
    [fulcro.client.data-fetch :as df]
    [fulcro.client.localized-dom :as ldom]
    [ucv.ui.components :as u.components]
    [ucv.lib.math :as math]))

    (defsc TaxListItem [this {:tax/keys [id title enabled? percentage]}]
    {:query [:tax/id :tax/title :tax/enabled? :tax/percentage]
    :ident [:tax/id :tax/id]}
    {:query [:tax/id :tax/title :tax/enabled? :tax/percentage]
    :ident [:tax/id :tax/id]
    :componentDidMount (fn []
    (df/load this [:tax/id (:tax/id (prim/props this))]
    TaxListItem))}
    (let [{:keys [clickable-item]} (css/get-classnames SharedCss)]
    (div :.item {:onClick #(uism/trigger! this ::machine :event/edit
    {:ident [:tax/id id]})
    @@ -13,9 +38,13 @@
    (def ui-tax-list-item (prim/factory TaxListItem {:keyfn :tax/id}))

    (defsc TaxList [this {:keys [:entities] :as props}]
    {:query [{:entities (prim/get-query TaxListItem)}]
    :ident (fn [] [:COMPONENT/by-id ::tax-list])
    :initial-state {:entities []}}
    {:query [{:entities (prim/get-query TaxListItem)}]
    :ident (fn [] [:COMPONENT/by-id ::tax-list])
    :initial-state {:entities []}
    :componentDidMount (fn []
    (df/load this :server/list-of-taxes
    TaxList
    {:target [:COMPONENT/by-id ::tax-list :entities]}))}
    (let [add-tax-button (dom/a :.item {:onClick #(uism/trigger! this ::machine :event/create)}
    (dom/i :.plus.icon))]
    (div :.ui.container
    @@ -107,4 +136,4 @@
    :default-complete-fields #{:tax/enabled? :tax/percentage}}))}
    (dom/div "Error Router in bad state."))

    (def ui-tax-master-detail (prim/factory TaxMasterDetail))
    (def ui-tax-master-detail (prim/factory TaxMasterDetail))
  3. currentoor created this gist Jan 26, 2019.
    110 changes: 110 additions & 0 deletions mixed-router.cljs
    Original file line number Diff line number Diff line change
    @@ -0,0 +1,110 @@
    (defsc TaxListItem [this {:tax/keys [id title enabled? percentage]}]
    {:query [:tax/id :tax/title :tax/enabled? :tax/percentage]
    :ident [:tax/id :tax/id]}
    (let [{:keys [clickable-item]} (css/get-classnames SharedCss)]
    (div :.item {:onClick #(uism/trigger! this ::machine :event/edit
    {:ident [:tax/id id]})
    :classes [clickable-item]}
    (div :.right.floated
    (u.components/ui-percent {:value percentage}))
    (div :.content
    (dom/span title)))))

    (def ui-tax-list-item (prim/factory TaxListItem {:keyfn :tax/id}))

    (defsc TaxList [this {:keys [:entities] :as props}]
    {:query [{:entities (prim/get-query TaxListItem)}]
    :ident (fn [] [:COMPONENT/by-id ::tax-list])
    :initial-state {:entities []}}
    (let [add-tax-button (dom/a :.item {:onClick #(uism/trigger! this ::machine :event/create)}
    (dom/i :.plus.icon))]
    (div :.ui.container
    (u.menus/ui-back-menu {:header "Taxes"
    :go-back #(uism/trigger! this ::machine :event/exit)
    :right-item add-tax-button})
    (util/error-boundary :.ui.basic.segment :.ui.middle.aligned.celled.list.massive
    (map ui-tax-list-item (sort-by :tax/title entities)))
    (util/divs :.ui.basic.center.aligned.segment :.ui.message
    (dom/p "Tax rates can be applied to specific item categories and will be automatically calculated at purchase.")))))

    (def ui-tax-list (prim/factory TaxList {:keyfn :db/id}))

    (defn tax-form [this {:tax/keys [percentage enabled?]}]
    (dom/form :.ui.form
    (form-helper/text-input
    this {:field :tax/title
    :required true
    :label "Title"
    :error-label "Title is required."})
    (div :.field
    (form-helper/toggle-input this {:field :tax/enabled?
    :label "Enabled"}))
    (form-helper/percent-input
    this {:field :tax/percentage
    :required true
    :label "Percentage"
    :placeholder "0"
    :error-label "Percentage is required."})))

    (defsc TaxDetail [this {:ui/keys [show-confirm-delete?]
    :tax/keys [id title enabled? percentage]
    :as props}]
    {:query [:tax/id :tax/title :tax/enabled? :tax/percentage :tax/categories
    fs/form-config-join [df/marker-table :actor/detail]
    :ui/show-confirm-cancel? :ui/show-confirm-delete?]
    :form-fields #{:tax/title :tax/enabled? :tax/percentage}
    :ident [:tax/id :tax/id]}
    (let [active-state (uism/get-active-state this ::machine)
    new? (= :state/creating-entity active-state)]
    (div :.ui.container {:onClick #(when show-confirm-delete?
    (m/set-value! this :ui/show-confirm-delete? false))}
    (imd/detail-menu this props
    {:title (if new? "Create Tax" "Edit Tax")
    :machine-id ::machine
    :save-params (if new?
    {:delta {:tax/id id
    :tax/title title
    :tax/enabled? enabled?
    :tax/percentage percentage}}
    {:delta (fs/dirty-fields props false)})
    :new? new?})

    (util/error-boundary
    (if (df/loading? (get props [df/marker-table :actor/detail]))
    (div :.ui.active.centered.inline.loader)
    (prim/fragment
    (div :.ui.basic.segment
    (tax-form this props))

    (div :.ui.basic.segment
    (imd/delete-button this props {:new? new? :machine-id ::machine}))))))))

    (def ui-tax-detail (prim/factory TaxDetail {:keyfn :tax/id}))

    (defsc-router TaxMasterDetail [this {:keys [tax/id] :as props}]
    {:router-id ::pos-config-router
    :ident (fn [] (if id
    [:tax/id id]
    [:COMPONENT/by-id ::tax-list]))
    :default-route TaxList
    :router-targets {:COMPONENT/by-id TaxList
    :tax/id TaxDetail}
    :componentDidMount (fn []
    (log/info "Starting crud-machine for" ::machine)
    (uism/begin! this crud/crud-machine ::machine
    {:actor/router this
    :actor/list TaxList
    :actor/list-item (uism/with-actor-class [:tax/id :none] TaxListItem)
    :actor/detail (uism/with-actor-class [:tax/id :none] TaxDetail)}
    {:create-mutation-sym 'ucv.ui.pos-config.backend/create-tax
    :read-list-key :ucv.models.tax/all-taxes
    :update-mutation-sym 'ucv.ui.pos-config.backend/update-tax
    :delete-mutation-sym 'ucv.ui.pos-config.backend/delete-tax
    :parent-machine ::sm/pos-config-machine
    :entity-template {:tax/title ""
    :tax/percentage (math/bigdecimal "0")
    :tax/enabled? true}
    :default-complete-fields #{:tax/enabled? :tax/percentage}}))}
    (dom/div "Error Router in bad state."))

    (def ui-tax-master-detail (prim/factory TaxMasterDetail))