Fix #3013 Swipe chat based deletion
Signed-off-by: Andrey Shovkoplyas <motor4ik@gmail.com>
This commit is contained in:
parent
0a17d75ff4
commit
f4f1ab4e2f
|
@ -0,0 +1,3 @@
|
||||||
|
<svg xmlns="http://www.w3.org/2000/svg" width="24" height="24" viewBox="0 0 24 24">
|
||||||
|
<path fill="" d="M7.00001034,5 C7.004297,3.34182361 8.34093668,2 10,2 L14,2 C15.6555111,2 16.9973018,3.34290405 16.9999959,5 L18.5454545,5 C19.9047426,5 21,6.12948418 21,7.5 C21,8.87051582 19.9047426,10 18.5454545,10 L5.45454545,10 C4.09525738,10 3,8.87051582 3,7.5 C3,6.12948418 4.09525738,5 5.45454545,5 L7.0000096,5 Z M14.9999879,5 C14.9973085,4.44655807 14.5500233,4 14,4 L10,4 C9.44811686,4 9.00424986,4.44383154 9.00003034,5 L14.9999888,5 Z M12,13.5857864 L13.2928932,12.2928932 C13.6834175,11.9023689 14.3165825,11.9023689 14.7071068,12.2928932 C15.0976311,12.6834175 15.0976311,13.3165825 14.7071068,13.7071068 L13.4142136,15 L14.7071068,16.2928932 C15.0976311,16.6834175 15.0976311,17.3165825 14.7071068,17.7071068 C14.3165825,18.0976311 13.6834175,18.0976311 13.2928932,17.7071068 L12,16.4142136 L10.7071068,17.7071068 C10.3165825,18.0976311 9.68341751,18.0976311 9.29289322,17.7071068 C8.90236893,17.3165825 8.90236893,16.6834175 9.29289322,16.2928932 L10.5857864,15 L9.29289322,13.7071068 C8.90236893,13.3165825 8.90236893,12.6834175 9.29289322,12.2928932 C9.68341751,11.9023689 10.3165825,11.9023689 10.7071068,12.2928932 L12,13.5857864 Z M17,12 C17,11.4477153 17.4477153,11 18,11 C18.5522847,11 19,11.4477153 19,12 L19,19.998 C19,21.604 17.953,23 16.4985,23 L7.5,23 C6.047,23 5,21.604 5,20 L5,12 C5,11.4477153 5.44771525,11 6,11 C6.55228475,11 7,11.4477153 7,12 L7,20 C7,20.604 7.297,21 7.5,21 L16.4985,21 C16.703,21 17,20.604 17,19.998 L17,12 Z M18.5454545,8 C18.7861665,8 19,7.77948418 19,7.5 C19,7.22051582 18.7861665,7 18.5454545,7 L5.45454545,7 C5.21383352,7 5,7.22051582 5,7.5 C5,7.77948418 5.21383352,8 5.45454545,8 L18.5454545,8 Z"/>
|
||||||
|
</svg>
|
After Width: | Height: | Size: 1.7 KiB |
|
@ -17,3 +17,7 @@
|
||||||
(defn save
|
(defn save
|
||||||
[{:keys [browser-id] :as browser}]
|
[{:keys [browser-id] :as browser}]
|
||||||
(data-store/save browser (exists? browser-id)))
|
(data-store/save browser (exists? browser-id)))
|
||||||
|
|
||||||
|
(defn delete
|
||||||
|
[browser-id]
|
||||||
|
(data-store/delete (exists? browser-id)))
|
|
@ -14,6 +14,11 @@
|
||||||
[browser update?]
|
[browser update?]
|
||||||
(realm/save @realm/account-realm :browser browser update?))
|
(realm/save @realm/account-realm :browser browser update?))
|
||||||
|
|
||||||
|
(defn delete
|
||||||
|
[browser-id]
|
||||||
|
(when-let [browser (realm/get-one-by-field-clj @realm/account-realm :browser :browser-id browser-id)]
|
||||||
|
(realm/delete @realm/account-realm browser)))
|
||||||
|
|
||||||
(defn exists?
|
(defn exists?
|
||||||
[browser-id]
|
[browser-id]
|
||||||
(realm/exists? @realm/account-realm :browser {:browser-id browser-id}))
|
(realm/exists? @realm/account-realm :browser {:browser-id browser-id}))
|
||||||
|
|
|
@ -35,9 +35,6 @@
|
||||||
(defn stop-animation [anim-value]
|
(defn stop-animation [anim-value]
|
||||||
(.stopAnimation anim-value))
|
(.stopAnimation anim-value))
|
||||||
|
|
||||||
(defn value [anim-value]
|
|
||||||
(.-value anim-value))
|
|
||||||
|
|
||||||
(defn set-value [anim-value value]
|
(defn set-value [anim-value value]
|
||||||
(.setValue anim-value value))
|
(.setValue anim-value value))
|
||||||
|
|
||||||
|
|
|
@ -11,4 +11,5 @@
|
||||||
(def gray-lighter "#eef2f5") ;; Used as a background or shadow
|
(def gray-lighter "#eef2f5") ;; Used as a background or shadow
|
||||||
(def blue "#4360df") ;; Used as main wallet color
|
(def blue "#4360df") ;; Used as main wallet color
|
||||||
(def red "#ff2d55") ;; Used to highlight errors or "dangerous" actions
|
(def red "#ff2d55") ;; Used to highlight errors or "dangerous" actions
|
||||||
|
(def light-red "#ffe6e6") ;; Used as a background for delete icon
|
||||||
(def text-light-gray "#212121") ;; Used for labels (home items)
|
(def text-light-gray "#212121") ;; Used for labels (home items)
|
||||||
|
|
|
@ -47,6 +47,7 @@
|
||||||
:icons/browse (slurp/slurp-svg "./resources/icons/browse.svg")
|
:icons/browse (slurp/slurp-svg "./resources/icons/browse.svg")
|
||||||
:icons/close (slurp/slurp-svg "./resources/icons/close.svg")
|
:icons/close (slurp/slurp-svg "./resources/icons/close.svg")
|
||||||
:icons/copy-from (slurp/slurp-svg "./resources/icons/copy_from.svg")
|
:icons/copy-from (slurp/slurp-svg "./resources/icons/copy_from.svg")
|
||||||
|
:icons/delete (slurp/slurp-svg "./resources/icons/delete.svg")
|
||||||
:icons/dots-horizontal (slurp/slurp-svg "./resources/icons/dots_horizontal.svg")
|
:icons/dots-horizontal (slurp/slurp-svg "./resources/icons/dots_horizontal.svg")
|
||||||
:icons/dots-vertical (slurp/slurp-svg "./resources/icons/dots_vertical.svg")
|
:icons/dots-vertical (slurp/slurp-svg "./resources/icons/dots_vertical.svg")
|
||||||
:icons/exclamation_mark (slurp/slurp-svg "./resources/icons/exclamation_mark.svg")
|
:icons/exclamation_mark (slurp/slurp-svg "./resources/icons/exclamation_mark.svg")
|
||||||
|
|
|
@ -25,6 +25,11 @@
|
||||||
(fn [browser]
|
(fn [browser]
|
||||||
(browser-store/save browser)))
|
(browser-store/save browser)))
|
||||||
|
|
||||||
|
(re-frame/reg-fx
|
||||||
|
:remove-browser
|
||||||
|
(fn [browser-id]
|
||||||
|
(browser-store/delete browser-id)))
|
||||||
|
|
||||||
(defn match-url [url]
|
(defn match-url [url]
|
||||||
(str (when (and url (not (re-find #"^[a-zA-Z-_]+:/" url))) "http://") url))
|
(str (when (and url (not (re-find #"^[a-zA-Z-_]+:/" url))) "http://") url))
|
||||||
|
|
||||||
|
@ -77,3 +82,10 @@
|
||||||
[re-frame/trim-v]
|
[re-frame/trim-v]
|
||||||
(fn [{:keys [db now] :as cofx} [options]]
|
(fn [{:keys [db now] :as cofx} [options]]
|
||||||
{:db (update db :browser/options merge options)}))
|
{:db (update db :browser/options merge options)}))
|
||||||
|
|
||||||
|
(handlers/register-handler-fx
|
||||||
|
:remove-browser
|
||||||
|
[re-frame/trim-v]
|
||||||
|
(fn [{:keys [db]} [browser-id]]
|
||||||
|
{:db (update-in db [:browser/browsers] dissoc browser-id)
|
||||||
|
:remove-browser browser-id}))
|
||||||
|
|
|
@ -404,3 +404,10 @@
|
||||||
:request-permissions
|
:request-permissions
|
||||||
(fn [_ [_ permissions then else]]
|
(fn [_ [_ permissions then else]]
|
||||||
{::request-permissions-fx [permissions then else]}))
|
{::request-permissions-fx [permissions then else]}))
|
||||||
|
|
||||||
|
(handlers/register-handler-db
|
||||||
|
:set-swipe-position
|
||||||
|
[re-frame/trim-v]
|
||||||
|
(fn [db [item-id value]]
|
||||||
|
(-> db
|
||||||
|
(assoc-in [:chat-animations item-id :delete-swiped] value))))
|
||||||
|
|
|
@ -0,0 +1,35 @@
|
||||||
|
(ns status-im.ui.screens.home.animations.responder
|
||||||
|
(:require [status-im.ui.components.react :as react]
|
||||||
|
[re-frame.core :as re-frame]
|
||||||
|
[status-im.ui.components.animation :as animation]))
|
||||||
|
|
||||||
|
(defn get-updated-value [gesture end-offset-x swiped?]
|
||||||
|
(let [base-value (if swiped? end-offset-x 0)]
|
||||||
|
(- base-value (.-dx gesture))))
|
||||||
|
|
||||||
|
(defn on-start [_ gesture]
|
||||||
|
(> (js/Math.abs (.-dx gesture)) 10))
|
||||||
|
|
||||||
|
(defn on-move [animated-offset-x end-offset-x swiped?]
|
||||||
|
(fn [_ gesture]
|
||||||
|
(let [to-value (get-updated-value gesture end-offset-x swiped?)]
|
||||||
|
(animation/start (animation/spring animated-offset-x {:toValue to-value})))))
|
||||||
|
|
||||||
|
(defn on-release [animated-offset-x end-offset-x chat-id swiped?]
|
||||||
|
(fn [_ gesture]
|
||||||
|
(let [updated-value (get-updated-value gesture end-offset-x swiped?)
|
||||||
|
should-open? (> updated-value (/ end-offset-x 2))
|
||||||
|
to-value (if should-open? end-offset-x 0)]
|
||||||
|
(re-frame/dispatch [:set-swipe-position chat-id should-open?])
|
||||||
|
(animation/start (animation/spring animated-offset-x {:toValue to-value})))))
|
||||||
|
|
||||||
|
(defn swipe-pan-responder [animated-offset-x end-offset-x chat-id swiped?]
|
||||||
|
(.create react/pan-responder
|
||||||
|
(clj->js {:onMoveShouldSetPanResponder on-start
|
||||||
|
:onPanResponderMove (on-move animated-offset-x end-offset-x swiped?)
|
||||||
|
:onPanResponderRelease (on-release animated-offset-x end-offset-x chat-id swiped?)
|
||||||
|
:onPanResponderTerminate (on-release animated-offset-x end-offset-x chat-id swiped?)})))
|
||||||
|
|
||||||
|
|
||||||
|
(defn pan-handlers [pan-responder]
|
||||||
|
(js->clj (.-panHandlers pan-responder)))
|
|
@ -3,6 +3,8 @@
|
||||||
(:require [status-im.ui.components.styles :as component.styles]
|
(:require [status-im.ui.components.styles :as component.styles]
|
||||||
[status-im.ui.components.colors :as colors]))
|
[status-im.ui.components.colors :as colors]))
|
||||||
|
|
||||||
|
(def delete-button-width 100)
|
||||||
|
|
||||||
(defn toolbar []
|
(defn toolbar []
|
||||||
{:background-color colors/white})
|
{:background-color colors/white})
|
||||||
|
|
||||||
|
@ -155,3 +157,17 @@
|
||||||
:width 14
|
:width 14
|
||||||
:height 9
|
:height 9
|
||||||
:tint-color :white})
|
:tint-color :white})
|
||||||
|
|
||||||
|
(def delete-icon-highlight
|
||||||
|
{:position :absolute
|
||||||
|
:top 0
|
||||||
|
:bottom 0
|
||||||
|
:right -800
|
||||||
|
:width 800
|
||||||
|
:background-color colors/light-red})
|
||||||
|
|
||||||
|
(def delete-icon-container
|
||||||
|
{:flex 1
|
||||||
|
:width delete-button-width
|
||||||
|
:justify-content :center
|
||||||
|
:align-items :center})
|
||||||
|
|
|
@ -12,6 +12,9 @@
|
||||||
[status-im.ui.components.sync-state.offline :refer [offline-view]]
|
[status-im.ui.components.sync-state.offline :refer [offline-view]]
|
||||||
[status-im.ui.screens.home.views.inner-item :as inner-item]
|
[status-im.ui.screens.home.views.inner-item :as inner-item]
|
||||||
[status-im.ui.screens.home.styles :as styles]
|
[status-im.ui.screens.home.styles :as styles]
|
||||||
|
[status-im.ui.components.icons.vector-icons :as vector-icons]
|
||||||
|
[status-im.ui.components.animation :as animation]
|
||||||
|
[status-im.ui.screens.home.animations.responder :as responder]
|
||||||
[status-im.utils.platform :as platform]))
|
[status-im.utils.platform :as platform]))
|
||||||
|
|
||||||
(defn- toolbar []
|
(defn- toolbar []
|
||||||
|
@ -29,14 +32,24 @@
|
||||||
:accessibility-label :plus-button
|
:accessibility-label :plus-button
|
||||||
:on-press #(re-frame/dispatch [:navigate-to :new])}])
|
:on-press #(re-frame/dispatch [:navigate-to :new])}])
|
||||||
|
|
||||||
(defn- home-list-item [[home-item-id home-item]]
|
(defn- home-list-deletable [[home-item-id home-item]]
|
||||||
(if (:chat-id home-item)
|
(views/letsubs [swiped? [:delete-swipe-position home-item-id]]
|
||||||
[react/touchable-highlight {:on-press #(re-frame/dispatch [:navigate-to-chat home-item-id])}
|
(let [delete-action (if (:chat-id home-item) :remove-chat :remove-browser)
|
||||||
[react/view
|
inner-view (if (:chat-id home-item)
|
||||||
[inner-item/home-list-chat-item-inner-view home-item]]]
|
inner-item/home-list-chat-item-inner-view
|
||||||
[react/touchable-highlight {:on-press #(re-frame/dispatch [:open-browser home-item])}
|
inner-item/home-list-browser-item-inner-view)
|
||||||
[react/view
|
offset-x (animation/create-value (if swiped? styles/delete-button-width 0))
|
||||||
[inner-item/home-list-browser-item-inner-view home-item]]]))
|
swipe-pan-responder (responder/swipe-pan-responder offset-x styles/delete-button-width home-item-id swiped?)
|
||||||
|
swipe-pan-handler (responder/pan-handlers swipe-pan-responder)]
|
||||||
|
[react/view swipe-pan-handler
|
||||||
|
[react/animated-view {:style {:right offset-x}}
|
||||||
|
[inner-view home-item]
|
||||||
|
[react/touchable-highlight {:style styles/delete-icon-highlight
|
||||||
|
:on-press #(do
|
||||||
|
(re-frame/dispatch [:set-swipe-position home-item-id false])
|
||||||
|
(re-frame/dispatch [delete-action home-item-id]))}
|
||||||
|
[react/view {:style styles/delete-icon-container}
|
||||||
|
[vector-icons/icon :icons/delete {:color colors/red}]]]]])))
|
||||||
|
|
||||||
(views/defview home []
|
(views/defview home []
|
||||||
(views/letsubs [home-items [:home-items]]
|
(views/letsubs [home-items [:home-items]]
|
||||||
|
@ -44,7 +57,7 @@
|
||||||
[toolbar]
|
[toolbar]
|
||||||
[list/flat-list {:data home-items
|
[list/flat-list {:data home-items
|
||||||
:render-fn (fn [[home-item-id :as home-item]]
|
:render-fn (fn [[home-item-id :as home-item]]
|
||||||
^{:key home-item-id} [home-list-item home-item])}]
|
^{:key home-item-id} [home-list-deletable home-item])}]
|
||||||
(when platform/android?
|
(when platform/android?
|
||||||
[home-action-button])
|
[home-action-button])
|
||||||
[offline-view]]))
|
[offline-view]]))
|
||||||
|
|
|
@ -1,8 +1,8 @@
|
||||||
(ns status-im.ui.screens.home.views.inner-item
|
(ns status-im.ui.screens.home.views.inner-item
|
||||||
(:require-macros [status-im.utils.views :refer [defview letsubs]])
|
(:require-macros [status-im.utils.views :refer [defview letsubs]])
|
||||||
(:require [clojure.string :as str]
|
(:require [re-frame.core :as re-frame]
|
||||||
|
[clojure.string :as str]
|
||||||
[status-im.ui.components.react :as react]
|
[status-im.ui.components.react :as react]
|
||||||
[status-im.ui.components.icons.vector-icons :as vector-icons]
|
|
||||||
[status-im.ui.screens.home.styles :as styles]
|
[status-im.ui.screens.home.styles :as styles]
|
||||||
[status-im.ui.components.styles :as component.styles]
|
[status-im.ui.components.styles :as component.styles]
|
||||||
[status-im.utils.core :as utils]
|
[status-im.utils.core :as utils]
|
||||||
|
@ -11,6 +11,7 @@
|
||||||
[status-im.utils.datetime :as time]
|
[status-im.utils.datetime :as time]
|
||||||
[status-im.utils.gfycat.core :as gfycat]
|
[status-im.utils.gfycat.core :as gfycat]
|
||||||
[status-im.constants :as const]
|
[status-im.constants :as const]
|
||||||
|
[status-im.ui.components.icons.vector-icons :as vector-icons]
|
||||||
[status-im.ui.components.chat-icon.screen :as chat-icon.screen]))
|
[status-im.ui.components.chat-icon.screen :as chat-icon.screen]))
|
||||||
|
|
||||||
(defn message-content-text [{:keys [content] :as message}]
|
(defn message-content-text [{:keys [content] :as message}]
|
||||||
|
@ -87,38 +88,40 @@
|
||||||
public-key unremovable? :as chat]}]
|
public-key unremovable? :as chat]}]
|
||||||
(letsubs [last-message [:get-last-message chat-id]]
|
(letsubs [last-message [:get-last-message chat-id]]
|
||||||
(let [name (or (i18n/get-contact-translated chat-id :name name)
|
(let [name (or (i18n/get-contact-translated chat-id :name name)
|
||||||
(gfycat/generate-gfy public-key))]
|
(gfycat/generate-gfy public-key))]
|
||||||
[react/view styles/chat-container
|
[react/touchable-highlight {:on-press #(re-frame/dispatch [:navigate-to-chat chat-id])}
|
||||||
[react/view styles/chat-icon-container
|
[react/view styles/chat-container
|
||||||
[chat-icon.screen/chat-icon-view-chat-list chat-id group-chat name color online]]
|
[react/view styles/chat-icon-container
|
||||||
[react/view styles/chat-info-container
|
[chat-icon.screen/chat-icon-view-chat-list chat-id group-chat name color online]]
|
||||||
[react/view styles/item-upper-container
|
[react/view styles/chat-info-container
|
||||||
[chat-list-item-name name group-chat public? public-key]
|
[react/view styles/item-upper-container
|
||||||
(when last-message
|
[chat-list-item-name name group-chat public? public-key]
|
||||||
[react/view styles/message-status-container
|
(when last-message
|
||||||
[message-status chat last-message]
|
[react/view styles/message-status-container
|
||||||
[message-timestamp last-message]])]
|
[message-status chat last-message]
|
||||||
[react/view styles/item-lower-container
|
[message-timestamp last-message]])]
|
||||||
[message-content-text last-message]
|
[react/view styles/item-lower-container
|
||||||
[unviewed-indicator chat-id]]]])))
|
[message-content-text last-message]
|
||||||
|
[unviewed-indicator chat-id]]]]])))
|
||||||
|
|
||||||
(defview home-list-browser-item-inner-view [{:keys [browser-id name url dapp? contact] :as browser}]
|
(defview home-list-browser-item-inner-view [{:keys [browser-id name url dapp? contact] :as browser}]
|
||||||
(letsubs [contact' [:contact-by-identity contact]]
|
(letsubs [contact' [:contact-by-identity contact]]
|
||||||
[react/view styles/chat-container
|
[react/touchable-highlight {:on-press #(re-frame/dispatch [:open-browser browser])}
|
||||||
[react/view styles/chat-icon-container
|
[react/view styles/chat-container
|
||||||
(if contact'
|
[react/view styles/chat-icon-container
|
||||||
[chat-icon.screen/dapp-icon-browser contact' 36]
|
(if contact'
|
||||||
[react/view styles/browser-icon-container
|
[chat-icon.screen/dapp-icon-browser contact' 36]
|
||||||
[vector-icons/icon :icons/discover {:color component.styles/color-light-gray6}]])]
|
[react/view styles/browser-icon-container
|
||||||
[react/view styles/chat-info-container
|
[vector-icons/icon :icons/discover {:color component.styles/color-light-gray6}]])]
|
||||||
[react/view styles/item-upper-container
|
[react/view styles/chat-info-container
|
||||||
[react/view styles/name-view
|
[react/view styles/item-upper-container
|
||||||
[react/view {:flex-shrink 1}
|
[react/view styles/name-view
|
||||||
[react/text {:style styles/name-text
|
[react/view {:flex-shrink 1}
|
||||||
|
[react/text {:style styles/name-text
|
||||||
|
:number-of-lines 1}
|
||||||
|
name]]]]
|
||||||
|
[react/view styles/item-lower-container
|
||||||
|
[react/view styles/last-message-container
|
||||||
|
[react/text {:style styles/last-message-text
|
||||||
:number-of-lines 1}
|
:number-of-lines 1}
|
||||||
name]]]]
|
(or url (i18n/label :t/dapp))]]]]]]))
|
||||||
[react/view styles/item-lower-container
|
|
||||||
[react/view styles/last-message-container
|
|
||||||
[react/text {:style styles/last-message-text
|
|
||||||
:number-of-lines 1}
|
|
||||||
(or url (i18n/label :t/dapp))]]]]]))
|
|
||||||
|
|
|
@ -55,3 +55,8 @@
|
||||||
(reg-sub :get-screen-params
|
(reg-sub :get-screen-params
|
||||||
(fn [db [_ view-id]]
|
(fn [db [_ view-id]]
|
||||||
(get-in db [:navigation/screen-params (or view-id (:view-id db))])))
|
(get-in db [:navigation/screen-params (or view-id (:view-id db))])))
|
||||||
|
|
||||||
|
(reg-sub :delete-swipe-position
|
||||||
|
(fn [db [_ item-id]]
|
||||||
|
(let [item-animation (get-in db [:chat-animations item-id])]
|
||||||
|
(if (some? item-animation) (:delete-swiped item-animation) nil))))
|
||||||
|
|
Loading…
Reference in New Issue