add :between operator

feat/tables
Tienson Qin 2024-06-30 16:09:45 +08:00
parent 0e0592aaee
commit 8990bef6c2
1 changed files with 70 additions and 14 deletions

View File

@ -189,7 +189,7 @@
:on-key-down (fn [e] :on-key-down (fn [e]
(when (= "Escape" (util/ekey e)) (when (= "Escape" (util/ekey e))
(set-show-input! false))) (set-show-input! false)))
:class "max-w-sm !h-7 !py-0 border-none"}) :class "max-w-sm !h-7 !py-0 border-none focus-visible:ring-0 focus-visible:ring-offset-0"})
(shui/button (shui/button
{:variant "ghost" {:variant "ghost"
;; FIXME: remove ring when focused ;; FIXME: remove ring when focused
@ -274,12 +274,13 @@
:is-not-empty "is not empty" :is-not-empty "is not empty"
:string-contains "text contains" :string-contains "text contains"
:string-not-contains "text not contains" :string-not-contains "text not contains"
:date-before "Date before" :date-before "date before"
:date-after "Date after" :date-after "date after"
:number-gt ">" :number-gt ">"
:number-lt "<" :number-lt "<"
:number-gte ">=" :number-gte ">="
:number-lte "<=")) :number-lte "<="
:between "between"))
(defn get-property-operators (defn get-property-operators
[property] [property]
@ -289,9 +290,9 @@
(:default :url :page :object) (:default :url :page :object)
[:string-contains :string-not-contains] [:string-contains :string-not-contains]
:date :date
[:date-before :date-after] [:date-before :date-after :between]
:number :number
[:number-gt :number-lt :number-gte :number-lte] [:number-gt :number-lt :number-gte :number-lte :between]
nil) nil)
[:is-empty :is-not-empty])) [:is-empty :is-not-empty]))
@ -310,6 +311,9 @@
(:number-gt :number-lt :number-gte :number-lte) (:number-gt :number-lt :number-gte :number-lte)
(when (number? value) value) (when (number? value) value)
:between
(when (every? number? value) value)
(:date-before :date-after) (:date-before :date-after)
;; FIXME: should be a valid date number ;; FIXME: should be a valid date number
(when (number? value) value))) (when (number? value) value)))
@ -339,23 +343,65 @@
(set-filters! new-filters)))} (set-filters! new-filters)))}
(operator->text operator))))))) (operator->text operator)))))))
(rum/defc between < rum/static
[property [start end] filters set-filters! idx]
[:<>
(shui/input
{:auto-focus true
:placeholder "from"
:value (str start)
:onChange (fn [e]
(let [input-value (util/evalue e)
number-value (when-not (string/blank? input-value)
(util/safe-parse-float input-value))
value [number-value end]
value (if (every? nil? value) nil value)]
(let [new-filters (update filters idx
(fn [[property operator _old_value]]
(if (nil? value)
[property operator]
[property operator value])))]
(set-filters! new-filters))))
:class "w-24 !h-6 !py-0 border-none focus-visible:ring-0 focus-visible:ring-offset-0"})
(shui/input
{:value (str end)
:placeholder "to"
:onChange (fn [e]
(let [input-value (util/evalue e)
number-value (when-not (string/blank? input-value)
(util/safe-parse-float input-value))
value [start number-value]
value (if (every? nil? value) nil value)]
(let [new-filters (update filters idx
(fn [[property operator _old_value]]
(if (nil? value)
[property operator]
[property operator value])))]
(set-filters! new-filters))))
:class "w-24 !h-6 !py-0 border-none focus-visible:ring-0 focus-visible:ring-offset-0"})])
(rum/defc filter-value < rum/static (rum/defc filter-value < rum/static
[property operator value filters set-filters! idx] [property operator value filters set-filters! idx]
(let [number-operator? (string/starts-with? (name operator) "number-")] (let [number-operator? (string/starts-with? (name operator) "number-")]
(case operator (case operator
:between
(between property value filters set-filters! idx)
(:string-contains :string-not-contains :number-gt :number-lt :number-gte :number-lte) (:string-contains :string-not-contains :number-gt :number-lt :number-gte :number-lte)
(shui/input (shui/input
{:auto-focus true {:auto-focus true
:value (or value "") :value (or value "")
:onChange (fn [e] :onChange (fn [e]
(let [value (util/evalue e) (let [value (util/evalue e)
number-value (and number-operator? (util/safe-parse-float value))] number-value (and number-operator? (when-not (string/blank? value)
(when-not (and number-operator? (nil? number-value)) (util/safe-parse-float value)))]
(let [new-filters (update filters idx (let [new-filters (update filters idx
(fn [[property operator _value]] (fn [[property operator _value]]
[property operator (or number-value value)]))] (if (and number-operator? (nil? number-value))
(set-filters! new-filters))))) [property operator]
:class "w-24 !h-6 !py-0 border-none"}) [property operator (or number-value value)])))]
(set-filters! new-filters))))
:class "w-24 !h-6 !py-0 border-none focus-visible:ring-0 focus-visible:ring-offset-0"})
(when value (when value
(shui/button (shui/button
{:class "!px-2 rounded-none border-r" {:class "!px-2 rounded-none border-r"
@ -442,7 +488,17 @@
:number-lt :number-lt
(if match (some #(< (db-property/property-value-content %) match) value') true) (if match (some #(< (db-property/property-value-content %) match) value') true)
:number-lte :number-lte
(if match (some #(<= (db-property/property-value-content %) match) value') true))] (if match (some #(<= (db-property/property-value-content %) match) value') true)
:between
(if (seq match)
(some (fn [row]
(let [[start end] match
value (db-property/property-value-content row)
conditions [(if start (<= start value) true)
(if end (<= value end) true)]]
(if (seq match) (every? true? conditions) true))) value')
true))]
result)) result))
filters))) filters)))