Fix response suggestions:

Fix scrolling messages when response view is shown.
Empty suggestions can't be fully opened.
Fix UI delays after animation.
Code improvements.


Former-commit-id: a7e694cb46
This commit is contained in:
virvar 2016-06-06 15:05:35 +03:00
parent 543d89ece3
commit f4a1d332f2
7 changed files with 95 additions and 83 deletions

View File

@ -48,11 +48,11 @@
(update-in [:chats current-chat-id :input-text] safe-trim)))) (update-in [:chats current-chat-id :input-text] safe-trim))))
(register-handler :start-cancel-command (register-handler :start-cancel-command
(fn [db _] (u/side-effect!
(if (commands/get-chat-command-to-msg-id db) (fn [db _]
(dispatch [:animate-cancel-command]) (if (commands/get-chat-command-to-msg-id db)
(dispatch [:cancel-command #(dispatch [:cancel-command])])) (dispatch [:animate-cancel-command])
db)) (dispatch [:cancel-command])))))
(register-handler :set-chat-command-content (register-handler :set-chat-command-content
(fn [{:keys [current-chat-id] :as db} [_ content]] (fn [{:keys [current-chat-id] :as db} [_ content]]
@ -79,8 +79,8 @@
(commands/stage-command db command-info)))) (commands/stage-command db command-info))))
(register-handler :set-response-chat-command (register-handler :set-response-chat-command
(after #(dispatch [:animate-show-response]))
(fn [db [_ to-msg-id command-key]] (fn [db [_ to-msg-id command-key]]
(dispatch [:animate-show-response])
(commands/set-response-chat-command db to-msg-id command-key))) (commands/set-response-chat-command db to-msg-id command-key)))
(defn update-text (defn update-text

View File

@ -1,5 +1,6 @@
(ns status-im.chat.handlers.animation (ns status-im.chat.handlers.animation
(:require [re-frame.core :refer [register-handler after dispatch]] (:require [re-frame.core :refer [register-handler after dispatch]]
[re-frame.middleware :refer [path]]
[status-im.models.commands :as commands] [status-im.models.commands :as commands]
[status-im.handlers.content-suggestions :refer [get-content-suggestions]] [status-im.handlers.content-suggestions :refer [get-content-suggestions]]
[status-im.chat.styles.plain-input :refer [input-height]] [status-im.chat.styles.plain-input :refer [input-height]]
@ -14,16 +15,16 @@
(assoc-in db [:animations :commands-input-is-switching?] false))) (assoc-in db [:animations :commands-input-is-switching?] false)))
(register-handler :animate-cancel-command (register-handler :animate-cancel-command
(path :animations)
(fn [db _] (fn [db _]
(let [hiding? (get-in db [:animations :commands-input-is-switching?])] (if-not (:commands-input-is-switching? db)
(if-not hiding? (assoc db
(-> db :commands-input-is-switching? true
(assoc-in [:animations :commands-input-is-switching?] true) :message-input-buttons-scale 1
(assoc-in [:animations :message-input-buttons-scale] 1) :message-input-offset 0
(assoc-in [:animations :message-input-offset] 0) :to-response-height zero-height
(assoc-in [:animations :to-response-height] zero-height) :messages-offset 0)
(assoc-in [:animations :messages-offset] 0)) db)))
db))))
(register-handler :finish-animate-response-resize (register-handler :finish-animate-response-resize
(fn [db _] (fn [db _]
@ -71,22 +72,39 @@
(register-handler :set-response-max-height (register-handler :set-response-max-height
(fn [db [_ height]] (fn [db [_ height]]
(assoc-in db [:animations :response-height-max] height))) (let [prev-height (get-in db [:animations :response-height-max])]
(if (not= height prev-height)
(let [db (assoc-in db [:animations :response-height-max] height)]
(if (= prev-height (get-in db [:animations :to-response-height]))
(-> db
(assoc-in [:animations :to-response-height] height)
(assoc-in [:animations :response-height-current] height))
db))
db))))
(register-handler :on-drag-response (register-handler :on-drag-response
(fn [db [_ dy]] (fn [db [_ dy]]
(let [fixed (get-in db [:animations :to-response-height])] (let [fixed (get-in db [:animations :to-response-height])]
(assoc-in db [:animations :response-height-current] (- fixed dy))))) (-> db
(assoc-in [:animations :response-height-current] (- fixed dy))
(assoc-in [:animations :response-resize?] false)))))
(register-handler :fix-response-height (register-handler :fix-response-height
(fn [db _] (fn [db _]
(let [current (get-in db [:animations :response-height-current]) (if (and (commands/get-chat-command-to-msg-id db)
normal-height response-height-normal (not (get-in db [:animations :commands-input-is-switching?])))
max-height (get-in db [:animations :response-height-max]) (let [current (get-in db [:animations :response-height-current])
delta (/ normal-height 2) normal-height response-height-normal
new-fixed (cond command (commands/get-chat-command db)
(<= current (+ zero-height delta)) (+ zero-height request-info-height) text (commands/get-chat-command-content db)
(<= current (+ zero-height normal-height delta)) (get-response-height db) suggestions (get-content-suggestions command text)
:else max-height)] max-height (get-in db [:animations :response-height-max])
(dispatch [:animate-response-resize]) delta (/ normal-height 2)
(assoc-in db [:animations :to-response-height] new-fixed)))) new-fixed (cond
(or (<= current (+ zero-height delta))
(empty? suggestions)) (+ zero-height request-info-height)
(<= current (+ zero-height normal-height delta)) (get-response-height db)
:else max-height)]
(dispatch [:animate-response-resize])
(assoc-in db [:animations :to-response-height] new-fixed))
db)))

View File

@ -260,7 +260,10 @@
show-actions-atom [:show-actions] show-actions-atom [:show-actions]
command [:get-chat-command] command [:get-chat-command]
to-msg-id [:get-chat-command-to-msg-id]] to-msg-id [:get-chat-command-to-msg-id]]
[view st/chat-view [view {:style st/chat-view
:onLayout (fn [event]
(let [height (.. event -nativeEvent -layout -height)]
(dispatch [:set-response-max-height height])))}
[chat-toolbar] [chat-toolbar]
[messages-container [messages-container
[messages-view group-chat]] [messages-view group-chat]]

View File

@ -51,21 +51,15 @@
:opacity 0.69 :opacity 0.69
:color color-white}) :color color-white})
(def container (defn response-view [height]
{:flexDirection :column {:flexDirection :column
:justifyContent :flex-end
:position :absolute :position :absolute
:left 0 :left 0
:right 0 :right 0
:top 0
:bottom 0 :bottom 0
:backgroundColor :transparent
:elevation 2})
(defn response-view [height]
{:flexDirection :column
:height height :height height
:backgroundColor color-white}) :backgroundColor color-white
:elevation 2})
(def input-placeholder (def input-placeholder
{:height input-height}) {:height input-height})

View File

@ -18,14 +18,15 @@
(defn show-input [command] (defn show-input [command]
[plain-message-input-view [plain-message-input-view
(case (:command command) (when command
:phone {:input-options {:keyboardType :phone-pad} (case (:command command)
:validator valid-mobile-number?} :phone {:input-options {:keyboardType :phone-pad}
:keypair-password {:input-options {:secureTextEntry true}} :validator valid-mobile-number?}
:confirmation-code {:input-options {:keyboardType :numeric}} :keypair-password {:input-options {:secureTextEntry true}}
:money {:input-options {:keyboardType :numeric}} :confirmation-code {:input-options {:keyboardType :numeric}}
:request {:input-options {:keyboardType :numeric}} :money {:input-options {:keyboardType :numeric}}
nil)]) :request {:input-options {:keyboardType :numeric}}
(throw (js/Error. "Uknown command type"))))])
(defn chat-message-new [] (defn chat-message-new []
(let [command-atom (subscribe [:get-chat-command]) (let [command-atom (subscribe [:get-chat-command])

View File

@ -33,18 +33,28 @@
;; TODO stub data: request message info ;; TODO stub data: request message info
"By ???, MMM 1st at HH:mm"]]) "By ???, MMM 1st at HH:mm"]])
(defview request-info [] (defn create-response-pan-responder []
[command [:get-chat-command]] (drag/create-pan-responder
[view (st/request-info (:color command)) {:on-move (fn [e gesture]
[drag-icon] (dispatch [:on-drag-response (.-dy gesture)]))
[view st/inner-container :on-release (fn [e gesture]
[command-icon nil] (dispatch [:fix-response-height]))}))
[info-container command]
[touchable-highlight {:on-press #(dispatch [:start-cancel-command])}
[view st/cancel-container
[icon :close-white st/cancel-icon]]]]])
(defn inner-container-animation-logic [{:keys [animation? to-value current-value val]}] (defn request-info []
(let [pan-responder (create-response-pan-responder)
command (subscribe [:get-chat-command])]
(fn []
[view (merge (drag/pan-handlers pan-responder)
{:style (st/request-info (:color @command))})
[drag-icon]
[view st/inner-container
[command-icon nil]
[info-container @command]
[touchable-highlight {:on-press #(dispatch [:start-cancel-command])}
[view st/cancel-container
[icon :close-white st/cancel-icon]]]]])))
(defn container-animation-logic [{:keys [animation? to-value current-value val]}]
(fn [_] (fn [_]
(if @animation? (if @animation?
(let [to-value @to-value] (let [to-value @to-value]
@ -58,16 +68,8 @@
(dispatch [:cancel-command])))))) (dispatch [:cancel-command]))))))
(anim/set-value val @current-value)))) (anim/set-value val @current-value))))
(defn create-response-pan-responder [] (defn container [& children]
(drag/create-pan-responder (let [commands-input-is-switching? (subscribe [:get-in [:animations :commands-input-is-switching?]])
{:on-move (fn [e gesture]
(dispatch [:on-drag-response (.-dy gesture)]))
:on-release (fn [e gesture]
(dispatch [:fix-response-height]))}))
(defn inner-container [content]
(let [pan-responder (create-response-pan-responder)
commands-input-is-switching? (subscribe [:get-in [:animations :commands-input-is-switching?]])
response-resize? (subscribe [:get-in [:animations :response-resize?]]) response-resize? (subscribe [:get-in [:animations :response-resize?]])
to-response-height (subscribe [:get-in [:animations :to-response-height]]) to-response-height (subscribe [:get-in [:animations :to-response-height]])
cur-response-height (subscribe [:get-in [:animations :response-height-current]]) cur-response-height (subscribe [:get-in [:animations :response-height-current]])
@ -76,28 +78,22 @@
:to-value to-response-height :to-value to-response-height
:current-value cur-response-height :current-value cur-response-height
:val response-height} :val response-height}
on-update (inner-container-animation-logic context)] on-update (container-animation-logic context)]
(r/create-class (r/create-class
{:component-did-mount {:component-did-mount
on-update on-update
:component-did-update :component-did-update
on-update on-update
:reagent-render :reagent-render
(fn [content] (fn [& children]
@to-response-height @to-response-height
[animated-view (merge (drag/pan-handlers pan-responder) (into [animated-view {:style (st/response-view (if (or @commands-input-is-switching? @response-resize?)
{:style (st/response-view (if (or @commands-input-is-switching? @response-resize?) response-height
response-height (or @cur-response-height 0)))}]
(or @cur-response-height 0)))}) children))})))
content])})))
(defn response-view [] (defn response-view []
[view {:style st/container [container
:onLayout (fn [event] [request-info]
(let [height (.. event -nativeEvent -layout -height)] [response-suggestions-view]
(dispatch [:set-response-max-height height])))} [view st/input-placeholder]])
[inner-container
[view
[request-info]
[response-suggestions-view]
[view st/input-placeholder]]]])

View File

@ -33,7 +33,7 @@
(defview group-name-input [] (defview group-name-input []
[group-name [:get :new-chat-name] [group-name [:get :new-chat-name]
validation-messages [:new-chat-name-validation-messages]] validation-messages [:new-chat-name-validation-messages]]
[view nil [view
[text-input [text-input
{:underlineColorAndroid color-purple {:underlineColorAndroid color-purple
:style st/group-name-input :style st/group-name-input