0
Fork 0
mirror of https://github.com/penpot/penpot.git synced 2025-03-11 07:11:32 -05:00

🐛 Fix problems with CTRL in MacOS

This commit is contained in:
alonso.torres 2022-03-24 14:45:52 +01:00
parent 5a591d2acd
commit 32e4569495
14 changed files with 120 additions and 68 deletions

View file

@ -61,6 +61,7 @@
- Fix problems with trackpad zoom and scroll in MacOS [#1161](https://github.com/penpot/penpot/issues/1161)
- Fix problem with copy/paste in Safari [#1209](https://github.com/penpot/penpot/issues/1209)
- Fix paste ordering for frames not being respected [Taiga #3097](https://tree.taiga.io/project/penpot/issue/3097)
- Improved command support for MacOS [Taiga #2789](https://tree.taiga.io/project/penpot/issue/2789)
### :arrow_up: Deps updates
### :heart: Community contributions by (Thank you!)

View file

@ -541,13 +541,13 @@
initial-angle (gpt/angle @ms/mouse-position group-center)
calculate-angle
(fn [pos ctrl? shift?]
(fn [pos mod? shift?]
(let [angle (- (gpt/angle pos group-center) initial-angle)
angle (if (neg? angle) (+ 360 angle) angle)
angle (if (= angle 360)
0
angle)
angle (if ctrl?
angle (if mod?
(* (mth/floor (/ angle 45)) 45)
angle)
angle (if shift?
@ -556,11 +556,11 @@
angle))]
(rx/concat
(->> ms/mouse-position
(rx/with-latest vector ms/mouse-position-ctrl)
(rx/with-latest vector ms/mouse-position-mod)
(rx/with-latest vector ms/mouse-position-shift)
(rx/map
(fn [[[pos ctrl?] shift?]]
(let [delta-angle (calculate-angle pos ctrl? shift?)]
(fn [[[pos mod?] shift?]]
(let [delta-angle (calculate-angle pos mod? shift?)]
(set-rotation-modifiers delta-angle shapes group-center))))
(rx/take-until stoper))
(rx/of (apply-modifiers (map :id shapes))

View file

@ -7,6 +7,7 @@
(ns app.main.streams
"User interaction events and streams."
(:require
[app.config :as cfg]
[app.main.store :as st]
[app.util.globals :as globals]
[app.util.keyboard :as kbd]
@ -20,7 +21,7 @@
[v]
(instance? KeyboardEvent v))
(defrecord MouseEvent [type ctrl shift alt])
(defrecord MouseEvent [type ctrl shift alt meta])
(defn mouse-event?
[v]
@ -46,7 +47,7 @@
(and (mouse-event? v)
(= :double-click (:type v))))
(defrecord PointerEvent [source pt ctrl shift alt])
(defrecord PointerEvent [source pt ctrl shift alt meta])
(defn pointer-event?
[v]
@ -83,6 +84,20 @@
(rx/subscribe-with ob sub)
sub))
(defonce mouse-position-meta
(let [sub (rx/behavior-subject nil)
ob (->> st/stream
(rx/filter pointer-event?)
(rx/map :meta)
(rx/dedupe))]
(rx/subscribe-with ob sub)
sub))
(defonce mouse-position-mod
(if (cfg/check-platform? :macos)
mouse-position-meta
mouse-position-ctrl))
(defonce mouse-position-shift
(let [sub (rx/behavior-subject nil)
ob (->> st/stream
@ -111,7 +126,7 @@
ob (->> (rx/merge
(->> st/stream
(rx/filter keyboard-event?)
(rx/filter kbd/altKey?)
(rx/filter kbd/alt-key?)
(rx/map #(= :down (:type %))))
;; Fix a situation caused by using `ctrl+alt` kind of shortcuts,
;; that makes keyboard-alt stream registering the key pressed but
@ -119,15 +134,15 @@
(->> window-blur
(rx/map (constantly false))))
(rx/dedupe))]
(rx/subscribe-with ob sub)
sub))
(rx/subscribe-with ob sub)
sub))
(defonce keyboard-ctrl
(let [sub (rx/behavior-subject nil)
ob (->> (rx/merge
(->> st/stream
(rx/filter keyboard-event?)
(rx/filter kbd/ctrlKey?)
(rx/filter kbd/ctrl-key?)
(rx/map #(= :down (:type %))))
;; Fix a situation caused by using `ctrl+alt` kind of shortcuts,
;; that makes keyboard-alt stream registering the key pressed but
@ -135,9 +150,30 @@
(->> window-blur
(rx/map (constantly false))))
(rx/dedupe))]
(rx/subscribe-with ob sub)
(rx/subscribe-with ob sub)
sub))
(defonce keyboard-meta
(let [sub (rx/behavior-subject nil)
ob (->> (rx/merge
(->> st/stream
(rx/filter keyboard-event?)
(rx/filter kbd/meta-key?)
(rx/map #(= :down (:type %))))
;; Fix a situation caused by using `ctrl+alt` kind of shortcuts,
;; that makes keyboard-alt stream registering the key pressed but
;; on blurring the window (unfocus) the key down is never arrived.
(->> window-blur
(rx/map (constantly false))))
(rx/dedupe))]
(rx/subscribe-with ob sub)
sub))
(defonce keyboard-mod
(if (cfg/check-platform? :macos)
keyboard-meta
keyboard-ctrl))
(defonce keyboard-space
(let [sub (rx/behavior-subject nil)
ob (->> st/stream

View file

@ -14,6 +14,7 @@
[app.main.ui.dashboard.sidebar :refer [profile-section]]
[app.main.ui.icons :as i]
[app.util.i18n :as i18n :refer [tr]]
[app.util.keyboard :as kbd]
[app.util.router :as rt]
[potok.core :as ptk]
[rumext.alpha :as mf]))
@ -55,8 +56,7 @@
(fn [event]
(let [version (:main @cf/version)]
(st/emit! (ptk/event ::ev/event {::ev/name "show-release-notes" :version version}))
(if (and (.-ctrlKey ^js event)
(.-altKey ^js event))
(if (and (kbd/alt? event) (kbd/mod? event))
(st/emit! (modal/show {:type :onboarding}))
(st/emit! (modal/show {:type :release-notes :version version}))))))]

View file

@ -28,7 +28,7 @@
[{:keys [local file page frame]}]
(let [on-mouse-wheel
(fn [event]
(when (or (kbd/ctrl? event) (kbd/meta? event))
(when (kbd/mod? event)
(dom/prevent-default event)
(let [event (.getBrowserEvent ^js event)
delta (+ (.-deltaY ^js event)

View file

@ -45,7 +45,7 @@
(dom/prevent-default event)
(let [id (:id item)]
(cond
(or (kbd/ctrl? event) (kbd/meta? event))
(kbd/mod? event)
(st/emit! (dv/toggle-selection id))
(kbd/shift? event)

View file

@ -61,7 +61,7 @@
on-mouse-wheel
(fn [event]
(when (or (kbd/ctrl? event) (kbd/meta? event))
(when (kbd/mod? event)
(dom/prevent-default event)
(let [event (.getBrowserEvent ^js event)
delta (+ (.-deltaY ^js event) (.-deltaX ^js event))]

View file

@ -47,15 +47,15 @@
(st/emit! (drp/create-node-at-position (meta position))))
(let [shift? (kbd/shift? event)
ctrl? (kbd/ctrl? event)]
mod? (kbd/mod? event)]
(cond
last-p?
(st/emit! (drp/reset-last-handler))
(and (= edit-mode :move) ctrl? (not curve?))
(and (= edit-mode :move) mod? (not curve?))
(st/emit! (drp/make-curve position))
(and (= edit-mode :move) ctrl? curve?)
(and (= edit-mode :move) mod? curve?)
(st/emit! (drp/make-corner position))
(= edit-mode :move)

View file

@ -1491,7 +1491,7 @@
(mf/deps extend-selected-assets selected-assets)
(fn [asset-type asset-groups event asset-id default-click]
(cond
(kbd/ctrl? event)
(kbd/mod? event)
(do
(dom/stop-propagation event)
(st/emit! (dw/toggle-selected-assets asset-id asset-type)))

View file

@ -134,7 +134,7 @@
(kbd/shift? event)
(st/emit! (dw/shift-select-shapes id))
(or (kbd/ctrl? event) (kbd/meta? event))
(kbd/mod? event)
(st/emit! (dw/select-shape id true))
(> (count selected) 1)

View file

@ -77,7 +77,7 @@
;; STATE
alt? (mf/use-state false)
ctrl? (mf/use-state false)
mod? (mf/use-state false)
space? (mf/use-state false)
cursor (mf/use-state (utils/get-cursor :pointer-inner))
hover-ids (mf/use-state nil)
@ -171,9 +171,9 @@
(hooks/setup-dom-events viewport-ref zoom disable-paste in-viewport?)
(hooks/setup-viewport-size viewport-ref)
(hooks/setup-cursor cursor alt? ctrl? space? panning drawing-tool drawing-path? node-editing?)
(hooks/setup-keyboard alt? ctrl? space?)
(hooks/setup-hover-shapes page-id move-stream base-objects transform selected ctrl? hover hover-ids @hover-disabled? focus zoom)
(hooks/setup-cursor cursor alt? mod? space? panning drawing-tool drawing-path? node-editing?)
(hooks/setup-keyboard alt? mod? space?)
(hooks/setup-hover-shapes page-id move-stream base-objects transform selected mod? hover hover-ids @hover-disabled? focus zoom)
(hooks/setup-viewport-modifiers modifiers base-objects)
(hooks/setup-shortcuts node-editing? drawing-path?)
(hooks/setup-active-frames base-objects vbox hover active-frames)
@ -258,7 +258,7 @@
{:objects base-objects
:selected selected
:hover (cond
(and @hover (or @ctrl? (not= :frame (:type @hover))))
(and @hover (or @mod? (not= :frame (:type @hover))))
#{(:id @hover)}
@frame-hover
@ -271,7 +271,7 @@
{:shapes selected-shapes
:zoom zoom
:edition edition
:disable-handlers (or drawing-tool edition @space? @ctrl?)
:disable-handlers (or drawing-tool edition @space? @mod?)
:on-move-selected on-move-selected
:on-context-menu on-menu-selected}])

View file

@ -41,8 +41,10 @@
(let [event (.-nativeEvent bevent)
ctrl? (kbd/ctrl? event)
meta? (kbd/meta? event)
shift? (kbd/shift? event)
alt? (kbd/alt? event)
mod? (kbd/mod? event)
left-click? (and (not panning) (= 1 (.-which event)))
middle-click? (and (not panning) (= 2 (.-which event)))
@ -54,7 +56,7 @@
middle-click?
(do
(dom/prevent-default bevent)
(if ctrl?
(if mod?
(let [raw-pt (dom/get-client-position event)
viewport (mf/ref-val viewport-ref)
pt (utils/translate-point-to-viewport viewport zoom raw-pt)]
@ -64,7 +66,7 @@
left-click?
(do
(st/emit! (ms/->MouseEvent :down ctrl? shift? alt?))
(st/emit! (ms/->MouseEvent :down ctrl? shift? alt? meta?))
(when (and (not= edition id) text-editing?)
(st/emit! dw/clear-edition-mode))
@ -79,7 +81,7 @@
;; Handle path node area selection
(st/emit! (dwdp/handle-area-selection shift?))
(and @space? ctrl?)
(and @space? mod?)
(let [raw-pt (dom/get-client-position event)
viewport (mf/ref-val viewport-ref)
pt (utils/translate-point-to-viewport viewport zoom raw-pt)]
@ -91,8 +93,8 @@
drawing-tool
(st/emit! (dd/start-drawing drawing-tool))
(or (not id) (and frame? (not selected?)) ctrl?)
(st/emit! (dw/handle-area-selection shift? ctrl?))
(or (not id) (and frame? (not selected?)) mod?)
(st/emit! (dw/handle-area-selection shift? mod?))
(not drawing-tool)
(st/emit! (when (or shift? (not selected?))
@ -106,11 +108,11 @@
(fn [bevent]
(let [event (.-nativeEvent bevent)
shift? (kbd/shift? event)
ctrl? (kbd/ctrl? event)
mod? (kbd/mod? event)
left-click? (= 1 (.-which event))]
(when (and left-click?
(not ctrl?)
(not mod?)
(not shift?)
(not @space?)
(or (not @hover)
@ -154,14 +156,16 @@
(let [ctrl? (kbd/ctrl? event)
shift? (kbd/shift? event)
alt? (kbd/alt? event)
meta? (kbd/meta? event)
mod? (kbd/mod? event)
hovering? (some? @hover)
frame? (= :frame (:type @hover))
selected? (contains? selected (:id @hover))]
(st/emit! (ms/->MouseEvent :click ctrl? shift? alt?))
(st/emit! (ms/->MouseEvent :click ctrl? shift? alt? meta?))
(when (and hovering?
(or (not frame?) ctrl?)
(or (not frame?) mod?)
(not @space?)
(not selected?)
(not edition)
@ -178,13 +182,14 @@
(let [ctrl? (kbd/ctrl? event)
shift? (kbd/shift? event)
alt? (kbd/alt? event)
meta? (kbd/meta? event)
{:keys [id type] :as shape} @hover
frame? (= :frame type)
group? (= :group type)]
(st/emit! (ms/->MouseEvent :double-click ctrl? shift? alt?))
(st/emit! (ms/->MouseEvent :double-click ctrl? shift? alt? meta?))
;; Emit asynchronously so the double click to exit shapes won't break
(timers/schedule
@ -243,12 +248,13 @@
ctrl? (kbd/ctrl? event)
shift? (kbd/shift? event)
alt? (kbd/alt? event)
meta? (kbd/meta? event)
left-click? (= 1 (.-which event))
middle-click? (= 2 (.-which event))]
(when left-click?
(st/emit! (ms/->MouseEvent :up ctrl? shift? alt?)))
(st/emit! (ms/->MouseEvent :up ctrl? shift? alt? meta?)))
(when middle-click?
(dom/prevent-default event)
@ -344,11 +350,13 @@
(st/emit! (ms/->PointerEvent :delta delta
(kbd/ctrl? event)
(kbd/shift? event)
(kbd/alt? event)))
(kbd/alt? event)
(kbd/meta? event)))
(st/emit! (ms/->PointerEvent :viewport pt
(kbd/ctrl? event)
(kbd/shift? event)
(kbd/alt? event))))))))
(kbd/alt? event)
(kbd/meta? event))))))))
(defn on-pointer-move [viewport-ref zoom move-stream]
(mf/use-callback
@ -372,8 +380,7 @@
(let [pt (->> (dom/get-client-position event)
(utils/translate-point-to-viewport viewport zoom))
ctrl? (kbd/ctrl? event)
meta? (kbd/meta? event)
mod? (kbd/mod? event)
delta-mode (.-deltaMode ^js event)
@ -389,7 +396,7 @@
delta-x (-> (.-deltaX ^js event)
(* unit)
(/ zoom))]
(if (or ctrl? meta?)
(if mod?
(let [delta (* -1 (+ (.-deltaY ^js event) (.-deltaX ^js event)))
scale (-> (+ 1 (/ delta 100)) (mth/clamp 0.77 1.3))]
(st/emit! (dw/set-zoom pt scale)))

View file

@ -58,16 +58,16 @@
;; We schedule the event so it fires after `initialize-page` event
(timers/schedule #(st/emit! (dw/initialize-viewport size)))))))
(defn setup-cursor [cursor alt? ctrl? space? panning drawing-tool drawing-path? path-editing?]
(defn setup-cursor [cursor alt? mod? space? panning drawing-tool drawing-path? path-editing?]
(mf/use-effect
(mf/deps @cursor @alt? @ctrl? @space? panning drawing-tool drawing-path? path-editing?)
(mf/deps @cursor @alt? @mod? @space? panning drawing-tool drawing-path? path-editing?)
(fn []
(let [show-pen? (or (= drawing-tool :path)
(and drawing-path?
(not= drawing-tool :curve)))
new-cursor
(cond
(and @ctrl? @space?) (utils/get-cursor :zoom)
(and @mod? @space?) (utils/get-cursor :zoom)
(or panning @space?) (utils/get-cursor :hand)
(= drawing-tool :comments) (utils/get-cursor :comments)
(= drawing-tool :frame) (utils/get-cursor :create-artboard)
@ -82,9 +82,9 @@
(when (not= @cursor new-cursor)
(reset! cursor new-cursor))))))
(defn setup-keyboard [alt? ctrl? space?]
(defn setup-keyboard [alt? mod? space?]
(hooks/use-stream ms/keyboard-alt #(reset! alt? %))
(hooks/use-stream ms/keyboard-ctrl #(reset! ctrl? %))
(hooks/use-stream ms/keyboard-mod #(reset! mod? %))
(hooks/use-stream ms/keyboard-space #(reset! space? %)))
(defn group-empty-space?
@ -100,10 +100,10 @@
(some #(cph/is-parent? objects % group-id))
(not))))
(defn setup-hover-shapes [page-id move-stream objects transform selected ctrl? hover hover-ids hover-disabled? focus zoom]
(defn setup-hover-shapes [page-id move-stream objects transform selected mod? hover hover-ids hover-disabled? focus zoom]
(let [;; We use ref so we don't recreate the stream on a change
zoom-ref (mf/use-ref zoom)
ctrl-ref (mf/use-ref @ctrl?)
mod-ref (mf/use-ref @mod?)
transform-ref (mf/use-ref nil)
selected-ref (mf/use-ref selected)
hover-disabled-ref (mf/use-ref hover-disabled?)
@ -114,7 +114,7 @@
(mf/deps page-id)
(fn [point]
(let [zoom (mf/ref-val zoom-ref)
ctrl? (mf/ref-val ctrl-ref)
mod? (mf/ref-val mod-ref)
rect (gsh/center->rect point (/ 5 zoom) (/ 5 zoom))]
(if (mf/ref-val hover-disabled-ref)
(rx/of nil)
@ -123,7 +123,7 @@
:page-id page-id
:rect rect
:include-frames? true
:clip-children? (not ctrl?)
:clip-children? (not mod?)
:reverse? true}))))) ;; we want the topmost shape to be selected first
over-shapes-stream
@ -150,8 +150,8 @@
#(mf/set-ref-val! zoom-ref zoom))
(mf/use-effect
(mf/deps @ctrl?)
#(mf/set-ref-val! ctrl-ref @ctrl?))
(mf/deps @mod?)
#(mf/set-ref-val! mod-ref @mod?))
(mf/use-effect
(mf/deps selected)
@ -176,14 +176,14 @@
selected (mf/ref-val selected-ref)
focus (mf/ref-val focus-ref)
ctrl? (mf/ref-val ctrl-ref)
mod? (mf/ref-val mod-ref)
remove-xfm (mapcat #(cph/get-parent-ids objects %))
remove-id? (cond-> (into #{} remove-xfm selected)
(not ctrl?)
(not mod?)
(into (filter #(group-empty-space? % objects ids)) ids)
ctrl?
mod?
(into (filter is-group?) ids))
hover-shape (->> ids

View file

@ -4,37 +4,45 @@
;;
;; Copyright (c) UXBOX Labs SL
(ns app.util.keyboard)
(ns app.util.keyboard
(:require
[app.config :as cfg]))
(defn is-key?
[key]
(fn [e]
[^string key]
(fn [^js e]
(= (.-key e) key)))
(defn ^boolean alt?
[event]
[^js event]
(.-altKey event))
(defn ^boolean ctrl?
[event]
[^js event]
(.-ctrlKey event))
(defn ^boolean meta?
[event]
[^js event]
(.-metaKey event))
(defn ^boolean shift?
[event]
[^js event]
(.-shiftKey event))
(defn ^boolean mod?
[^js event]
(if (cfg/check-platform? :macos)
(meta? event)
(ctrl? event)))
(def esc? (is-key? "Escape"))
(def enter? (is-key? "Enter"))
(def space? (is-key? " "))
(def up-arrow? (is-key? "ArrowUp"))
(def down-arrow? (is-key? "ArrowDown"))
(def altKey? (is-key? "Alt"))
(def ctrlKey? (or (is-key? "Control")
(is-key? "Meta")))
(def alt-key? (is-key? "Alt"))
(def ctrl-key? (is-key? "Control"))
(def meta-key? (is-key? "Meta"))
(def comma? (is-key? ","))
(def backspace? (is-key? "Backspace"))