From d4128397b908a617ea53b47a1f802e6e8509833a Mon Sep 17 00:00:00 2001 From: Roman Volosovskyi Date: Thu, 23 Feb 2017 15:54:48 +0200 Subject: [PATCH] fix cursor position for command input --- src/status_im/chat/handlers/commands.cljs | 5 +- src/status_im/chat/views/message_input.cljs | 98 +++++++++++++++------ 2 files changed, 76 insertions(+), 27 deletions(-) diff --git a/src/status_im/chat/handlers/commands.cljs b/src/status_im/chat/handlers/commands.cljs index 35257cac20..4e69f1c25c 100644 --- a/src/status_im/chat/handlers/commands.cljs +++ b/src/status_im/chat/handlers/commands.cljs @@ -151,7 +151,8 @@ (-> db (commands/set-command-input (or type :commands) command-key) (assoc-in [:chats current-chat-id :command-input :content] cu/command-prefix) - (assoc :disable-input true))) + (assoc :disable-input true) + (assoc :just-set-command? true))) (register-handler :set-chat-command [(after invoke-suggestions-handler!) @@ -305,4 +306,4 @@ (defn fib-lazy ([] (fib-lazy 0 1)) - ([x1 x2] (cons x1 (lazy-seq (fib-lazy x2 (+ x1 x2)))))) \ No newline at end of file + ([x1 x2] (cons x1 (lazy-seq (fib-lazy x2 (+ x1 x2)))))) diff --git a/src/status_im/chat/views/message_input.cljs b/src/status_im/chat/views/message_input.cljs index fad381cbca..0dac0d9170 100644 --- a/src/status_im/chat/views/message_input.cljs +++ b/src/status_im/chat/views/message_input.cljs @@ -15,7 +15,9 @@ [status-im.accessibility-ids :as id] [reagent.core :as r] [clojure.string :as str] - [taoensso.timbre :as log])) + [taoensso.timbre :as log] + [clojure.string :as s] + [status-im.commands.utils :refer [command-prefix]])) (defn send-button [{:keys [on-press accessibility-label]}] [touchable-highlight {:on-press on-press @@ -40,9 +42,15 @@ :multiline true :editable (not disable?)}) -(defn command-input-options [{:keys [icon-width disable? sending-disabled?]}] +(defn command-input-options [{:keys [icon-width disable? sending-disabled? flag]}] {:style (st-response/command-input icon-width disable?) - :on-change-text (when-not disable? command/set-input-message) + :on-change-text (when-not disable? (fn [text] + ;; update flag only when the first + ;; character was added to commands input + (when (and (s/starts-with? text command-prefix) + (= (inc (count command-prefix)) (count text))) + (reset! flag true)) + (command/set-input-message text))) :on-submit-editing (fn [] (when-not sending-disabled? (dispatch [:send-command!]))) @@ -62,6 +70,21 @@ options) (assoc options :placeholder "")))) +(defn get-selection + [{:keys [focused? flag input-command command? just-set?]}] + (cond (and command? + (= input-command command-prefix) + focused? + (not just-set?)) + {:start 2 + :end 2} + + (and focused? flag) + {:start 3 + :end 3} + + :else nil)) + (defview message-input [set-layout-size] [input-message [:get-chat-input-text] input-command [:get-chat-command-content] @@ -72,24 +95,49 @@ command? [:command?] parameter [:get-command-parameter] type [:command-type] - sending-disabled? [:chat-ui-props :sending-disabled?]] - [text-input - (merge - (if command? - (command-input-options {:icon-width icon-width - :disable? disable? - :sendind-disabled? sending-disabled?}) - (plain-input-options {:set-layout-size-fn set-layout-size - :disable? (or disable? (not active?))})) - {:placeholder-text-color :#c0c5c9 - :auto-focus (when command? - (not (:fullscreen command))) - :accessibility-label id/chat-message-input - :default-value (if command? - (or input-command "") - (or input-message ""))} - (when command? - (get-options parameter type)))]) + just-set? [:get :just-set-command?] + sending-disabled? [:chat-ui-props :sending-disabled?] + state {:input (atom nil) + :focused? (atom nil) + :3-symbols-flag (r/atom false)}] + {:component-did-update (fn [] + (when just-set? + (dispatch [:set :just-set-command? false])) + (when @(:3-symbols-flag state) + (reset! (:3-symbols-flag state) false)) + (when (and command? + (not (:fullscreen command))) + (.focus @(:input state))))} + + (do + @(:3-symbols-flag state) + [text-input + (merge + (if command? + (command-input-options {:icon-width icon-width + :disable? disable? + :sendind-disabled? sending-disabled? + :flag (:3-symbols-flag state)}) + (plain-input-options {:set-layout-size-fn set-layout-size + :disable? (or disable? (not active?))})) + {:placeholder-text-color :#c0c5c9 + :onFocus #(reset! (:focused? state) true) + :onBlur #(reset! (:focused? state) false) + :auto-focus (when command? (not (:fullscreen command))) + :ref #(reset! (:input state) %) + :accessibility-label id/chat-message-input + ;; for some reason app crashes when this property is not nil and + ;; input is not focused + :selection (get-selection {:focused? @(:focused? state) + :flag @(:3-symbols-flag state) + :input-command input-command + :command? command? + :just-set? just-set?}) + :default-value (if command? + (or input-command "") + (or input-message ""))} + (when command? + (get-options parameter type)))])) (defn plain-message-get-initial-state [_] {:height 0}) @@ -125,10 +173,10 @@ (let [on-press (if @command? #(dispatch [:send-command!]) plain-message/send)] - [send-button {:on-press (fn [e] - (when-not @sending-disabled? - (dispatch [:set-chat-ui-props :show-emoji? false]) - (on-press e))) + [send-button {:on-press (fn [e] + (when-not @sending-disabled? + (dispatch [:set-chat-ui-props :show-emoji? false]) + (on-press e))) :accessibility-label id/chat-send-button}])) (when (and @command? (= :command (:type @command))) [command/command-icon @command])]]))})))