mirror of
https://github.com/penpot/penpot.git
synced 2025-07-31 05:28:30 +02:00
Merge pull request #6664 from penpot/niwinz-hotfix-1
🐛 Add better fix for path transformation
This commit is contained in:
commit
5faa619bc4
3 changed files with 70 additions and 59 deletions
|
@ -104,36 +104,11 @@
|
||||||
(impl/path-data
|
(impl/path-data
|
||||||
(reduce apply-to-index (vec content) modifiers))))
|
(reduce apply-to-index (vec content) modifiers))))
|
||||||
|
|
||||||
(defn- transform-content-legacy
|
|
||||||
[content transform]
|
|
||||||
(if (some? transform)
|
|
||||||
(let [set-tr
|
|
||||||
(fn [params px py]
|
|
||||||
(let [tr-point (-> (gpt/point (get params px) (get params py))
|
|
||||||
(gpt/transform transform))]
|
|
||||||
(assoc params
|
|
||||||
px (:x tr-point)
|
|
||||||
py (:y tr-point))))
|
|
||||||
|
|
||||||
transform-params
|
|
||||||
(fn [{:keys [x c1x c2x] :as params}]
|
|
||||||
(cond-> params
|
|
||||||
(some? x) (set-tr :x :y)
|
|
||||||
(some? c1x) (set-tr :c1x :c1y)
|
|
||||||
(some? c2x) (set-tr :c2x :c2y)))]
|
|
||||||
|
|
||||||
(into []
|
|
||||||
(map #(update % :params transform-params))
|
|
||||||
content))
|
|
||||||
content))
|
|
||||||
|
|
||||||
(defn transform-content
|
(defn transform-content
|
||||||
"Applies a transformation matrix over content and returns a new
|
"Applies a transformation matrix over content and returns a new
|
||||||
content as PathData instance."
|
content as PathData instance."
|
||||||
[content transform]
|
[content transform]
|
||||||
#_(segment/transform-content content transform)
|
(segment/transform-content content transform))
|
||||||
(some-> (transform-content-legacy (vec content) transform)
|
|
||||||
(impl/from-plain)))
|
|
||||||
|
|
||||||
(defn move-content
|
(defn move-content
|
||||||
[content move-vec]
|
[content move-vec]
|
||||||
|
|
|
@ -65,34 +65,34 @@
|
||||||
(let [t (buf/read-short buffer offset)]
|
(let [t (buf/read-short buffer offset)]
|
||||||
(case t
|
(case t
|
||||||
(1 2)
|
(1 2)
|
||||||
(let [x (buf/read-float buffer (+ offset 20))
|
(let [x (buf/read-float buffer (+ offset 20))
|
||||||
y (buf/read-float buffer (+ offset 24))
|
y (buf/read-float buffer (+ offset 24))
|
||||||
x (+ (* x a) (* y c) e)
|
x' (+ (* x a) (* y c) e)
|
||||||
y (+ (* x b) (* y d) f)]
|
y' (+ (* x b) (* y d) f)]
|
||||||
(buf/write-float buffer (+ offset 20) x)
|
(buf/write-float buffer (+ offset 20) x')
|
||||||
(buf/write-float buffer (+ offset 24) y))
|
(buf/write-float buffer (+ offset 24) y'))
|
||||||
|
|
||||||
3
|
3
|
||||||
(let [c1x (buf/read-float buffer (+ offset 4))
|
(let [c1x (buf/read-float buffer (+ offset 4))
|
||||||
c1y (buf/read-float buffer (+ offset 8))
|
c1y (buf/read-float buffer (+ offset 8))
|
||||||
c2x (buf/read-float buffer (+ offset 12))
|
c2x (buf/read-float buffer (+ offset 12))
|
||||||
c2y (buf/read-float buffer (+ offset 16))
|
c2y (buf/read-float buffer (+ offset 16))
|
||||||
x (buf/read-float buffer (+ offset 20))
|
x (buf/read-float buffer (+ offset 20))
|
||||||
y (buf/read-float buffer (+ offset 24))
|
y (buf/read-float buffer (+ offset 24))
|
||||||
|
|
||||||
c1x (+ (* c1x a) (* c1y c) e)
|
c1x' (+ (* c1x a) (* c1y c) e)
|
||||||
c1y (+ (* c1x b) (* c1y d) f)
|
c1y' (+ (* c1x b) (* c1y d) f)
|
||||||
c2x (+ (* c2x a) (* c2y c) e)
|
c2x' (+ (* c2x a) (* c2y c) e)
|
||||||
c2y (+ (* c2x b) (* c2y d) f)
|
c2y' (+ (* c2x b) (* c2y d) f)
|
||||||
x (+ (* x a) (* y c) e)
|
x' (+ (* x a) (* y c) e)
|
||||||
y (+ (* x b) (* y d) f)]
|
y' (+ (* x b) (* y d) f)]
|
||||||
|
|
||||||
(buf/write-float buffer (+ offset 4) c1x)
|
(buf/write-float buffer (+ offset 4) c1x')
|
||||||
(buf/write-float buffer (+ offset 8) c1y)
|
(buf/write-float buffer (+ offset 8) c1y')
|
||||||
(buf/write-float buffer (+ offset 12) c2x)
|
(buf/write-float buffer (+ offset 12) c2x')
|
||||||
(buf/write-float buffer (+ offset 16) c2y)
|
(buf/write-float buffer (+ offset 16) c2y')
|
||||||
(buf/write-float buffer (+ offset 20) x)
|
(buf/write-float buffer (+ offset 20) x')
|
||||||
(buf/write-float buffer (+ offset 24) y))
|
(buf/write-float buffer (+ offset 24) y'))
|
||||||
|
|
||||||
nil)))
|
nil)))
|
||||||
|
|
||||||
|
|
|
@ -25,6 +25,15 @@
|
||||||
{:command :curve-to :params {:c1x 368.0 :c1y 737.0 :c2x 310.0 :c2y 681.0 :x 264.0 :y 634.0}}
|
{:command :curve-to :params {:c1x 368.0 :c1y 737.0 :c2x 310.0 :c2y 681.0 :x 264.0 :y 634.0}}
|
||||||
{:command :close-path :params {}}])
|
{:command :close-path :params {}}])
|
||||||
|
|
||||||
|
(def sample-content-square
|
||||||
|
[{:command :move-to, :params {:x 0, :y 0}}
|
||||||
|
{:command :line-to, :params {:x 10, :y 0}}
|
||||||
|
{:command :line-to, :params {:x 10, :y 10}}
|
||||||
|
{:command :line-to, :params {:x 10, :y 0}}
|
||||||
|
{:command :line-to, :params {:x 0, :y 10}}
|
||||||
|
{:command :line-to, :params {:x 0, :y 0}}
|
||||||
|
{:command :close-path :params {}}])
|
||||||
|
|
||||||
(def sample-content-large
|
(def sample-content-large
|
||||||
[{:command :move-to :params {:x 480.0 :y 839.0}}
|
[{:command :move-to :params {:x 480.0 :y 839.0}}
|
||||||
{:command :line-to :params {:x 439.0 :y 802.0}}
|
{:command :line-to :params {:x 439.0 :y 802.0}}
|
||||||
|
@ -179,6 +188,42 @@
|
||||||
(t/is (= (vec result1) result2))
|
(t/is (= (vec result1) result2))
|
||||||
(t/is (= result2 result3))))
|
(t/is (= result2 result3))))
|
||||||
|
|
||||||
|
(t/deftest path-transform-3
|
||||||
|
(let [matrix (gmt/rotate-matrix 42 (gpt/point 0 0))
|
||||||
|
content (path/content sample-content-square)
|
||||||
|
|
||||||
|
result1 (path/transform-content content matrix)
|
||||||
|
result2 (transform-plain-content sample-content-square matrix)
|
||||||
|
result3 (transform-plain-content content matrix)]
|
||||||
|
|
||||||
|
(t/is (= (count result1) (count result2)))
|
||||||
|
(doseq [[seg-a seg-b] (map vector result1 result2)]
|
||||||
|
(t/is (= (:command seg-a)
|
||||||
|
(:command seg-b)))
|
||||||
|
|
||||||
|
(let [params-a (get seg-a :params)
|
||||||
|
params-b (get seg-b :params)]
|
||||||
|
|
||||||
|
(t/is (mth/close? (get params-a :x 0)
|
||||||
|
(get params-b :x 0)))
|
||||||
|
(t/is (mth/close? (get params-a :y 0)
|
||||||
|
(get params-b :y 0)))))
|
||||||
|
|
||||||
|
|
||||||
|
(doseq [[seg-a seg-b] (map vector result1 result3)]
|
||||||
|
(t/is (= (:command seg-a)
|
||||||
|
(:command seg-b)))
|
||||||
|
|
||||||
|
(let [params-a (get seg-a :params)
|
||||||
|
params-b (get seg-b :params)]
|
||||||
|
|
||||||
|
(t/is (mth/close? (get params-a :x 0)
|
||||||
|
(get params-b :x 0)))
|
||||||
|
(t/is (mth/close? (get params-a :y 0)
|
||||||
|
(get params-b :y 0)))))))
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
(defn- content->points
|
(defn- content->points
|
||||||
"Given a content return all points.
|
"Given a content return all points.
|
||||||
|
|
||||||
|
@ -278,15 +323,6 @@
|
||||||
(t/is (= result2 expect))
|
(t/is (= result2 expect))
|
||||||
(t/is (= result3 expect))))
|
(t/is (= result3 expect))))
|
||||||
|
|
||||||
(def sample-content-square
|
|
||||||
[{:command :move-to, :params {:x 0, :y 0}}
|
|
||||||
{:command :line-to, :params {:x 10, :y 0}}
|
|
||||||
{:command :line-to, :params {:x 10, :y 10}}
|
|
||||||
{:command :line-to, :params {:x 10, :y 0}}
|
|
||||||
{:command :line-to, :params {:x 0, :y 10}}
|
|
||||||
{:command :line-to, :params {:x 0, :y 0}}
|
|
||||||
{:command :close-path :params {}}])
|
|
||||||
|
|
||||||
(t/deftest points-to-content
|
(t/deftest points-to-content
|
||||||
(let [initial [(gpt/point 0.0 0.0)
|
(let [initial [(gpt/point 0.0 0.0)
|
||||||
(gpt/point 10.0 10.0)
|
(gpt/point 10.0 10.0)
|
||||||
|
|
Loading…
Add table
Add a link
Reference in a new issue