From 5d18c714758bdc64b03005d171174c9de8e26439 Mon Sep 17 00:00:00 2001 From: or-else Date: Wed, 20 Sep 2017 15:01:19 -0700 Subject: [PATCH] add green dot to shortcut icon to indicate unread messages --- README.md | 4 ++-- img/logo32x32.png | Bin 1218 -> 2066 bytes index.html | 23 +++++++++++++++++++---- 3 files changed, 21 insertions(+), 6 deletions(-) diff --git a/README.md b/README.md index 36e11a0f..145913f7 100644 --- a/README.md +++ b/README.md @@ -6,7 +6,7 @@ and [icons](https://google.github.io/material-design-icons/#icon-font-for-the-we This is work in progress. Bugs are expected. The app was tested in the latest Chrome & Firefox only. -Try it (possibly newer or older version) live at https://api.tinode.co/x/example-react-js/. Login as one of `alice`, `bob`, `carol`, `dave`, `frank`. Password is `123`, e.g. password for `alice` is `alice123`. You can discover other users by email or phone by prefixing them with `email:` or `tel:` respectively. Emails are `@example.com`, e.g. `alice@example.com`, phones are `17025550001` through `17025550009`. The demo is reset every night at 2:15 am Pacific time. +Try possibly newer or older version live at https://api.tinode.co/x/example-react-js/. Login as one of `alice`, `bob`, `carol`, `dave`, `frank`. Password is `123`, e.g. password for `alice` is `alice123`. You can discover other users by email or phone by prefixing them with `email:` or `tel:` respectively. Emails are `@example.com`, e.g. `alice@example.com`, phones are `17025550001` through `17025550009`. The demo is reset every night at 2:15am Pacific time. License: [Apache 2.0](http://www.apache.org/licenses/LICENSE-2.0) @@ -20,7 +20,7 @@ Background pattern from http://subtlepatterns.com/, commercial and non-commercia * Cannot delete messages. * No indication of chat status (muted, blocked, etc.). * Browser push notifications are missing. -* No encryption. +* No end-to-end encryption. * Editing chat permissions is incomplete. ## Responsive design diff --git a/img/logo32x32.png b/img/logo32x32.png index 98636712f9b4744ffceb74f431e88c6f0a3e2544..cd4d256b374f7254238e5d1be087713904566377 100644 GIT binary patch literal 2066 zcmZvddpy(oAIImGOB{?)9A@rf7q{BXEpwR-{UohlP21RJ#kRI#6@KNgTuzc(h*2ln zk|OHlI6{`o(NAh_(a~}_IHjLMBBI|`opXMd^LaczxA*t;zC7QbKfalJLjtrkc4zC}tdl6wM@4AiOx1Obq~_cu3hXj>08@cyX}|4wB~q{-i+4&T=yp4EiMD9`gX> zgZF}bnQRKk72*Pcfju=qAP|ZjO+|*G{lB=&ZXVzmE|-ObLK71cA&JfqCYuI@BM=BE z%n9n`Atn$-jJd`$Y9Q8A{d~q%WI7;xgIcOlGX7oQTdi z#)%@aC~__o^nVq9R*I5`M252I6d9|W$Pc#ctDA1Nx-^?G3IJ7gwTn z3uC~j3#T7j`&(JBPAC~2@$&(;ukzas&Fo91P;v1h*r!rU3*WX;UT*d{kwz=AJ9Mak zXYJ0JdDJqq{-$ZB?9_oJRH)vCvlo?e3oG{3M!23BkB0|K^uB|?Cm1~P%Bc0eT7OY< zllBbD3MqGPtt{?-Eoz7}zH&?Srq7qE*#V1jSWq0>D!M!-O30cfzn*Hkwa_tWcDZM| zCK;R*)jNDWREzo2GiAM~yzpynl0@o%HJ=`!dED-{W!u3H&f$46^9cFXYy-YxhyP$r zm?O}8o%!({+AhG9vmo6s`Bs;RN$68r#@?|9K`1~!FT z(q5^(a|{9}+K!2h`n+l!*})Sqip z>Iv7_XxSLy&%oT=_{>7-87qPjrG*ka^NzZ6}5hcKHR4N)HmI=u?qcS(JX=N%9EPM{l zwxiRdb~hWjC%*Y+K>zi~W~zOy0;~&>V_|9w8Y?JTtsh`lBGSpCw4f?r0Xd--D^`l1 zcR3e!C-rjh&V|ue>#W&@Yf^#F-vl~CNqOkO(Inh9qK?#(JF?Bn zeD=&g$F>UBfNLo=v`H(qy{&=uIw>!O9~O#0uL95Z&Z;q2U__% zaLw0``Mz@~&I?I@>IhVRUY~4?XU%2=YNp4!9PRs2d3lb9|2{@N?6@8UtC4+r8Z*(e zZRGv0W4pOi!YuAdQFH*7XCd|8)u1Y#E=zu5N1AH`YTnh9N@-mr44|`$bsWJLMA})7 z=LuEU*oa0o%rM0-Hdms+o<}$<%n5g{9DsW{n|W+_^iLwcN^)5C&H+{zjHKq`ZQ#Fk zs+zqN?eBdujL@dowekz5N}_);Z3Ho<@0JB!d-8Mn!_vX?}@;Me56x}ZKQ72k>NKX9tx@ogOuPRg$JXwreC<~M=uoC@4S~Vf8E4%65rnfm@l8t zz^+%IUz5mW#mULZI)|+#xGe+%A%?*y+P}B5OjycoIvgpC#YCNdJ#1;9`>TDC19~uP zmbL_TYa!Rq_LRK5`=$|#OXb|%gIk)i733??BgP92^&6W1VS&f>ox9lF+&uVVsZ~Ld W1u9JbxgODw3F(Xh_sI<0B+$ zwY4At5wuNeYI>ox>lWDA>&zSn{0M+=KOxY&$;~0{EkpcMHd$re=rPV zx0F)jF-r)cRUT#QDeuLLiB-v>Y`Rs9!21kTnBB&DoA=W@9V zBAd0omf>NpE z=u%2uDMhhZWa#>5jAqByI>-m=h1ByL>wk|(B!Z@Cx`gFv|MS+3bq@|Ok{#vd?VHu5 zmP#pH*Clf=v+ltIE!}^`{_Xvw=hMv1&G98) zH#j+@AH=rpM}`PeSO|fXl2|N8I-Mq&Orq;LuInxX09ckqI-MpSk7HRD%rrXe?d_$b zqoYdSOn<)b<9Qyw?<1u|(=;?q!!Qg?)5I{0YTqh=5CYRQkx~+kMnfG(A`#l#+c8bE zX>iZ;SXj((?yK`mOiuCSwjSPn=WUY71*0yNXem1~^%3T(_>h;<^-z#m58iAPA)tp67+yc%Jw800M{)KOSnj z94i$Td`$oV!(+d5{M4C8hFCK|Sa$q!=?ceBox#cHTY^{>z;ipEXbSQE$=jh=B2mwD{YJ^ygR-J|cM0a;LM-Cle|DFNX zQY*J~4m3dQeYRzYmJgzp5QBRLTB?>B0Do#ftq*%w3-S8lgADF|Cfrsv|HOv^XqtxY zx7W4Xo*i0Htb}-J_dr7sP1iyPrj!Z?uq=!H#vrD@T=|&3!OO-VmSu&Gq<%SGW#Fkk zM6fFa?AtX^y$vFMbqkx0}*6bglVVs>`++jucX_k9Y50=Zm{ zQmKSxS;XUU+S=OcE|<+9a=9FL?%b)`rcxFMdShGD#> z>v|;U5EK_d{a0)JFnOMb=XtoUD<^baS3y-A$aUSK>$=}}b#)#4AE&0x&j{|`$^ZZW M07*qoM6N<$f@5JoJOBUy diff --git a/index.html b/index.html index ec4501f0..9b7cfbdf 100644 --- a/index.html +++ b/index.html @@ -4,7 +4,7 @@ Tinode example: chat web application in react.js - + @@ -75,6 +75,20 @@ 'data:image/' + photo.type + ';base64,' + photo.data : null; } + // Make shortcut icon appear with a green dot. + function updateFavicon(on) { + var oldIcon = document.getElementById("shortcut-icon"); + if (oldIcon) { + var head = document.head || document.getElementsByTagName('head')[0]; + var newIcon = document.createElement('link'); + newIcon.type = "image/png"; + newIcon.id = "shortcut-icon"; + newIcon.rel = "shortcut icon"; + newIcon.href = "img/logo32x32" + (on ? 'a' : '') + ".png"; + head.removeChild(oldIcon); + head.appendChild(newIcon); + } + } // Get 32 bit integer hash value for a string. Ideally it should produce the same value // as Java's String#hash(). function stringHash(value) { @@ -1067,7 +1081,6 @@ this.props.state === 'contacts' ? : @@ -1355,11 +1368,15 @@ prepareContactList: function() { var contacts = []; + var totalUnread = 0; Tinode.getMeTopic().contacts(function(c) { c.unread = c.seq - (c.read > 0 ? c.read : 0); + totalUnread += c.unread; contacts.push(c); }, this); + updateFavicon(totalUnread > 0); + return contacts; }, @@ -2800,7 +2817,6 @@ liveConnection: navigator.onLine, topicSelected: '', loginDisabled: false, - subscriptions: {}, displayMobile: (window.innerWidth <= MEDIA_BREAKPOINT), showInfoPanel: false, infoPanelShowMembers: false, @@ -3272,7 +3288,6 @@ state={this.state.sidePanelSelected} title={this.state.sidePanelTitle} avatar={this.state.sidePanelAvatar} - subscriptions={this.state.subscriptions} login={this.state.login} myUserId={this.state.myUserId} loginDisabled={this.state.loginDisabled}