parent
00d431e69c
commit
f3d0f3765d
|
@ -46,6 +46,10 @@ index.android.js
|
||||||
index.ios.js
|
index.ios.js
|
||||||
target/
|
target/
|
||||||
|
|
||||||
|
# Generated by lein voom
|
||||||
|
#
|
||||||
|
pom.xml
|
||||||
|
|
||||||
# Figwheel
|
# Figwheel
|
||||||
#
|
#
|
||||||
figwheel_server.log
|
figwheel_server.log
|
||||||
|
|
|
@ -8,9 +8,8 @@
|
||||||
[reagent "0.5.1" :exclusions [cljsjs/react]]
|
[reagent "0.5.1" :exclusions [cljsjs/react]]
|
||||||
[re-frame "0.7.0"]
|
[re-frame "0.7.0"]
|
||||||
[prismatic/schema "1.0.4"]
|
[prismatic/schema "1.0.4"]
|
||||||
^{:voom {:repo "git@github.com:status-im/status-lib.git"
|
^{:voom {:repo "git@github.com:status-im/status-lib.git" :branch "master"}}
|
||||||
:branch "message-delivery"}}
|
[status-im/protocol "0.2.1-20160908_061908-geefb360"]
|
||||||
[status-im/protocol "0.2.0-20160829_094621-g83381b2"]
|
|
||||||
[natal-shell "0.3.0"]
|
[natal-shell "0.3.0"]
|
||||||
[com.andrewmcveigh/cljs-time "0.4.0"]
|
[com.andrewmcveigh/cljs-time "0.4.0"]
|
||||||
[tailrecursion/cljs-priority-map "1.2.0"]
|
[tailrecursion/cljs-priority-map "1.2.0"]
|
||||||
|
|
|
@ -33,7 +33,8 @@
|
||||||
status-im.chat.handlers.receive-message
|
status-im.chat.handlers.receive-message
|
||||||
[cljs.core.async :as a]
|
[cljs.core.async :as a]
|
||||||
status-im.chat.handlers.webview-bridge
|
status-im.chat.handlers.webview-bridge
|
||||||
status-im.chat.handlers.wallet-chat))
|
status-im.chat.handlers.wallet-chat
|
||||||
|
[status-im.utils.logging :as log]))
|
||||||
|
|
||||||
(register-handler :set-show-actions
|
(register-handler :set-show-actions
|
||||||
(fn [db [_ show-actions]]
|
(fn [db [_ show-actions]]
|
||||||
|
@ -291,10 +292,11 @@
|
||||||
(update :chats assoc chat-id new-chat)
|
(update :chats assoc chat-id new-chat)
|
||||||
(update :chats-ids conj chat-id)))
|
(update :chats-ids conj chat-id)))
|
||||||
|
|
||||||
(defn save-chat!
|
(defn save-new-chat!
|
||||||
[{:keys [new-chat]} _]
|
[{:keys [new-chat]} _]
|
||||||
(chats/create-chat new-chat))
|
(chats/create-chat new-chat))
|
||||||
|
|
||||||
|
|
||||||
(defn open-chat!
|
(defn open-chat!
|
||||||
[_ [_ chat-id _ navigation-type]]
|
[_ [_ chat-id _ navigation-type]]
|
||||||
(dispatch [(or navigation-type :navigate-to) :chat chat-id]))
|
(dispatch [(or navigation-type :navigate-to) :chat chat-id]))
|
||||||
|
@ -302,20 +304,20 @@
|
||||||
(register-handler ::start-chat!
|
(register-handler ::start-chat!
|
||||||
(-> prepare-chat
|
(-> prepare-chat
|
||||||
((enrich add-chat))
|
((enrich add-chat))
|
||||||
((after save-chat!))
|
((after save-new-chat!))
|
||||||
((after open-chat!))))
|
((after open-chat!))))
|
||||||
|
|
||||||
(register-handler :start-chat
|
(register-handler :start-chat
|
||||||
(u/side-effect!
|
(u/side-effect!
|
||||||
(fn [{:keys [chats]} [_ contcat-id options navigation-type]]
|
(fn [{:keys [chats]} [_ contact-id options navigation-type]]
|
||||||
(if (chats contcat-id)
|
(if (chats contact-id)
|
||||||
(dispatch [(or navigation-type :navigate-to) :chat contcat-id])
|
(dispatch [(or navigation-type :navigate-to) :chat contact-id])
|
||||||
(dispatch [::start-chat! contcat-id options navigation-type])))))
|
(dispatch [::start-chat! contact-id options navigation-type])))))
|
||||||
|
|
||||||
(register-handler :add-chat
|
(register-handler :add-chat
|
||||||
(-> prepare-chat
|
(-> prepare-chat
|
||||||
((enrich add-chat))
|
((enrich add-chat))
|
||||||
((after save-chat!))))
|
((after save-new-chat!))))
|
||||||
|
|
||||||
(register-handler :switch-command-suggestions!
|
(register-handler :switch-command-suggestions!
|
||||||
(u/side-effect!
|
(u/side-effect!
|
||||||
|
@ -417,11 +419,16 @@
|
||||||
(fn [db [_ chat-id mode]]
|
(fn [db [_ chat-id mode]]
|
||||||
(assoc-in db [:kb-mode chat-id] mode)))
|
(assoc-in db [:kb-mode chat-id] mode)))
|
||||||
|
|
||||||
|
(defn save-chat!
|
||||||
|
[_ [_ chat]]
|
||||||
|
(chats/create-chat chat))
|
||||||
|
|
||||||
(register-handler :update-chat!
|
(register-handler :update-chat!
|
||||||
(fn [db [_ chat-id new-chat-data]]
|
(-> (fn [db [_ {:keys [chat-id] :as chat}]]
|
||||||
(if (get-in db [:chats chat-id])
|
(if (get-in db [:chats chat-id])
|
||||||
(update-in db [:chats chat-id] merge new-chat-data)
|
(update-in db [:chats chat-id] merge chat)
|
||||||
db)))
|
db))
|
||||||
|
((after save-chat!))))
|
||||||
|
|
||||||
(register-handler :check-autorun
|
(register-handler :check-autorun
|
||||||
(u/side-effect!
|
(u/side-effect!
|
||||||
|
|
|
@ -22,13 +22,13 @@
|
||||||
[status-im.chat.views.suggestions :refer [suggestion-container]]
|
[status-im.chat.views.suggestions :refer [suggestion-container]]
|
||||||
[status-im.chat.views.response :refer [response-view]]
|
[status-im.chat.views.response :refer [response-view]]
|
||||||
[status-im.chat.views.new-message :refer [chat-message-new]]
|
[status-im.chat.views.new-message :refer [chat-message-new]]
|
||||||
|
[status-im.chat.views.actions :refer [actions-view]]
|
||||||
[status-im.i18n :refer [label label-pluralize]]
|
[status-im.i18n :refer [label label-pluralize]]
|
||||||
[status-im.components.animation :as anim]
|
[status-im.components.animation :as anim]
|
||||||
[reagent.core :as r]
|
[reagent.core :as r]
|
||||||
[clojure.string :as str]
|
[clojure.string :as str]
|
||||||
[cljs-time.core :as t]))
|
[cljs-time.core :as t]))
|
||||||
|
|
||||||
|
|
||||||
(defn contacts-by-identity [contacts]
|
(defn contacts-by-identity [contacts]
|
||||||
(->> contacts
|
(->> contacts
|
||||||
(map (fn [{:keys [identity] :as contact}]
|
(map (fn [{:keys [identity] :as contact}]
|
||||||
|
@ -86,114 +86,6 @@
|
||||||
[view nil]]
|
[view nil]]
|
||||||
items])
|
items])
|
||||||
|
|
||||||
(defn action-view [{{:keys [icon-style
|
|
||||||
custom-icon
|
|
||||||
handler
|
|
||||||
title
|
|
||||||
subtitle]
|
|
||||||
icon-name :icon} :action
|
|
||||||
platform-specific :platform-specific}]
|
|
||||||
[touchable-highlight {:on-press (fn []
|
|
||||||
(dispatch [:set-show-actions false])
|
|
||||||
(when handler
|
|
||||||
(handler)))}
|
|
||||||
[view st/action-icon-row
|
|
||||||
[view st/action-icon-view
|
|
||||||
(or custom-icon
|
|
||||||
[icon icon-name icon-style])]
|
|
||||||
[view st/action-view
|
|
||||||
[text {:style st/action-title
|
|
||||||
:platform-specific platform-specific
|
|
||||||
:font :medium} title]
|
|
||||||
(when-let [subtitle subtitle]
|
|
||||||
[text {:style st/action-subtitle
|
|
||||||
:platform-specific platform-specific
|
|
||||||
:font :default}
|
|
||||||
subtitle])]]])
|
|
||||||
|
|
||||||
(defview menu-item-icon-profile []
|
|
||||||
[chat-id [:chat :chat-id]
|
|
||||||
group-chat [:chat :group-chat]
|
|
||||||
name [:chat :name]
|
|
||||||
color [:chat :color]]
|
|
||||||
;; TODO stub data ('online' property)
|
|
||||||
[chat-icon-view-menu-item chat-id group-chat name color true])
|
|
||||||
|
|
||||||
(defn members-text [members]
|
|
||||||
(truncate-str (str (s/join ", " (map #(:name %) members)) " " (label :t/and-you)) 35))
|
|
||||||
|
|
||||||
(defn actions-list-view [{styles :styles :as platform-specific}]
|
|
||||||
(let [{:keys [group-chat chat-id]} (subscribe [:chat-properties [:group-chat :chat-id]])
|
|
||||||
members (subscribe [:current-chat-contacts])
|
|
||||||
status-bar-height (get-in styles [:components :status-bar :default :height])]
|
|
||||||
(when-let [actions (if @group-chat
|
|
||||||
[{:title (label :t/members-title)
|
|
||||||
:subtitle (members-text @members)
|
|
||||||
:icon :menu_group
|
|
||||||
:icon-style {:width 25
|
|
||||||
:height 19}
|
|
||||||
;; TODO not implemented: action Members
|
|
||||||
:handler nil}
|
|
||||||
{:title (label :t/search-chat)
|
|
||||||
:subtitle (label :t/not-implemented)
|
|
||||||
:icon :search_gray_copy
|
|
||||||
:icon-style {:width 17
|
|
||||||
:height 17}
|
|
||||||
;; TODO not implemented: action Search chat
|
|
||||||
:handler nil}
|
|
||||||
{:title (label :t/notifications-title)
|
|
||||||
:subtitle (label :t/not-implemented)
|
|
||||||
;;:subtitle "Chat muted"
|
|
||||||
:icon :muted
|
|
||||||
:icon-style {:width 18
|
|
||||||
:height 21}
|
|
||||||
;; TODO not implemented: action Notifications
|
|
||||||
:handler nil}
|
|
||||||
{:title (label :t/settings)
|
|
||||||
:icon :settings
|
|
||||||
:icon-style {:width 20
|
|
||||||
:height 13}
|
|
||||||
:handler #(dispatch [:show-group-settings])}]
|
|
||||||
[{:title (label :t/profile)
|
|
||||||
:custom-icon [menu-item-icon-profile]
|
|
||||||
:icon :menu_group
|
|
||||||
:icon-style {:width 25
|
|
||||||
:height 19}
|
|
||||||
:handler #(dispatch [:show-profile @chat-id])}
|
|
||||||
{:title (label :t/search-chat)
|
|
||||||
:subtitle (label :t/not-implemented)
|
|
||||||
:icon :search_gray_copy
|
|
||||||
:icon-style {:width 17
|
|
||||||
:height 17}
|
|
||||||
;; TODO not implemented: action Search chat
|
|
||||||
:handler nil}
|
|
||||||
{:title (label :t/notifications-title)
|
|
||||||
:subtitle (label :t/not-implemented)
|
|
||||||
;;:subtitle "Notifications on"
|
|
||||||
:icon :muted
|
|
||||||
:icon-style {:width 18
|
|
||||||
:height 21}
|
|
||||||
;; TODO not implemented: action Notifications
|
|
||||||
:handler nil}
|
|
||||||
{:title (label :t/settings)
|
|
||||||
:subtitle (label :t/not-implemented)
|
|
||||||
:icon :settings
|
|
||||||
:icon-style {:width 20
|
|
||||||
:height 13}
|
|
||||||
;; TODO not implemented: action Settings
|
|
||||||
:handler nil}])]
|
|
||||||
[view (-> (st/actions-wrapper status-bar-height)
|
|
||||||
(merge (get-in styles [:components :actions-list-view])))
|
|
||||||
[view st/actions-separator]
|
|
||||||
[view st/actions-view
|
|
||||||
(for [action actions]
|
|
||||||
^{:key action} [action-view {:platform-specific platform-specific
|
|
||||||
:action action}])]])))
|
|
||||||
|
|
||||||
(defn actions-view [platform-specific]
|
|
||||||
[overlay {:on-click-outside #(dispatch [:set-show-actions false])}
|
|
||||||
[actions-list-view platform-specific]])
|
|
||||||
|
|
||||||
(defn online-text [contact chat-id]
|
(defn online-text [contact chat-id]
|
||||||
(if contact
|
(if contact
|
||||||
(let [last-online (get contact :last-online)
|
(let [last-online (get contact :last-online)
|
||||||
|
@ -215,10 +107,11 @@
|
||||||
[view (st/chat-name-view @show-actions)
|
[view (st/chat-name-view @show-actions)
|
||||||
[text {:style st/chat-name-text
|
[text {:style st/chat-name-text
|
||||||
:platform-specific platform-specific
|
:platform-specific platform-specific
|
||||||
|
:number-of-lines 1
|
||||||
:font :medium}
|
:font :medium}
|
||||||
(if (str/blank? @name)
|
(if (str/blank? @name)
|
||||||
(label :t/user-anonymous)
|
(label :t/user-anonymous)
|
||||||
(truncate-str (or @name (label :t/chat-name)) 30))]
|
(or @name (label :t/chat-name)))]
|
||||||
(if @group-chat
|
(if @group-chat
|
||||||
[view {:flexDirection :row}
|
[view {:flexDirection :row}
|
||||||
[icon :group st/group-icon]
|
[icon :group st/group-icon]
|
||||||
|
|
|
@ -0,0 +1,145 @@
|
||||||
|
(ns status-im.chat.views.actions
|
||||||
|
(:require-macros [status-im.utils.views :refer [defview]])
|
||||||
|
(:require [re-frame.core :refer [subscribe dispatch]]
|
||||||
|
[clojure.string :as s]
|
||||||
|
[status-im.components.react :refer [view
|
||||||
|
animated-view
|
||||||
|
text
|
||||||
|
icon
|
||||||
|
touchable-highlight
|
||||||
|
list-view
|
||||||
|
list-item]]
|
||||||
|
[status-im.components.chat-icon.screen :refer [chat-icon-view-menu-item]]
|
||||||
|
[status-im.chat.styles.screen :as st]
|
||||||
|
[status-im.i18n :refer [label label-pluralize]]
|
||||||
|
[status-im.utils.logging :as log]))
|
||||||
|
|
||||||
|
(defview menu-item-icon-profile []
|
||||||
|
[chat-id [:chat :chat-id]
|
||||||
|
group-chat [:chat :group-chat]
|
||||||
|
name [:chat :name]
|
||||||
|
color [:chat :color]]
|
||||||
|
;; TODO stub data ('online' property)
|
||||||
|
[chat-icon-view-menu-item chat-id group-chat name color true])
|
||||||
|
|
||||||
|
(defn- members-text [members]
|
||||||
|
(str (s/join ", " (map #(:name %) members))
|
||||||
|
" "
|
||||||
|
(label :t/and-you)))
|
||||||
|
|
||||||
|
(defn item-members [members]
|
||||||
|
{:title (label :t/members-title)
|
||||||
|
:subtitle (members-text members)
|
||||||
|
:icon :menu_group
|
||||||
|
:icon-style {:width 25
|
||||||
|
:height 19}
|
||||||
|
;; TODO not implemented: action Members
|
||||||
|
:handler nil})
|
||||||
|
|
||||||
|
(defn item-user [chat-id]
|
||||||
|
{:title (label :t/profile)
|
||||||
|
:custom-icon [menu-item-icon-profile]
|
||||||
|
:icon :menu_group
|
||||||
|
:icon-style {:width 25
|
||||||
|
:height 19}
|
||||||
|
:handler #(dispatch [:show-profile chat-id])})
|
||||||
|
|
||||||
|
(defn item-add-to-contacts [contact]
|
||||||
|
{:title (label :t/add-to-contacts)
|
||||||
|
:icon :menu_group
|
||||||
|
:icon-style {:width 20
|
||||||
|
:height 17}
|
||||||
|
:handler #(dispatch [:add-pending-contact contact])})
|
||||||
|
|
||||||
|
(def item-search
|
||||||
|
{:title (label :t/search-chat)
|
||||||
|
:subtitle (label :t/not-implemented)
|
||||||
|
:icon :search_gray_copy
|
||||||
|
:icon-style {:width 17
|
||||||
|
:height 17}
|
||||||
|
;; TODO not implemented: action Search chat
|
||||||
|
:handler nil})
|
||||||
|
|
||||||
|
(def item-notifications
|
||||||
|
{:title (label :t/notifications-title)
|
||||||
|
:subtitle (label :t/not-implemented)
|
||||||
|
;;:subtitle "Chat muted"
|
||||||
|
:icon :muted
|
||||||
|
:icon-style {:width 18
|
||||||
|
:height 21}
|
||||||
|
;; TODO not implemented: action Notifications
|
||||||
|
:handler nil})
|
||||||
|
|
||||||
|
(def item-settings
|
||||||
|
{:title (label :t/settings)
|
||||||
|
:icon :settings
|
||||||
|
:icon-style {:width 20
|
||||||
|
:height 13}
|
||||||
|
:handler #(dispatch [:show-group-settings])})
|
||||||
|
|
||||||
|
(defn group-chat-items [members]
|
||||||
|
[(item-members members)
|
||||||
|
item-search
|
||||||
|
item-notifications
|
||||||
|
item-settings])
|
||||||
|
|
||||||
|
(defn user-chat-items [chat-id {:keys [pending] :as contact}]
|
||||||
|
[(item-user chat-id)
|
||||||
|
(if pending (item-add-to-contacts contact) nil)
|
||||||
|
item-search
|
||||||
|
item-notifications
|
||||||
|
item-settings])
|
||||||
|
|
||||||
|
(defn overlay [{:keys [on-click-outside]} items]
|
||||||
|
[view st/actions-overlay
|
||||||
|
[touchable-highlight {:on-press on-click-outside
|
||||||
|
:style st/overlay-highlight}
|
||||||
|
[view nil]]
|
||||||
|
items])
|
||||||
|
|
||||||
|
(defn action-view [{{:keys [icon-style
|
||||||
|
custom-icon
|
||||||
|
handler
|
||||||
|
title
|
||||||
|
subtitle]
|
||||||
|
icon-name :icon} :action
|
||||||
|
platform-specific :platform-specific}]
|
||||||
|
[touchable-highlight {:on-press (fn []
|
||||||
|
(dispatch [:set-show-actions false])
|
||||||
|
(when handler
|
||||||
|
(handler)))}
|
||||||
|
[view st/action-icon-row
|
||||||
|
[view st/action-icon-view
|
||||||
|
(or custom-icon
|
||||||
|
[icon icon-name icon-style])]
|
||||||
|
[view st/action-view
|
||||||
|
[text {:style st/action-title
|
||||||
|
:platform-specific platform-specific
|
||||||
|
:number-of-lines 1
|
||||||
|
:font :medium} title]
|
||||||
|
(when-let [subtitle subtitle]
|
||||||
|
[text {:style st/action-subtitle
|
||||||
|
:platform-specific platform-specific
|
||||||
|
:number-of-lines 1
|
||||||
|
:font :default}
|
||||||
|
subtitle])]]])
|
||||||
|
|
||||||
|
(defn actions-list-view [{styles :styles :as platform-specific}]
|
||||||
|
(let [{:keys [group-chat chat-id]} (subscribe [:chat-properties [:group-chat :chat-id]])
|
||||||
|
members (subscribe [:current-chat-contacts])
|
||||||
|
status-bar-height (get-in styles [:components :status-bar :default :height])]
|
||||||
|
(when-let [actions (if @group-chat
|
||||||
|
(group-chat-items @members)
|
||||||
|
(user-chat-items @chat-id (first @members)))]
|
||||||
|
[view (-> (st/actions-wrapper status-bar-height)
|
||||||
|
(merge (get-in styles [:components :actions-list-view])))
|
||||||
|
[view st/actions-separator]
|
||||||
|
[view st/actions-view
|
||||||
|
(for [action actions]
|
||||||
|
(if action
|
||||||
|
^{:key action} [action-view {:platform-specific platform-specific
|
||||||
|
:action action}]))]])))
|
||||||
|
|
||||||
|
(defn actions-view [platform-specific]
|
||||||
|
[overlay {:on-click-outside #(dispatch [:set-show-actions false])}
|
||||||
|
[actions-list-view platform-specific]])
|
|
@ -19,9 +19,10 @@
|
||||||
[chat-icon-view-chat-list chat-id group-chat name color online]]
|
[chat-icon-view-chat-list chat-id group-chat name color online]]
|
||||||
[view st/item-container
|
[view st/item-container
|
||||||
[view st/name-view
|
[view st/name-view
|
||||||
[text {:style st/name-text} (if (str/blank? name)
|
[text {:style st/name-text}
|
||||||
(label :t/user-anonymous)
|
(if (str/blank? name)
|
||||||
(truncate-str name 20))]
|
(label :t/user-anonymous)
|
||||||
|
(truncate-str name 30))]
|
||||||
(when group-chat
|
(when group-chat
|
||||||
[icon :group st/group-icon])
|
[icon :group st/group-icon])
|
||||||
(when group-chat
|
(when group-chat
|
||||||
|
|
|
@ -16,12 +16,17 @@
|
||||||
(contacts/save-contacts [contact]))
|
(contacts/save-contacts [contact]))
|
||||||
|
|
||||||
(defn watch-contact
|
(defn watch-contact
|
||||||
[_ [_ contact]]
|
[_ [_ {:keys [whisper-identity]}]]
|
||||||
(api/watch-user contact))
|
(api/watch-user whisper-identity))
|
||||||
|
|
||||||
(register-handler :watch-contact (u/side-effect! watch-contact))
|
(register-handler :watch-contact (u/side-effect! watch-contact))
|
||||||
|
|
||||||
(register-handler :update-contact
|
(defn send-contact-request
|
||||||
|
[{:keys [current-account-id accounts]} [_ contact]]
|
||||||
|
(let [account (get accounts current-account-id)]
|
||||||
|
(api/send-contact-request contact account)))
|
||||||
|
|
||||||
|
(register-handler :update-contact!
|
||||||
(-> (fn [db [_ {:keys [whisper-identity] :as contact}]]
|
(-> (fn [db [_ {:keys [whisper-identity] :as contact}]]
|
||||||
(update-in db [:contacts whisper-identity] merge contact))
|
(update-in db [:contacts whisper-identity] merge contact))
|
||||||
((after save-contact))))
|
((after save-contact))))
|
||||||
|
@ -101,10 +106,18 @@
|
||||||
(defn save-contacts! [{:keys [new-contacts]} _]
|
(defn save-contacts! [{:keys [new-contacts]} _]
|
||||||
(contacts/save-contacts new-contacts))
|
(contacts/save-contacts new-contacts))
|
||||||
|
|
||||||
|
(defn update-pending-status [old-contacts {:keys [whisper-identity pending] :as contact}]
|
||||||
|
(let [{old-pending :pending
|
||||||
|
:as old-contact} (get old-contacts whisper-identity)]
|
||||||
|
(if old-contact
|
||||||
|
(assoc contact :pending (and old-pending pending))
|
||||||
|
(assoc contact :pending pending))))
|
||||||
|
|
||||||
(defn add-new-contacts
|
(defn add-new-contacts
|
||||||
[{:keys [contacts] :as db} [_ new-contacts]]
|
[{:keys [contacts] :as db} [_ new-contacts]]
|
||||||
(let [identities (set (map :whisper-identity contacts))
|
(let [identities (set (map :whisper-identity contacts))
|
||||||
new-contacts' (->> new-contacts
|
new-contacts' (->> new-contacts
|
||||||
|
(map #(update-pending-status contacts %))
|
||||||
(remove #(identities (:whisper-identity %)))
|
(remove #(identities (:whisper-identity %)))
|
||||||
(map #(vector (:whisper-identity %) %))
|
(map #(vector (:whisper-identity %) %))
|
||||||
(into {}))]
|
(into {}))]
|
||||||
|
@ -122,16 +135,28 @@
|
||||||
(assoc :new-contact-identity "")))
|
(assoc :new-contact-identity "")))
|
||||||
|
|
||||||
(register-handler :add-new-contact
|
(register-handler :add-new-contact
|
||||||
(u/side-effect!
|
(u/side-effect!
|
||||||
(fn [_ [_ {:keys [whisper-identity] :as contact}]]
|
(fn [_ [_ {:keys [whisper-identity] :as contact}]]
|
||||||
(when-not (contacts/get-contact whisper-identity)
|
(when-not (contacts/get-contact whisper-identity)
|
||||||
(dispatch [::new-contact contact])))))
|
(dispatch [::prepare-contact contact])))))
|
||||||
|
|
||||||
(register-handler ::new-contact
|
(register-handler ::prepare-contact
|
||||||
(-> add-new-contact
|
(-> add-new-contact
|
||||||
((after save-contact))
|
((after save-contact))
|
||||||
|
((after send-contact-request))
|
||||||
((after watch-contact))))
|
((after watch-contact))))
|
||||||
|
|
||||||
|
(register-handler ::update-pending-contact
|
||||||
|
(-> add-new-contact
|
||||||
|
((after save-contact))))
|
||||||
|
|
||||||
|
(register-handler :add-pending-contact
|
||||||
|
(u/side-effect!
|
||||||
|
(fn [_ [_ {:keys [whisper-identity] :as contact}]]
|
||||||
|
(let [contact (assoc contact :pending false)]
|
||||||
|
(api/send-discovery-keypair whisper-identity)
|
||||||
|
(dispatch [::update-pending-contact contact])))))
|
||||||
|
|
||||||
(defn set-contact-identity-from-qr
|
(defn set-contact-identity-from-qr
|
||||||
[db [_ _ contact-identity]]
|
[db [_ _ contact-identity]]
|
||||||
(assoc db :new-contact-identity contact-identity))
|
(assoc db :new-contact-identity contact-identity))
|
||||||
|
@ -143,16 +168,30 @@
|
||||||
;; TODO: security issue: we should use `from` instead of `public-key` here, but for testing it is much easier to use `public-key`
|
;; TODO: security issue: we should use `from` instead of `public-key` here, but for testing it is much easier to use `public-key`
|
||||||
(fn [db [_ from {{:keys [public-key last-updated name] :as account} :account}]]
|
(fn [db [_ from {{:keys [public-key last-updated name] :as account} :account}]]
|
||||||
(let [prev-last-updated (get-in db [:contacts public-key :last-updated])]
|
(let [prev-last-updated (get-in db [:contacts public-key :last-updated])]
|
||||||
(if (< prev-last-updated last-updated)
|
(if (<= prev-last-updated last-updated)
|
||||||
(let [contact (-> (assoc account :whisper-identity public-key)
|
(let [contact (-> (assoc account :whisper-identity public-key)
|
||||||
(dissoc :public-key))]
|
(dissoc :public-key))]
|
||||||
(dispatch [:update-contact contact])
|
(dispatch [:update-contact! contact])
|
||||||
(dispatch [:update-chat! public-key {:name name}])))))))
|
(dispatch [:update-chat! {:chat-id public-key
|
||||||
|
:name name}])))))))
|
||||||
|
|
||||||
(register-handler :contact-online-received
|
(register-handler :contact-online-received
|
||||||
(u/side-effect!
|
(u/side-effect!
|
||||||
(fn [db [_ from {last-online :at :as payload}]]
|
(fn [db [_ from {last-online :at :as payload}]]
|
||||||
(let [prev-last-online (get-in db [:contacts from :last-online])]
|
(let [prev-last-online (get-in db [:contacts from :last-online])]
|
||||||
(if (< prev-last-online last-online)
|
(if (< prev-last-online last-online)
|
||||||
(dispatch [:update-contact {:whisper-identity from
|
(dispatch [:update-contact! {:whisper-identity from
|
||||||
:last-online last-online}]))))))
|
:last-online last-online}]))))))
|
||||||
|
|
||||||
|
(register-handler :contact-request-received
|
||||||
|
(u/side-effect!
|
||||||
|
(fn [_ [_ {:keys [contact from]}]]
|
||||||
|
(let [contact (assoc contact :whisper-identity from
|
||||||
|
:pending true)]
|
||||||
|
(dispatch [:add-contacts [contact]])))))
|
||||||
|
|
||||||
|
(register-handler :contact-keypair-received
|
||||||
|
(u/side-effect!
|
||||||
|
(fn [_ [_ from]]
|
||||||
|
(api/stop-watching-user from)
|
||||||
|
(api/watch-user from))))
|
|
@ -69,8 +69,8 @@
|
||||||
[text {:style st/show-all-text} (label :show-all)]]])])
|
[text {:style st/show-all-text} (label :show-all)]]])])
|
||||||
|
|
||||||
(defn contact-list [{platform-specific :platform-specific}]
|
(defn contact-list [{platform-specific :platform-specific}]
|
||||||
(let [contacts (subscribe [:get-contacts-with-limit contacts-limit])
|
(let [contacts (subscribe [:get-added-contacts-with-limit contacts-limit])
|
||||||
contcats-count (subscribe [:contacts-count])
|
contacts-count (subscribe [:added-contacts-count])
|
||||||
click-handler (subscribe [:get :contacts-click-handler])
|
click-handler (subscribe [:get :contacts-click-handler])
|
||||||
show-toolbar-shadow? (r/atom false)]
|
show-toolbar-shadow? (r/atom false)]
|
||||||
(fn []
|
(fn []
|
||||||
|
@ -80,20 +80,20 @@
|
||||||
(when @show-toolbar-shadow?
|
(when @show-toolbar-shadow?
|
||||||
[linear-gradient {:style st/contact-group-header-gradient-bottom
|
[linear-gradient {:style st/contact-group-header-gradient-bottom
|
||||||
:colors st/contact-group-header-gradient-bottom-colors}])]
|
:colors st/contact-group-header-gradient-bottom-colors}])]
|
||||||
(if (pos? @contcats-count)
|
(if (pos? @contacts-count)
|
||||||
[scroll-view {:style st/contact-groups
|
[scroll-view {:style st/contact-groups
|
||||||
:onScroll (fn [e]
|
:onScroll (fn [e]
|
||||||
(let [offset (.. e -nativeEvent -contentOffset -y)]
|
(let [offset (.. e -nativeEvent -contentOffset -y)]
|
||||||
(reset! show-toolbar-shadow? (<= st/contact-group-header-height offset))))}
|
(reset! show-toolbar-shadow? (<= st/contact-group-header-height offset))))}
|
||||||
[contact-group
|
[contact-group
|
||||||
@contacts
|
@contacts
|
||||||
@contcats-count
|
@contacts-count
|
||||||
(label :t/contacs-group-dapps)
|
(label :t/contacs-group-dapps)
|
||||||
:dapps true
|
:dapps true
|
||||||
@click-handler]
|
@click-handler]
|
||||||
[contact-group
|
[contact-group
|
||||||
@contacts
|
@contacts
|
||||||
@contcats-count
|
@contacts-count
|
||||||
(label :t/contacs-group-people)
|
(label :t/contacs-group-people)
|
||||||
:people false
|
:people false
|
||||||
@click-handler]]
|
@click-handler]]
|
||||||
|
|
|
@ -12,19 +12,21 @@
|
||||||
(sort-by :name #(compare (clojure.string/lower-case %1)
|
(sort-by :name #(compare (clojure.string/lower-case %1)
|
||||||
(clojure.string/lower-case %2)) (vals contacts)))
|
(clojure.string/lower-case %2)) (vals contacts)))
|
||||||
|
|
||||||
(register-sub :all-contacts
|
(register-sub :all-added-contacts
|
||||||
(fn [db _]
|
(fn [db _]
|
||||||
(let [contacts (reaction (:contacts @db))]
|
(let [contacts (reaction (:contacts @db))]
|
||||||
(reaction (sort-contacts @contacts)))))
|
(->> (remove #(:pending %) @contacts)
|
||||||
|
(sort-contacts)
|
||||||
|
(reaction)))))
|
||||||
|
|
||||||
(register-sub :get-contacts-with-limit
|
(register-sub :get-added-contacts-with-limit
|
||||||
(fn [_ [_ limit]]
|
(fn [_ [_ limit]]
|
||||||
(let [contacts (subscribe [:all-contacts])]
|
(let [contacts (subscribe [:all-added-contacts])]
|
||||||
(reaction (take limit @contacts)))))
|
(reaction (take limit @contacts)))))
|
||||||
|
|
||||||
(register-sub :contacts-count
|
(register-sub :added-contacts-count
|
||||||
(fn [_ _]
|
(fn [_ _]
|
||||||
(let [contacts (subscribe [:all-contacts])]
|
(let [contacts (subscribe [:all-added-contacts])]
|
||||||
(reaction (count @contacts)))))
|
(reaction (count @contacts)))))
|
||||||
|
|
||||||
(defn get-contact-letter [contact]
|
(defn get-contact-letter [contact]
|
||||||
|
|
|
@ -16,7 +16,8 @@
|
||||||
[view st/contact-inner-container
|
[view st/contact-inner-container
|
||||||
[contact-photo contact]
|
[contact-photo contact]
|
||||||
[view st/info-container
|
[view st/info-container
|
||||||
[text {:style st/name-text}
|
[text {:style st/name-text
|
||||||
|
:number-of-lines 1}
|
||||||
(if (pos? (count (:name contact)))
|
(if (pos? (count (:name contact)))
|
||||||
name
|
name
|
||||||
;; todo is this correct behaviour?
|
;; todo is this correct behaviour?
|
||||||
|
|
|
@ -42,7 +42,7 @@
|
||||||
(defn create-chat
|
(defn create-chat
|
||||||
([{:keys [last-message-id] :as chat}]
|
([{:keys [last-message-id] :as chat}]
|
||||||
(let [chat (assoc chat :last-message-id (or last-message-id ""))]
|
(let [chat (assoc chat :last-message-id (or last-message-id ""))]
|
||||||
(r/write :account #(r/create :account :chat chat))))
|
(r/write :account #(r/create :account :chat chat true))))
|
||||||
([db chat-id identities group-chat? chat-name]
|
([db chat-id identities group-chat? chat-name]
|
||||||
(when-not (chat-exists? chat-id)
|
(when-not (chat-exists? chat-id)
|
||||||
(let [chat-name (or chat-name
|
(let [chat-name (or chat-name
|
||||||
|
|
|
@ -2,7 +2,8 @@
|
||||||
(:require [status-im.persistence.realm.core :as r]
|
(:require [status-im.persistence.realm.core :as r]
|
||||||
[status-im.utils.identicon :refer [identicon]]
|
[status-im.utils.identicon :refer [identicon]]
|
||||||
[status-im.persistence.realm-queries :refer [include-query
|
[status-im.persistence.realm-queries :refer [include-query
|
||||||
exclude-query]]))
|
exclude-query]]
|
||||||
|
[status-im.utils.logging :as log]))
|
||||||
|
|
||||||
(defn get-contacts []
|
(defn get-contacts []
|
||||||
(-> (r/get-all :account :contact)
|
(-> (r/get-all :account :contact)
|
||||||
|
@ -12,10 +13,14 @@
|
||||||
(defn get-contact [id]
|
(defn get-contact [id]
|
||||||
(r/get-one-by-field :account :contact :whisper-identity id))
|
(r/get-one-by-field :account :contact :whisper-identity id))
|
||||||
|
|
||||||
(defn create-contact [{:keys [whisper-identity] :as contact}]
|
(defn create-contact [{:keys [whisper-identity pending] :as contact}]
|
||||||
(let [contact-from-db (r/get-one-by-field :account :contact
|
(let [{pending-db :pending
|
||||||
:whisper-identity whisper-identity)]
|
:as contact-db} (r/get-one-by-field :account :contact
|
||||||
(r/create :account :contact contact (if contact-from-db true false))))
|
:whisper-identity whisper-identity)
|
||||||
|
contact (assoc contact :pending (boolean (if contact-db
|
||||||
|
(and pending-db pending)
|
||||||
|
pending)))]
|
||||||
|
(r/create :account :contact contact (if contact-db true false))))
|
||||||
|
|
||||||
(defn save-contacts [contacts]
|
(defn save-contacts [contacts]
|
||||||
(r/write :account #(mapv create-contact contacts)))
|
(r/write :account #(mapv create-contact contacts)))
|
||||||
|
|
|
@ -7,7 +7,8 @@
|
||||||
[clojure.walk :refer [stringify-keys keywordize-keys]]
|
[clojure.walk :refer [stringify-keys keywordize-keys]]
|
||||||
[status-im.constants :as c]
|
[status-im.constants :as c]
|
||||||
[status-im.utils.types :refer [clj->json json->clj]]
|
[status-im.utils.types :refer [clj->json json->clj]]
|
||||||
[status-im.commands.utils :refer [generate-hiccup]]))
|
[status-im.commands.utils :refer [generate-hiccup]]
|
||||||
|
[status-im.utils.logging :as log]))
|
||||||
|
|
||||||
(defn get-pending-messages []
|
(defn get-pending-messages []
|
||||||
(let [collection (-> (r/get-by-fields :account :pending-message :or [[:status :sending]
|
(let [collection (-> (r/get-by-fields :account :pending-message :or [[:status :sending]
|
||||||
|
|
|
@ -49,7 +49,7 @@
|
||||||
[text {:style st/group-name-validation-message} (first validation-messages)])])
|
[text {:style st/group-name-validation-message} (first validation-messages)])])
|
||||||
|
|
||||||
(defview new-group [{platform-specific :platform-specific}]
|
(defview new-group [{platform-specific :platform-specific}]
|
||||||
[contacts [:all-contacts]]
|
[contacts [:all-added-contacts]]
|
||||||
[view st/new-group-container
|
[view st/new-group-container
|
||||||
[new-group-toolbar platform-specific]
|
[new-group-toolbar platform-specific]
|
||||||
[view st/chat-name-container
|
[view st/chat-name-container
|
||||||
|
|
|
@ -24,7 +24,8 @@
|
||||||
:name {:type "string" :optional true}
|
:name {:type "string" :optional true}
|
||||||
:photo-path {:type "string" :optional true}
|
:photo-path {:type "string" :optional true}
|
||||||
:last-updated {:type "int" :default 0}
|
:last-updated {:type "int" :default 0}
|
||||||
:last-online {:type "int" :default 0}}}
|
:last-online {:type "int" :default 0}
|
||||||
|
:pending {:type "bool" :default false}}}
|
||||||
{:name :request
|
{:name :request
|
||||||
:properties {:message-id :string
|
:properties {:message-id :string
|
||||||
:chat-id :string
|
:chat-id :string
|
||||||
|
|
|
@ -21,6 +21,8 @@
|
||||||
(dispatch [:received-message (assoc payload :chat-id from
|
(dispatch [:received-message (assoc payload :chat-id from
|
||||||
:from from
|
:from from
|
||||||
:to to)]))
|
:to to)]))
|
||||||
|
:contact-request (let [{:keys [from payload]} event]
|
||||||
|
(dispatch [:contact-request-received (assoc payload :from from)]))
|
||||||
:message-delivered (let [{:keys [message-id from]} event]
|
:message-delivered (let [{:keys [message-id from]} event]
|
||||||
(dispatch [:message-delivered from message-id]))
|
(dispatch [:message-delivered from message-id]))
|
||||||
:message-seen (let [{:keys [message-id from]} event]
|
:message-seen (let [{:keys [message-id from]} event]
|
||||||
|
@ -29,6 +31,8 @@
|
||||||
(dispatch [:message-failed chat-id message-id]))
|
(dispatch [:message-failed chat-id message-id]))
|
||||||
:message-sent (let [{:keys [message-id chat-id]} event]
|
:message-sent (let [{:keys [message-id chat-id]} event]
|
||||||
(dispatch [:message-sent chat-id message-id]))
|
(dispatch [:message-sent chat-id message-id]))
|
||||||
|
:user-discovery-keypair (let [{:keys [from]} event]
|
||||||
|
(dispatch [:contact-keypair-received from]))
|
||||||
:pending-message-upsert (let [{message :message} event]
|
:pending-message-upsert (let [{message :message} event]
|
||||||
(dispatch [:pending-message-upsert message]))
|
(dispatch [:pending-message-upsert message]))
|
||||||
:pending-message-remove (let [{:keys [message-id]} event]
|
:pending-message-remove (let [{:keys [message-id]} event]
|
||||||
|
|
|
@ -54,6 +54,7 @@
|
||||||
:phone-number "Phone number"
|
:phone-number "Phone number"
|
||||||
:email "Email"
|
:email "Email"
|
||||||
:profile-no-status "No status"
|
:profile-no-status "No status"
|
||||||
|
:add-to-contacts "Add to contacts"
|
||||||
|
|
||||||
;;make_photo
|
;;make_photo
|
||||||
:image-source-title "Profile image"
|
:image-source-title "Profile image"
|
||||||
|
|
Loading…
Reference in New Issue