Fix problems with extreme values

This commit is contained in:
alonso.torres 2022-03-02 15:50:06 +01:00
parent 999af63118
commit ed9400912c
59 changed files with 359 additions and 340 deletions

View file

@ -108,9 +108,12 @@
(= v base)) (= v base))
(defn translate-matrix (defn translate-matrix
[{x :x y :y :as pt}] ([{x :x y :y :as pt}]
(assert (gpt/point? pt)) (assert (gpt/point? pt))
(Matrix. 1 0 0 1 x y)) (Matrix. 1 0 0 1 x y))
([x y]
(translate-matrix (gpt/point x y))))
(defn scale-matrix (defn scale-matrix
([pt center] ([pt center]

View file

@ -132,9 +132,8 @@
(assert (point? other)) (assert (point? other))
(let [dx (- x ox) (let [dx (- x ox)
dy (- y oy)] dy (- y oy)]
(-> (mth/sqrt (+ (mth/pow dx 2) (mth/sqrt (+ (mth/pow dx 2)
(mth/pow dy 2))) (mth/pow dy 2)))))
(mth/precision 6))))
(defn length (defn length
[{x :x y :y :as p}] [{x :x y :y :as p}]
@ -168,8 +167,7 @@
(* y oy)) (* y oy))
(* length-p length-other)) (* length-p length-other))
a (mth/acos (if (< a -1) -1 (if (> a 1) 1 a))) a (mth/acos (if (< a -1) -1 (if (> a 1) 1 a)))
d (-> (mth/degrees a) d (mth/degrees a)]
(mth/precision 6))]
(if (mth/nan? d) 0 d))))) (if (mth/nan? d) 0 d)))))
(defn angle-sign [v1 v2] (defn angle-sign [v1 v2]
@ -195,7 +193,9 @@
(defn round (defn round
"Change the precision of the point coordinates." "Change the precision of the point coordinates."
([point] (round point 0)) ([point]
(round point 0))
([{:keys [x y] :as p} decimals] ([{:keys [x y] :as p} decimals]
(assert (point? p)) (assert (point? p))
(assert (number? decimals)) (assert (number? decimals))

View file

@ -106,12 +106,12 @@
:width (- x2 x1) :width (- x2 x1)
:height (- y2 y1) :height (- y2 y1)
:type :rect})) :type :rect}))
{frame-x1 :x1 frame-x2 :x2 frame-y1 :y1 frame-y2 :y2} bounds {bound-x1 :x1 bound-x2 :x2 bound-y1 :y1 bound-y2 :y2} bounds
{sr-x1 :x1 sr-x2 :x2 sr-y1 :y1 sr-y2 :y2} selrect] {sr-x1 :x1 sr-x2 :x2 sr-y1 :y1 sr-y2 :y2} selrect]
{:left (make-selrect frame-x1 sr-y1 (- sr-x1 2) sr-y2) {:left (make-selrect bound-x1 sr-y1 sr-x1 sr-y2)
:top (make-selrect sr-x1 frame-y1 sr-x2 (- sr-y1 2)) :top (make-selrect sr-x1 bound-y1 sr-x2 sr-y1)
:right (make-selrect (+ sr-x2 2) sr-y1 frame-x2 sr-y2) :right (make-selrect sr-x2 sr-y1 bound-x2 sr-y2)
:bottom (make-selrect sr-x1 (+ sr-y2 2) sr-x2 frame-y2)})) :bottom (make-selrect sr-x1 sr-y2 sr-x2 bound-y2)}))
(defn distance-selrect [selrect other] (defn distance-selrect [selrect other]
(let [{:keys [x1 y1]} other (let [{:keys [x1 y1]} other

View file

@ -7,8 +7,7 @@
(ns app.common.geom.shapes.common (ns app.common.geom.shapes.common
(:require (:require
[app.common.geom.matrix :as gmt] [app.common.geom.matrix :as gmt]
[app.common.geom.point :as gpt] [app.common.geom.point :as gpt]))
[app.common.math :as mth]))
(defn center-rect (defn center-rect
[{:keys [x y width height]}] [{:keys [x y width height]}]

View file

@ -7,7 +7,6 @@
(ns app.common.geom.shapes.rect (ns app.common.geom.shapes.rect
(:require (:require
[app.common.geom.point :as gpt] [app.common.geom.point :as gpt]
[app.common.geom.shapes.common :as gco]
[app.common.math :as mth])) [app.common.math :as mth]))
(defn rect->points [{:keys [x y width height]}] (defn rect->points [{:keys [x y width height]}]
@ -130,10 +129,3 @@
(>= (:y1 sr2) (:y1 sr1)) (>= (:y1 sr2) (:y1 sr1))
(<= (:y2 sr2) (:y2 sr1)))) (<= (:y2 sr2) (:y2 sr1))))
(defn round-selrect
[selrect]
(-> selrect
(update :x mth/round)
(update :y mth/round)
(update :width mth/round)
(update :height mth/round)))

View file

@ -249,8 +249,8 @@
;; This rectangle is the new data for the current rectangle. We want to change our rectangle ;; This rectangle is the new data for the current rectangle. We want to change our rectangle
;; to have this width, height, x, y ;; to have this width, height, x, y
new-width (max 1 (:width points-temp-dim)) new-width (max 0.01 (:width points-temp-dim))
new-height (max 1 (:height points-temp-dim)) new-height (max 0.01 (:height points-temp-dim))
selrect (gco/make-centered-selrect center new-width new-height) selrect (gco/make-centered-selrect center new-width new-height)
rect-points (gpr/rect->points selrect) rect-points (gpr/rect->points selrect)
@ -263,7 +263,7 @@
(defn- apply-transform (defn- apply-transform
"Given a new set of points transformed, set up the rectangle so it keeps "Given a new set of points transformed, set up the rectangle so it keeps
its properties. We adjust de x,y,width,height and create a custom transform" its properties. We adjust de x,y,width,height and create a custom transform"
[shape transform-mtx round-coords?] [shape transform-mtx]
(let [points' (:points shape) (let [points' (:points shape)
points (gco/transform-points points' transform-mtx) points (gco/transform-points points' transform-mtx)
@ -276,8 +276,8 @@
[(gpr/points->selrect points) nil nil] [(gpr/points->selrect points) nil nil]
(adjust-rotated-transform shape points)) (adjust-rotated-transform shape points))
selrect (cond-> selrect ;;selrect (cond-> selrect
round-coords? gpr/round-selrect) ;; round-coords? gpr/round-selrect)
;; Redondear los points? ;; Redondear los points?
base-rotation (or (:rotation shape) 0) base-rotation (or (:rotation shape) 0)
@ -345,7 +345,7 @@
;; need to remove the flip flags ;; need to remove the flip flags
(assoc :flip-x false) (assoc :flip-x false)
(assoc :flip-y false) (assoc :flip-y false)
(apply-transform (gmt/matrix) true)))) (apply-transform (gmt/matrix)))))
(defn update-mask-selrect (defn update-mask-selrect
[masked-group children] [masked-group children]
@ -525,7 +525,6 @@
(d/parse-double) (d/parse-double)
(* (get-in modifiers [:resize-vector :x] 1)) (* (get-in modifiers [:resize-vector :x] 1))
(* (get-in modifiers [:resize-vector-2 :x] 1)) (* (get-in modifiers [:resize-vector-2 :x] 1))
(mth/precision 2)
(str))] (str))]
(attrs/merge attrs {:font-size font-size})))] (attrs/merge attrs {:font-size font-size})))]
(update shape :content #(txt/transform-nodes (update shape :content #(txt/transform-nodes
@ -535,35 +534,32 @@
shape)) shape))
(defn apply-modifiers (defn apply-modifiers
[shape modifiers round-coords?] [shape modifiers]
(let [center (gco/center-shape shape) (let [center (gco/center-shape shape)
transform (modifiers->transform center modifiers)] transform (modifiers->transform center modifiers)]
(apply-transform shape transform round-coords?))) (apply-transform shape transform)))
(defn transform-shape (defn transform-shape
([shape] [shape]
(transform-shape shape nil)) (let [modifiers (:modifiers shape)]
(cond
(nil? modifiers)
shape
([shape {:keys [round-coords?] :or {round-coords? true}}] (empty-modifiers? modifiers)
(let [modifiers (:modifiers shape)] (dissoc shape :modifiers)
(cond
(nil? modifiers)
shape
(empty-modifiers? modifiers) :else
(dissoc shape :modifiers) (let [shape (apply-displacement shape)
modifiers (:modifiers shape)]
(cond-> shape
(not (empty-modifiers? modifiers))
(-> (set-flip modifiers)
(apply-modifiers modifiers)
(apply-text-resize modifiers))
:else :always
(let [shape (apply-displacement shape) (dissoc :modifiers))))))
modifiers (:modifiers shape)]
(cond-> shape
(not (empty-modifiers? modifiers))
(-> (set-flip modifiers)
(apply-modifiers modifiers round-coords?)
(apply-text-resize modifiers))
:always
(dissoc :modifiers)))))))
(defn transform-selrect (defn transform-selrect
[selrect {:keys [displacement resize-transform-inverse resize-vector resize-origin resize-vector-2 resize-origin-2]}] [selrect {:keys [displacement resize-transform-inverse resize-vector resize-origin resize-vector-2 resize-origin-2]}]

View file

@ -115,7 +115,7 @@
(defn precision (defn precision
[v n] [v n]
(when (and (number? v) (number? n)) (when (and (number? v) (integer? n))
(let [d (pow 10 n)] (let [d (pow 10 n)]
(/ (round (* v d)) d)))) (/ (round (* v d)) d))))
@ -165,3 +165,7 @@
[v0 v1 t] [v0 v1 t]
(+ (* (- 1 t) v0) (+ (* (- 1 t) v0)
(* t v1))) (* t v1)))
(defn max-abs
[a b]
(max (abs a) (abs b)))

View file

@ -91,8 +91,8 @@
(def empty-selrect (def empty-selrect
{:x 0 :y 0 {:x 0 :y 0
:x1 0 :y1 0 :x1 0 :y1 0
:x2 1 :y2 1 :x2 0.01 :y2 0.01
:width 1 :height 1}) :width 0.01 :height 0.01})
(defn make-minimal-shape (defn make-minimal-shape
[type] [type]
@ -111,16 +111,16 @@
(not= :path (:type shape)) (not= :path (:type shape))
(assoc :x 0 (assoc :x 0
:y 0 :y 0
:width 1 :width 0.01
:height 1 :height 0.01
:selrect {:x 0 :selrect {:x 0
:y 0 :y 0
:x1 0 :x1 0
:y1 0 :y1 0
:x2 1 :x2 0.01
:y2 1 :y2 0.01
:width 1 :width 0.01
:height 1})))) :height 0.01}))))
(defn make-minimal-group (defn make-minimal-group
[frame-id selection-rect group-name] [frame-id selection-rect group-name]

View file

@ -9,7 +9,7 @@
[app.common.geom.matrix :as gmt] [app.common.geom.matrix :as gmt]
[app.common.geom.point :as gpt] [app.common.geom.point :as gpt]
[app.common.geom.shapes :as gsh] [app.common.geom.shapes :as gsh]
[app.common.math :refer [close?]] [app.common.math :as mth]
[app.common.pages :refer [make-minimal-shape]] [app.common.pages :refer [make-minimal-shape]]
[clojure.test :as t])) [clojure.test :as t]))
@ -52,7 +52,7 @@
(t/testing "Shape without modifiers should stay the same" (t/testing "Shape without modifiers should stay the same"
(t/are [type] (t/are [type]
(let [shape-before (create-test-shape type) (let [shape-before (create-test-shape type)
shape-after (gsh/transform-shape shape-before {:round-coords? false})] shape-after (gsh/transform-shape shape-before)]
(= shape-before shape-after)) (= shape-before shape-after))
:rect :path)) :rect :path))
@ -61,7 +61,7 @@
(t/are [type] (t/are [type]
(let [modifiers {:displacement (gmt/translate-matrix (gpt/point 10 -10))}] (let [modifiers {:displacement (gmt/translate-matrix (gpt/point 10 -10))}]
(let [shape-before (create-test-shape type {:modifiers modifiers}) (let [shape-before (create-test-shape type {:modifiers modifiers})
shape-after (gsh/transform-shape shape-before {:round-coords? false})] shape-after (gsh/transform-shape shape-before)]
(t/is (not= shape-before shape-after)) (t/is (not= shape-before shape-after))
(t/is (close? (get-in shape-before [:selrect :x]) (t/is (close? (get-in shape-before [:selrect :x])
@ -82,7 +82,7 @@
(t/are [type] (t/are [type]
(let [modifiers {:displacement (gmt/matrix)} (let [modifiers {:displacement (gmt/matrix)}
shape-before (create-test-shape type {:modifiers modifiers}) shape-before (create-test-shape type {:modifiers modifiers})
shape-after (gsh/transform-shape shape-before {:round-coords? false})] shape-after (gsh/transform-shape shape-before)]
(t/are [prop] (t/are [prop]
(t/is (close? (get-in shape-before [:selrect prop]) (t/is (close? (get-in shape-before [:selrect prop])
(get-in shape-after [:selrect prop]))) (get-in shape-after [:selrect prop])))
@ -95,7 +95,7 @@
:resize-vector (gpt/point 2 2) :resize-vector (gpt/point 2 2)
:resize-transform (gmt/matrix)} :resize-transform (gmt/matrix)}
shape-before (create-test-shape type {:modifiers modifiers}) shape-before (create-test-shape type {:modifiers modifiers})
shape-after (gsh/transform-shape shape-before {:round-coords? false})] shape-after (gsh/transform-shape shape-before)]
(t/is (not= shape-before shape-after)) (t/is (not= shape-before shape-after))
(t/is (close? (get-in shape-before [:selrect :x]) (t/is (close? (get-in shape-before [:selrect :x])
@ -117,7 +117,7 @@
:resize-vector (gpt/point 1 1) :resize-vector (gpt/point 1 1)
:resize-transform (gmt/matrix)} :resize-transform (gmt/matrix)}
shape-before (create-test-shape type {:modifiers modifiers}) shape-before (create-test-shape type {:modifiers modifiers})
shape-after (gsh/transform-shape shape-before {:round-coords? false})] shape-after (gsh/transform-shape shape-before)]
(t/are [prop] (t/are [prop]
(t/is (close? (get-in shape-before [:selrect prop]) (t/is (close? (get-in shape-before [:selrect prop])
(get-in shape-after [:selrect prop]))) (get-in shape-after [:selrect prop])))
@ -130,7 +130,7 @@
:resize-vector (gpt/point 0 0) :resize-vector (gpt/point 0 0)
:resize-transform (gmt/matrix)} :resize-transform (gmt/matrix)}
shape-before (create-test-shape type {:modifiers modifiers}) shape-before (create-test-shape type {:modifiers modifiers})
shape-after (gsh/transform-shape shape-before {:round-coords? false})] shape-after (gsh/transform-shape shape-before)]
(t/is (> (get-in shape-before [:selrect :width]) (t/is (> (get-in shape-before [:selrect :width])
(get-in shape-after [:selrect :width]))) (get-in shape-after [:selrect :width])))
(t/is (> (get-in shape-after [:selrect :width]) 0)) (t/is (> (get-in shape-after [:selrect :width]) 0))
@ -144,7 +144,7 @@
(t/are [type] (t/are [type]
(let [modifiers {:rotation 30} (let [modifiers {:rotation 30}
shape-before (create-test-shape type {:modifiers modifiers}) shape-before (create-test-shape type {:modifiers modifiers})
shape-after (gsh/transform-shape shape-before {:round-coords? false})] shape-after (gsh/transform-shape shape-before)]
(t/is (not= shape-before shape-after)) (t/is (not= shape-before shape-after))
@ -168,7 +168,7 @@
(t/are [type] (t/are [type]
(let [modifiers {:rotation 0} (let [modifiers {:rotation 0}
shape-before (create-test-shape type {:modifiers modifiers}) shape-before (create-test-shape type {:modifiers modifiers})
shape-after (gsh/transform-shape shape-before {:round-coords? false})] shape-after (gsh/transform-shape shape-before)]
(t/are [prop] (t/are [prop]
(t/is (close? (get-in shape-before [:selrect prop]) (t/is (close? (get-in shape-before [:selrect prop])
(get-in shape-after [:selrect prop]))) (get-in shape-after [:selrect prop])))
@ -180,7 +180,7 @@
(let [modifiers {:displacement (gmt/matrix)} (let [modifiers {:displacement (gmt/matrix)}
shape-before (-> (create-test-shape type {:modifiers modifiers}) shape-before (-> (create-test-shape type {:modifiers modifiers})
(assoc :selrect selrect)) (assoc :selrect selrect))
shape-after (gsh/transform-shape shape-before {:round-coords? false})] shape-after (gsh/transform-shape shape-before)]
(= (:selrect shape-before) (= (:selrect shape-before)
(:selrect shape-after))) (:selrect shape-after)))

View file

@ -241,12 +241,13 @@ $height-palette-max: 80px;
position: relative; position: relative;
.viewport-overlays { .viewport-overlays {
cursor: initial;
height: 100%;
overflow: hidden;
pointer-events: none;
position: absolute; position: absolute;
width: 100%; width: 100%;
height: 100%;
z-index: 10; z-index: 10;
pointer-events: none;
cursor: initial;
.pixel-overlay { .pixel-overlay {
height: 100%; height: 100%;

View file

@ -6,7 +6,6 @@
(ns app.main.data.workspace.comments (ns app.main.data.workspace.comments
(:require (:require
[app.common.math :as mth]
[app.common.spec :as us] [app.common.spec :as us]
[app.main.data.comments :as dcm] [app.main.data.comments :as dcm]
[app.main.data.workspace :as dw] [app.main.data.workspace :as dw]
@ -78,8 +77,8 @@
(fn [{:keys [vbox zoom] :as local}] (fn [{:keys [vbox zoom] :as local}]
(let [pw (/ 160 zoom) (let [pw (/ 160 zoom)
ph (/ 160 zoom) ph (/ 160 zoom)
nw (mth/round (- (/ (:width vbox) 2) pw)) nw (- (/ (:width vbox) 2) pw)
nh (mth/round (- (/ (:height vbox) 2) ph)) nh (- (/ (:height vbox) 2) ph)
nx (- (:x position) nw) nx (- (:x position) nw)
ny (- (:y position) nh)] ny (- (:y position) nh)]
(update local :vbox assoc :x nx :y ny))))))) (update local :vbox assoc :x nx :y ny)))))))

View file

@ -27,8 +27,8 @@
shapev (gpt/point width height) shapev (gpt/point width height)
deltav (gpt/to-vec initial point) deltav (gpt/to-vec initial point)
scalev (-> (gpt/divide (gpt/add shapev deltav) shapev) scalev (-> (gpt/divide (gpt/add shapev deltav) shapev)
(update :x truncate-zero 1) (update :x truncate-zero 0.01)
(update :y truncate-zero 1)) (update :y truncate-zero 0.01))
scalev (if lock? scalev (if lock?
(let [v (max (:x scalev) (:y scalev))] (let [v (max (:x scalev) (:y scalev))]
(gpt/point v v)) (gpt/point v v))
@ -45,9 +45,7 @@
(defn move-drawing (defn move-drawing
[{:keys [x y]}] [{:keys [x y]}]
(fn [state] (fn [state]
(let [x (mth/precision x 0) (update-in state [:workspace-drawing :object] gsh/absolute-move (gpt/point x y))))
y (mth/precision y 0)]
(update-in state [:workspace-drawing :object] gsh/absolute-move (gpt/point x y)))))
(defn handle-drawing-box [] (defn handle-drawing-box []
(ptk/reify ::handle-drawing-box (ptk/reify ::handle-drawing-box
@ -72,7 +70,7 @@
shape (-> state shape (-> state
(get-in [:workspace-drawing :object]) (get-in [:workspace-drawing :object])
(gsh/setup {:x (:x initial) :y (:y initial) :width 1 :height 1}) (gsh/setup {:x (:x initial) :y (:y initial) :width 0.01 :height 0.01})
(assoc :frame-id fid) (assoc :frame-id fid)
(assoc :initialized? true) (assoc :initialized? true)
(assoc :click-draw? true))] (assoc :click-draw? true))]
@ -85,7 +83,7 @@
(rx/map move-drawing)) (rx/map move-drawing))
(->> ms/mouse-position (->> ms/mouse-position
(rx/filter #(> (gpt/distance % initial) 2)) (rx/filter #(> (gpt/distance % initial) (/ 2 zoom)))
(rx/with-latest vector ms/mouse-position-shift) (rx/with-latest vector ms/mouse-position-shift)
(rx/switch-map (rx/switch-map
(fn [[point :as current]] (fn [[point :as current]]

View file

@ -6,8 +6,9 @@
(ns app.main.data.workspace.drawing.common (ns app.main.data.workspace.drawing.common
(:require (:require
[app.common.geom.point :as gpt] [app.common.geom.matrix :as gmt]
[app.common.geom.shapes :as gsh] [app.common.geom.shapes :as gsh]
[app.common.math :as mth]
[app.main.data.workspace.common :as dwc] [app.main.data.workspace.common :as dwc]
[app.main.data.workspace.undo :as dwu] [app.main.data.workspace.undo :as dwu]
[app.main.worker :as uw] [app.main.worker :as uw]
@ -29,27 +30,30 @@
(rx/concat (rx/concat
(when (:initialized? shape) (when (:initialized? shape)
(let [page-id (:current-page-id state) (let [page-id (:current-page-id state)
shape-click-width (case (:type shape)
:text 3
20)
shape-click-height (case (:type shape)
:text 16
20)
shape (if (:click-draw? shape)
(-> shape
(assoc-in [:modifiers :resize-vector]
(gpt/point shape-click-width shape-click-height))
(assoc-in [:modifiers :resize-origin]
(gpt/point (:x shape) (:y shape))))
shape)
shape (cond-> shape click-draw? (:click-draw? shape)
(= (:type shape) :text) (assoc :grow-type text? (= :text (:type shape))
(if (:click-draw? shape) :auto-width :fixed)))
shape (-> shape min-side (min 100
(gsh/transform-shape) (mth/floor (get-in state [:workspace-local :vbox :width]))
(dissoc :initialized? :click-draw?))] (mth/floor (get-in state [:workspace-local :vbox :height])))
shape
(cond-> shape
(and click-draw? (not text?))
(-> (assoc :width min-side :height min-side)
(assoc-in [:modifiers :displacement]
(gmt/translate-matrix (- (/ min-side 2)) (- (/ min-side 2)))))
(and click-draw? text?)
(assoc :height 17 :width 4 :grow-type :auto-width)
click-draw?
(gsh/setup-selrect)
:always
(-> (gsh/transform-shape)
(dissoc :initialized? :click-draw?)))]
;; Add & select the created shape to the workspace ;; Add & select the created shape to the workspace
(rx/concat (rx/concat
(if (= :text (:type shape)) (if (= :text (:type shape))

View file

@ -11,7 +11,6 @@
[app.common.geom.matrix :as gmt] [app.common.geom.matrix :as gmt]
[app.common.geom.point :as gpt] [app.common.geom.point :as gpt]
[app.common.geom.shapes :as gsh] [app.common.geom.shapes :as gsh]
[app.common.math :as mth]
[app.common.pages.changes-builder :as pcb] [app.common.pages.changes-builder :as pcb]
[app.common.pages.helpers :as cph] [app.common.pages.helpers :as cph]
[app.common.spec :refer [max-safe-int min-safe-int]] [app.common.spec :refer [max-safe-int min-safe-int]]

View file

@ -495,12 +495,13 @@
(watch [_ state stream] (watch [_ state stream]
(let [initial (deref ms/mouse-position) (let [initial (deref ms/mouse-position)
selected (wsh/lookup-selected state {:omit-blocked? true}) selected (wsh/lookup-selected state {:omit-blocked? true})
stopper (rx/filter ms/mouse-up? stream)] stopper (rx/filter ms/mouse-up? stream)
zoom (get-in state [:workspace-local :zoom] 1)]
(when-not (empty? selected) (when-not (empty? selected)
(->> ms/mouse-position (->> ms/mouse-position
(rx/map #(gpt/to-vec initial %)) (rx/map #(gpt/to-vec initial %))
(rx/map #(gpt/length %)) (rx/map #(gpt/length %))
(rx/filter #(> % 1)) (rx/filter #(> % (/ 10 zoom)))
(rx/take 1) (rx/take 1)
(rx/with-latest vector ms/mouse-position-alt) (rx/with-latest vector ms/mouse-position-alt)
(rx/mapcat (rx/mapcat

View file

@ -22,7 +22,7 @@
(def ^:const snap-accuracy 10) (def ^:const snap-accuracy 10)
(def ^:const snap-path-accuracy 10) (def ^:const snap-path-accuracy 10)
(def ^:const snap-distance-accuracy 10) (def ^:const snap-distance-accuracy 20)
(defn- remove-from-snap-points (defn- remove-from-snap-points
[remove-snap?] [remove-snap?]
@ -82,13 +82,13 @@
;; Otherwise the root frame is the common ;; Otherwise the root frame is the common
:else zero))) :else zero)))
(defn get-snap-points [page-id frame-id remove-snap? point coord] (defn get-snap-points [page-id frame-id remove-snap? zoom point coord]
(let [value (get point coord)] (let [value (get point coord)]
(->> (uw/ask! {:cmd :snaps/range-query (->> (uw/ask! {:cmd :snaps/range-query
:page-id page-id :page-id page-id
:frame-id frame-id :frame-id frame-id
:axis coord :axis coord
:ranges [[(- value 0.5) (+ value 0.5)]]}) :ranges [[(- value (/ 0.5 zoom)) (+ value (/ 0.5 zoom))]]})
(rx/take 1) (rx/take 1)
(rx/map (remove-from-snap-points remove-snap?)) (rx/map (remove-from-snap-points remove-snap?))
(rx/map flatten-to-points)))) (rx/map flatten-to-points))))
@ -238,6 +238,18 @@
(rx/map #(or % (gpt/point 0 0))) (rx/map #(or % (gpt/point 0 0)))
(rx/map #(gpt/add point %))))) (rx/map #(gpt/add point %)))))
(defn combine-snaps-points
([] nil)
([p1] p1)
([p1 p2]
(cond
(nil? p2) p1
(nil? p1) p2
:else
(gpt/point (mth/max-abs (:x p1) (:x p2))
(mth/max-abs (:y p1) (:y p2))))))
(defn closest-snap-move (defn closest-snap-move
[page-id shapes objects layout zoom focus movev] [page-id shapes objects layout zoom focus movev]
(let [frame-id (snap-frame-id shapes) (let [frame-id (snap-frame-id shapes)
@ -256,7 +268,7 @@
(->> (rx/merge (closest-snap page-id frame-id shapes-points remove-snap? zoom) (->> (rx/merge (closest-snap page-id frame-id shapes-points remove-snap? zoom)
(when (contains? layout :dynamic-alignment) (when (contains? layout :dynamic-alignment)
(closest-distance-snap page-id shapes objects zoom movev))) (closest-distance-snap page-id shapes objects zoom movev)))
(rx/reduce gpt/min) (rx/reduce combine-snaps-points)
(rx/map #(or % (gpt/point 0 0)))))) (rx/map #(or % (gpt/point 0 0))))))
@ -360,8 +372,8 @@
dy (if (not= 0 (:y snap-delta)) dy (if (not= 0 (:y snap-delta))
(- (+ (:y snap-pos) (:y snap-delta)) (:y position)) (- (+ (:y snap-pos) (:y snap-delta)) (:y position))
0)] 0)]
(-> position
(update :x + dx)
(update :y + dy)))
(cond-> position
(<= (mth/abs dx) snap-accuracy) (update :x + dx)
(<= (mth/abs dy) snap-accuracy) (update :y + dy)))
position)) position))

View file

@ -7,7 +7,7 @@
(ns app.main.ui.components.editable-select (ns app.main.ui.components.editable-select
(:require (:require
[app.common.data :as d] [app.common.data :as d]
[app.common.math :as math] [app.common.math :as mth]
[app.common.uuid :as uuid] [app.common.uuid :as uuid]
[app.main.ui.components.dropdown :refer [dropdown]] [app.main.ui.components.dropdown :refer [dropdown]]
[app.main.ui.icons :as i] [app.main.ui.icons :as i]
@ -29,8 +29,8 @@
max-val (get params :max) max-val (get params :max)
num? (fn [val] (and (number? val) num? (fn [val] (and (number? val)
(not (math/nan? val)) (not (mth/nan? val))
(math/finite? val))) (mth/finite? val)))
emit-blur? (mf/use-ref nil) emit-blur? (mf/use-ref nil)
font-size-wrapper-ref (mf/use-ref) font-size-wrapper-ref (mf/use-ref)
@ -58,8 +58,7 @@
handle-change-input handle-change-input
(fn [event] (fn [event]
(let [value (-> event dom/get-target dom/get-value) (let [value (-> event dom/get-target dom/get-value)
value (-> (or (d/parse-double value) value) value (or (d/parse-double value) value)]
(math/precision 2))]
(set-value value))) (set-value value)))
on-node-load on-node-load
@ -89,8 +88,7 @@
(when (or up? down?) (when (or up? down?)
(dom/prevent-default event) (dom/prevent-default event)
(let [value (-> event dom/get-target dom/get-value) (let [value (-> event dom/get-target dom/get-value)
value (-> (or (d/parse-double value) value) value (or (d/parse-double value) value)
(math/precision 2))
increment (cond increment (cond
(kbd/shift? event) (kbd/shift? event)
@ -102,8 +100,7 @@
:else :else
(if up? 1 -1)) (if up? 1 -1))
new-value (-> (+ value increment) new-value (+ value increment)
(math/precision 2))
new-value (cond new-value (cond
(and (num? min-val) (< new-value min-val)) min-val (and (num? min-val) (< new-value min-val)) min-val
@ -135,7 +132,7 @@
(let [wrapper-node (mf/ref-val font-size-wrapper-ref) (let [wrapper-node (mf/ref-val font-size-wrapper-ref)
node (dom/get-element-by-class "checked-element is-selected" wrapper-node) node (dom/get-element-by-class "checked-element is-selected" wrapper-node)
nodes (dom/get-elements-by-class "checked-element-value" wrapper-node) nodes (dom/get-elements-by-class "checked-element-value" wrapper-node)
closest (fn [a b] (first (sort-by #(math/abs (- % b)) a))) closest (fn [a b] (first (sort-by #(mth/abs (- % b)) a)))
closest-value (str (closest options value))] closest-value (str (closest options value))]
(when (:is-open? @state) (when (:is-open? @state)
(if (some? node) (if (some? node)

View file

@ -6,23 +6,22 @@
(ns app.main.ui.components.numeric-input (ns app.main.ui.components.numeric-input
(:require (:require
[app.main.ui.formats :as fmt]
[app.common.data :as d] [app.common.data :as d]
[app.common.math :as math]
[app.common.spec :as us] [app.common.spec :as us]
[app.util.dom :as dom] [app.util.dom :as dom]
[app.util.globals :as globals] [app.util.globals :as globals]
[app.util.keyboard :as kbd] [app.util.keyboard :as kbd]
[app.util.object :as obj] [app.util.object :as obj]
[app.util.simple-math :as sm] [app.util.simple-math :as sm]
[app.util.strings :as ust]
[goog.events :as events] [goog.events :as events]
[rumext.alpha :as mf]) [rumext.alpha :as mf])
(:import goog.events.EventType)) (:import goog.events.EventType))
(defn num? [val] (defn num? [val]
(and (number? val) (and (number? val)
(not (math/nan? val)) (not (mth/nan? val))
(math/finite? val))) (mth/finite? val)))
(mf/defc numeric-input (mf/defc numeric-input
{::mf/wrap-props false {::mf/wrap-props false
@ -37,7 +36,6 @@
on-blur (obj/get props "onBlur") on-blur (obj/get props "onBlur")
title (obj/get props "title") title (obj/get props "title")
default-val (obj/get props "default" 0) default-val (obj/get props "default" 0)
precision (obj/get props "precision")
;; We need a ref pointing to the input dom element, but the user ;; We need a ref pointing to the input dom element, but the user
;; of this component may provide one (that is forwarded here). ;; of this component may provide one (that is forwarded here).
@ -85,10 +83,6 @@
(sm/expr-eval value))] (sm/expr-eval value))]
(when (num? new-value) (when (num? new-value)
(-> new-value (-> new-value
(cond-> (number? precision)
(math/precision precision))
(cond-> (nil? precision)
(math/round))
(cljs.core/max us/min-safe-int) (cljs.core/max us/min-safe-int)
(cljs.core/min us/max-safe-int) (cljs.core/min us/max-safe-int)
(cond-> (cond->
@ -103,9 +97,7 @@
(mf/deps ref) (mf/deps ref)
(fn [new-value] (fn [new-value]
(let [input-node (mf/ref-val ref)] (let [input-node (mf/ref-val ref)]
(dom/set-value! input-node (if (some? precision) (dom/set-value! input-node (fmt/format-number new-value)))))
(ust/format-precision new-value precision)
(str new-value))))))
apply-value apply-value
(mf/use-callback (mf/use-callback
@ -193,17 +185,17 @@
(obj/set! "className" "input-text") (obj/set! "className" "input-text")
(obj/set! "type" "text") (obj/set! "type" "text")
(obj/set! "ref" ref) (obj/set! "ref" ref)
(obj/set! "defaultValue" value-str) (obj/set! "defaultValue" (fmt/format-number value))
(obj/set! "title" title) (obj/set! "title" title)
(obj/set! "onWheel" handle-mouse-wheel) (obj/set! "onWheel" handle-mouse-wheel)
(obj/set! "onKeyDown" handle-key-down) (obj/set! "onKeyDown" handle-key-down)
(obj/set! "onBlur" handle-blur))] (obj/set! "onBlur" handle-blur))]
(mf/use-effect (mf/use-effect
(mf/deps value-str) (mf/deps value)
(fn [] (fn []
(when-let [input-node (mf/ref-val ref)] (when-let [input-node (mf/ref-val ref)]
(dom/set-value! input-node value-str)))) (dom/set-value! input-node (fmt/format-number value)))))
(mf/use-effect (mf/use-effect
(mf/deps handle-blur) (mf/deps handle-blur)

View file

@ -0,0 +1,36 @@
;; This Source Code Form is subject to the terms of the Mozilla Public
;; License, v. 2.0. If a copy of the MPL was not distributed with this
;; file, You can obtain one at http://mozilla.org/MPL/2.0/.
;;
;; Copyright (c) UXBOX Labs SL
(ns app.main.ui.formats
(:require
[app.common.data.macros :as dm]
[app.common.math :as mth]))
(defn format-percent
([value]
(format-percent value nil))
([value {:keys [precision] :or {precision 2}}]
(let [percent-val (mth/precision (* value 100) precision)]
(dm/str percent-val "%"))))
(defn format-number
([value]
(format-number value nil))
([value {:keys [precision] :or {precision 2}}]
(let [value (mth/precision value precision)]
(dm/str value))))
(defn format-pixels
([value]
(format-pixels value nil))
([value {:keys [precision] :or {precision 2}}]
(let [value (mth/precision value precision)]
(dm/str value "px"))))
(defn format-int
[value]
(let [value (mth/precision value 0)]
(dm/str value)))

View file

@ -12,6 +12,7 @@
[app.common.geom.shapes :as gsh] [app.common.geom.shapes :as gsh]
[app.common.math :as mth] [app.common.math :as mth]
[app.common.uuid :as uuid] [app.common.uuid :as uuid]
[app.main.ui.formats :as fmt]
[rumext.alpha :as mf])) [rumext.alpha :as mf]))
;; ------------------------------------------------ ;; ------------------------------------------------
@ -97,7 +98,7 @@
(mf/defc size-display [{:keys [selrect zoom]}] (mf/defc size-display [{:keys [selrect zoom]}]
(let [{:keys [x y width height]} selrect (let [{:keys [x y width height]} selrect
size-label (dm/str (mth/round width) " x " (mth/round height)) size-label (dm/str (fmt/format-number width) " x " (fmt/format-number height))
rect-height (/ size-display-height zoom) rect-height (/ size-display-height zoom)
rect-width (/ (if (<= (count size-label) 9) rect-width (/ (if (<= (count size-label) 9)
@ -164,7 +165,7 @@
:height distance-pill-height :height distance-pill-height
:style {:fill distance-text-color :style {:fill distance-text-color
:font-size font-size}} :font-size font-size}}
distance]])) (fmt/format-pixels distance)]]))
(mf/defc selection-rect [{:keys [selrect zoom]}] (mf/defc selection-rect [{:keys [selrect zoom]}]
(let [{:keys [x y width height]} selrect (let [{:keys [x y width height]} selrect
@ -214,7 +215,7 @@
{:x center-x {:x center-x
:y center-y :y center-y
:zoom zoom :zoom zoom
:distance (dm/str (mth/round distance) "px") :distance distance
:bounds bounds}]]))))) :bounds bounds}]])))))
(mf/defc selection-guides [{:keys [bounds selrect zoom]}] (mf/defc selection-guides [{:keys [bounds selrect zoom]}]

View file

@ -83,7 +83,7 @@
base #js {:textDecoration text-decoration base #js {:textDecoration text-decoration
:textTransform text-transform :textTransform text-transform
:lineHeight (or line-height "inherit") :lineHeight (or line-height "inherit")
:color (if show-text? text-color "transparent") :color (if show-text? text-color "red")
:caretColor (or text-color "black") :caretColor (or text-color "black")
:overflowWrap "initial"} :overflowWrap "initial"}

View file

@ -6,7 +6,6 @@
(ns app.main.ui.viewer.handoff.attributes.common (ns app.main.ui.viewer.handoff.attributes.common
(:require (:require
[app.common.math :as mth]
[app.main.store :as st] [app.main.store :as st]
[app.main.ui.components.color-bullet :refer [color-bullet color-name]] [app.main.ui.components.color-bullet :refer [color-bullet color-name]]
[app.main.ui.components.copy-button :refer [copy-button]] [app.main.ui.components.copy-button :refer [copy-button]]
@ -50,9 +49,9 @@
(if (:gradient color) (if (:gradient color)
[:& color-name {:color color}] [:& color-name {:color color}]
(case format (case format
:rgba (let [[r g b a] (->> (uc/hex->rgba (:color color) (:opacity color)) (map #(mth/precision % 2)))] :rgba (let [[r g b a] (uc/hex->rgba (:color color) (:opacity color))]
[:div (str/fmt "%s, %s, %s, %s" r g b a)]) [:div (str/fmt "%s, %s, %s, %s" r g b a)])
:hsla (let [[h s l a] (->> (uc/hex->hsla (:color color) (:opacity color)) (map #(mth/precision % 2)))] :hsla (let [[h s l a] (uc/hex->hsla (:color color) (:opacity color))]
[:div (str/fmt "%s, %s, %s, %s" h s l a)]) [:div (str/fmt "%s, %s, %s, %s" h s l a)])
[:* [:*
[:& color-name {:color color}] [:& color-name {:color color}]

View file

@ -6,7 +6,6 @@
(ns app.main.ui.viewer.handoff.attributes.layout (ns app.main.ui.viewer.handoff.attributes.layout
(:require (:require
[app.common.math :as mth]
[app.common.spec.radius :as ctr] [app.common.spec.radius :as ctr]
[app.main.ui.components.copy-button :refer [copy-button]] [app.main.ui.components.copy-button :refer [copy-button]]
[app.util.code-gen :as cg] [app.util.code-gen :as cg]
@ -39,46 +38,46 @@
[:* [:*
[:div.attributes-unit-row [:div.attributes-unit-row
[:div.attributes-label (t locale "handoff.attributes.layout.width")] [:div.attributes-label (t locale "handoff.attributes.layout.width")]
[:div.attributes-value (mth/precision width 2) "px"] [:div.attributes-value width "px"]
[:& copy-button {:data (copy-data selrect :width)}]] [:& copy-button {:data (copy-data selrect :width)}]]
[:div.attributes-unit-row [:div.attributes-unit-row
[:div.attributes-label (t locale "handoff.attributes.layout.height")] [:div.attributes-label (t locale "handoff.attributes.layout.height")]
[:div.attributes-value (mth/precision height 2) "px"] [:div.attributes-value height "px"]
[:& copy-button {:data (copy-data selrect :height)}]] [:& copy-button {:data (copy-data selrect :height)}]]
(when (not= (:x shape) 0) (when (not= (:x shape) 0)
[:div.attributes-unit-row [:div.attributes-unit-row
[:div.attributes-label (t locale "handoff.attributes.layout.left")] [:div.attributes-label (t locale "handoff.attributes.layout.left")]
[:div.attributes-value (mth/precision x 2) "px"] [:div.attributes-value x "px"]
[:& copy-button {:data (copy-data selrect :x)}]]) [:& copy-button {:data (copy-data selrect :x)}]])
(when (not= (:y shape) 0) (when (not= (:y shape) 0)
[:div.attributes-unit-row [:div.attributes-unit-row
[:div.attributes-label (t locale "handoff.attributes.layout.top")] [:div.attributes-label (t locale "handoff.attributes.layout.top")]
[:div.attributes-value (mth/precision y 2) "px"] [:div.attributes-value y "px"]
[:& copy-button {:data (copy-data selrect :y)}]]) [:& copy-button {:data (copy-data selrect :y)}]])
(when (ctr/radius-1? shape) (when (ctr/radius-1? shape)
[:div.attributes-unit-row [:div.attributes-unit-row
[:div.attributes-label (t locale "handoff.attributes.layout.radius")] [:div.attributes-label (t locale "handoff.attributes.layout.radius")]
[:div.attributes-value (mth/precision (:rx shape 0) 2) "px"] [:div.attributes-value (:rx shape 0) "px"]
[:& copy-button {:data (copy-data shape :rx)}]]) [:& copy-button {:data (copy-data shape :rx)}]])
(when (ctr/radius-4? shape) (when (ctr/radius-4? shape)
[:div.attributes-unit-row [:div.attributes-unit-row
[:div.attributes-label (t locale "handoff.attributes.layout.radius")] [:div.attributes-label (t locale "handoff.attributes.layout.radius")]
[:div.attributes-value [:div.attributes-value
(mth/precision (:r1 shape) 2) ", " (:r1 shape) ", "
(mth/precision (:r2 shape) 2) ", " (:r2 shape) ", "
(mth/precision (:r3 shape) 2) ", " (:r3 shape) ", "
(mth/precision (:r4 shape) 2) "px"] (:r4 shape) "px"]
[:& copy-button {:data (copy-data shape :r1)}]]) [:& copy-button {:data (copy-data shape :r1)}]])
(when (not= (:rotation shape 0) 0) (when (not= (:rotation shape 0) 0)
[:div.attributes-unit-row [:div.attributes-unit-row
[:div.attributes-label (t locale "handoff.attributes.layout.rotation")] [:div.attributes-label (t locale "handoff.attributes.layout.rotation")]
[:div.attributes-value (mth/precision (:rotation shape) 2) "deg"] [:div.attributes-value (:rotation shape) "deg"]
[:& copy-button {:data (copy-data shape :rotation)}]])])) [:& copy-button {:data (copy-data shape :rotation)}]])]))

View file

@ -7,7 +7,6 @@
(ns app.main.ui.viewer.handoff.attributes.stroke (ns app.main.ui.viewer.handoff.attributes.stroke
(:require (:require
[app.common.data :as d] [app.common.data :as d]
[app.common.math :as mth]
[app.main.ui.components.copy-button :refer [copy-button]] [app.main.ui.components.copy-button :refer [copy-button]]
[app.main.ui.viewer.handoff.attributes.common :refer [color-row]] [app.main.ui.viewer.handoff.attributes.common :refer [color-row]]
[app.util.code-gen :as cg] [app.util.code-gen :as cg]
@ -67,7 +66,7 @@
stroke-alignment (or stroke-alignment :center)] stroke-alignment (or stroke-alignment :center)]
[:div.attributes-stroke-row [:div.attributes-stroke-row
[:div.attributes-label (t locale "handoff.attributes.stroke.width")] [:div.attributes-label (t locale "handoff.attributes.stroke.width")]
[:div.attributes-value (mth/precision (:stroke-width shape) 2) "px"] [:div.attributes-value (:stroke-width shape) "px"]
[:div.attributes-value (->> stroke-style d/name (str "handoff.attributes.stroke.style.") (t locale))] [:div.attributes-value (->> stroke-style d/name (str "handoff.attributes.stroke.style.") (t locale))]
[:div.attributes-label (->> stroke-alignment d/name (str "handoff.attributes.stroke.alignment.") (t locale))] [:div.attributes-label (->> stroke-alignment d/name (str "handoff.attributes.stroke.alignment.") (t locale))]
[:& copy-button {:data (copy-stroke-data shape)}]])])) [:& copy-button {:data (copy-stroke-data shape)}]])]))

View file

@ -6,16 +6,12 @@
(ns app.main.ui.viewer.handoff.attributes.svg (ns app.main.ui.viewer.handoff.attributes.svg
(:require (:require
#_[app.common.math :as mth]
#_[app.main.ui.icons :as i]
#_[app.util.code-gen :as cg]
[app.common.data :as d] [app.common.data :as d]
[app.main.ui.components.copy-button :refer [copy-button]] [app.main.ui.components.copy-button :refer [copy-button]]
[app.util.i18n :refer [tr]] [app.util.i18n :refer [tr]]
[cuerdas.core :as str] [cuerdas.core :as str]
[rumext.alpha :as mf])) [rumext.alpha :as mf]))
(defn map->css [attr] (defn map->css [attr]
(->> attr (->> attr
(map (fn [[attr-key attr-value]] (str (d/name attr-key) ":" attr-value))) (map (fn [[attr-key attr-value]] (str (d/name attr-key) ":" attr-value)))

View file

@ -6,13 +6,13 @@
(ns app.main.ui.viewer.header (ns app.main.ui.viewer.header
(:require (:require
[app.common.math :as mth]
[app.main.data.modal :as modal] [app.main.data.modal :as modal]
[app.main.data.viewer :as dv] [app.main.data.viewer :as dv]
[app.main.data.viewer.shortcuts :as sc] [app.main.data.viewer.shortcuts :as sc]
[app.main.refs :as refs] [app.main.refs :as refs]
[app.main.store :as st] [app.main.store :as st]
[app.main.ui.components.dropdown :refer [dropdown]] [app.main.ui.components.dropdown :refer [dropdown]]
[app.main.ui.formats :as fmt]
[app.main.ui.icons :as i] [app.main.ui.icons :as i]
[app.main.ui.viewer.comments :refer [comments-menu]] [app.main.ui.viewer.comments :refer [comments-menu]]
[app.main.ui.viewer.interactions :refer [flows-menu interactions-menu]] [app.main.ui.viewer.interactions :refer [flows-menu interactions-menu]]
@ -32,7 +32,7 @@
:as props}] :as props}]
(let [show-dropdown? (mf/use-state false)] (let [show-dropdown? (mf/use-state false)]
[:div.zoom-widget {:on-click #(reset! show-dropdown? true)} [:div.zoom-widget {:on-click #(reset! show-dropdown? true)}
[:span.label {} (str (mth/round (* 100 zoom)) "%")] [:span.label (fmt/format-percent zoom)]
[:span.icon i/arrow-down] [:span.icon i/arrow-down]
[:& dropdown {:show @show-dropdown? [:& dropdown {:show @show-dropdown?
:on-close #(reset! show-dropdown? false)} :on-close #(reset! show-dropdown? false)}
@ -43,7 +43,7 @@
(dom/stop-propagation event) (dom/stop-propagation event)
(dom/prevent-default event) (dom/prevent-default event)
(on-decrease))} "-"] (on-decrease))} "-"]
[:p.zoom-size {} (str (mth/round (* 100 zoom)) "%")] [:p.zoom-size (fmt/format-percent zoom)]
[:button {:on-click (fn [event] [:button {:on-click (fn [event]
(dom/stop-propagation event) (dom/stop-propagation event)
(dom/prevent-default event) (dom/prevent-default event)

View file

@ -6,7 +6,6 @@
(ns app.main.ui.workspace.colorpalette (ns app.main.ui.workspace.colorpalette
(:require (:require
[app.common.math :as mth]
[app.main.data.workspace.colors :as mdc] [app.main.data.workspace.colors :as mdc]
[app.main.refs :as refs] [app.main.refs :as refs]
[app.main.store :as st] [app.main.store :as st]
@ -57,7 +56,7 @@
(let [state (mf/use-state {:show-menu false}) (let [state (mf/use-state {:show-menu false})
width (:width @state 0) width (:width @state 0)
visible (mth/round (/ width 66)) visible (/ width 66)
offset (:offset @state 0) offset (:offset @state 0)
max-offset (- (count current-colors) max-offset (- (count current-colors)
@ -75,7 +74,7 @@
(swap! state update :offset (swap! state update :offset
(fn [offset] (fn [offset]
(if (pos? offset) (if (pos? offset)
(max (- offset (mth/round (/ visible 2))) 0) (max (- offset (/ visible 2)) 0)
offset))))) offset)))))
on-right-arrow-click on-right-arrow-click
@ -85,7 +84,7 @@
(swap! state update :offset (swap! state update :offset
(fn [offset] (fn [offset]
(if (< offset max-offset) (if (< offset max-offset)
(min max-offset (+ offset (mth/round (/ visible 2)))) (min max-offset (+ offset (/ visible 2)))
offset))))) offset)))))
on-scroll on-scroll

View file

@ -6,7 +6,7 @@
(ns app.main.ui.workspace.colorpicker.color-inputs (ns app.main.ui.workspace.colorpicker.color-inputs
(:require (:require
[app.common.math :as math] [app.common.math :as mth]
[app.util.color :as uc] [app.util.color :as uc]
[app.util.dom :as dom] [app.util.dom :as dom]
[rumext.alpha :as mf])) [rumext.alpha :as mf]))
@ -52,7 +52,7 @@
on-change-property on-change-property
(fn [property max-value] (fn [property max-value]
(fn [e] (fn [e]
(let [val (-> e dom/get-target-val (math/clamp 0 max-value)) (let [val (-> e dom/get-target-val (mth/clamp 0 max-value))
val (if (#{:s} property) (/ val 100) val)] val (if (#{:s} property) (/ val 100) val)]
(when (not (nil? val)) (when (not (nil? val))
(if (#{:r :g :b} property) (if (#{:r :g :b} property)
@ -72,7 +72,7 @@
on-change-opacity on-change-opacity
(fn [e] (fn [e]
(when-let [new-alpha (-> e dom/get-target-val (math/clamp 0 100) (/ 100))] (when-let [new-alpha (-> e dom/get-target-val (mth/clamp 0 100) (/ 100))]
(on-change {:alpha new-alpha})))] (on-change {:alpha new-alpha})))]
@ -86,9 +86,9 @@
(when (and property-val property-ref) (when (and property-val property-ref)
(when-let [node (mf/ref-val property-ref)] (when-let [node (mf/ref-val property-ref)]
(case ref-key (case ref-key
(:s :alpha) (dom/set-value! node (math/round (* property-val 100))) (:s :alpha) (dom/set-value! node (* property-val 100))
:hex (dom/set-value! node property-val) :hex (dom/set-value! node property-val)
(dom/set-value! node (math/round property-val))))))))) (dom/set-value! node property-val))))))))
[:div.color-values [:div.color-values
{:class (when disable-opacity "disable-opacity")} {:class (when disable-opacity "disable-opacity")}
@ -156,7 +156,7 @@
:min 0 :min 0
:step 1 :step 1
:max 100 :max 100
:default-value (if (= alpha :multiple) "" (math/precision alpha 2)) :default-value (if (= alpha :multiple) "" alpha)
:on-change on-change-opacity}]) :on-change on-change-opacity}])
[:label.hex-label {:for "hex-value"} "HEX"] [:label.hex-label {:for "hex-value"} "HEX"]

View file

@ -7,7 +7,7 @@
(ns app.main.ui.workspace.colorpicker.harmony (ns app.main.ui.workspace.colorpicker.harmony
(:require (:require
[app.common.geom.point :as gpt] [app.common.geom.point :as gpt]
[app.common.math :as math] [app.common.math :as mth]
[app.main.ui.workspace.colorpicker.slider-selector :refer [slider-selector]] [app.main.ui.workspace.colorpicker.slider-selector :refer [slider-selector]]
[app.util.color :as uc] [app.util.color :as uc]
[app.util.dom :as dom] [app.util.dom :as dom]
@ -28,9 +28,9 @@
(.clearRect ctx 0 0 width height) (.clearRect ctx 0 0 width height)
(doseq [degrees (range 0 360 step)] (doseq [degrees (range 0 360 step)]
(let [degrees-rad (math/radians degrees) (let [degrees-rad (mth/radians degrees)
x (* radius (math/cos (- degrees-rad))) x (* radius (mth/cos (- degrees-rad)))
y (* radius (math/sin (- degrees-rad)))] y (* radius (mth/sin (- degrees-rad)))]
(obj/set! ctx "strokeStyle" (str/format "hsl(%s, 100%, 50%)" degrees)) (obj/set! ctx "strokeStyle" (str/format "hsl(%s, 100%, 50%)" degrees))
(.beginPath ctx) (.beginPath ctx)
(.moveTo ctx cx cy) (.moveTo ctx cx cy)
@ -43,15 +43,15 @@
(obj/set! ctx "fillStyle" grd) (obj/set! ctx "fillStyle" grd)
(.beginPath ctx) (.beginPath ctx)
(.arc ctx cx cy radius 0 (* 2 math/PI) true) (.arc ctx cx cy radius 0 (* 2 mth/PI) true)
(.closePath ctx) (.closePath ctx)
(.fill ctx)))) (.fill ctx))))
(defn color->point (defn color->point
[canvas-side hue saturation] [canvas-side hue saturation]
(let [hue-rad (math/radians (- hue)) (let [hue-rad (mth/radians (- hue))
comp-x (* saturation (math/cos hue-rad)) comp-x (* saturation (mth/cos hue-rad))
comp-y (* saturation (math/sin hue-rad)) comp-y (* saturation (mth/sin hue-rad))
x (+ (/ canvas-side 2) (* comp-x (/ canvas-side 2))) x (+ (/ canvas-side 2) (* comp-x (/ canvas-side 2)))
y (+ (/ canvas-side 2) (* comp-y (/ canvas-side 2)))] y (+ (/ canvas-side 2) (* comp-y (/ canvas-side 2)))]
(gpt/point x y))) (gpt/point x y)))
@ -68,15 +68,15 @@
calculate-pos (fn [ev] calculate-pos (fn [ev]
(let [{:keys [left right top bottom]} (-> ev dom/get-target dom/get-bounding-rect) (let [{:keys [left right top bottom]} (-> ev dom/get-target dom/get-bounding-rect)
{:keys [x y]} (-> ev dom/get-client-position) {:keys [x y]} (-> ev dom/get-client-position)
px (math/clamp (/ (- x left) (- right left)) 0 1) px (mth/clamp (/ (- x left) (- right left)) 0 1)
py (math/clamp (/ (- y top) (- bottom top)) 0 1) py (mth/clamp (/ (- y top) (- bottom top)) 0 1)
px (- (* 2 px) 1) px (- (* 2 px) 1)
py (- (* 2 py) 1) py (- (* 2 py) 1)
angle (math/degrees (math/atan2 px py)) angle (mth/degrees (mth/atan2 px py))
new-hue (math/precision (mod (- angle 90 ) 360) 2) new-hue (mod (- angle 90 ) 360)
new-saturation (math/clamp (math/distance [px py] [0 0]) 0 1) new-saturation (mth/clamp (mth/distance [px py] [0 0]) 0 1)
hex (uc/hsv->hex [new-hue new-saturation value]) hex (uc/hsv->hex [new-hue new-saturation value])
[r g b] (uc/hex->rgb hex)] [r g b] (uc/hex->rgb hex)]
(on-change {:hex hex (on-change {:hex hex

View file

@ -6,7 +6,7 @@
(ns app.main.ui.workspace.colorpicker.ramp (ns app.main.ui.workspace.colorpicker.ramp
(:require (:require
[app.common.math :as math] [app.common.math :as mth]
[app.main.ui.components.color-bullet :refer [color-bullet]] [app.main.ui.components.color-bullet :refer [color-bullet]]
[app.main.ui.workspace.colorpicker.slider-selector :refer [slider-selector]] [app.main.ui.workspace.colorpicker.slider-selector :refer [slider-selector]]
[app.util.color :as uc] [app.util.color :as uc]
@ -19,8 +19,8 @@
(fn [ev] (fn [ev]
(let [{:keys [left right top bottom]} (-> ev dom/get-target dom/get-bounding-rect) (let [{:keys [left right top bottom]} (-> ev dom/get-target dom/get-bounding-rect)
{:keys [x y]} (-> ev dom/get-client-position) {:keys [x y]} (-> ev dom/get-client-position)
px (math/clamp (/ (- x left) (- right left)) 0 1) px (mth/clamp (/ (- x left) (- right left)) 0 1)
py (* 255 (- 1 (math/clamp (/ (- y top) (- bottom top)) 0 1)))] py (* 255 (- 1 (mth/clamp (/ (- y top) (- bottom top)) 0 1)))]
(on-change px py))) (on-change px py)))
handle-start-drag handle-start-drag

View file

@ -6,7 +6,7 @@
(ns app.main.ui.workspace.colorpicker.slider-selector (ns app.main.ui.workspace.colorpicker.slider-selector
(:require (:require
[app.common.math :as math] [app.common.math :as mth]
[app.util.dom :as dom] [app.util.dom :as dom]
[app.util.object :as obj] [app.util.object :as obj]
[rumext.alpha :as mf])) [rumext.alpha :as mf]))
@ -41,13 +41,13 @@
(let [{:keys [left right top bottom]} (-> ev dom/get-target dom/get-bounding-rect) (let [{:keys [left right top bottom]} (-> ev dom/get-target dom/get-bounding-rect)
{:keys [x y]} (-> ev dom/get-client-position) {:keys [x y]} (-> ev dom/get-client-position)
unit-value (if vertical? unit-value (if vertical?
(math/clamp (/ (- bottom y) (- bottom top)) 0 1) (mth/clamp (/ (- bottom y) (- bottom top)) 0 1)
(math/clamp (/ (- x left) (- right left)) 0 1)) (mth/clamp (/ (- x left) (- right left)) 0 1))
unit-value (if reverse? unit-value (if reverse?
(math/abs (- unit-value 1.0)) (mth/abs (- unit-value 1.0))
unit-value) unit-value)
value (+ min-value (* unit-value (- max-value min-value)))] value (+ min-value (* unit-value (- max-value min-value)))]
(on-change (math/precision value 2)))))] (on-change value))))]
[:div.slider-selector [:div.slider-selector
{:class (str (if vertical? "vertical " "") class) {:class (str (if vertical? "vertical " "") class)
@ -60,7 +60,7 @@
(- max-value min-value)) 100) (- max-value min-value)) 100)
value-percent (if reverse? value-percent (if reverse?
(math/abs (- value-percent 100)) (mth/abs (- value-percent 100))
value-percent) value-percent)
value-percent-str (str value-percent "%") value-percent-str (str value-percent "%")

View file

@ -7,7 +7,6 @@
(ns app.main.ui.workspace.header (ns app.main.ui.workspace.header
(:require (:require
[app.common.data :as d] [app.common.data :as d]
[app.common.math :as mth]
[app.config :as cf] [app.config :as cf]
[app.main.data.events :as ev] [app.main.data.events :as ev]
[app.main.data.messages :as dm] [app.main.data.messages :as dm]
@ -18,6 +17,7 @@
[app.main.repo :as rp] [app.main.repo :as rp]
[app.main.store :as st] [app.main.store :as st]
[app.main.ui.components.dropdown :refer [dropdown]] [app.main.ui.components.dropdown :refer [dropdown]]
[app.main.ui.formats :as fmt]
[app.main.ui.hooks.resize :as r] [app.main.ui.hooks.resize :as r]
[app.main.ui.icons :as i] [app.main.ui.icons :as i]
[app.main.ui.workspace.presence :refer [active-sessions]] [app.main.ui.workspace.presence :refer [active-sessions]]
@ -71,7 +71,7 @@
:as props}] :as props}]
(let [show-dropdown? (mf/use-state false)] (let [show-dropdown? (mf/use-state false)]
[:div.zoom-widget {:on-click #(reset! show-dropdown? true)} [:div.zoom-widget {:on-click #(reset! show-dropdown? true)}
[:span.label {} (str (mth/round (* 100 zoom)) "%")] [:span.label (fmt/format-percent zoom {:precision 0})]
[:span.icon i/arrow-down] [:span.icon i/arrow-down]
[:& dropdown {:show @show-dropdown? [:& dropdown {:show @show-dropdown?
:on-close #(reset! show-dropdown? false)} :on-close #(reset! show-dropdown? false)}
@ -82,7 +82,7 @@
(dom/stop-propagation event) (dom/stop-propagation event)
(dom/prevent-default event) (dom/prevent-default event)
(on-decrease))} "-"] (on-decrease))} "-"]
[:p.zoom-size {} (str (mth/round (* 100 zoom)) "%")] [:p.zoom-size {} (fmt/format-percent zoom {:precision 0})]
[:button {:on-click (fn [event] [:button {:on-click (fn [event]
(dom/stop-propagation event) (dom/stop-propagation event)
(dom/prevent-default event) (dom/prevent-default event)

View file

@ -7,7 +7,6 @@
(ns app.main.ui.workspace.left-toolbar (ns app.main.ui.workspace.left-toolbar
(:require (:require
[app.common.geom.point :as gpt] [app.common.geom.point :as gpt]
[app.common.math :as mth]
[app.common.media :as cm] [app.common.media :as cm]
[app.main.data.events :as ev] [app.main.data.events :as ev]
[app.main.data.workspace :as dw] [app.main.data.workspace :as dw]
@ -40,8 +39,8 @@
;; We don't want to add a ref because that redraws the component ;; We don't want to add a ref because that redraws the component
;; for everychange. Better direct access on the callback. ;; for everychange. Better direct access on the callback.
(let [vbox (deref refs/vbox) (let [vbox (deref refs/vbox)
x (mth/round (+ (:x vbox) (/ (:width vbox) 2))) x (+ (:x vbox) (/ (:width vbox) 2))
y (mth/round (+ (:y vbox) (/ (:height vbox) 2))) y (+ (:y vbox) (/ (:height vbox) 2))
params {:file-id (:id file) params {:file-id (:id file)
:blobs (seq blobs) :blobs (seq blobs)
:position (gpt/point x y)}] :position (gpt/point x y)}]

View file

@ -49,12 +49,12 @@
[:div.input-wrapper [:div.input-wrapper
[:span [:span
[:p.nudge-subtitle (tr "modals.small-nudge")] [:p.nudge-subtitle (tr "modals.small-nudge")]
[:> numeric-input {:min 1 [:> numeric-input {:min 0.01
:value (:small nudge) :value (:small nudge)
:on-change update-small}]]] :on-change update-small}]]]
[:div.input-wrapper [:div.input-wrapper
[:span [:span
[:p.nudge-subtitle (tr "modals.big-nudge")] [:p.nudge-subtitle (tr "modals.big-nudge")]
[:> numeric-input {:min 1 [:> numeric-input {:min 0.01
:value (:big nudge) :value (:big nudge)
:on-change update-big}]]]]]])) :on-change update-big}]]]]]]))

View file

@ -89,6 +89,7 @@
:style {:cursor (cond :style {:cursor (cond
(= edit-mode :draw) cur/pen-node (= edit-mode :draw) cur/pen-node
(= edit-mode :move) cur/pointer-node) (= edit-mode :move) cur/pointer-node)
:stroke-width 0
:fill "none"}}]])) :fill "none"}}]]))
(mf/defc path-handler [{:keys [index prefix point handler zoom selected? hover? edit-mode snap-angle?]}] (mf/defc path-handler [{:keys [index prefix point handler zoom selected? hover? edit-mode snap-angle?]}]
@ -147,7 +148,8 @@
:on-mouse-enter on-enter :on-mouse-enter on-enter
:on-mouse-leave on-leave :on-mouse-leave on-leave
:style {:cursor (when (= edit-mode :move) cur/pointer-move) :style {:cursor (when (= edit-mode :move) cur/pointer-move)
:fill "none"}}]]))) :fill "none"
:stroke-width 0}}]])))
(mf/defc path-preview [{:keys [zoom command from]}] (mf/defc path-preview [{:keys [zoom command from]}]
[:g.preview {:style {:pointer-events "none"}} [:g.preview {:style {:pointer-events "none"}}

View file

@ -209,7 +209,7 @@
;; and updates the selrect accordingly ;; and updates the selrect accordingly
[:* [:*
[:g.text-shape {:ref on-change-node [:g.text-shape {:ref on-change-node
:opacity (when show-svg-text? 0) :opacity (when show-svg-text? 0.2)
:pointer-events "none"} :pointer-events "none"}
;; The `:key` prop here is mandatory because the ;; The `:key` prop here is mandatory because the

View file

@ -6,7 +6,6 @@
(ns app.main.ui.workspace.sidebar.options.menus.frame-grid (ns app.main.ui.workspace.sidebar.options.menus.frame-grid
(:require (:require
[app.common.math :as mth]
[app.main.data.workspace.grid :as dw] [app.main.data.workspace.grid :as dw]
[app.main.refs :as refs] [app.main.refs :as refs]
[app.main.store :as st] [app.main.store :as st]
@ -71,8 +70,7 @@
(let [{:keys [margin gutter item-length]} (:params grid) (let [{:keys [margin gutter item-length]} (:params grid)
frame-length (if (= :column (:type grid)) frame-width frame-height) frame-length (if (= :column (:type grid)) frame-width frame-height)
item-length (if (nil? size) item-length (if (nil? size)
(-> (gg/calculate-default-item-length frame-length margin gutter) (gg/calculate-default-item-length frame-length margin gutter)
(mth/precision 2))
item-length)] item-length)]
(-> grid (-> grid
(update :params assoc :size size :item-length item-length) (update :params assoc :size size :item-length item-length)
@ -140,7 +138,7 @@
(if (= type :square) (if (= type :square)
[:div.input-element.pixels {:title (tr "workspace.options.size")} [:div.input-element.pixels {:title (tr "workspace.options.size")}
[:> numeric-input {:min 1 [:> numeric-input {:min 0.01
:value (or (:size params) "") :value (or (:size params) "")
:no-validate true :no-validate true
:on-change (handle-change :params :size)}]] :on-change (handle-change :params :size)}]]
@ -162,7 +160,7 @@
(when (= :square type) (when (= :square type)
[:& input-row {:label (tr "workspace.options.grid.params.size") [:& input-row {:label (tr "workspace.options.grid.params.size")
:class "pixels" :class "pixels"
:min 1 :min 0.01
:value (:size params) :value (:size params)
:on-change (handle-change :params :size)}]) :on-change (handle-change :params :size)}])

View file

@ -7,7 +7,6 @@
(ns app.main.ui.workspace.sidebar.options.menus.layer (ns app.main.ui.workspace.sidebar.options.menus.layer
(:require (:require
[app.common.data :as d] [app.common.data :as d]
[app.common.math :as mth]
[app.main.data.workspace.changes :as dch] [app.main.data.workspace.changes :as dch]
[app.main.store :as st] [app.main.store :as st]
[app.main.ui.components.numeric-input :refer [numeric-input]] [app.main.ui.components.numeric-input :refer [numeric-input]]
@ -23,8 +22,7 @@
"" ""
(str (-> opacity (str (-> opacity
(d/coalesce 1) (d/coalesce 1)
(* 100) (* 100)))))
(mth/round)))))
(defn select-all [event] (defn select-all [event]
(dom/select-text! (dom/get-target event))) (dom/select-text! (dom/get-target event)))

View file

@ -8,7 +8,6 @@
(:require (:require
[app.common.data :as d] [app.common.data :as d]
[app.common.geom.shapes :as gsh] [app.common.geom.shapes :as gsh]
[app.common.math :as math]
[app.common.spec.radius :as ctr] [app.common.spec.radius :as ctr]
[app.main.data.workspace :as udw] [app.main.data.workspace :as udw]
[app.main.data.workspace.changes :as dch] [app.main.data.workspace.changes :as dch]
@ -46,9 +45,7 @@
(let [value (attr values)] (let [value (attr values)]
(if (= value :multiple) (if (= value :multiple)
"" ""
(str (-> value (str (-> value (d/coalesce 0))))))
(d/coalesce 0)
(math/precision 2))))))
(declare +size-presets+) (declare +size-presets+)
@ -239,7 +236,7 @@
[:div.row-flex [:div.row-flex
[:span.element-set-subtitle (tr "workspace.options.size")] [:span.element-set-subtitle (tr "workspace.options.size")]
[:div.input-element.width {:title (tr "workspace.options.width")} [:div.input-element.width {:title (tr "workspace.options.width")}
[:> numeric-input {:min 1 [:> numeric-input {:min 0.01
:no-validate true :no-validate true
:placeholder "--" :placeholder "--"
:on-click select-all :on-click select-all
@ -247,7 +244,7 @@
:value (attr->string :width values)}]] :value (attr->string :width values)}]]
[:div.input-element.height {:title (tr "workspace.options.height")} [:div.input-element.height {:title (tr "workspace.options.height")}
[:> numeric-input {:min 1 [:> numeric-input {:min 0.01
:no-validate true :no-validate true
:placeholder "--" :placeholder "--"
:on-click select-all :on-click select-all
@ -271,15 +268,13 @@
:placeholder "--" :placeholder "--"
:on-click select-all :on-click select-all
:on-change on-pos-x-change :on-change on-pos-x-change
:value (attr->string :x values) :value (attr->string :x values)}]]
:precision 2}]]
[:div.input-element.Yaxis {:title (tr "workspace.options.y")} [:div.input-element.Yaxis {:title (tr "workspace.options.y")}
[:> numeric-input {:no-validate true [:> numeric-input {:no-validate true
:placeholder "--" :placeholder "--"
:on-click select-all :on-click select-all
:on-change on-pos-y-change :on-change on-pos-y-change
:value (attr->string :y values) :value (attr->string :y values)}]]])
:precision 2}]]])
;; ROTATION ;; ROTATION
(when (options :rotation) (when (options :rotation)

View file

@ -386,7 +386,6 @@
{:min -200 {:min -200
:max 200 :max 200
:step 0.1 :step 0.1
:precision 2
:value (attr->string line-height) :value (attr->string line-height)
:placeholder (tr "settings.multiple") :placeholder (tr "settings.multiple")
:on-change #(handle-change % :line-height) :on-change #(handle-change % :line-height)
@ -400,7 +399,6 @@
{:min -200 {:min -200
:max 200 :max 200
:step 0.1 :step 0.1
:precision 2
:value (attr->string letter-spacing) :value (attr->string letter-spacing)
:placeholder (tr "settings.multiple") :placeholder (tr "settings.multiple")
:on-change #(handle-change % :letter-spacing) :on-change #(handle-change % :letter-spacing)

View file

@ -7,7 +7,6 @@
(ns app.main.ui.workspace.sidebar.options.rows.color-row (ns app.main.ui.workspace.sidebar.options.rows.color-row
(:require (:require
[app.common.data :as d] [app.common.data :as d]
[app.common.math :as math]
[app.common.pages :as cp] [app.common.pages :as cp]
[app.main.data.modal :as modal] [app.main.data.modal :as modal]
[app.main.refs :as refs] [app.main.refs :as refs]
@ -54,8 +53,7 @@
"" ""
(str (-> opacity (str (-> opacity
(d/coalesce 1) (d/coalesce 1)
(* 100) (* 100)))))
(math/round)))))
(defn remove-multiple [v] (defn remove-multiple [v]
(if (= v :multiple) nil v)) (if (= v :multiple) nil v))

View file

@ -97,7 +97,6 @@
[:> numeric-input [:> numeric-input
{:min 0 {:min 0
:value (-> (:stroke-width stroke) width->string) :value (-> (:stroke-width stroke) width->string)
:precision 2
:placeholder (tr "settings.multiple") :placeholder (tr "settings.multiple")
:on-change (on-stroke-width-change index) :on-change (on-stroke-width-change index)
:on-click select-all :on-click select-all

View file

@ -345,6 +345,7 @@
:zoom zoom :zoom zoom
:transform transform :transform transform
:selected selected :selected selected
:selected-shapes selected-shapes
:page-id page-id}]) :page-id page-id}])
(when show-cursor-tooltip? (when show-cursor-tooltip?

View file

@ -7,7 +7,6 @@
(ns app.main.ui.workspace.viewport.frame-grid (ns app.main.ui.workspace.viewport.frame-grid
(:require (:require
[app.common.geom.shapes :as gsh] [app.common.geom.shapes :as gsh]
[app.common.math :as mth]
[app.common.uuid :as uuid] [app.common.uuid :as uuid]
[app.main.refs :as refs] [app.main.refs :as refs]
[app.util.geom.grid :as gg] [app.util.geom.grid :as gg]
@ -58,10 +57,10 @@
[:g.grid [:g.grid
(for [{:keys [x y width height] :as area} (gg/grid-areas frame grid)] (for [{:keys [x y width height] :as area} (gg/grid-areas frame grid)]
[:rect {:key (str key "-" x "-" y) [:rect {:key (str key "-" x "-" y)
:x (mth/round x) :x x
:y (mth/round y) :y y
:width (- (mth/round (+ x width)) (mth/round x)) :width (- (+ x width) x)
:height (- (mth/round (+ y height)) (mth/round y)) :height (- (+ y height) y)
:style style}])])) :style style}])]))
(mf/defc grid-display-frame (mf/defc grid-display-frame

View file

@ -281,9 +281,7 @@
(fn [point] (fn [point]
(let [point (gpt/transform point transform-inverse) (let [point (gpt/transform point transform-inverse)
start-x (/ (- (:x point) x) width) start-x (/ (- (:x point) x) width)
start-y (/ (- (:y point) y) height) start-y (/ (- (:y point) y) height)]
start-x (mth/precision start-x 2)
start-y (mth/precision start-y 2)]
(change! {:start-x start-x :start-y start-y})))) (change! {:start-x start-x :start-y start-y}))))
on-change-finish on-change-finish
@ -292,9 +290,7 @@
(fn [point] (fn [point]
(let [point (gpt/transform point transform-inverse) (let [point (gpt/transform point transform-inverse)
end-x (/ (- (:x point) x) width) end-x (/ (- (:x point) x) width)
end-y (/ (- (:y point) y) height) end-y (/ (- (:y point) y) height)]
end-x (mth/precision end-x 2)
end-y (mth/precision end-y 2)]
(change! {:end-x end-x :end-y end-y})))) (change! {:end-x end-x :end-y end-y}))))
on-change-width on-change-width

View file

@ -9,7 +9,6 @@
[app.common.colors :as colors] [app.common.colors :as colors]
[app.common.geom.point :as gpt] [app.common.geom.point :as gpt]
[app.common.geom.shapes :as gsh] [app.common.geom.shapes :as gsh]
[app.common.math :as mth]
[app.common.uuid :as uuid] [app.common.uuid :as uuid]
[app.main.data.workspace :as dw] [app.main.data.workspace :as dw]
[app.main.refs :as refs] [app.main.refs :as refs]
@ -102,7 +101,6 @@
(+ start-pos delta)) (+ start-pos delta))
;; TODO: Change when pixel-grid flag exists ;; TODO: Change when pixel-grid flag exists
new-position (mth/round new-position)
new-frame-id (:id (get-hover-frame))] new-frame-id (:id (get-hover-frame))]
(swap! state assoc (swap! state assoc
:new-position new-position :new-position new-position
@ -366,7 +364,7 @@
:style {:font-size (/ rules/font-size zoom) :style {:font-size (/ rules/font-size zoom)
:font-family rules/font-family :font-family rules/font-family
:fill colors/black}} :fill colors/black}}
(str (mth/round pos))]]))]))) (str pos)]]))])))
(mf/defc new-guide-area (mf/defc new-guide-area
[{:keys [vbox zoom axis get-hover-frame disabled-guides?]}] [{:keys [vbox zoom axis get-hover-frame disabled-guides?]}]

View file

@ -146,12 +146,12 @@
:else :else
(connect-to-point orig-shape (connect-to-point orig-shape
{:x (+ (:x2 (:selrect orig-shape)) 100) {:x (+ (:x2 (:selrect orig-shape)) (/ 100 zoom))
:y (+ (- (:y1 (:selrect orig-shape)) 50) :y (+ (- (:y1 (:selrect orig-shape)) (/ 50 zoom))
(/ (* level 32) zoom))})) (/ (* level 32) zoom))}))
orig-dx (if (= orig-pos :right) 100 -100) orig-dx (/ (if (= orig-pos :right) 100 -100) zoom)
dest-dx (if (= dest-pos :right) 100 -100) dest-dx (/ (if (= dest-pos :right) 100 -100) zoom)
path ["M" orig-x orig-y "C" (+ orig-x orig-dx) orig-y (+ dest-x dest-dx) dest-y dest-x dest-y] path ["M" orig-x orig-y "C" (+ orig-x orig-dx) orig-y (+ dest-x dest-dx) dest-y dest-x dest-y]
pdata (str/join " " path) pdata (str/join " " path)
@ -182,7 +182,8 @@
:d pdata}] :d pdata}]
(when dest-shape (when dest-shape
[:& outline {:shape dest-shape [:& outline {:zoom zoom
:shape dest-shape
:color "var(--color-primary)"}]) :color "var(--color-primary)"}])
[:& interaction-marker {:index index [:& interaction-marker {:index index

View file

@ -10,6 +10,7 @@
[app.common.data :as d] [app.common.data :as d]
[app.common.geom.shapes :as gsh] [app.common.geom.shapes :as gsh]
[app.common.math :as mth] [app.common.math :as mth]
[app.main.ui.formats :as fmt]
[app.main.ui.hooks :as hooks] [app.main.ui.hooks :as hooks]
[app.util.object :as obj] [app.util.object :as obj]
[rumext.alpha :as mf])) [rumext.alpha :as mf]))
@ -131,9 +132,9 @@
(let [{:keys [start end]} (get-rule-params vbox axis) (let [{:keys [start end]} (get-rule-params vbox axis)
minv (max (mth/round start) -100000) minv (max start -100000)
minv (* (mth/ceil (/ minv step)) step) minv (* (mth/ceil (/ minv step)) step)
maxv (min (mth/round end) 100000) maxv (min end 100000)
maxv (* (mth/floor (/ maxv step)) step)] maxv (* (mth/floor (/ maxv step)) step)]
(for [step-val (range minv (inc maxv) step)] (for [step-val (range minv (inc maxv) step)]
@ -149,7 +150,7 @@
:style {:font-size (/ font-size zoom) :style {:font-size (/ font-size zoom)
:font-family font-family :font-family font-family
:fill colors/gray-30}} :fill colors/gray-30}}
(str (mth/round step-val))] (fmt/format-number step-val)]
[:line {:key (str "line-" (d/name axis) "-" step-val) [:line {:key (str "line-" (d/name axis) "-" step-val)
:x1 line-x1 :x1 line-x1
@ -184,7 +185,7 @@
:style {:font-size (/ font-size zoom) :style {:font-size (/ font-size zoom)
:font-family font-family :font-family font-family
:fill selection-area-color}} :fill selection-area-color}}
(str (mth/round (:x1 selection-rect)))] (fmt/format-number (:x1 selection-rect))]
[:rect {:x (:x2 selection-rect) [:rect {:x (:x2 selection-rect)
:y (:y vbox) :y (:y vbox)
@ -200,7 +201,7 @@
:style {:font-size (/ font-size zoom) :style {:font-size (/ font-size zoom)
:font-family font-family :font-family font-family
:fill selection-area-color}} :fill selection-area-color}}
(str (mth/round (:x2 selection-rect)))]] (fmt/format-number (:x2 selection-rect))]]
(let [center-x (+ (:x vbox) (/ rule-area-half-size zoom)) (let [center-x (+ (:x vbox) (/ rule-area-half-size zoom))
center-y (- (+ (:y selection-rect) (/ (:height selection-rect) 2)) (/ rule-area-half-size zoom))] center-y (- (+ (:y selection-rect) (/ (:height selection-rect) 2)) (/ rule-area-half-size zoom))]
@ -234,7 +235,7 @@
:style {:font-size (/ font-size zoom) :style {:font-size (/ font-size zoom)
:font-family font-family :font-family font-family
:fill selection-area-color}} :fill selection-area-color}}
(str (mth/round (:y2 selection-rect)))] (fmt/format-number (:y2 selection-rect))]
[:text {:x (+ center-x (/ (:height selection-rect) 2) ) [:text {:x (+ center-x (/ (:height selection-rect) 2) )
:y center-y :y center-y
@ -243,7 +244,7 @@
:style {:font-size (/ font-size zoom) :style {:font-size (/ font-size zoom)
:font-family font-family :font-family font-family
:fill selection-area-color}} :fill selection-area-color}}
(str (mth/round (:y1 selection-rect)))]])]) (fmt/format-number (:y1 selection-rect))]])])
(mf/defc rules (mf/defc rules
{::mf/wrap-props false {::mf/wrap-props false

View file

@ -131,7 +131,7 @@
(let [viewport (mf/ref-val viewport-ref) (let [viewport (mf/ref-val viewport-ref)
start-pt (mf/ref-val start-ref) start-pt (mf/ref-val start-ref)
current-pt (dom/get-client-position event) current-pt (dom/get-client-position event)
current-pt-viewport (utils/translate-point-to-viewport-raw viewport zoom current-pt) current-pt-viewport (utils/translate-point-to-viewport viewport zoom current-pt)
y-delta (/ (* (mf/ref-val height-factor-ref) (- (:y current-pt) (:y start-pt))) zoom) y-delta (/ (* (mf/ref-val height-factor-ref) (- (:y current-pt) (:y start-pt))) zoom)
x-delta (/ (* (mf/ref-val width-factor-ref) (- (:x current-pt) (:x start-pt))) zoom) x-delta (/ (* (mf/ref-val width-factor-ref) (- (:x current-pt) (:x start-pt))) zoom)
new-v-scrollbar-y (-> current-pt-viewport new-v-scrollbar-y (-> current-pt-viewport
@ -156,8 +156,9 @@
(fn [event axis] (fn [event axis]
(let [viewport (mf/ref-val viewport-ref) (let [viewport (mf/ref-val viewport-ref)
start-pt (dom/get-client-position event) start-pt (dom/get-client-position event)
new-v-scrollbar-y (-> (utils/translate-point-to-viewport-raw viewport zoom start-pt) :y) viewport-point (utils/translate-point-to-viewport viewport zoom start-pt)
new-h-scrollbar-x (-> (utils/translate-point-to-viewport-raw viewport zoom start-pt) :x) new-h-scrollbar-x (:x viewport-point)
new-v-scrollbar-y (:y viewport-point)
v-scrollbar-y-padding (- v-scrollbar-y new-v-scrollbar-y) v-scrollbar-y-padding (- v-scrollbar-y new-v-scrollbar-y)
h-scrollbar-x-padding (- h-scrollbar-x new-h-scrollbar-x) h-scrollbar-x-padding (- h-scrollbar-x new-h-scrollbar-x)
vbox-rect {:x vbox-x vbox-rect {:x vbox-x
@ -206,7 +207,7 @@
:x v-scrollbar-x :x v-scrollbar-x
:y v-scrollbar-y :y v-scrollbar-y
:style {:stroke "white" :style {:stroke "white"
:stroke-width 0.15}}]]) :stroke-width (/ 0.15 zoom)}}]])
(when show-h-scroll? (when show-h-scroll?
[:g.h-scroll [:g.h-scroll
[:rect {:on-mouse-move #(on-mouse-move % :x) [:rect {:on-mouse-move #(on-mouse-move % :x)
@ -220,4 +221,4 @@
:x h-scrollbar-x :x h-scrollbar-x
:y h-scrollbar-y :y h-scrollbar-y
:style {:stroke "white" :style {:stroke "white"
:stroke-width 0.15}}]])])) :stroke-width (/ 0.15 zoom)}}]])]))

View file

@ -67,38 +67,18 @@
:position :top-left :position :top-left
:props {:cx x :cy y}} :props {:cx x :cy y}}
(when show-resize-point?
{:type :resize-point
:position :top-left
:props {:cx x :cy y :align align}})
{:type :rotation {:type :rotation
:position :top-right :position :top-right
:props {:cx (+ x width) :cy y}} :props {:cx (+ x width) :cy y}}
(when show-resize-point?
{:type :resize-point
:position :top-right
:props {:cx (+ x width) :cy y :align align}})
{:type :rotation {:type :rotation
:position :bottom-right :position :bottom-right
:props {:cx (+ x width) :cy (+ y height)}} :props {:cx (+ x width) :cy (+ y height)}}
(when show-resize-point?
{:type :resize-point
:position :bottom-right
:props {:cx (+ x width) :cy (+ y height) :align align}})
{:type :rotation {:type :rotation
:position :bottom-left :position :bottom-left
:props {:cx x :cy (+ y height)}} :props {:cx x :cy (+ y height)}}
(when show-resize-point?
{:type :resize-point
:position :bottom-left
:props {:cx x :cy (+ y height) :align align}})
(when min-side-top? (when min-side-top?
{:type :resize-side {:type :resize-side
:position :top :position :top
@ -117,7 +97,30 @@
(when min-side-side? (when min-side-side?
{:type :resize-side {:type :resize-side
:position :left :position :left
:props {:x x :y (+ y height) :length height :angle 270 :align align}})] :props {:x x :y (+ y height) :length height :angle 270 :align align}})
(when show-resize-point?
{:type :resize-point
:position :top-left
:props {:cx x :cy y :align align}})
(when show-resize-point?
{:type :resize-point
:position :top-right
:props {:cx (+ x width) :cy y :align align}})
(when show-resize-point?
{:type :resize-point
:position :bottom-right
:props {:cx (+ x width) :cy (+ y height) :align align}})
(when show-resize-point?
{:type :resize-point
:position :bottom-left
:props {:cx x :cy (+ y height) :align align}})
]
(filterv (comp not nil?))))) (filterv (comp not nil?)))))
@ -136,6 +139,8 @@
:width size :width size
:height size :height size
:fill (if (debug? :rotation-handler) "blue" "none") :fill (if (debug? :rotation-handler) "blue" "none")
:stroke (if (debug? :rotation-handler) "blue" "none")
:stroke-width 0
:transform transform :transform transform
:on-mouse-down on-rotate}])) :on-mouse-down on-rotate}]))
@ -168,6 +173,8 @@
:height resize-point-circle-radius :height resize-point-circle-radius
:transform (when rotation (str/fmt "rotate(%s, %s, %s)" rotation cx' cy')) :transform (when rotation (str/fmt "rotate(%s, %s, %s)" rotation cx' cy'))
:style {:fill (if (debug? :resize-handler) "red" "none") :style {:fill (if (debug? :resize-handler) "red" "none")
:stroke (if (debug? :resize-handler) "red" "none")
:stroke-width 0
:cursor cursor} :cursor cursor}
:on-mouse-down #(on-resize {:x cx' :y cy'} %)}]) :on-mouse-down #(on-resize {:x cx' :y cy'} %)}])
@ -176,7 +183,10 @@
:cx cx' :cx cx'
:cy cy' :cy cy'
:style {:fill (if (debug? :resize-handler) "red" "none") :style {:fill (if (debug? :resize-handler) "red" "none")
:cursor cursor}}])])) :stroke (if (debug? :resize-handler) "red" "none")
:stroke-width 0
:cursor cursor}}]
)]))
(mf/defc resize-side-handler (mf/defc resize-side-handler
"The side handler is always rendered horizontally and then rotated" "The side handler is always rendered horizontally and then rotated"
@ -202,6 +212,8 @@
(gmt/rotate-matrix angle (gpt/point x y))) (gmt/rotate-matrix angle (gpt/point x y)))
:on-mouse-down #(on-resize res-point %) :on-mouse-down #(on-resize res-point %)
:style {:fill (if (debug? :resize-handler) "yellow" "none") :style {:fill (if (debug? :resize-handler) "yellow" "none")
:stroke (if (debug? :resize-handler) "yellow" "none")
:stroke-width 0
:cursor (if (#{:left :right} position) :cursor (if (#{:left :right} position)
(cur/resize-ew rotation) (cur/resize-ew rotation)
(cur/resize-ns rotation)) }}])) (cur/resize-ns rotation)) }}]))
@ -292,7 +304,7 @@
:pointer-events "visible" :pointer-events "visible"
:style {:stroke color :style {:stroke color
:stroke-width (/ 0.5 zoom) :stroke-width (/ 0.5 zoom)
:stroke-opacity "1" :stroke-opacity 1
:fill "none"}}]])) :fill "none"}}]]))
(mf/defc multiple-handlers (mf/defc multiple-handlers
@ -344,7 +356,7 @@
(mf/defc single-handlers (mf/defc single-handlers
[{:keys [shape zoom color disable-handlers] :as props}] [{:keys [shape zoom color disable-handlers] :as props}]
(let [shape-id (:id shape) (let [shape-id (:id shape)
shape (geom/transform-shape shape {:round-coords? false}) shape (geom/transform-shape shape)
on-resize on-resize
(fn [current-position _initial-position event] (fn [current-position _initial-position event]

View file

@ -11,6 +11,7 @@
[app.common.math :as mth] [app.common.math :as mth]
[app.common.pages.helpers :as cph] [app.common.pages.helpers :as cph]
[app.main.refs :as refs] [app.main.refs :as refs]
[app.main.ui.formats :as fmt]
[app.main.worker :as uw] [app.main.worker :as uw]
[beicon.core :as rx] [beicon.core :as rx]
[clojure.set :as set] [clojure.set :as set]
@ -54,7 +55,7 @@
(get sr2 (if (= :x coord) :x1 :y1))) (get sr2 (if (= :x coord) :x1 :y1)))
distance (- to-c from-c) distance (- to-c from-c)
distance-str (-> distance (mth/precision 0) str) distance-str (str distance)
half-point (half-point coord sr1 sr2) half-point (half-point coord sr1 sr2)
width (-> distance-str width (-> distance-str
count count
@ -81,7 +82,7 @@
:font-size (/ pill-text-font-size zoom) :font-size (/ pill-text-font-size zoom)
:fill "var(--color-white)" :fill "var(--color-white)"
:text-anchor "middle"} :text-anchor "middle"}
(mth/precision distance 0)]]) (fmt/format-number distance)]])
(let [p1 [(+ from-c (/ segment-gap zoom)) (+ half-point (/ segment-gap-side zoom))] (let [p1 [(+ from-c (/ segment-gap zoom)) (+ half-point (/ segment-gap-side zoom))]
p2 [(+ from-c (/ segment-gap zoom)) (- half-point (/ segment-gap-side zoom))] p2 [(+ from-c (/ segment-gap zoom)) (- half-point (/ segment-gap-side zoom))]
@ -110,7 +111,7 @@
sr2 (:selrect sh2) sr2 (:selrect sh2)
c1 (if (= coord :x) :x1 :y1) c1 (if (= coord :x) :x1 :y1)
c2 (if (= coord :x) :x2 :y2) c2 (if (= coord :x) :x2 :y2)
dist (mth/precision (- (c1 sr2) (c2 sr1)) 0)] dist (- (c1 sr2) (c2 sr1))]
[dist [sh1 sh2]])) [dist [sh1 sh2]]))
(defn overlap? [coord sh1 sh2] (defn overlap? [coord sh1 sh2]
@ -134,8 +135,7 @@
(-> (if (<= (coord sr) (coord selrect)) (-> (if (<= (coord sr) (coord selrect))
(gsh/distance-selrect sr selrect) (gsh/distance-selrect sr selrect)
(gsh/distance-selrect selrect sr)) (gsh/distance-selrect selrect sr))
coord coord)))
(mth/precision 0))))
get-shapes-match get-shapes-match
(fn [pred? shapes] (fn [pred? shapes]
@ -149,9 +149,9 @@
check-in-set check-in-set
(fn [value number-set] (fn [value number-set]
(->> number-set (->> number-set
(some #(<= (mth/abs (- value %)) 1)))) (some #(<= (mth/abs (- value %)) 0.01))))
;; Left/Top shapes and right/bottom shapes (depends on `coord` parameter ;; Left/Top shapes and right/bottom shapes (depends on `coord` parameter)
;; Gets the distance to the current selection ;; Gets the distance to the current selection
distances-xf (comp (map distance-to-selrect) (filter pos?)) distances-xf (comp (map distance-to-selrect) (filter pos?))
@ -195,6 +195,7 @@
(map #(vector selrect (:selrect %)))) (map #(vector selrect (:selrect %))))
segments-to-display (d/concat-set other-shapes-segments selection-segments)] segments-to-display (d/concat-set other-shapes-segments selection-segments)]
segments-to-display)) segments-to-display))
(mf/defc shape-distance (mf/defc shape-distance
@ -217,8 +218,9 @@
container-selrec (or (:selrect frame) container-selrec (or (:selrect frame)
(gsh/rect->selrect @refs/vbox)) (gsh/rect->selrect @refs/vbox))
areas (gsh/selrect->areas container-selrec selrect) areas (gsh/selrect->areas container-selrec selrect)
query-side (fn [side] query-side (fn [side]
(let [rect (gsh/pad-selrec (areas side))] (let [rect (get areas side)]
(if (and (> (:width rect) 0) (> (:height rect) 0)) (if (and (> (:width rect) 0) (> (:height rect) 0))
(->> (uw/ask! {:cmd :selection/query (->> (uw/ask! {:cmd :selection/query
:page-id page-id :page-id page-id
@ -264,15 +266,10 @@
(let [page-id (unchecked-get props "page-id") (let [page-id (unchecked-get props "page-id")
zoom (unchecked-get props "zoom") zoom (unchecked-get props "zoom")
selected (unchecked-get props "selected") selected (unchecked-get props "selected")
selected-shapes (mf/deref (refs/objects-by-id selected)) selected-shapes (unchecked-get props "selected-shapes")
frame-id (-> selected-shapes first :frame-id) frame-id (-> selected-shapes first :frame-id)
frame (mf/deref (refs/object-by-id frame-id)) frame (mf/deref (refs/object-by-id frame-id))
local (mf/deref refs/workspace-local) selrect (gsh/selection-rect selected-shapes)]
update-shape (fn [shape] (-> shape
(update :modifiers merge (:modifiers local))
gsh/transform-shape))
selrect (->> selected-shapes (map update-shape) gsh/selection-rect)]
[:g.distance [:g.distance
[:& shape-distance [:& shape-distance
{:selrect selrect {:selrect selrect

View file

@ -8,7 +8,6 @@
(:require (:require
[app.common.data :as d] [app.common.data :as d]
[app.common.geom.shapes :as gsh] [app.common.geom.shapes :as gsh]
[app.common.math :as mth]
[app.common.pages.helpers :as cph] [app.common.pages.helpers :as cph]
[app.common.spec :as us] [app.common.spec :as us]
[app.main.snap :as snap] [app.main.snap :as snap]
@ -28,8 +27,6 @@
(mf/defc snap-point (mf/defc snap-point
[{:keys [point zoom]}] [{:keys [point zoom]}]
(let [{:keys [x y]} point (let [{:keys [x y]} point
x (mth/round x)
y (mth/round y)
cross-width (/ 3 zoom)] cross-width (/ 3 zoom)]
[:g [:g
[:line {:x1 (- x cross-width) [:line {:x1 (- x cross-width)
@ -45,15 +42,15 @@
(mf/defc snap-line (mf/defc snap-line
[{:keys [snap point zoom]}] [{:keys [snap point zoom]}]
[:line {:x1 (mth/round (:x snap)) [:line {:x1 (:x snap)
:y1 (mth/round (:y snap)) :y1 (:y snap)
:x2 (mth/round (:x point)) :x2 (:x point)
:y2 (mth/round (:y point)) :y2 (:y point)
:style {:stroke line-color :stroke-width (str (/ line-width zoom))} :style {:stroke line-color :stroke-width (str (/ line-width zoom))}
:opacity line-opacity}]) :opacity line-opacity}])
(defn get-snap (defn get-snap
[coord {:keys [shapes page-id remove-snap? modifiers]}] [coord {:keys [shapes page-id remove-snap? zoom modifiers]}]
(let [shape (if (> (count shapes) 1) (let [shape (if (> (count shapes) 1)
(->> shapes (map gsh/transform-shape) gsh/selection-rect (gsh/setup {:type :rect})) (->> shapes (map gsh/transform-shape) gsh/selection-rect (gsh/setup {:type :rect}))
(->> shapes (first))) (->> shapes (first)))
@ -69,7 +66,7 @@
(->> (sp/shape-snap-points shape) (->> (sp/shape-snap-points shape)
(map #(vector frame-id %))))) (map #(vector frame-id %)))))
(rx/flat-map (fn [[frame-id point]] (rx/flat-map (fn [[frame-id point]]
(->> (snap/get-snap-points page-id frame-id remove-snap? point coord) (->> (snap/get-snap-points page-id frame-id remove-snap? zoom point coord)
(rx/map #(vector point % coord))))) (rx/map #(vector point % coord)))))
(rx/reduce conj [])))) (rx/reduce conj []))))
@ -119,12 +116,19 @@
(mf/use-effect (mf/use-effect
(fn [] (fn []
(let [sub (->> subject (let [sub (->> subject
(rx/switch-map #(rx/combine-latest (get-snap :x %) (rx/switch-map
(get-snap :y %))) (fn [props]
(rx/map (fn [result] (->> (get-snap :y props)
(apply d/concat-vec (seq result)))) (rx/combine-latest (get-snap :x props)))))
(rx/subs #(let [rs (filter (fn [[_ snaps _]] (> (count snaps) 0)) %)]
(reset! state rs))))] (rx/map
(fn [result]
(apply d/concat-vec (seq result))))
(rx/subs
(fn [data]
(let [rs (filter (fn [[_ snaps _]] (> (count snaps) 0)) data)]
(reset! state rs)))))]
;; On unmount callback ;; On unmount callback
#(rx/dispose! sub)))) #(rx/dispose! sub))))

View file

@ -6,6 +6,7 @@
(ns app.main.ui.workspace.viewport.thumbnail-renderer (ns app.main.ui.workspace.viewport.thumbnail-renderer
(:require (:require
[app.common.math :as mth]
[app.main.data.workspace.persistence :as dwp] [app.main.data.workspace.persistence :as dwp]
[app.main.store :as st] [app.main.store :as st]
[app.util.dom :as dom] [app.util.dom :as dom]
@ -21,6 +22,10 @@
(let [thumbnail-img (mf/use-ref nil) (let [thumbnail-img (mf/use-ref nil)
thumbnail-canvas (mf/use-ref nil) thumbnail-canvas (mf/use-ref nil)
{:keys [width height]} shape
fixed-width (mth/clamp width 250 2000)
fixed-height (/ (* height fixed-width) width)
on-dom-rendered on-dom-rendered
(mf/use-callback (mf/use-callback
(mf/deps (:id shape)) (mf/deps (:id shape))
@ -71,23 +76,23 @@
_ (.rect canvas-context 0 0 canvas-width canvas-height) _ (.rect canvas-context 0 0 canvas-width canvas-height)
_ (set! (.-fillStyle canvas-context) background) _ (set! (.-fillStyle canvas-context) background)
_ (.fill canvas-context) _ (.fill canvas-context)
_ (.drawImage canvas-context img-node 0 0) _ (.drawImage canvas-context img-node 0 0 canvas-width canvas-height)
data (.toDataURL canvas-node "image/jpeg" 0.8)] data (.toDataURL canvas-node "image/jpg" 1)]
(on-thumbnail-data data))))] (on-thumbnail-data data))))]
[:div.frame-renderer {:ref on-dom-rendered [:div.frame-renderer {:ref on-dom-rendered
:style {:display "none"}} :style {:display "none"}}
[:img.thumbnail-img [:img.thumbnail-img
{:ref thumbnail-img {:ref thumbnail-img
:width (:width shape) :width width
:height (:height shape) :height height
:on-load on-image-load}] :on-load on-image-load}]
[:canvas.thumbnail-canvas [:canvas.thumbnail-canvas
{:ref thumbnail-canvas {:ref thumbnail-canvas
:width (:width shape) :width fixed-width
:height (:height shape)}]])) :height fixed-height}]]))
(mf/defc frame-renderer (mf/defc frame-renderer
"Component in charge of creating thumbnails and storing them" "Component in charge of creating thumbnails and storing them"

View file

@ -163,7 +163,7 @@
(:width vbox 0) (:width vbox 0)
(:height vbox 0)])) (:height vbox 0)]))
(defn translate-point-to-viewport-raw [viewport zoom pt] (defn translate-point-to-viewport [viewport zoom pt]
(let [vbox (.. ^js viewport -viewBox -baseVal) (let [vbox (.. ^js viewport -viewBox -baseVal)
brect (dom/get-bounding-rect viewport) brect (dom/get-bounding-rect viewport)
brect (gpt/point (d/parse-integer (:left brect)) brect (gpt/point (d/parse-integer (:left brect))
@ -174,10 +174,6 @@
(gpt/divide zoom) (gpt/divide zoom)
(gpt/add box)))) (gpt/add box))))
(defn translate-point-to-viewport [viewport zoom pt]
(-> (translate-point-to-viewport-raw viewport zoom pt)
(gpt/round 0)))
(defn get-cursor [cursor] (defn get-cursor [cursor]
(case cursor (case cursor
:hand cur/hand :hand cur/hand

View file

@ -32,8 +32,8 @@
:pattern-units "userSpaceOnUse"} :pattern-units "userSpaceOnUse"}
[:path {:d "M 1 0 L 0 0 0 1" [:path {:d "M 1 0 L 0 0 0 1"
:style {:fill "none" :style {:fill "none"
:stroke "var(--color-info)" :stroke "var(--color-gray-20)"
:stroke-opacity "0.2" :stroke-opacity "1"
:stroke-width (str (/ 1 zoom))}}]]] :stroke-width (str (/ 1 zoom))}}]]]
[:rect {:x (:x vbox) [:rect {:x (:x vbox)
:y (:y vbox) :y (:y vbox)

View file

@ -7,7 +7,6 @@
(ns app.util.code-gen (ns app.util.code-gen
(:require (:require
[app.common.data :as d] [app.common.data :as d]
[app.common.math :as mth]
[app.common.text :as txt] [app.common.text :as txt]
[app.util.color :as uc] [app.util.color :as uc]
[cuerdas.core :as str])) [cuerdas.core :as str]))
@ -109,7 +108,7 @@
(every? #(or (nil? %) (= % 0)) value) (every? #(or (nil? %) (= % 0)) value)
(or (nil? value) (= value 0)))) (or (nil? value) (= value 0))))
default-format (fn [value] (str (mth/precision value 2) "px")) default-format (fn [value] (str value "px"))
format-property (fn [prop] format-property (fn [prop]
(let [css-prop (or (prop to-prop) (name prop)) (let [css-prop (or (prop to-prop) (name prop))
format-fn (or (prop format) default-format) format-fn (or (prop format) default-format)

View file

@ -9,7 +9,6 @@
[app.common.data :as d] [app.common.data :as d]
[app.common.geom.point :as gpt] [app.common.geom.point :as gpt]
[app.common.geom.shapes.path :as upg] [app.common.geom.shapes.path :as upg]
[app.common.math :as mth]
[app.common.path.commands :as upc] [app.common.path.commands :as upc]
[clojure.set :as set])) [clojure.set :as set]))
@ -402,9 +401,7 @@
(rest segments)))))) (rest segments))))))
(defn calculate-merge-points [group-segments points] (defn calculate-merge-points [group-segments points]
(let [index-merge-point (fn [group] (vector group (-> (gpt/center-points group) (let [index-merge-point (fn [group] (vector group (gpt/center-points group)))
(update :x mth/round)
(update :y mth/round))))
index-group (fn [point] (vector point (d/seek #(contains? % point) group-segments))) index-group (fn [point] (vector point (d/seek #(contains? % point) group-segments)))
group->merge-point (into {} (map index-merge-point) group-segments) group->merge-point (into {} (map index-merge-point) group-segments)

View file

@ -8,7 +8,7 @@
"Performance profiling for react components." "Performance profiling for react components."
(:require-macros [app.util.perf]) (:require-macros [app.util.perf])
(:require (:require
[app.common.math :as math] [app.common.math :as mth]
[rumext.alpha :as mf] [rumext.alpha :as mf]
[goog.functions :as f] [goog.functions :as f]
["react" :as react] ["react" :as react]

View file

@ -7,7 +7,6 @@
(ns debug (ns debug
(:require (:require
[app.common.data :as d] [app.common.data :as d]
[app.common.math :as mth]
[app.common.pages.helpers :as cph] [app.common.pages.helpers :as cph]
[app.common.transit :as t] [app.common.transit :as t]
[app.common.uuid :as uuid] [app.common.uuid :as uuid]
@ -130,7 +129,7 @@
ts (/ 1000 (* (- cur @last))) ts (/ 1000 (* (- cur @last)))
val (+ @avg (* (- ts @avg) 0.1))] val (+ @avg (* (- ts @avg) 0.1))]
(obj/set! node "innerText" (mth/precision val 0)) (obj/set! node "innerText" val)
(vreset! last cur) (vreset! last cur)
(vreset! avg val) (vreset! avg val)
(do-thing)))))] (do-thing)))))]