Compare commits

..
Author SHA1 Message Date
alwx 349c707066 Updated Go version 2023-08-17 11:46:49 +02:00
Churikova Tetiana aecad2136e e2e: starting to-dos 2023-08-17 05:09:19 +03:00
codemaster 673b1afc3a chore: update group-avatar component (#17014)
We merge it without QA because it only changes the API and doesn't need design review because nothing has been changed 👍
2023-08-17 06:44:30 +10:00
Icaro Motta b0f748cb73 Refactor Quo preview (#16996)
Improvements to quo previews:

- Change quo-preview.preview code to be more aligned with our guidelines.
- Remove duplication when setting up preview screens in quo-preview.main. Now we
  only need to specify the :name and :component keys and fallback to a good
  default for "{:options {:topBar {:visible true}}".
- Auto-generate descriptor labels based on the key.
- Fix form field colors for dark & light, especially for Android.
- Redesigned form fields to look nicer 💄
- Create component that abstracts away the code for rendering the form fields
  and the preview area. This will aid us in creating more consistent looking
  preview screens and keep things DRY.

How do we use the new code?

Just as before, define a state binding and use it to build up the arguments of
the component. Then, use the preview/preview-container to wrap the component.
You can use certain props to control how the preview is styled, etc, but that's
about it.

    (def descriptor
      [{:type :text :key :label}
       {:key     :chevron-position
        :type    :select
        :options [{:key :left}
                  {:key :right}]}])
    
    (defn view
      []
      (let [state (reagent/atom {:chevron-position :left
                                 :label            "Welcome"})]
        (fn []
          [preview/preview-container {:state state :descriptor descriptor}
           [quo/divider-label @state]])))
2023-08-16 11:30:21 +00:00
Andrea Maria Piana d988296ecf Add next in line for communities 2023-08-16 12:16:32 +01:00
Andrea Maria Piana dc8a09ce75 Update wallet team members 2023-08-16 12:16:08 +01:00
Andrea Maria Piana 0dea703ca0 3 lines community description 2023-08-16 12:15:12 +01:00
47 changed files with 716 additions and 814 deletions
+1 -1
View File
@@ -10,7 +10,7 @@ These are just guidelines, not rules. Use your best judgment, and feel free to p
* [Mission and Principles](https://status.im/about)
* [Read our FAQ](https://status.im/docs/FAQs.html)
* [Join our Chat](http://status.app/chat/public/status-core-dev)
* [Join our Chat](http://join.status.im/chat/public/status-core-dev)
* [Developer Introduction](https://status.im/developer_tools/)
* [Build Status Yourself](https://status.im/technical/build_status)
* [Find issues to work on](https://github.com/status-im/)
+2 -2
View File
@@ -62,8 +62,8 @@
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" />
<category android:name="android.intent.category.BROWSABLE" />
<data android:scheme="http" android:host="status.app" />
<data android:scheme="https" android:host="status.app" />
<data android:scheme="http" android:host="join.status.im" />
<data android:scheme="https" android:host="join.status.im" />
</intent-filter>
<intent-filter android:autoVerify="true">
<action android:name="android.intent.action.VIEW" />
+3 -5
View File
@@ -16,7 +16,7 @@ The responsibilities of the team are to implement the new wallet UI, with the su
## Decision
Some team members have already expressed interest and some have been asked and accepted to join the wallet team, these team members are:
The team members for the initial wallet team are:
- @rasom
- @OmarBasem
@@ -25,7 +25,5 @@ Some team members have already expressed interest and some have been asked and a
- @briansztamfater
- @smohamedjavid
- @ulisesmac
# Follow-up Actions
- We still need 3/4 team members to join the wallet team
- @erikseppanen
- @mmilad75
+1 -1
View File
@@ -33,7 +33,7 @@ The people identified for each sections are as follow:
- Messaging @flexsurfer, followed by @alwx
- Syncing & Onboarding @siddarthkay
- Communities @ilmotta
- Communities @ilmotta, followed by @ajayesivan
- Activity Center & Shell @J-Son89, followed by @Parveshdhull
- Wallet (once the vertical team is created) @J-Son89, followed by @briansztamfater
+1 -1
View File
@@ -11,7 +11,7 @@
<string>development</string>
<key>com.apple.developer.associated-domains</key>
<array>
<string>applinks:status.app</string>
<string>applinks:join.status.im</string>
</array>
<key>keychain-access-groups</key>
<array>
+1 -1
View File
@@ -11,7 +11,7 @@
<string>development</string>
<key>com.apple.developer.associated-domains</key>
<array>
<string>applinks:status.app/string>
<string>applinks:join.status.im</string>
</array>
<key>keychain-access-groups</key>
<array>
@@ -3,12 +3,12 @@
(defn container
[{:keys [container-size customization-color theme]}]
{:width container-size
:height container-size
:align-items :center
:justify-content :center
:border-radius (/ container-size 2)
:background-color
(colors/theme-colors (colors/custom-color customization-color 50)
(colors/custom-color customization-color 60)
theme)})
{:width container-size
:height container-size
:align-items :center
:justify-content :center
:border-radius (/ container-size 2)
:overflow :hidden
:background-color (colors/theme-colors (colors/custom-color customization-color 50)
(colors/custom-color customization-color 60)
theme)})
@@ -7,34 +7,27 @@
[quo2.components.avatars.group-avatar.style :as style]))
(def sizes
{:icon {:x-small 12
:small 16
:medium 16
:large 20
:x-large 32}
:container {:x-small 20
:small 28
:medium 32
:large 48
:x-large 80}})
{20 {:icon 12}
28 {:icon 16}
32 {:icon 16}
48 {:icon 20}
80 {:icon 32}})
(defn- view-internal
[_]
(fn [{:keys [size theme customization-color picture]
:or {size :x-small
customization-color :blue
picture nil}}]
(let [container-size (get-in sizes [:container size])
icon-size (get-in sizes [:icon size])]
:or {size 20
customization-color :blue}}]
(let [icon-size (get-in sizes [size :icon])]
[rn/view
{:style (style/container {:container-size container-size
{:style (style/container {:container-size size
:customization-color customization-color
:theme theme})}
(if picture
[fast-image/fast-image
{:source picture
:style {:width container-size
:height container-size}}]
:style {:width size
:height size}}]
[icon/icon :i/members
{:size icon-size
:color colors/white-opa-70}])])))
+1 -1
View File
@@ -22,7 +22,7 @@
(def web-prefixes ["https://" "http://" "https://www." "http://wwww."])
(def web2-domain "status.app")
(def web2-domain "join.status.im")
(def web-urls (map #(str % web2-domain "/") web-prefixes))
+5 -5
View File
@@ -30,20 +30,20 @@
(str "status-im://g/args?a=" public-key "&a1=" chat-name-url "&a2=" chat-id)
[:group-chat {:params "arg"} {"a" public-key "a1" chat-name "a2" chat-id}]
(str "https://status.app/g/args?a=" public-key "&a1=" chat-name-url "&a2=" chat-id)
(str "https://join.status.im/g/args?a=" public-key "&a1=" chat-name-url "&a2=" chat-id)
[:group-chat {:params "arg"} {"a" public-key "a1" chat-name "a2" chat-id}]
"https://status.app/u/statuse2e"
"https://join.status.im/u/statuse2e"
[:user {:user-id "statuse2e"}]
(str "https://status.app/user/" public-key)
(str "https://join.status.im/user/" public-key)
[:user {:user-id public-key}]
;; Last char removed by: https://github.com/juxt/bidi/issues/104
"https://status.app/b/www.cryptokitties.co"
"https://join.status.im/b/www.cryptokitties.co"
[:browser {:domain "www.cryptokitties.c"}]
"https://status.app/b/https://www.google.com/"
"https://join.status.im/b/https://www.google.com/"
[:browser {:domain "https://www.google.co"}]
"ethereum:0x89205a3a3b2a69de6dbf7f01ed13b2108b2c43e7"
@@ -20,7 +20,7 @@
;; domains should be without the trailing slash
(def domains
{:external "https://status.app"
{:external "https://join.status.im"
:internal "status-im:/"})
(def links
@@ -19,9 +19,9 @@
(is (nil? (get-in (links/handle-url {:db db} "some-url")
[:db :universal-links/url]))))
(testing "Handle a custom string"
(is (= (get-in (links/handle-url {:db db} "https://status.app/u/statuse2e")
(is (= (get-in (links/handle-url {:db db} "https://join.status.im/u/statuse2e")
[::router/handle-uri :uri])
"https://status.app/u/statuse2e")))))))
"https://join.status.im/u/statuse2e")))))))
(deftest url-event-listener
(testing "the url is not nil"
@@ -4,7 +4,7 @@
;; domains should be without the trailing slash
(def domains
{:external "https://status.app"
{:external "https://join.status.im"
:internal "status-im:/"})
(def links
@@ -12,15 +12,15 @@
(testing "ethereum:0x89205a3a3b2a69de6dbf7f01ed13b2108b2c43e7"
(testing "it returns true"
(is (links/deep-link? "ethereum:0x89205a3a3b2a69de6dbf7f01ed13b2108b2c43e7"))))
(testing "http://status.app/blah"
(testing "http://join.status.im/blah"
(testing "it returns true"
(is (links/universal-link? "http://status.app/blah"))))
(testing "https://status.app/blah"
(is (links/universal-link? "http://join.status.im/blah"))))
(testing "https://join.status.im/blah"
(testing "it returns true"
(is (links/universal-link? "https://status.app/blah"))))
(is (links/universal-link? "https://join.status.im/blah"))))
(testing "unicode characters"
(testing "it returns false"
(is (not (links/universal-link? "https://status.app/browse/www.аррӏе.com")))))
(is (not (links/universal-link? "https://join.status.im/browse/www.аррӏе.com")))))
(testing "not-status-im://blah"
(testing "it returns false"
(is (not (links/universal-link? "https://not.status.im/blah")))))
@@ -30,6 +30,6 @@
(testing "https://not.status.im/blah"
(testing "it returns false"
(is (not (links/universal-link? "https://not.status.im/blah")))))
(testing "http://status.app/blah"
(testing "http://join.status.im/blah"
(testing "it returns false"
(is (not (links/deep-link? "http://status.app/blah"))))))
(is (not (links/deep-link? "http://join.status.im/blah"))))))
+2 -2
View File
@@ -179,8 +179,8 @@
(def regx-bold #"\*[^*]+\*")
(def regx-italic #"~[^~]+~")
(def regx-backquote #"`[^`]+`")
(def regx-universal-link #"((^https?://status.app/)|(^status-im://))[\x00-\x7F]+$")
(def regx-community-universal-link #"((^https?://status.app/)|(^status-im://))c/([\x00-\x7F]+)$")
(def regx-universal-link #"((^https?://join.status.im/)|(^status-im://))[\x00-\x7F]+$")
(def regx-community-universal-link #"((^https?://join.status.im/)|(^status-im://))c/([\x00-\x7F]+)$")
(def regx-deep-link #"((^ethereum:.*)|(^status-im://[\x00-\x7F]+$))")
(def ^:const dapp-permission-contact-code "contact-code")
@@ -33,7 +33,7 @@
(zipmap (repeat nil))))
([kv] (-> (init-contact) (merge kv))))
(def url-regex #"^https?://status.app/u/(.+)")
(def url-regex #"^https?://join.status.im/u/(.+)")
(defn ->id
[{:keys [input] :as contact}]
@@ -10,8 +10,8 @@
(def ckey "zQ3shWj4WaBdf2zYKCkXe6PHxDxNTzZyid1i75879Ue9cX9gA")
(def ens "esep")
(def ens-stateofus-eth (str ens ".stateofus.eth"))
(def link-ckey (str "https://status.app/u/" ckey))
(def link-ens (str "https://status.app/u/" ens))
(def link-ckey (str "https://join.status.im/u/" ckey))
(def link-ens (str "https://join.status.im/u/" ens))
;;; unit tests (no app-db involved)
@@ -9,7 +9,7 @@
(defn community-link
[id]
(str "https://status.app/c/" id))
(str "https://join.status.im/c/" id))
(rf/defn cache-link-preview-data
{:events [:chat.ui/cache-link-preview-data]}
@@ -256,7 +256,7 @@
[description]
[quo/text
{:accessibility-label :community-description-text
:number-of-lines 2
:number-of-lines 4
:ellipsize-mode :tail
:weight :regular
:size :paragraph-1
@@ -10,28 +10,28 @@
[{:label "Size"
:key :size
:type :select
:options [{:key :x-small
:value "x-small"}
{:key :small
:value "Small"}
{:key :medium
:value "Medium"}
{:key :large
:value "Large"}
{:key :x-large
:value "x-Large"}]}
:options [{:key 20
:value 20}
{:key 28
:value 28}
{:key 32
:value 32}
{:key 48
:value 48}
{:key 80
:value 80}]}
{:label "Avatar"
:key :picture?
:type :boolean}
(preview/customization-color-option)])
(def avatar (resources/get-mock-image :user-picture-male4))
(def avatar (resources/get-mock-image :photo1))
(defn cool-preview
[]
(let [state (reagent/atom {:theme :light
:customization-color :blue
:size :small
:size 20
:picture? false})]
(fn []
[rn/touchable-without-feedback {:on-press rn/dismiss-keyboard!}
@@ -1,48 +1,26 @@
(ns status-im2.contexts.quo-preview.colors.color-picker
(:require [quo2.core :as quo]
[quo2.foundations.colors :as colors]
[react-native.blur :as blur]
[react-native.core :as rn]
[reagent.core :as reagent]
[status-im2.contexts.quo-preview.preview :as preview]))
(def descriptor
[{:label "Color:"
:key :color
[{:key :selected
:type :select
:options (map (fn [color]
(let [k (get color :name)]
{:key k :value k}))
(quo/picker-colors))}
{:label "Blur?"
:key :blur
:type :boolean}])
{:key :blur?
:type :boolean}])
(defn cool-preview
(defn view
[]
(let [state (reagent/atom {:color "orange" :blur false})
blur (reagent/cursor state [:blur])
color (reagent/cursor state [:color])]
(let [state (reagent/atom {:selected :orange
:blur? false})]
(fn []
[rn/touchable-without-feedback {:on-press rn/dismiss-keyboard!}
[rn/view {:padding-bottom 150}
[preview/customizer state descriptor]
[(if @blur blur/view :<>)
[rn/view {:padding-vertical 60 :align-items :center}
[quo/color-picker
{:blur? @blur
:selected @color
:on-change #(reset! color %)}]]]]])))
(defn preview-color-picker
[]
[rn/view
{:background-color (colors/theme-colors
colors/white
colors/neutral-95)
:flex 1}
[rn/flat-list
{:flex 1
:keyboard-should-persist-taps :always
:header [cool-preview]
:key-fn str}]])
[preview/preview-container
{:state state
:descriptor descriptor
:blur? (:blur? @state)
:show-blur-background? true}
[quo/color-picker (assoc @state :on-change #(swap! state assoc :selected %))]])))
@@ -1,54 +1,29 @@
(ns status-im2.contexts.quo-preview.dividers.divider-label
(:require [quo2.components.dividers.divider-label :as divider-label]
[quo2.foundations.colors :as colors]
[react-native.core :as rn]
(:require [quo2.core :as quo]
[reagent.core :as reagent]
[status-im2.contexts.quo-preview.preview :as preview]))
(def descriptor
[{:label "Label:"
:key :label
:type :text}
{:label "Chevron position:"
:key :chevron-position
[{:type :text :key :label}
{:type :text :key :counter-value}
{:type :boolean :key :increase-padding-top?}
{:type :boolean :key :blur?}
{:key :chevron-position
:type :select
:options [{:key :left
:value "Left"}
{:key :right
:value "Right"}]}
{:label "Counter value:"
:key :counter-value
:type :text}
{:label "Increase padding top:"
:key :increase-padding-top?
:type :boolean}
{:label "Blur:"
:key :blur?
:type :boolean}])
:options [{:key :left}
{:key :right}]}])
(defn cool-preview
(defn view
[]
(let [state (reagent/atom {:label "Welcome"
(let [state (reagent/atom {:blur? false
:chevron-position :left
:counter-value 0
:counter-value "0"
:increase-padding-top? true
:blur? false})]
:label "Welcome"})]
(fn []
[rn/touchable-without-feedback {:on-press rn/dismiss-keyboard!}
[rn/view {:padding-bottom 150}
[preview/customizer state descriptor]
[rn/view {:padding-vertical 60}
[divider-label/divider-label @state]]]])))
(defn preview-divider-label
[]
[rn/view
{:background-color (colors/theme-colors
colors/white
colors/neutral-90)
:flex 1}
[rn/flat-list
{:flex 1
:keyboard-should-persist-taps :always
:header [cool-preview]
:key-fn str}]])
[preview/preview-container
{:state state
:descriptor descriptor
:blur? (:blur? @state)
:show-blur-background? true}
[quo/divider-label @state]])))
@@ -1,100 +1,56 @@
(ns status-im2.contexts.quo-preview.links.link-preview
(:require [clojure.string :as string]
[quo2.core :as quo]
[quo2.foundations.colors :as colors]
[react-native.core :as rn]
(:require [quo2.core :as quo]
[reagent.core :as reagent]
[status-im2.common.resources :as resources]
[status-im2.contexts.quo-preview.preview :as preview]
utils.number))
[status-im2.contexts.quo-preview.preview :as preview]))
(def descriptor
[{:label "Title"
:key :title
:type :text}
{:label "Description"
:key :description
:type :text}
{:label "Link"
:key :link
:type :text}
{:label "Container width"
:key :width
:type :text}
{:label "With logo?"
:key :with-logo?
:type :boolean}
{:label "With description?"
:key :with-description?
:type :boolean}
{:label "With thumbnail?"
:key :with-thumbnail?
:type :boolean}
{:label "Disabled text"
:key :disabled-text
:type :text}
{:label "Enabled?"
:key :enabled?
:type :boolean}
{:label "Thumbnail"
:key :thumbnail
[{:type :text :key :title}
{:type :text :key :description}
{:type :text :key :link}
{:type :number :key :width}
{:type :boolean :key :with-logo?}
{:type :boolean :key :with-description?}
{:type :boolean :key :with-thumbnail?}
{:type :text :key :disabled-text}
{:type :boolean :key :enabled?}
{:key :thumbnail
:type :select
:options (mapv (fn [k]
{:key k
:value (string/capitalize (name k))})
:options (mapv (fn [k] {:key k})
(keys resources/mock-images))}
{:label "Thumbnail size"
:key :thumbnail-size
{:key :thumbnail-size
:type :select
:options [{:key :normal
:value :normal}
{:key :large
:value :large}]}])
:options [{:key :normal}
{:key :large}]}])
(defn cool-preview
(defn view
[]
(let [state (reagent/atom
{:title "Rarible - NFT Marketplace"
:description "Turn your products or services into publicly tradeable items"
{:description "Turn your products or services into publicly tradeable items"
:disabled-text "Enable Preview"
:enabled? true
:link "rarible.com"
:thumbnail :collectible
:width "295"
:with-logo? true
:with-thumbnail? true
:with-description? true
:enabled? true
:thumbnail-size :normal
:disabled-text "Enable Preview"})]
:title "Rarible - NFT Marketplace"
:width 295
:with-description? true
:with-logo? true
:with-thumbnail? true})]
(fn []
(let [width (utils.number/parse-int (:width @state) 295)
thumbnail (get resources/mock-images (:thumbnail @state))]
[rn/view {:style {:margin-bottom 20}}
[preview/customizer state descriptor]
[rn/view
{:style {:align-items :center
:margin-top 20}}
[quo/link-preview
{:logo (when (:with-logo? @state)
(resources/get-mock-image :status-logo))
:title (:title @state)
:description (when (:with-description? @state)
(:description @state))
:enabled? (:enabled? @state)
:on-enable #(js/alert "Button pressed")
:disabled-text (:disabled-text @state)
:link (:link @state)
:thumbnail (when (:with-thumbnail? @state)
thumbnail)
:thumbnail-size (:thumbnail-size @state)
:container-style {:width width}}]]]))))
(defn preview
[]
[rn/view
{:style {:background-color (colors/theme-colors colors/neutral-5 colors/neutral-95)
:flex 1}}
[rn/flat-list
{:flex 1
:keyboard-should-persist-taps :always
:header [cool-preview]
:key-fn str}]])
(let [thumbnail (get resources/mock-images (:thumbnail @state))]
[preview/preview-container {:state state :descriptor descriptor}
[quo/link-preview
{:logo (when (:with-logo? @state)
(resources/get-mock-image :status-logo))
:title (:title @state)
:description (when (:with-description? @state)
(:description @state))
:enabled? (:enabled? @state)
:on-enable #(js/alert "Button pressed")
:disabled-text (:disabled-text @state)
:link (:link @state)
:thumbnail (when (:with-thumbnail? @state)
thumbnail)
:thumbnail-size (:thumbnail-size @state)
:container-style {:width (:width @state)}}]]))))
@@ -1,30 +1,18 @@
(ns status-im2.contexts.quo-preview.links.url-preview
(:require
[quo2.core :as quo]
[quo2.foundations.colors :as colors]
[react-native.core :as rn]
[reagent.core :as reagent]
[status-im2.common.resources :as resources]
[status-im2.contexts.quo-preview.preview :as preview]))
(def descriptor
[{:label "Title"
:key :title
:type :text}
{:label "Body"
:key :body
:type :text}
{:label "With logo?"
:key :with-logo?
:type :boolean}
{:label "Loading?"
:key :loading?
:type :boolean}
{:label "Loading message"
:key :loading-message
:type :text}])
[{:type :text :key :title}
{:type :text :key :body}
{:type :boolean :key :with-logo?}
{:type :boolean :key :loading?}
{:type :text :key :loading-message}])
(defn cool-preview
(defn view
[]
(let [state (reagent/atom
{:title "Status - Private, Secure Communication"
@@ -33,29 +21,12 @@
:loading? false
:loading-message "Generating preview"})]
(fn []
[rn/touchable-without-feedback {:on-press rn/dismiss-keyboard!}
[rn/view {:style {:padding-bottom 150}}
[preview/customizer state descriptor]
[rn/view
{:style {:align-items :center
:padding-horizontal 16
:margin-top 50}}
[quo/url-preview
{:title (:title @state)
:body (:body @state)
:logo (when (:with-logo? @state)
(resources/get-mock-image :status-logo))
:loading? (:loading? @state)
:loading-message (:loading-message @state)
:on-clear #(js/alert "Clear button pressed")}]]]])))
(defn preview
[]
[rn/view
{:style {:background-color (colors/theme-colors colors/white colors/neutral-95)
:flex 1}}
[rn/flat-list
{:flex 1
:keyboard-should-persist-taps :always
:header [cool-preview]
:key-fn str}]])
[preview/preview-container {:state state :descriptor descriptor}
[quo/url-preview
{:title (:title @state)
:body (:body @state)
:logo (when (:with-logo? @state)
(resources/get-mock-image :status-logo))
:loading? (:loading? @state)
:loading-message (:loading-message @state)
:on-clear #(js/alert "Clear button pressed")}]])))
@@ -1,50 +1,34 @@
(ns status-im2.contexts.quo-preview.links.url-preview-list
(:require
[quo2.core :as quo]
[quo2.foundations.colors :as colors]
[react-native.core :as rn]
[reagent.core :as reagent]
[status-im2.common.resources :as resources]
[status-im2.contexts.quo-preview.preview :as preview]
utils.number))
[status-im2.contexts.quo-preview.preview :as preview]))
(def descriptor
[{:label "Number of previews"
:key :previews-length
:type :text}])
[{:type :number :key :previews-length}])
(defn cool-preview
(defn view
[]
(let [state (reagent/atom {:previews-length "3"})]
(let [state (reagent/atom {:previews-length 3})
padding 20]
(fn []
(let [previews-length (min 6 (utils.number/parse-int (:previews-length @state)))
padding 20]
[rn/view {:style {:padding-bottom 150}}
[preview/customizer state descriptor]
[rn/view
{:style {:align-items :center
:margin-top 50}}
[quo/url-preview-list
{:horizontal-spacing padding
:preview-width (- (:width (rn/get-window))
(* 2 padding))
:on-clear #(js/alert "Clear button pressed")
:key-fn :url
:data (for [index (range previews-length)
:let [index (inc index)]]
{:title (str "Title " index)
:body (str "status.im." index)
:logo (resources/get-mock-image :status-logo)
:loading? false
:url (str "status.im." index)})}]]]))))
(defn preview
[]
[rn/view
{:style {:background-color (colors/theme-colors colors/white colors/neutral-95)
:flex 1}}
[rn/flat-list
{:flex 1
:keyboard-should-persist-taps :always
:header [cool-preview]
:key-fn str}]])
[preview/preview-container
{:state state
:descriptor descriptor
:component-container-style {:padding-horizontal 0}}
[quo/url-preview-list
{:horizontal-spacing padding
:preview-width (- (:width (rn/get-window))
(* 2 padding))
:on-clear #(js/alert "Clear button pressed")
:key-fn :url
:data (for [index (range (:previews-length @state))
:let [index (inc index)]]
{:title (str "Title " index)
:body (str "status.im." index)
:logo (resources/get-mock-image
:status-logo)
:loading? false
:url (str "status.im." index)})}]])))
@@ -2,39 +2,33 @@
(:require [quo2.core :as quo]
[quo2.foundations.colors :as colors]
[quo2.theme :as quo.theme]
[react-native.core :as rn]
[reagent.core :as reagent]
[status-im2.common.resources :as resources]
[status-im2.contexts.quo-preview.community.data :as data]
[status-im2.contexts.quo-preview.preview :as preview]))
(def descriptor-type
{:label "Type:"
{:type :select
:key :type
:type :select
:options [{:key :discover :value "Discover"}
{:key :engage :value "Engage"}
{:key :share :value "Share"}]})
:options [{:key :discover}
{:key :engage}
{:key :share}]})
(def descriptor-locked
{:label "Locked?" :key :locked? :type :boolean})
{:type :boolean :key :locked?})
(def descriptor-unread-count
{:label "Unread count:" :key :unread-count :type :number})
{:type :number :key :unread-count})
(def descriptor-title
{:label "Title:" :key :title :type :text})
{:type :text :key :title})
(def descriptor-blur
{:label "Blur?" :key :blur? :type :boolean})
{:type :boolean :key :blur?})
(def descriptor-member-stats
[{:label "Total member count:"
:key :members-count
:type :number}
{:label "Active member count:"
:key :active-count
:type :number}])
[{:type :number :key :members-count}
{:type :number :key :active-count}])
(def descriptors-base
[descriptor-type
@@ -43,29 +37,27 @@
(def descriptors-type-discover
(conj descriptors-base
{:label "Info:"
{:type :select
:key :info
:type :select
:options [{:key :token-gated :value "Token gated"}
{:key :default :value "Default"}]}
:options [{:key :token-gated}
{:key :default}]}
{:label "Member stats?"
:key :members?
:type :boolean}))
:type :boolean
:key :members?}))
(def descriptors-type-engage
(conj descriptors-base
{:label "Info:"
{:type :select
:key :info
:type :select
:options [{:key :notification :value "Notification"}
{:key :mention :value "Mention"}
{:key :muted :value "Muted"}
{:key :token-gated :value "Token gated"}
{:key :navigation :value "Navigation"}
{:key :default :value "Default"}]}))
:options [{:key :notification}
{:key :mention}
{:key :muted}
{:key :token-gated}
{:key :navigation}
{:key :default}]}))
(def descriptors-type-share
(conj descriptors-base {:label "Subtitle:" :key :subtitle :type :text}))
(conj descriptors-base {:type :text :key :subtitle}))
(defn descriptors
[{:keys [members? info] :as state}]
@@ -88,7 +80,7 @@
(into [descriptor-blur] descs)
descs)))
(defn cool-preview
(defn view
[]
(let [state (reagent/atom {:blur? false
:customization-color :blue
@@ -103,30 +95,16 @@
:unread-count 5})]
(fn []
(let [customization-color (colors/custom-color-by-theme (:customization-color @state) 50 60)]
[rn/touchable-without-feedback {:on-press rn/dismiss-keyboard!}
[rn/view {:style {:margin-bottom 20}}
[preview/customizer state (descriptors @state)]
[rn/view {:style {:margin-vertical 30 :align-items :center}}
[quo/community-list-item
(merge @state
{:container-style {:width 335}
:logo (resources/get-mock-image :status-logo)
:tokens (:tokens data/community)
:customization-color customization-color
:on-press #(js/alert "List item pressed")
:on-long-press #(js/alert "Long pressed item")
:on-press-info #(js/alert "Info pressed")
:members (when (:members? @state)
{:members-count (:members-count @state)
:active-count (:active-count @state)})})]]]]))))
(defn preview
[]
[rn/view
{:style {:background-color (colors/theme-colors colors/neutral-5 colors/neutral-95)
:flex 1}}
[rn/flat-list
{:style {:flex 1}
:keyboard-should-persist-taps :always
:header [cool-preview]
:key-fn str}]])
[preview/preview-container {:state state :descriptor (descriptors @state)}
[quo/community-list-item
(merge @state
{:container-style {:width 335}
:logo (resources/get-mock-image :status-logo)
:tokens (:tokens data/community)
:customization-color customization-color
:on-press #(js/alert "List item pressed")
:on-long-press #(js/alert "Long pressed item")
:on-press-info #(js/alert "Info pressed")
:members (when (:members? @state)
{:members-count (:members-count @state)
:active-count (:active-count @state)})})]]))))
+48 -156
View File
@@ -2,9 +2,9 @@
(:refer-clojure :exclude [filter])
(:require
[quo2.core :as quo]
[quo2.foundations.colors :as colors]
[reagent.core :as reagent]
[react-native.core :as rn]
[status-im2.contexts.quo-preview.style :as style]
[status-im2.common.theme.core :as theme]
[status-im2.contexts.quo-preview.animated-header-list.animated-header-list :as animated-header-list]
[status-im2.contexts.quo-preview.avatars.account-avatar :as account-avatar]
@@ -120,344 +120,233 @@
(def screens-categories
{:foundations [{:name :shadows
:options {:topBar {:visible true}}
:component shadows/preview-shadows}]
:animated-list [{:name :animated-header-list
:options {:topBar {:visible false}}
:component animated-header-list/mock-screen}]
:avatar [{:name :group-avatar
:options {:topBar {:visible true}}
:component group-avatar/preview-group-avatar}
{:name :icon-avatar
:options {:topBar {:visible true}}
:component icon-avatar/preview-icon-avatar}
{:name :user-avatar
:options {:topBar {:visible true}}
:component user-avatar/preview-user-avatar}
{:name :wallet-user-avatar
:options {:topBar {:visible true}}
:component wallet-user-avatar/preview-wallet-user-avatar}
{:name :channel-avatar
:options {:topBar {:visible true}}
:component channel-avatar/preview-channel-avatar}
{:name :account-avatar
:options {:topBar {:visible true}}
:component account-avatar/preview-account-avatar}]
:banner [{:name :banner
:options {:topBar {:visible true}}
:component banner/preview-banner}]
:buttons [{:name :button
:options {:topBar {:visible true}}
:component button/preview-button}
{:name :composer-button
:options {:topBar {:visible true}}
:component composer-button/preview-composer-button}
{:name :dynamic-button
:options {:topBar {:visible true}}
:component dynamic-button/preview-dynamic-button}
{:name :slide-button
:options {:topBar {:visible true}}
:component slide-button/preview-slide-button}
{:name :predictive-keyboard
:options {:topBar {:visible true}}
:component predictive-keyboard/preview-predictive-keyboard}]
:browser [{:name :browser-input
:options {:topBar {:visible false}}
:component browser-input/preview-browser-input}]
:calendar [{:name :calendar
:options {:topBar {:visible true}}
:component calendar/preview-calendar}
{:name :calendar-day
:options {:topBar {:visible true}}
:component calendar-day/preview-calendar-day}
{:name :calendar-year
:options {:topBar {:visible true}}
:component calendar-year/preview-calendar-year}]
:code [{:name :snippet
:options {:topBar {:visible true}}
:component code-snippet/preview-code-snippet}]
:colors [{:name :color-picker
:options {:topBar {:visible true}}
:component color-picker/preview-color-picker}]
:component color-picker/view}]
:community [{:name :community-card-view
:options {:topBar {:visible true}}
:component community-card/preview-community-card}
{:name :community-membership-list-view
:options {:topBar {:visible true}}
:component community-membership-list-view/preview-community-list-view}
{:name :discover-card
:options {:topBar {:visible true}}
:component discover-card/preview-discoverd-card}
{:name :token-gating
:options {:insets {:bottom? true}
:topBar {:visible true}}
:options {:insets {:bottom? true}}
:component token-gating/preview-token-gating}
{:name :channel-actions
:options {:insets {:bottom? true}
:topBar {:visible true}}
:options {:insets {:bottom? true}}
:component channel-actions/preview-channel-actions}]
:counter [{:name :counter
:options {:topBar {:visible true}}
:component counter/preview-counter}
{:name :step
:options {:topBar {:visible true}}
:component step/preview-step}]
:dividers [{:name :divider-label
:options {:topBar {:visible true}}
:component divider-label/preview-divider-label}
:component divider-label/view}
{:name :new-messages
:options {:topBar {:visible true}}
:component new-messages/preview-new-messages}
{:name :divider-date
:options {:topBar {:visible true}}
:component divider-date/preview-divider-date}
{:name :strength-divider
:options {:topBar {:visible true}}
:component strength-divider/preview-strength-divider}]
:drawers [{:name :action-drawers
:options {:topBar {:visible true}}
:component action-drawers/preview-action-drawers}
{:name :documentation-drawer
:options {:topBar {:visible true}}
:component documenation-drawers/preview-documenation-drawers}
{:name :drawer-buttons
:options {:topBar {:visible true}}
:component drawer-buttons/preview-drawer-buttons}
{:name :permission-drawers
:options {:topBar {:visible true}}
:component permission-drawers/preview-permission-drawers}]
:dropdowns [{:name :dropdown
:options {:topBar {:visible true}}
:component dropdown/preview-dropdown}]
:empty-state [{:name :empty-state
:options {:topBar {:visible true}}
:component empty-state/preview-empty-state}]
:gradient [{:name :gradient-cover
:options {:topBar {:visible true}}
:component gradient-cover/preview-gradient-cover}]
:graph [{:name :wallet-graph
:options {:topBar {:visible true}}
:component wallet-graph/preview-wallet-graph}]
:info [{:name :info-message
:options {:topBar {:visible true}}
:component info-message/preview-info-message}
{:name :information-box
:options {:topBar {:visible true}}
:component information-box/preview-information-box}]
:inputs [{:name :input
:options {:topBar {:visible true}}
:component input/preview-input}
{:name :locked-input
:options {:topBar {:visible true}}
:component locked-input/preview-locked-input}
{:name :profile-input
:options {:topBar {:visible true}}
:component profile-input/preview-profile-input}
{:name :recovery-phrase-input
:options {:topBar {:visible true}}
:component recovery-phrase-input/preview-recovery-phrase-input}
{:name :search-input
:options {:topBar {:visible true}}
:component search-input/preview-search-input}
{:name :title-input
:options {:topBar {:visible true}}
:component title-input/preview-title-input}]
:numbered-keyboard [{:name :keyboard-key
:options {:insets {:top? true}
:topBar {:visible true}}
:options {:insets {:top? true}}
:component keyboard-key/preview-keyboard-key}
{:name :numbered-keyboard
:options {:insets {:top? true}
:topBar {:visible true}}
:options {:insets {:top? true}}
:component numbered-keyboard/preview-numbered-keyboard}]
:links [{:name :url-preview
:options {:insets {:top? true}
:topBar {:visible true}}
:component url-preview/preview}
:options {:insets {:top? true}}
:component url-preview/view}
{:name :url-preview-list
:options {:insets {:top? true}
:topBar {:visible true}}
:component url-preview-list/preview}
:options {:insets {:top? true}}
:component url-preview-list/view}
{:name :link-preview
:options {:insets {:top? true}
:topBar {:visible true}}
:component link-preview/preview}]
:options {:insets {:top? true}}
:component link-preview/view}]
:list-items [{:name :account-list-card
:options {:topBar {:visible true}}
:component account-list-card/preview}
{:name :channel
:options {:topBar {:visible true}}
:component channel/preview-channel}
{:name :community-list
:options {:insets {:top? true}
:topBar {:visible true}}
:component community-list/preview}
:options {:insets {:top? true}}
:component community-list/view}
{:name :preview-lists
:options {:topBar {:visible true}}
:component preview-lists/preview-preview-lists}
{:name :user-list
:options {:topBar {:visible true}}
:component user-list/preview-user-list}
{:name :token-value
:options {:topBar {:visible true}}
:component token-value/preview}]
:loaders [{:name :skeleton
:options {:topBar {:visible true}}
:component skeleton/preview-skeleton}]
:markdown [{:name :texts
:options {:topBar {:visible true}}
:component text/preview-text}
{:name :markdown-list
:options {:topBar {:visible true}}
:component markdown-list/preview-markdown-list}]
:messages [{:name :gap
:options {:topBar {:visible true}}
:component messages-gap/preview-messages-gap}
{:name :system-messages
:options {:topBar {:visible true}}
:component system-message/preview-system-message}
{:name :author
:options {:topBar {:visible true}}
:component messages-author/preview-author}]
:navigation [{:name :bottom-nav-tab
:options {:topBar {:visible true}}
:component bottom-nav-tab/preview-bottom-nav-tab}
{:name :top-nav
:options {:topBar {:visible true}}
:component top-nav/preview-top-nav}
{:name :page-nav
:options {:topBar {:visible true}}
:component page-nav/preview-page-nav}
{:name :floating-shell-button
:options {:topBar {:visible true}}
:component floating-shell-button/preview-floating-shell-button}]
:notifications [{:name :activity-logs
:options {:topBar {:visible true}}
:component activity-logs/preview-activity-logs}
{:name :activity-logs-photos
:options {:topBar {:visible true}}
:component activity-logs-photos/preview-activity-logs-photos}
{:name :toast
:options {:topBar {:visible true}}
:component toast/preview-toasts}
{:name :notification
:options {:topBar {:visible true}}
:component notification/preview-notification}]
:onboarding [{:name :small-option-card
:options {:topBar {:visible true}}
:component small-option-card/preview-small-option-card}]
:password [{:name :tips
:options {:topBar {:visible true}}
:component tips/preview-tips}]
:profile [{:name :profile-card
:options {:topBar {:visible true}}
:component profile-card/preview-profile-card}
{:name :collectible
:options {:topBar {:visible true}}
:component collectible/preview-collectible}
{:name :select-profile
:options {:topBar {:visible true}}
:component select-profile/preview-select-profile}]
:reactions [{:name :react
:options {:topBar {:visible true}}
:component react/preview-react}]
:record-audio [{:name :record-audio
:options {:topBar {:visible true}}
:component record-audio/preview-record-audio}]
:switcher [{:name :switcher-cards
:options {:topBar {:visible true}}
:component switcher-cards/preview-switcher-cards}]
:selectors [{:name :disclaimer
:options {:topBar {:visible true}}
:component disclaimer/preview-disclaimer}
{:name :filter
:options {:topBar {:visible true}}
:component filter/preview}
{:name :selectors
:options {:topBar {:visible true}}
:component selectors/preview-selectors}
{:name :select-reactions
:options {:topBar {:visible true}}
:component selector-reactions/preview}]
:settings [{:name :privacy-option
:options {:topBar {:visible true}}
:component privacy-option/preview-options}
{:name :accounts
:options {:topBar {:visible true}}
:component accounts/preview-accounts}
{:name :settings-list
:options {:topBar {:visible true}}
:component settings-list/preview-settings-list}
{:name :reorder-item
:options {:topBar {:visible true}}
:component reorder-item/preview-reorder-item}
{:name :category
:options {:topBar {:visible true}}
:component category/preview}]
:share [{:name :qr-code
:options {:topBar {:visible true}}
:component qr-code/preview-qr-code}
{:name :share-qr-code
:options {:topBar {:visible true}}
:component share-qr-code/preview-share-qr-code}]
:tabs [{:name :segmented
:options {:topBar {:visible true}}
:component segmented/preview-segmented}
{:name :tabs
:options {:topBar {:visible true}}
:component tabs/preview-tabs}
{:name :account-selector
:options {:topBar {:visible true}}
:component account-selector/preview-this}]
:tags [{:name :context-tags
:options {:topBar {:visible true}}
:component context-tags/preview-context-tags}
{:name :tags
:options {:topBar {:visible true}}
:component tags/preview-tags}
{:name :permission-tag
:options {:topBar {:visible true}}
:component permission-tag/preview-permission-tag}
{:name :status-tags
:options {:topBar {:visible true}}
:component status-tags/preview-status-tags}
{:name :token-tag
:options {:topBar {:visible true}}
:component token-tag/preview-token-tag}]
:text-combinations [{:name :title
:options {:topBar {:visible true}}
:component title/preview-title}]
:wallet [{:name :account-card
:options {:topBar {:visible true}}
:component account-card/preview-account-card}
{:name :account-overview
:options {:topBar {:visible true}}
:component account-overview/preview-account-overview}
{:name :network-amount
:options {:topBar {:visible true}}
:component network-amount/preview}
{:name :network-bridge
:options {:topBar {:visible true}}
:component network-bridge/preview}
{:name :progress-bar
:options {:topBar {:visible true}}
:component progress-bar/preview}
{:name :summary-info
:options {:topBar {:visible true}}
:component summary-info/preview}
{:name :token-input
:options {:topBar {:visible true}}
:component token-input/preview}
{:name :wallet-overview
:options {:topBar {:visible true}}
:component wallet-overview/preview-wallet-overview}]
:keycard [{:name :keycard-component
:options {:topBar {:visible true}}
:component keycard/preview-keycard}]})
(def screens (flatten (map val screens-categories)))
(defn navigation-bar
(defn- navigation-bar
[]
(let [logged-in? (rf/sub [:multiaccount/logged-in?])
has-profiles? (boolean (rf/sub [:profile/profiles-overview]))
@@ -477,48 +366,51 @@
(theme/set-theme :dark)
(rf/dispatch [:init-root root]))))}}]))
(defn theme-switcher
(defn- theme-switcher
[]
[rn/view
{:style {:flex-direction :row
:justify-content :space-between
:padding-horizontal 24
:padding-vertical 12}}
[rn/view {:style style/theme-switcher}
[quo/button {:on-press #(theme/set-theme :light)} "Set light theme"]
[quo/button {:on-press #(theme/set-theme :dark)} "Set dark theme"]])
(defn category-view
(defn- category-view
[]
(let [open? (reagent/atom false)]
(let [open? (reagent/atom false)
on-change #(swap! open? not)]
(fn [category]
[rn/view {:style {:margin-vertical 8}}
[quo/dropdown {:selected @open? :on-change #(swap! open? not) :type :grey}
(clojure.core/name (key category))]
[quo/dropdown
{:selected @open?
:on-change on-change
:type :grey}
(name (key category))]
(when @open?
(for [{:keys [name]} (val category)]
^{:key name}
(for [{category-name :name} (val category)]
^{:key category-name}
[quo/button
{:type :outline
:container-style {:margin-vertical 8}
:on-press #(rf/dispatch [:navigate-to name])}
(clojure.core/name name)]))])))
:on-press #(rf/dispatch [:navigate-to category-name])}
(name category-name)]))])))
(defn main-screen
(defn- main-screen
[]
(fn []
[:<>
[navigation-bar]
[theme-switcher]
[rn/scroll-view
{:flex 1
:padding-bottom 8
:padding-horizontal 16
:background-color (colors/theme-colors colors/white colors/neutral-90)}
[rn/view
(map (fn [category]
^{:key (get category 0)}
[category-view category])
(sort screens-categories))]]]))
[:<>
[navigation-bar]
[theme-switcher]
[rn/scroll-view {:style (style/main)}
(for [category (sort screens-categories)]
^{:key (first category)}
[category-view category])]])
(def screens
(->> screens-categories
(map val)
flatten
(map (fn [subcategory]
(update-in subcategory
[:options :topBar]
merge
{:visible true})))))
(def main-screens
[{:name :quo2-preview
+163 -187
View File
@@ -1,216 +1,178 @@
(ns status-im2.contexts.quo-preview.preview
(:require [clojure.string :as string]
(:require [camel-snake-kebab.core :as camel-snake-kebab]
[clojure.string :as string]
[quo2.core :as quo]
[quo2.foundations.colors :as colors]
[quo2.theme :as theme]
[quo2.theme :as quo.theme]
[react-native.blur :as blur]
[react-native.core :as rn]
[reagent.core :as reagent]
[status-im2.common.resources :as resources]
[status-im2.contexts.quo-preview.style :as style]
utils.number)
(:require-macros status-im2.contexts.quo-preview.preview))
(def container
{:flex-direction :row
:padding-vertical 8
:flex 1
:align-items :center})
(defn touchable-style
[]
{:flex 1
:align-items :center
:justify-content :center
:padding-horizontal 16
:height 44})
(defn select-style
[]
{:flex 1
:flex-direction :row
:align-items :center
:padding-horizontal 16
:height 44
:border-radius 4
:background-color colors/neutral-20
:border-width 1
:border-color colors/neutral-100})
(defn select-option-style
[selected]
(merge (select-style)
{:margin-vertical 8
:justify-content :center}
(if selected
{:background-color colors/primary-50-opa-30}
{:background-color (colors/theme-colors colors/neutral-20 colors/white)})))
(def label-style
{:flex 0.4
:padding-right 8})
(defn label-view
(defn- label-view
[_ label]
[rn/view {:style label-style}
[rn/text
(when-let [label-color (colors/theme-colors colors/neutral-100 colors/white)]
{:style {:color label-color}})
[rn/view {:style style/label-container}
[rn/text {:style (style/label)}
label]])
(defn modal-container
[]
{:flex 1
:justify-content :center
:padding-horizontal 24
:background-color "rgba(0,0,0,0.4)"})
(defn- humanize
[k]
;; We explicitly convert `k` to string because sometimes it's a number and
;; Clojure would throw an exception.
(-> (if (keyword? k) k (str k))
camel-snake-kebab/->kebab-case-keyword
name
(string/replace "-" " ")
string/capitalize))
(defn modal-view
[]
{:padding-horizontal 16
:padding-vertical 8
:border-radius 8
:flex-direction :column
:margin-vertical 100
:background-color (colors/theme-colors colors/neutral-20 colors/white)})
(defn- key->boolean-label
[k]
(let [label (humanize k)]
(if (string/ends-with? label "?")
label
(str label "?"))))
(defn customizer-boolean
(defn- key->text-label
[k]
(str (humanize k) ":"))
(defn- customizer-boolean
[{:keys [label state] :as args}]
(let [state* (reagent/cursor state [(:key args)])]
[rn/view {:style container}
(let [label (or label (key->boolean-label (:key args)))
field-value (reagent/cursor state [(:key args)])
active? @field-value]
[rn/view {:style style/field-row}
[label-view state label]
[rn/view
{:style {:flex-direction :row
:flex 0.6
:border-radius 4
:background-color (colors/theme-colors colors/neutral-20 colors/white)
:border-width 1
:border-color (colors/theme-colors colors/neutral-100 colors/white)}}
[rn/touchable-opacity
{:style (merge (touchable-style) {:background-color (when @state* colors/primary-50-opa-30)})
:on-press #(reset! state* true)}
[rn/text
[rn/view {:style (style/boolean-container)}
[rn/pressable
{:style (style/boolean-button {:active? active? :left? true})
:on-press #(reset! field-value true)}
[rn/text {:style (style/field-text active?)}
"True"]]
[rn/view
{:width 1
:margin-vertical 4
:background-color (colors/theme-colors colors/neutral-20 colors/white)}]
[rn/touchable-opacity
{:style (merge (touchable-style)
{:background-color (when (not @state*) colors/primary-50-opa-30)})
:on-press #(reset! state* false)}
[rn/text {}
[rn/pressable
{:style (style/boolean-button {:active? (not active?) :left? false})
:on-press #(reset! field-value false)}
[rn/text {:style (style/field-text (not active?))}
"False"]]]]))
(defn customizer-text
(defn- customizer-text
[{:keys [label state limit suffix] :as args}]
(let [state* (reagent/cursor state [(:key args)])]
[rn/view {:style container}
(let [label (or label (key->text-label (:key args)))
field-value (reagent/cursor state [(:key args)])]
[rn/view {:style style/field-row}
[label-view state label]
[rn/view {:style {:flex 0.6}}
[rn/view {:style style/field-column}
[rn/text-input
(merge
{:value @state*
{:value @field-value
:show-cancel false
:style {:border-radius 4
:border-width 1
:color (colors/theme-colors colors/neutral-100 colors/white)
:border-color (colors/theme-colors colors/neutral-100 colors/white)}
:keyboard-appearance (theme/theme-value :light :dark)
:on-change-text #(do
(reset! state* (if (and suffix (> (count %) (count @state*)))
(str (string/replace % suffix "") suffix)
%))
(reagent/flush))}
:style (style/field-container false)
:keyboard-appearance (quo.theme/theme-value :light :dark)
:on-change-text (fn [text]
(reset! field-value (if (and suffix
(> (count text) (count @field-value)))
(str (string/replace text suffix "") suffix)
text))
(reagent/flush))}
(when limit
{:max-length limit}))]]]))
(defn customizer-number
(defn- customizer-number
[{:keys [label state default] :as args}]
(let [state* (reagent/cursor state [(:key args)])]
[rn/view {:style container}
(let [label (or label (key->text-label (:key args)))
field-value (reagent/cursor state [(:key args)])]
[rn/view {:style style/field-row}
[label-view state label]
[rn/view {:style {:flex 0.6}}
[rn/view {:style style/field-column}
[rn/text-input
(merge
{:value (str @state*)
{:value (str @field-value)
:show-cancel false
:style {:border-radius 4
:border-width 1
:color (colors/theme-colors colors/neutral-100 colors/white)
:border-color (colors/theme-colors colors/neutral-100 colors/white)}
:keyboard-appearance (theme/theme-value :light :dark)
:on-change-text (fn [v]
(reset! state* (utils.number/parse-int v default))
:style (style/field-container false)
:keyboard-appearance (quo.theme/theme-value :light :dark)
:on-change-text (fn [text]
(reset! field-value (utils.number/parse-int text default))
(reagent/flush))})]]]))
(defn value-for-key
(defn- find-selected-option
[id v]
(:value (first (filter #(= (:key %) id) v))))
(first (filter #(= (:key %) id) v)))
(defn customizer-select
(defn- customizer-select-modal
[{:keys [open options field-value]}]
[rn/modal
{:visible @open
:on-request-close #(reset! open false)
:status-bar-translucent true
:transparent true
:animation :slide}
[rn/view {:style (style/modal-overlay)}
[rn/view {:style (style/modal-container)}
[rn/scroll-view {:shows-vertical-scroll-indicator false}
(doall
(for [{k :key v :value} options
:let [v (or v (humanize k))]]
^{:key k}
[rn/pressable
{:style (style/select-option (= @field-value k))
:on-press (fn []
(reset! open false)
(reset! field-value k))}
[rn/text {:style (style/field-text (= @field-value k))}
v]]))]
[rn/view {:style (style/footer)}
[rn/pressable
{:style (style/select-button)
:on-press (fn []
(reset! field-value nil)
(reset! open false))}
[rn/text {:style (style/field-text false)}
"Clear"]]
[rn/view {:style {:width 16}}]
[rn/touchable-opacity
{:style (style/select-button)
:on-press #(reset! open false)}
[rn/text {:style (style/field-text false)}
"Close"]]]]]])
(defn- customizer-select-button
[{:keys [open selected-key]}]
[rn/pressable
{:style (style/select-container)
:on-press #(reset! open true)}
[rn/text
{:style (style/field-select)
:number-of-lines 1}
(if selected-key
(humanize selected-key)
"Select option")]
[rn/view
[quo/icon :i/chevron-right]]])
(defn- customizer-select
[]
(let [open (reagent/atom nil)]
(fn [{:keys [label state options] :as args}]
(let [state* (reagent/cursor state [(:key args)])
selected (value-for-key @state* options)]
[rn/view {:style container}
(let [label (or label (key->text-label (:key args)))
field-value (reagent/cursor state [(:key args)])
selected-key (:key (find-selected-option @field-value options))]
[rn/view {:style style/field-row}
[label-view state label]
[rn/view {:style {:flex 0.6}}
[rn/modal
{:visible @open
:on-request-close #(reset! open false)
:statusBarTranslucent true
:transparent true
:animation :slide}
[rn/view {:style (modal-container)}
[rn/view {:style (modal-view)}
[rn/scroll-view
(doall
(for [{k :key v :value} options]
^{:key k}
[rn/touchable-opacity
{:style (select-option-style (= @state* k))
:on-press #(do
(reset! open false)
(reset! state* k))}
[rn/text {:color (if (= @state* k) :link :secondary)}
v]]))]
[rn/view
{:flex-direction :row
:padding-top 20
:margin-top 10
:border-top-width 1
:border-top-color (colors/theme-colors colors/neutral-100 colors/white)}
[rn/touchable-opacity
{:style (select-option-style false)
:on-press #(do
(reset! state* nil)
(reset! open false))}
[rn/text "Clear"]]
[rn/view {:width 16}]
[rn/touchable-opacity
{:style (select-option-style false)
:on-press #(reset! open false)}
[rn/text "Close"]]]]]]
[rn/touchable-opacity
{:style (select-style)
:on-press #(reset! open true)}
(if selected
[rn/text {:color :link} selected]
[rn/text "Select option"])
[rn/view
{:position :absolute
:right 16
:top 0
:bottom 0
:justify-content :center}
[rn/text "↓"]]]]]))))
[rn/view {:style style/field-column}
[customizer-select-modal
{:open open
:options options
:field-value field-value}]
[customizer-select-button {:open open :selected-key selected-key}]]]))))
(defn customizer
[state descriptors]
[rn/view
{:style {:flex 1}
:padding-horizontal 16}
{:style {:flex-shrink 1
:padding-horizontal 20}}
(doall
(for [desc descriptors
:let [descriptor (merge desc {:state state})]]
@@ -237,19 +199,6 @@
{:key k :value (string/capitalize (name k))})))}
opts)))
(comment
[{:label "Show error:"
:key :error
:type :boolean}
{:label "Label:"
:key :label
:type :text}
{:label "Type:"
:key :type
:type :select
:options [{:key :primary :value "Primary"}
{:key :secondary :value "Secondary"}]}])
(defn blur-view
[{:keys [show-blur-background? image height blur-view-props style]} children]
[rn/view
@@ -262,8 +211,7 @@
:overflow :hidden}}
[rn/image
{:source (or image (resources/get-mock-image :community-cover))
:style {:height "100%"
:width "100%"}}]
:style {:height "100%" :width "100%"}}]
[blur/view
(merge {:style {:position :absolute
:top 0
@@ -271,9 +219,7 @@
:left 0
:right 0}
:blur-amount 10
:overlay-color (colors/theme-colors
colors/white-opa-70
colors/neutral-80-opa-80)}
:overlay-color (colors/theme-colors colors/white-opa-70 colors/neutral-80-opa-80)}
blur-view-props)]])
[rn/view
{:style (merge {:position :absolute
@@ -281,3 +227,33 @@
:padding-horizontal 16}
style)}
children]])
(defn preview-container
[{:keys [state descriptor blur?
component-container-style
blur-container-style blur-view-props blur-height show-blur-background?]
:or {blur-height 200}}
component]
[rn/scroll-view
{:style (style/panel-basic)
:shows-vertical-scroll-indicator false}
[rn/pressable {:on-press rn/dismiss-keyboard!}
[rn/view {:style style/customizer-container}
[customizer state descriptor]]
[rn/view
(merge {:style style/component-container}
component-container-style)
(if blur?
[blur-view
{:show-blur-background? show-blur-background?
:height blur-height
:style (merge {:width "100%"
:flex-grow 1}
(when-not show-blur-background?
{:padding-horizontal 0
:top 0})
blur-container-style)
:blur-view-props (merge {:blur-type (quo.theme/get-theme)}
blur-view-props)}
component]
component)]]])
@@ -0,0 +1,179 @@
(ns status-im2.contexts.quo-preview.style
(:require [quo2.foundations.colors :as colors]
[quo2.foundations.typography :as typography]))
;;;; Form fields
(def field-border-radius 12)
(def field-flex-percentage 0.6)
(def text-default typography/paragraph-1)
(defn field-active-bg-color
[]
(colors/theme-colors colors/primary-50 colors/primary-60))
(defn field-default-color
[]
(colors/theme-colors colors/neutral-100 colors/white))
(defn field-default-bg-color
[]
(colors/theme-colors colors/neutral-20 colors/neutral-80))
(defn field-default-border-color
[]
(colors/theme-colors colors/neutral-30 colors/neutral-70))
(def field-row
{:flex-direction :row
:padding-vertical 6
:align-items :center})
(def field-column
{:flex field-flex-percentage})
(defn field-container
[active?]
(merge text-default
{:color (if active?
(colors/theme-colors colors/white colors/white-opa-95)
(colors/theme-colors colors/neutral-100 colors/white))
:border-width 1
:border-color (field-default-border-color)
:border-radius field-border-radius
:padding-vertical 9
:padding-horizontal 12}))
(defn field-text
[active?]
(merge text-default
{:color (if active?
(colors/theme-colors colors/white colors/white-opa-95)
(field-default-color))}))
(def customizer-container
{:flex-shrink 1
:padding-top 12})
(defn select-container
[]
(merge (field-container false)
{:flex-direction :row
:align-items :center
:border-radius field-border-radius
:background-color (field-default-bg-color)
:border-width 1
:border-color (field-default-border-color)}))
(defn field-select
[]
(merge text-default
{:flex-grow 1
:color (field-default-color)}))
(defn select-option
[selected?]
(merge (field-container selected?)
{:justify-content :center
:flex 1
:margin-vertical 4}
(if selected?
{:border-color (field-active-bg-color)
:background-color (field-active-bg-color)}
{:background-color (field-default-bg-color)})))
(defn select-button
[]
(merge (select-option false) {:align-items :center}))
(def label-container
{:flex (- 1 field-flex-percentage)
:padding-right 8})
(defn label
[]
(merge text-default
typography/font-medium
{:color (field-default-color)}))
(defn boolean-container
[]
{:flex-direction :row
:flex field-flex-percentage
:border-radius field-border-radius})
(defn boolean-button
[{:keys [active? left?]}]
(cond-> {:flex 1
:align-items :center
:justify-content :center
:padding-vertical 9
:padding-horizontal 12
:border-color (if active?
(field-active-bg-color)
(field-default-border-color))
:border-top-width 1
:border-bottom-width 1
:background-color (if active?
(field-active-bg-color)
(field-default-bg-color))}
left?
(assoc :border-top-left-radius field-border-radius
:border-bottom-left-radius field-border-radius
:border-left-width 1)
(not left?)
(assoc :border-top-right-radius field-border-radius
:border-bottom-right-radius field-border-radius
:border-right-width 1)))
;;;; Modal
(defn modal-overlay
[]
{:flex 1
:justify-content :center
:padding-horizontal 24
:background-color (colors/theme-colors colors/neutral-80-opa-60 colors/neutral-80-opa-80)})
(defn modal-container
[]
{:padding-horizontal 16
:padding-vertical 8
:border-radius 12
:margin-vertical 100
:background-color (colors/theme-colors colors/white colors/neutral-95)})
(defn footer
[]
{:flex-direction :row
:padding-top 10
:margin-top 10
:border-top-width 1
:border-top-color (colors/theme-colors colors/neutral-10 colors/neutral-80)})
;;;; Misc
(defn panel-basic
[]
{:background-color (colors/theme-colors colors/white colors/neutral-95)
:flex 1})
(def component-container
{:flex-grow 1
:min-height 200
:padding-vertical 20
:padding-horizontal 20})
(defn main
[]
{:flex 1
:padding-bottom 8
:padding-horizontal 16
:background-color (colors/theme-colors colors/white colors/neutral-90)})
(def theme-switcher
{:flex-direction :row
:justify-content :space-between
:padding-horizontal 24
:padding-vertical 12})
@@ -141,7 +141,7 @@
:group-avatar [quo2/group-avatar-tag (:label @state)
{:blur? (:blur? @state)
:size :x-small
:size 20
:customization-color :purple}]
:public-key [quo2/public-key-tag
@@ -9,7 +9,7 @@
[utils.re-frame :as rf]))
(def tag-params
{:size :small
{:size 20
:customization-color :blue
:style style/user-avatar-tag
:text-style style/user-avatar-tag-text
@@ -67,7 +67,7 @@
:context [[common/user-avatar-tag author]
(i18n/label :t/added-you-to)
[quo/group-avatar-tag chat-name
{:size :x-small
{:size 20
:customization-color :purple}]]
:items (when-not (or accepted dismissed)
[{:type :button
+2 -2
View File
@@ -17,11 +17,11 @@
(defn get-abbreviated-profile-url
"The goal here is to generate a string that begins with
status.app/u/ joined with the 1st 5 characters
join.status.im/u/ joined with the 1st 5 characters
of the compressed public key followed by an ellipsis followed by
the last 12 characters of the compressed public key"
[base-url public-key]
(if (and public-key base-url (> (count public-key) 17) (= "status.app/u/" base-url))
(if (and public-key base-url (> (count public-key) 17) (= "join.status.im/u/" base-url))
(let [first-part-of-public-pk (subs public-key 0 5)
ellipsis "..."
public-key-size (count public-key)
+7 -7
View File
@@ -21,22 +21,22 @@
(deftest test-get-abbreviated-profile-url
(testing "Ensure the function correctly generates an abbreviated profile URL for a valid public key"
(is (= "status.app/u/zQ3sh...aimrdYpzeFUa"
(is (= "join.status.im/u/zQ3sh...aimrdYpzeFUa"
(utils.address/get-abbreviated-profile-url
"status.app/u/"
"join.status.im/u/"
"zQ3shPrnUhhR42JJn3QdhodGest8w8MjiH8hPaimrdYpzeFUa"))))
(testing "Ensure the function returns nil when given an empty public key"
(is (nil? (utils.address/get-abbreviated-profile-url "status.app/u/" ""))))
(is (nil? (utils.address/get-abbreviated-profile-url "join.status.im/u/" ""))))
(testing "Ensure the function returns nil when given a nil public key"
(is (nil? (utils.address/get-abbreviated-profile-url "status.app/u/" nil))))
(is (nil? (utils.address/get-abbreviated-profile-url "join.status.im/u/" nil))))
(testing "Ensure the function returns nil when given an incorrect base URL"
(is (nil? (utils.address/get-abbreviated-profile-url
"status.app/uwu/"
"join.status.im/uwu/"
"zQ3shPrnUhhR42JJn3QdhodGest8w8MjiH8hPaimrdYpzeFUa"))))
(testing "Ensure the function returns nil when given a public key shorter than 17 characters"
(is (nil? (utils.address/get-abbreviated-profile-url "status.app/u/" "abc")))
(is (nil? (utils.address/get-abbreviated-profile-url "status.app/u/" "1234")))))
(is (nil? (utils.address/get-abbreviated-profile-url "join.status.im/u/" "abc")))
(is (nil? (utils.address/get-abbreviated-profile-url "join.status.im/u/" "1234")))))
+2 -2
View File
@@ -11,8 +11,8 @@
(def ^:const account-initials-action "/accountInitials")
(def ^:const contact-images-action "/contactImages")
(def ^:const generate-qr-action "/GenerateQRCode")
(def ^:const status-profile-base-url "https://status.app/u/")
(def ^:const status-profile-base-url-without-https "status.app/u/")
(def ^:const status-profile-base-url "https://join.status.im/u/")
(def ^:const status-profile-base-url-without-https "join.status.im/u/")
(defn get-font-file-ready
"setup font file and get the absolute path to it
+3 -3
View File
@@ -3,7 +3,7 @@
"_comment": "Instead use: scripts/update-status-go.sh <rev>",
"owner": "status-im",
"repo": "status-go",
"version": "v0.163.9",
"commit-sha1": "f2f599fe867a0eba90aaa717a29bb6e99cb5749e",
"src-sha256": "0p282pv2lz5f2b0vhpcx0nj74dp5mf7hb41l12js2hxsp21sprmj"
"version": "7603b10fb902244899836a19d906cd573fb26093",
"commit-sha1": "7603b10fb902244899836a19d906cd573fb26093",
"src-sha256": "0asnapan03skhxr1r9cmj3q2rfa36sky1qzczficw34kb2icgj15"
}
@@ -437,9 +437,6 @@ class TestCommunityOneDeviceMerged(MultipleSharedDeviceTestCase):
self.errors.verify_no_errors()
@marks.testrail_id(703133)
@marks.xfail(reason="Restoring communities issue: 16787; "
"restoring contacts issue: 15500",
run=False)
def test_restore_multiaccount_with_waku_backup_remove_switch(self):
self.home.jump_to_communities_home()
profile = self.home.profile_button.click()
@@ -458,12 +455,16 @@ class TestCommunityOneDeviceMerged(MultipleSharedDeviceTestCase):
"Incorrect contacts number restored: %s instead of %s" % (contacts_number, len(waku_user.contacts)))
else:
for i in range(contacts_number):
self.home.click_system_back_button_until_element_is_shown()
contact_row = self.home.contact_details_row(index=i + 1)
shown_name_text = contact_row.username_text.text
if shown_name_text in waku_user.contacts:
waku_user.contacts.remove(shown_name_text)
continue
key = waku_user.contacts[i]
if not self.home.element_by_text(key).is_element_displayed(30):
self.errors.append('%s was not restored as a contact from waku backup!' % key)
# Disabled for simple check as sometimes from waku-backup users restored with 3-random names
# self.home.click_system_back_button_until_element_is_shown()
# contact_row = self.home.contact_details_row(index=i + 1)
# shown_name_text = contact_row.username_text.text
# if shown_name_text in waku_user.contacts:
# waku_user.contacts.remove(shown_name_text)
# continue
# else:
# contact_row.click()
# shown_name_text = profile.default_username_text.text
@@ -477,9 +478,9 @@ class TestCommunityOneDeviceMerged(MultipleSharedDeviceTestCase):
# if chat.element_starts_with_text(name).is_element_displayed(sec=20):
# waku_user.contacts.remove(name)
# continue
if waku_user.contacts:
self.errors.append(
"Contact(s) was (were) not restored from backup: %s!" % ", ".join(waku_user.contacts))
# if waku_user.contacts:
# self.errors.append(
# "Contact(s) was (were) not restored from backup: %s!" % ", ".join(waku_user.contacts))
self.home.just_fyi("Check restored communities")
self.home.communities_tab.click()
@@ -564,10 +565,9 @@ class TestCommunityMultipleDeviceMerged(MultipleSharedDeviceTestCase):
self.channel_1.send_message(self.text_message)
self.community_1, self.community_2 = self.home_1.get_community_view(), self.home_2.get_community_view()
self.community_1.send_invite_to_community(self.community_name, self.username_2)
self.community_1.share_community(self.community_name, self.username_2)
self.home_1.get_to_community_channel_from_home(self.community_name)
# self.chat_2 = self.home_2.get_chat(self.username_1).click()
self.home_2.just_fyi("Send message to contact (need for blocking contact) test")
self.chat_2.send_message(self.text_message)
self.chat_2.chat_element_by_text(self.community_name).view_community_button.click()
@@ -978,9 +978,9 @@ class TestCommunityMultipleDeviceMerged(MultipleSharedDeviceTestCase):
@marks.testrail_id(703086)
def test_community_mark_all_messages_as_read(self):
self.home_1.jump_to_communities_home()
self.channel_2.click_system_back_button_until_element_is_shown()
self.home_2.communities_tab.click()
for home in self.home_1, self.home_2:
home.click_system_back_button_until_element_is_shown()
home.communities_tab.click()
self.home_2.get_chat(self.community_name, community=True).click()
self.community_2.get_channel(self.channel_name).click()
self.channel_2.send_message(self.text_message)
@@ -1144,8 +1144,6 @@ class TestCommunityMultipleDeviceMerged(MultipleSharedDeviceTestCase):
self.errors.append('Community is still shown in the list after leave')
self.errors.verify_no_errors()
@marks.xfail(reason="Can't invite user to closed community https://github.com/status-im/status-mobile/issues/16968",
run=False)
@marks.testrail_id(702948)
def test_community_hashtag_links_to_community_channels(self):
for home in self.homes:
@@ -1156,7 +1154,7 @@ class TestCommunityMultipleDeviceMerged(MultipleSharedDeviceTestCase):
self.home_1.just_fyi("Device 1 creates a closed community")
self.home_1.create_community(community_type="closed")
community_name = "closed community"
self.community_1.send_invite_to_community(community_name, self.username_2)
self.community_1.share_community(community_name, self.username_2)
self.home_2.just_fyi("Device 2 joins the community")
self.home_2.get_chat(self.username_1).click()
@@ -1165,31 +1163,40 @@ class TestCommunityMultipleDeviceMerged(MultipleSharedDeviceTestCase):
self.chat_2.chat_element_by_text(community_name).view_community_button.click()
self.community_2.join_community()
self.home_1.just_fyi("Device 1 accepts the community request")
self.home_1.jump_to_communities_home()
try:
self.home_1.notifications_unread_badge.wait_for_visibility_of_element(120)
except TimeoutException:
self.errors.append("Unread indicator is not shown in notifications on membership request")
self.home_1.open_activity_center_button.click()
reply_element = self.home_1.get_element_from_activity_center_view(self.username_2)
reply_element.swipe_right_on_element()
self.home_1.activity_notification_swipe_button.click()
self.home_1.close_activity_centre.click()
dogs_channel, cats_channel = "dogs", "cats"
cats_message = "Where is a cat?"
self.home_1.just_fyi("Device 1 sends a message in the cats channel")
self.home_1.get_to_community_channel_from_home(community_name=community_name, channel_name=cats_channel)
self.channel_1.send_message(cats_message)
self.channel_1.click_system_back_button_until_element_is_shown(
element=self.community_1.get_channel(dogs_channel))
self.channel_1.jump_to_communities_home()
self.home_1.get_to_community_channel_from_home(community_name=community_name, channel_name=dogs_channel)
self.home_1.just_fyi("Device 1 sends a message with hashtag in the dogs channel")
self.community_1.get_channel(dogs_channel).click_until_presence_of_element(self.channel_1.chat_message_input)
message_with_hashtag = "#cats"
self.channel_1.send_message(message_with_hashtag)
self.home_2.just_fyi("Device 2 clicks on the message with hashtag in the community channel")
self.community_2.get_channel(dogs_channel).click_until_presence_of_element(self.channel_2.chat_message_input)
self.channel_2.chat_element_by_text(message_with_hashtag).message_body.wait_for_visibility_of_element(30)
self.channel_2.chat_element_by_text(message_with_hashtag).message_body.click_inside_element_by_coordinate(
rel_x=0.2, rel_y=0.5)
self.home_2.jump_to_communities_home()
self.home_2.get_to_community_channel_from_home(community_name, dogs_channel)
self.channel_2.chat_element_by_text(message_with_hashtag).click_on_link_inside_message_body()
if not self.channel_2.chat_element_by_text(cats_message).is_element_displayed(30):
self.errors.append("Receiver was not navigated to the cats channel")
self.home_1.just_fyi("Device 1 clicks on the message with hashtag in the community channel")
self.channel_1.chat_element_by_text(message_with_hashtag).message_body.click_inside_element_by_coordinate(
rel_x=0.2, rel_y=0.5)
self.channel_1.chat_element_by_text(message_with_hashtag).click_on_link_inside_message_body()
if not self.channel_1.chat_element_by_text(cats_message).is_element_displayed(30):
self.errors.append("Sender was not navigated to the cats channel")
@@ -1201,15 +1208,12 @@ class TestCommunityMultipleDeviceMerged(MultipleSharedDeviceTestCase):
self.home_1.just_fyi("Device 1 clicks on the message with hashtag in 1-1 chat")
self.home_1.get_chat(self.username_2).click()
self.chat_1.chat_element_by_text(message_with_hashtag).message_body.wait_for_visibility_of_element(30)
self.chat_1.chat_element_by_text(message_with_hashtag).message_body.click_inside_element_by_coordinate(
rel_x=0.2, rel_y=0.5)
self.chat_1.chat_element_by_text(message_with_hashtag).click_on_link_inside_message_body()
if self.chat_1.chat_element_by_text(control_message_1_1_chat).is_element_disappeared():
self.errors.append("Receiver was navigated out of 1-1 chat")
self.home_2.just_fyi("Device 2 clicks on the message with hashtag in 1-1 chat")
self.chat_2.chat_element_by_text(message_with_hashtag).message_body.click_inside_element_by_coordinate(
rel_x=0.2, rel_y=0.5)
self.chat_2.chat_element_by_text(message_with_hashtag).click_on_link_inside_message_body()
if self.chat_2.chat_element_by_text(control_message_1_1_chat).is_element_disappeared():
self.errors.append("Sender was navigated out of 1-1 chat")
@@ -168,7 +168,7 @@ class TestActivityMultipleDevicePR(MultipleSharedDeviceTestCase):
self.channel_1.send_message(self.text_message)
self.community_1, self.community_2 = self.home_1.get_community_view(), self.home_2.get_community_view()
self.community_1.send_invite_to_community(self.community_name, self.username_2)
self.community_1.share_community(self.community_name, self.username_2)
self.home_1.get_to_community_channel_from_home(self.community_name)
self.chat_2 = self.home_2.get_chat(self.username_1).click()
@@ -321,8 +321,7 @@ class TestActivityMultipleDevicePR(MultipleSharedDeviceTestCase):
self.channel_name = "dogs"
self.home_1.create_community(community_type="closed")
self.home_1.reopen_app()
community_element = self.home_1.get_chat(community_name, community=True)
self.community_1.share_community(community_element, self.username_2)
self.community_1.share_community(community_name, self.username_2)
self.home_2.just_fyi("Request access to community")
self.home_2.jump_to_messages_home()
@@ -191,7 +191,7 @@ class TestBrowserProfileOneDevice(MultipleSharedDeviceTestCase):
self.home.just_fyi("Check it via 'Invite friends' on home view")
self.home.invite_friends_button.click()
self.home.share_via_messenger()
if not self.home.element_by_text_part('Hey join me on Status: https://status.app/u/%s' % chat_key).is_element_displayed(20):
if not self.home.element_by_text_part('Hey join me on Status: https://join.status.im/u/%s' % chat_key).is_element_displayed(20):
self.errors.append("No expected message in input field when sharing via 'Invite friend'")
self.home.click_system_back_button_until_element_is_shown()
@@ -199,7 +199,7 @@ class TestBrowserProfileOneDevice(MultipleSharedDeviceTestCase):
self.home.plus_button.click()
self.home.chats_menu_invite_friends_button.click()
self.home.share_via_messenger()
if not self.home.element_by_text_part('Hey join me on Status: https://status.app/u/%s' % chat_key).is_element_displayed(20):
if not self.home.element_by_text_part('Hey join me on Status: https://join.status.im/u/%s' % chat_key).is_element_displayed(20):
self.errors.append("No expected message in input field when sharing via 'bottom sheet'")
self.home.click_system_back_button_until_element_is_shown()
self.errors.verify_no_errors()
@@ -215,7 +215,7 @@ class TestBrowserProfileOneDevice(MultipleSharedDeviceTestCase):
users = {
'scanning_ens_with_stateofus_domain_deep_link': {
'contact_code': 'https://status.app/u/%s.stateofus.eth' % ens_user_message_sender['ens'],
'contact_code': 'https://join.status.im/u/%s.stateofus.eth' % ens_user_message_sender['ens'],
'username': ens_user_message_sender['username']
},
'scanning_public_key': {
@@ -96,7 +96,7 @@ class TestDeeplinkChatProfileOneDevice(MultipleSharedDeviceTestCase):
chat.share_button.click()
chat.share_via_messenger()
if not chat.element_by_text_part(
'https://status.app/u/%s' % dummy_user["public_key"]).is_element_displayed():
'https://join.status.im/u/%s' % dummy_user["public_key"]).is_element_displayed():
self.errors.append("Can't share public key of contact")
for _ in range(2):
chat.click_system_back_button_until_element_is_shown()
@@ -112,7 +112,7 @@ class TestDeeplinkChatProfileOneDevice(MultipleSharedDeviceTestCase):
self.public_chat.share_chat_button.click()
self.public_chat.share_via_messenger()
if not self.public_chat.element_by_text_part(
'https://status.app/%s' % self.public_chat_name).is_element_displayed():
'https://join.status.im/%s' % self.public_chat_name).is_element_displayed():
self.errors.append("Can't share link to public chat")
for _ in range(2):
self.public_chat.click_system_back_button_until_element_is_shown()
@@ -127,8 +127,8 @@ class TestDeeplinkChatProfileOneDevice(MultipleSharedDeviceTestCase):
browser.options_button.click()
browser.share_url_button.click()
browser.share_via_messenger()
expeceted_text_1 = 'https://status.app/b/https://dap.ps'
expeceted_text_2 = 'https://status.app/b/http://dap.ps'
expeceted_text_1 = 'https://join.status.im/b/https://dap.ps'
expeceted_text_2 = 'https://join.status.im/b/http://dap.ps'
if not (browser.element_by_text_part(expeceted_text_1).is_element_displayed() or
browser.element_by_text_part(expeceted_text_2).is_element_displayed()):
@@ -389,11 +389,11 @@ class TestDeeplinkChatProfileOneDevice(MultipleSharedDeviceTestCase):
# url_data = {
# 'ens_with_stateofus_domain_deep_link': {
# 'url': 'https://status.app/u/%s.stateofus.eth' % ens_user_message_sender['ens'],
# 'url': 'https://join.status.im/u/%s.stateofus.eth' % ens_user_message_sender['ens'],
# 'username': '@%s' % ens_user_message_sender['ens']
# },
# 'ens_without_stateofus_domain_deep_link': {
# 'url': 'https://status.app/u/%s' % ens_user_message_sender['ens'],
# 'url': 'https://join.status.im/u/%s' % ens_user_message_sender['ens'],
# 'username': '@%s' % ens_user_message_sender['ens']
# },
# 'ens_another_domain_deep_link': {
@@ -401,15 +401,15 @@ class TestDeeplinkChatProfileOneDevice(MultipleSharedDeviceTestCase):
# 'username': '@%s' % ens_user['ens']
# },
# 'own_profile_key_deep_link': {
# 'url': 'https://status.app/u/%s' % self.public_key,
# 'url': 'https://join.status.im/u/%s' % self.public_key,
# 'error': "That's you"
# },
# 'other_user_profile_key_deep_link': {
# 'url': 'https://status.app/u/%s' % transaction_senders['M']['public_key'],
# 'url': 'https://join.status.im/u/%s' % transaction_senders['M']['public_key'],
# 'username': transaction_senders['M']['username']
# },
# 'other_user_profile_key_deep_link_invalid': {
# 'url': 'https://status.app/u/%sinvalid' % ens_user['public_key'],
# 'url': 'https://join.status.im/u/%sinvalid' % ens_user['public_key'],
# 'error': 'Please enter or scan a valid chat key'
# },
# 'own_profile_key': {
@@ -155,11 +155,11 @@ class TestPermissionsScanQrOneDevice(MultipleSharedDeviceTestCase):
url_data = {
'ens_with_stateofus_domain_deep_link': {
'url': 'https://status.app/u/%s.stateofus.eth' % ens_user_message_sender['ens'],
'url': 'https://join.status.im/u/%s.stateofus.eth' % ens_user_message_sender['ens'],
'username': '@%s' % ens_user_message_sender['ens']
},
'ens_without_stateofus_domain_deep_link': {
'url': 'https://status.app/u/%s' % ens_user_message_sender['ens'],
'url': 'https://join.status.im/u/%s' % ens_user_message_sender['ens'],
'username': '@%s' % ens_user_message_sender['ens']
},
'ens_another_domain_deep_link': {
@@ -167,15 +167,15 @@ class TestPermissionsScanQrOneDevice(MultipleSharedDeviceTestCase):
'username': '@%s' % ens_user['ens']
},
'own_profile_key_deep_link': {
'url': 'https://status.app/u/%s' % self.public_key,
'url': 'https://join.status.im/u/%s' % self.public_key,
'error': "That's you"
},
'other_user_profile_key_deep_link': {
'url': 'https://status.app/u/%s' % transaction_senders['M']['public_key'],
'url': 'https://join.status.im/u/%s' % transaction_senders['M']['public_key'],
'username': transaction_senders['M']['username']
},
'other_user_profile_key_deep_link_invalid': {
'url': 'https://status.app/u/%sinvalid' % ens_user['public_key'],
'url': 'https://join.status.im/u/%sinvalid' % ens_user['public_key'],
'error': 'Please enter or scan a valid chat key'
},
'own_profile_key': {
@@ -225,7 +225,7 @@ class TestPermissionsScanQrOneDevice(MultipleSharedDeviceTestCase):
url_data = {
'ens_without_stateofus_domain_deep_link': {
'url': 'https://status.app/u/%s' % ens_user_message_sender['ens'],
'url': 'https://join.status.im/u/%s' % ens_user_message_sender['ens'],
'username': '@%s' % ens_user_message_sender['ens']
},
@@ -234,7 +234,7 @@ class TestPermissionsScanQrOneDevice(MultipleSharedDeviceTestCase):
'username': basic_user['username']
},
'other_user_profile_key_deep_link_invalid': {
'url': 'https://status.app/u/%sinvalid' % ens_user['public_key'],
'url': 'https://join.status.im/u/%sinvalid' % ens_user['public_key'],
'error': 'Unable to read this code'
},
'own_profile_key': {
@@ -265,13 +265,13 @@ class TestPermissionsScanQrOneDevice(MultipleSharedDeviceTestCase):
},
},
'dapp_deep_link': {
'url': 'https://status.app/b/%s' % test_dapp_url,
'url': 'https://join.status.im/b/%s' % test_dapp_url,
},
'dapp_deep_link_https': {
'url': 'https://status.app/b/%s' % test_dapp_url,
'url': 'https://join.status.im/b/%s' % test_dapp_url,
},
'public_chat_deep_link': {
'url': 'https://status.app/baga-ma-2020',
'url': 'https://join.status.im/baga-ma-2020',
'chat_name': 'baga-ma-2020'
},
}
+17 -8
View File
@@ -604,19 +604,28 @@ class BaseView(object):
sign_in_view = self.get_sign_in_view()
sign_in_view.sign_in(password)
def jump_to_messages_home(self):
def click_on_floating_jump_to(self):
self.hide_keyboard_if_shown()
self.jump_to_button.click()
self.chats_tab.click_until_presence_of_element(self.jump_to_button)
if self.chat_floating_screen.is_element_displayed(1):
Button(self.driver, xpath='//*[@content-desc="%s"]//*[@content-desc="%s"]' %
(self.chat_floating_screen.accessibility_id, self.jump_to_button.accessibility_id)).click()
elif self.community_floating_screen.is_element_displayed(1):
Button(self.driver, xpath='//*[@content-desc="%s"]//*[@content-desc="%s"]' %
(self.community_floating_screen.accessibility_id,
self.jump_to_button.accessibility_id)).click()
else:
self.jump_to_button.click()
def jump_to_messages_home(self):
self.click_on_floating_jump_to()
self.chats_tab.click()
def jump_to_communities_home(self):
self.hide_keyboard_if_shown()
self.jump_to_button.click()
self.communities_tab.click_until_presence_of_element(self.jump_to_button)
self.click_on_floating_jump_to()
self.communities_tab.click()
def jump_to_card_by_text(self, text: str):
self.hide_keyboard_if_shown()
self.jump_to_button.click()
self.click_on_floating_jump_to()
self.element_by_text(text).click()
def reopen_app(self, password=common_password, sign_in=True):
+13 -4
View File
@@ -183,6 +183,10 @@ class ChatElementByText(Text):
xpath="//%s//android.widget.TextView[contains(@text,'%s')]" % (self.chat_item_locator, self.message_text)
)
def click_on_link_inside_message_body(self):
self.message_body.wait_for_visibility_of_element(30)
self.message_body.click_inside_element_by_coordinate(rel_x=0.1, rel_y=0.9)
def wait_for_sent_state(self, wait_time=30):
return BaseElement(self.driver, prefix=self.locator,
xpath="//*[@content-desc='message-sent']").is_element_displayed(wait_time)
@@ -442,8 +446,8 @@ class CommunityView(HomeView):
self.driver.info("Copy community link")
self.community_options_button.click()
self.community_info_button.click()
self.element_starts_with_text('status.app/c/').click()
community_link_text = self.element_starts_with_text('status.app/c/').text
self.element_starts_with_text('join.status.im/c/').click()
community_link_text = self.element_starts_with_text('join.status.im/c/').text
self.home_button.double_click()
return 'https://%s' % community_link_text
@@ -458,6 +462,7 @@ class CommunityView(HomeView):
Button(self.driver, xpath="//*[starts-with(@text,'%s')]%s" % (username, decline_suffix)).click()
self.close_button.click()
# Should not be used anymore, outdated flow
def send_invite_to_community(self, community_name, user_names_to_invite):
if isinstance(user_names_to_invite, str):
user_names_to_invite = [user_names_to_invite]
@@ -474,11 +479,15 @@ class CommunityView(HomeView):
self.share_invite_button.click_until_presence_of_element(self.invite_button)
self.back_button.click_until_presence_of_element(self.plus_button)
def share_community(self, coummunity_element, user_names_to_share):
def share_community(self, community_name, user_names_to_share):
if isinstance(user_names_to_share, str):
user_names_to_share = [user_names_to_share]
self.driver.info("Share to %s community" % ', '.join(map(str, user_names_to_share)))
coummunity_element.long_press_until_element_is_shown(self.share_community_button)
self.jump_to_communities_home()
home = self.get_home_view()
community_element = home.get_chat(community_name, community=True)
# community_element.long_press_until_element_is_shown(self.view_members_button)
community_element.long_press_until_element_is_shown(self.share_community_button)
self.share_community_button.click()
for user_name in user_names_to_share:
user_contact = self.element_by_text_part(user_name)
+2 -2
View File
@@ -4,7 +4,7 @@ main = {
'messages': {
'text': 'before upgrade',
'reply': 'reply',
'invite': 'https://status.app/g/args?a=0x04359bb3e73cba0b815d71e562670ad00bb5d2db0d16cd1c4c92c668b61fde2274d6e487fcdffe66f913b3fea2a3058f53ce7946c2b501aa61a9ca8a883df72dc9&a1=empty&a2=a935c4fa-5530-407c-84c2-61512120d504-0x04359bb3e73cba0b815d71e562670ad00bb5d2db0d16cd1c4c92c668b61fde2274d6e487fcdffe66f913b3fea2a3058f53ce7946c2b501aa61a9ca8a883df72dc9'
'invite': 'https://join.status.im/g/args?a=0x04359bb3e73cba0b815d71e562670ad00bb5d2db0d16cd1c4c92c668b61fde2274d6e487fcdffe66f913b3fea2a3058f53ce7946c2b501aa61a9ca8a883df72dc9&a1=empty&a2=a935c4fa-5530-407c-84c2-61512120d504-0x04359bb3e73cba0b815d71e562670ad00bb5d2db0d16cd1c4c92c668b61fde2274d6e487fcdffe66f913b3fea2a3058f53ce7946c2b501aa61a9ca8a883df72dc9'
}
}
to_join = {
@@ -32,7 +32,7 @@ make_admin = {
}
timeline = {
'link': 'https://status.app/u/0x045efbcc044e5ae21ac3cf111ea6df6186e0cc50a2cd747f52a56d19ce516e683c66cb47f4b0a21110859aea9592dfba1e0bf4af11ff3eab995f844b3673643bf1',
'link': 'https://join.status.im/u/0x045efbcc044e5ae21ac3cf111ea6df6186e0cc50a2cd747f52a56d19ce516e683c66cb47f4b0a21110859aea9592dfba1e0bf4af11ff3eab995f844b3673643bf1',
'text': 'Hey there!',
'resolved_username': ens_user_message_sender['username']
+4 -2
View File
@@ -7,6 +7,8 @@ communities = {
'member_closed': 'test_comm_enc',
'member_pending': 'RC1 testing community'
}
# contacts = ['Test_contact', 'MyCustomNickname'] # enable back when https://github.com/status-im/status-mobile/issues/15500 is fixed
contacts = ['Used Bulky Wirehair', 'Vengeful Healthy Arcticseal']
#contacts = ['Test_contact', 'MyCustomNickname'] # enable back when https://github.com/status-im/status-mobile/issues/15500 is fixed
contacts = ['zQ3...rLSpUs', 'zQ3...mxAZUU']
blocked_user = 'Clear Flat Milkweedbug'
Binary file not shown.

Before

Width:  |  Height:  |  Size: 8.4 KiB

After

Width:  |  Height:  |  Size: 7.2 KiB

-1
View File
@@ -303,7 +303,6 @@ class HomeView(BaseView):
# New UI
self.new_chat_button = Button(self.driver, accessibility_id="new-chat-button")
self.jump_to_button = Button(self.driver, accessibility_id="jump-to")
self.discover_communities_button = Button(self.driver, accessibility_id="communities-home-discover-card")
# New UI bottom sheet