diff --git a/.re-natal b/.re-natal index 8fd652b4ea..38d8997409 100644 --- a/.re-natal +++ b/.re-natal @@ -1,7 +1,7 @@ { "name": "SyngIm", "interface": "reagent", - "androidHost": "10.0.3.2", + "androidHost": "10.0.2.2", "modules": [ "react-native-contacts", "react-native-invertible-scroll-view", @@ -13,7 +13,8 @@ "react-native-action-button", "react-native-vector-icons/Ionicons", "react-native-circle-checkbox", - "react-native-randombytes" + "react-native-randombytes", + "react-native-carousel-control" ], "imageDirs": [ "images" diff --git a/README.md b/README.md index 19e1fbc53f..65349be5fc 100644 --- a/README.md +++ b/README.md @@ -4,7 +4,24 @@ A Clojure library designed to ... well, that part is up to you. ## Usage -FIXME +- install syng-lib/protocol in lein + +Linux: + +optional: $ npm upgrade -g re-natal +optional: $ re-natal upgrade +$ re-natal deps +$ re-natal use-android-device +$ re-natal use-figwheel +$ lein figwheel android + +- new terminal(only for linux) +$ react-native start + +- new terminal +$ adb reverse tcp:8081 tcp:8081 +$ adb reverse tcp:3449 tcp:3449 +$ react-native run-android ## License diff --git a/env/dev/env/android/main.cljs b/env/dev/env/android/main.cljs index 2348604c4a..5519aa004d 100644 --- a/env/dev/env/android/main.cljs +++ b/env/dev/env/android/main.cljs @@ -11,7 +11,7 @@ (def root-el (r/as-element [reloader])) (figwheel/watch-and-reload - :websocket-url "ws://10.0.3.2:3449/figwheel-ws" + :websocket-url "ws://10.0.2.2:3449/figwheel-ws" :heads-up-display true :jsload-callback #(swap! cnt inc)) diff --git a/figwheel-bridge.js b/figwheel-bridge.js index 2a7cb1cc2f..6df4702339 100644 --- a/figwheel-bridge.js +++ b/figwheel-bridge.js @@ -5,6 +5,7 @@ */ var CLOSURE_UNCOMPILED_DEFINES = null; +var debugEnabled = false; var config = { basePath: "target/", @@ -13,13 +14,24 @@ var config = { }; var React = require('react-native'); +var WebSocket = require('WebSocket'); var self; var scriptQueue = []; var serverHost = null; // will be set dynamically var fileBasePath = null; // will be set dynamically var evaluate = eval; // This is needed, direct calls to eval does not work (RN packager???) var externalModules = {}; -var evalListeners = []; // functions to be called when a script is evaluated +var evalListeners = [ // Functions to be called after each js file is loaded and evaluated + function (url) { + if (url.indexOf('jsloader') > -1) { + shimJsLoader(); + } + }, + function (url) { + if (url.indexOf('/figwheel/client/socket') > -1) { + setCorrectWebSocketImpl(); + } + }]; var figwheelApp = function (platform, devHost) { return React.createClass({ @@ -40,7 +52,7 @@ var figwheelApp = function (platform, devHost) { componentDidMount: function () { var app = this; if (typeof goog === "undefined") { - loadApp(platform, devHost, function(appRoot) { + loadApp(platform, devHost, function (appRoot) { app.setState({root: appRoot, loaded: true}) }); } @@ -48,13 +60,19 @@ var figwheelApp = function (platform, devHost) { }) }; +function logDebug(msg) { + if (debugEnabled) { + console.log(msg); + } +} + // evaluates js code ensuring proper ordering function customEval(url, javascript, success, error) { if (scriptQueue.length > 0) { if (scriptQueue[0] === url) { try { evaluate(javascript); - console.info('Evaluated: ' + url); + logDebug('Evaluated: ' + url); scriptQueue.shift(); evalListeners.forEach(function (listener) { listener(url) @@ -81,7 +99,7 @@ var isChrome = function () { }; function asyncImportScripts(url, success, error) { - console.info('(asyncImportScripts) Importing: ' + url); + logDebug('(asyncImportScripts) Importing: ' + url); scriptQueue.push(url); fetch(url) .then(function (response) { @@ -100,7 +118,7 @@ function asyncImportScripts(url, success, error) { function syncImportScripts(url, success, error) { try { importScripts(url); - console.info('Evaluated: ' + url); + logDebug('Evaluated: ' + url); evalListeners.forEach(function (listener) { listener(url) }); @@ -123,7 +141,7 @@ function importJs(src, success, error) { var file = fileBasePath + '/' + src; - console.info('(importJs) Importing: ' + file); + logDebug('(importJs) Importing: ' + file); if (isChrome()) { syncImportScripts(serverBaseUrl("localhost") + '/' + file, success, error); } else { @@ -143,43 +161,49 @@ function interceptRequire() { }; } -// do not show debug messages in yellow box -function debugToLog() { - console.debug = console.log; +function compileWarningsToYellowBox() { + var log = window.console.log; + var compileWarningRx = /Figwheel: Compile/; + window.console.log = function (msg) { + if (compileWarningRx.test(msg)) { + console.warn(msg); + } else { + log.call(window.console, msg); + } + }; } function serverBaseUrl(host) { return "http://" + host + ":" + config.serverPort } +function setCorrectWebSocketImpl() { + figwheel.client.socket.get_websocket_imp = function () { + return WebSocket; + }; +} + function loadApp(platform, devHost, onLoadCb) { serverHost = devHost; fileBasePath = config.basePath + platform; - evalListeners.push(function (url) { - if (url.indexOf('jsloader') > -1) { - shimJsLoader(); - } - }); - // callback when app is ready to get the reloadable component var mainJs = '/env/' + platform + '/main.js'; evalListeners.push(function (url) { if (url.indexOf(mainJs) > -1) { onLoadCb(env[platform].main.root_el); - console.log('Done loading Clojure app'); + console.info('Done loading Clojure app'); } }); if (typeof goog === "undefined") { - console.log('Loading Closure base.'); + console.info('Loading Closure base.'); interceptRequire(); + compileWarningsToYellowBox(); importJs('goog/base.js', function () { shimBaseGoog(); - fakeLocalStorageAndDocument(); importJs('cljs_deps.js'); importJs('goog/deps.js', function () { - debugToLog(); // This is needed because of RN packager // seriously React packager? why. var googreq = goog.require; @@ -209,39 +233,6 @@ function shimBaseGoog() { importJs(src); return true; }; - goog.inHtmlDocument_ = function () { - return true; - }; -} - -function fakeLocalStorageAndDocument() { - window.localStorage = {}; - window.localStorage.getItem = function () { - return 'true'; - }; - window.localStorage.setItem = function () { - }; - - window.document = {}; - window.document.body = {}; - window.document.body.dispatchEvent = function () { - }; - window.document.createElement = function () { - }; - - if (typeof window.location === 'undefined') { - window.location = {}; - } - console.debug = console.warn; - window.addEventListener = function () { - }; - // make figwheel think that heads-up-display divs are there - window.document.querySelector = function (selector) { - return {}; - }; - window.document.getElementById = function (id) { - return {style:{}}; - }; } // Figwheel fixes diff --git a/package.json b/package.json index f069c032a4..bb1a49ac6a 100644 --- a/package.json +++ b/package.json @@ -9,6 +9,7 @@ "awesome-phonenumber": "^1.0.12", "react-native": "^0.22.0", "react-native-action-button": "^1.1.3", + "react-native-carousel-control": "^1.0.1", "react-native-circle-checkbox": "^0.1.3", "react-native-contacts": "^0.2.1", "react-native-i18n": "0.0.8", diff --git a/src/syng_im/android/core.cljs b/src/syng_im/android/core.cljs index 83fbd67e02..d4e74d348e 100644 --- a/src/syng_im/android/core.cljs +++ b/src/syng_im/android/core.cljs @@ -8,6 +8,7 @@ [syng-im.subs] [syng-im.components.react :refer [navigator app-registry]] [syng-im.components.contact-list.contact-list :refer [contact-list]] + [syng-im.components.discovery.discovery :refer [discovery]] [syng-im.components.chat :refer [chat]] [syng-im.components.sign-up :refer [sign-up-view]] [syng-im.components.sign-up-confirm :refer [sign-up-confirm-view]] @@ -34,7 +35,7 @@ (add-event-listener "hardwareBackPress" new-listener))))) (defn app-root [] - [navigator {:initial-route (clj->js {:view-id :chat-list}) + [navigator {:initial-route (clj->js {:view-id :discovery}) :render-scene (fn [route nav] (log/debug "route" route) (when true ;; nav/*nav-render* @@ -42,6 +43,7 @@ view-id (keyword view-id)] (init-back-button-handler! nav) (case view-id + :discovery (r/as-element [discovery {:navigator nav}]) :chat-list (r/as-element [chats-list {:navigator nav}]) :new-group (r/as-element [new-group {:navigator nav}]) :contact-list (r/as-element [contact-list {:navigator nav}]) @@ -51,6 +53,7 @@ (defn init [] (dispatch-sync [:initialize-db]) + ;;(dispatch-sync [:generate-discoveries]) (dispatch [:initialize-crypt]) (dispatch [:initialize-protocol]) (dispatch [:load-user-phone-number]) diff --git a/src/syng_im/components/react.cljs b/src/syng_im/components/react.cljs index a9f31957b7..020f657e7a 100644 --- a/src/syng_im/components/react.cljs +++ b/src/syng_im/components/react.cljs @@ -12,6 +12,7 @@ (def toolbar-android (r/adapt-react-class (.-ToolbarAndroid js/React))) (def list-view (r/adapt-react-class (.-ListView js/React))) (def text-input (r/adapt-react-class (.-TextInput js/React))) +(def scroll-view (r/adapt-react-class (.-ScrollView js/React))) (def platform (.. js/React -Platform -OS)) diff --git a/src/syng_im/db.cljs b/src/syng_im/db.cljs index 3f404f3b33..20be9042e8 100644 --- a/src/syng_im/db.cljs +++ b/src/syng_im/db.cljs @@ -28,3 +28,6 @@ (defn chat-command-content-path [chat-id] [:chats chat-id :command-input :content]) (def new-group-path [:new-group]) +(def updated-discovery-signal-path [:discovery-updated-signal]) +(defn updated-discovery-signal-path [discovery-id] + [:discoveries discovery-id :discovery-updated-signal]) diff --git a/src/syng_im/handlers.cljs b/src/syng_im/handlers.cljs index fc462f3ea7..97087f6f5e 100644 --- a/src/syng_im/handlers.cljs +++ b/src/syng_im/handlers.cljs @@ -9,6 +9,7 @@ set-initialized]] [syng-im.models.user-data :as user-data] [syng-im.models.contacts :as contacts] + [syng-im.models.discoveries :as discoveries] [syng-im.models.messages :refer [save-message update-message! message-by-id]] @@ -274,6 +275,12 @@ (log/debug action from group-id identities) (create-chat db group-id identities true group-name))) +;; -- Discovery -------------------------------------------------------------- + +(register-handler :generate-discoveries + (fn [db _] + (discoveries/save-discoveries (discoveries/generate-discoveries 10)))) + (comment ) diff --git a/src/syng_im/persistence/realm.cljs b/src/syng_im/persistence/realm.cljs index 694ff7af16..3007a23a42 100644 --- a/src/syng_im/persistence/realm.cljs +++ b/src/syng_im/persistence/realm.cljs @@ -44,7 +44,24 @@ :group-chat "bool" :timestamp "int" :contacts {:type "list" - :objectType "chat-contact"}}}]}) + :objectType "chat-contact"}}} + {:name :tag + :primaryKey :name + :properties {:name "string" + :count {:type "int" + :optional true + :default 1}}} + {:name :discoveries + :primaryKey :whisper-id + :properties {:name "string" + :status "string" + :whisper-id "string" + :photo "string" + :tags {:type "list" + :objectType "tag"} + :last-updated "date"}} + + ]}) (def realm (js/Realm. (clj->js opts))) @@ -122,7 +139,7 @@ (.-length objs)) (defn get-list [schema-name] - (vals (js->clj (.objects realm (to-string schema-name)) :keywordize-keys true))) + (vals (js->clj (.slice (.objects realm (to-string schema-name)) 0) :keywordize-keys true))) (comment diff --git a/src/syng_im/resources.cljs b/src/syng_im/resources.cljs index 52a956d3f6..086e68d7da 100644 --- a/src/syng_im/resources.cljs +++ b/src/syng_im/resources.cljs @@ -13,3 +13,5 @@ (def smile (js/require "./images/smile.png")) (def att (js/require "./images/att.png")) (def v (js/require "./images/v.png")) +(def menu (js/require "./images/ic_menu_black_24dp_1x.png")) +(def search (js.require "./images/ic_search_black_24dp_1x.png")) \ No newline at end of file diff --git a/src/syng_im/subs.cljs b/src/syng_im/subs.cljs index 2b13739689..6f0bb82ebb 100644 --- a/src/syng_im/subs.cljs +++ b/src/syng_im/subs.cljs @@ -7,6 +7,8 @@ [syng-im.models.chats :refer [chats-list chats-updated? chat-by-id]] + [syng-im.models.discoveries :refer [discovery-list + discovery-updated?]] [syng-im.models.messages :refer [get-messages]] [syng-im.models.contacts :refer [contacts-list]] [syng-im.handlers.suggestions :refer [get-suggestions]])) @@ -63,6 +65,16 @@ (chat-by-id chat-id)) (reaction))))) +;; -- Discoveries list -------------------------------------------------------------- + +(register-sub :get-discoveries + (fn [db _] + (let [discovery-updated (-> (discovery-updated? @db) + (reaction))] + (reaction + (let [_ @discovery-updated] + (discovery-list)))))) + ;; -- User data -------------------------------------------------------------- (register-sub