From b6e2701991f491be98f1f99d6a959c91de7e769b Mon Sep 17 00:00:00 2001 From: Bettenbuk Zoltan Date: Tue, 26 Feb 2019 11:41:57 +0100 Subject: [PATCH] [RN] Add invite screen --- css/_font.scss | 12 + fonts/jitsi.eot | Bin 9732 -> 10472 bytes fonts/jitsi.svg | 4 + fonts/jitsi.ttf | Bin 9576 -> 10316 bytes fonts/jitsi.woff | Bin 9652 -> 10392 bytes fonts/selection.json | 2 +- lang/main.json | 10 + react/features/base/react/Types.js | 5 + .../react/components/native/BackButton.js | 2 +- .../react/components/native/ForwardButton.js | 70 +++ .../base/react/components/native/Header.js | 2 +- .../react/components/native/HeaderLabel.js | 18 +- .../base/react/components/native/index.js | 1 + .../base/react/components/native/styles.js | 22 +- .../components/native/Conference.js | 3 +- react/features/invite/actionTypes.js | 10 + react/features/invite/actions.js | 17 + .../components/AddPeopleDialog.native.js | 0 .../invite/components/InviteButton.native.js | 51 +- .../AbstractAddPeopleDialog.js | 222 +++++++++ .../add-people-dialog/index.native.js | 3 + .../components/add-people-dialog/index.web.js | 3 + .../native/AddPeopleDialog.js | 469 ++++++++++++++++++ .../add-people-dialog/native/index.js | 3 + .../add-people-dialog/native/styles.js | 91 ++++ .../web/AddPeopleDialog.js} | 203 ++------ .../components/add-people-dialog/web/index.js | 3 + react/features/invite/components/index.js | 4 +- react/features/invite/middleware.web.js | 10 +- react/features/invite/reducer.js | 9 +- 30 files changed, 1021 insertions(+), 228 deletions(-) create mode 100644 react/features/base/react/components/native/ForwardButton.js delete mode 100644 react/features/invite/components/AddPeopleDialog.native.js create mode 100644 react/features/invite/components/add-people-dialog/AbstractAddPeopleDialog.js create mode 100644 react/features/invite/components/add-people-dialog/index.native.js create mode 100644 react/features/invite/components/add-people-dialog/index.web.js create mode 100644 react/features/invite/components/add-people-dialog/native/AddPeopleDialog.js create mode 100644 react/features/invite/components/add-people-dialog/native/index.js create mode 100644 react/features/invite/components/add-people-dialog/native/styles.js rename react/features/invite/components/{AddPeopleDialog.web.js => add-people-dialog/web/AddPeopleDialog.js} (70%) create mode 100644 react/features/invite/components/add-people-dialog/web/index.js diff --git a/css/_font.scss b/css/_font.scss index 53d8e31a2..5a0a4ed1d 100644 --- a/css/_font.scss +++ b/css/_font.scss @@ -25,6 +25,18 @@ -moz-osx-font-smoothing: grayscale; } +.icon-phone:before { + content: "\e0cd"; +} +.icon-radio_button_unchecked:before { + content: "\e836"; +} +.icon-radio_button_checked:before { + content: "\e837"; +} +.icon-search:before { + content: "\e8b6"; +} .icon-chat-unread:before { content: "\e0b7"; } diff --git a/fonts/jitsi.eot b/fonts/jitsi.eot index e5769a8144e3591bf9a2d56ca7f3058de656ea10..c9b528150e030aa1c86f6490427ad60740818c0c 100755 GIT binary patch delta 946 zcmZ`%X=oEc6n?Y2*<`bu<}lsa#29O`W|P_qZra2|(H688TQQ;pgjx-1Eo!x5@j`9T zAR^+mP*g-kP)qTL63}`dh`$s>>hVYMO2`j?c!G+EFI7iXs5e=x1vF8lHST~->tz5l0^CtDF10bZJp6kkN=!TiF z6Y&wmRjV>xo~2LsZ8?p^6>M15y?SjAuqZ*e#+XO8NAbGQ1Px#U9tc!DzwrFti>4O? zuN<$1!tKJn!h^z4kuA!_Q6;eyFC8uAOXm%a2?fwL{Xe$YFIy9%P98ncf79RY`{E=_G89zX1Z~M;f(@w zqBjd!7B@t23Yq!|HpQn9ETXzRin#e;KpRiAP<>r&64B*Kw@hW;OuW?ZZ;nK2+XY2b zXK5})arNbLcM=KAE=7`9PGIV4BavpmpSBAoPLhU&MB+{^hX%zJZdI)w0f=#ljpi@1 zR+E^9G&{f!z(|N22c1ddp>u*ExS|gHs((o^w=5EBOt6hCTa@`VnwE6pN@`loUv;_H zGxQJr%aXrt@e-AREcCIgYjSg1IEqYo1PmlRtsTm0u1#IdpZ=?`)h2#668a`7#Gkt})UWS>tmc?krcs2y^u?TNganyBkiy z4Z@RV(nfm79@0;qF+L{ETw|;8M}OzWbGx|vrUugi(Q52@AS1RKz;xNgZ!L~)Wj5#)=XUn2E{i(d9w_l0EZn*9Rq`s3Xrdoky}#n>beAw zsRYvhB_}^Q@%XC?3JeU&Hb8z&Zem3NgBwE!kiP@SSIA4ul}x=mp>{b?;0DkEc?J2! zB@E0!DF#)K$svr*xY;ibp{ZlZutx0l8S2A2JM5Zc=tqR#KKy+>$>fKTEKQmxw2bi--$} z3yKSf^NaI|^N4ecbBS~Ezvq9)KO5*O#>oenY$jh|Vx9b#Y0>0h7NgC9EL^OcnYqOn zH!tPcE+I3oBS<-(-{va=Hw(xM3^%4sl7!KdD^$%HZ6|L~6`y=s)r7SHs6uP9fZE3T zG=>I-V~iY(GK?mSevBE6^BC_ii80kNy<(PPE@OViV!`6WvV!Fd%OBPn) z*mkiCu=}yE;V|Jy;OOF5!*PRCfisMA73Ut#3tUWGc3dmC)wnab_wn%XbntTVcJQh2 hUEo*Yci@lXKL-p&1_oP(HU + @@ -21,8 +22,11 @@ + + + diff --git a/fonts/jitsi.ttf b/fonts/jitsi.ttf index 251c5fde8e2de51f700eb322939f23fd42cc867d..7a80e555f517ee113be9a6ca9d44df80caffa09e 100755 GIT binary patch delta 892 zcmZWnUu;WJ82`?_xA*q8w|}+w+-?4kQ0L&rO8wyBR=L!1} ze?V*&x_WkgeW70gnC8R%giTx4=HF+>I{~5^>ZPvy&Td!&hY+7Z9NL`k(mP)D?YV@+ zZCtRqd&{;S;8B9=+T%k9{MA@3ghsG{2n0eSH%6YmS;+bbl~QA8$I4^ZS%E~kk*BPe z=u*QkYLJ+XRkMQ+f^C5>0b(pN<{NX2jG^dX_0O6_U(p?OEzMJns?<+?bQ1MaH+4}b zb+|scKDy3f1B7|F*(}7l*kbOyQG_Co6XMvSN`nL!rsfeWlI*f*ES88tgTdx_ysk~w z?B=qVSJS-xrPAYc8nahZ6kd?IS#|Mvb1+ETWQ(9E6GA%uxKu)e=B-|8+H{!(`19-8W3h|} zMP(Ldg35$N8I+aSX`k0eM*c)A4 zAxf0=FW=go#UR(dWFnJEBwAE|IHZul2@@L86;`Suezhf0(f@dp zt4*amS02&=+34u>HLkhiU>7QX0$!fF)BZa%cQ~at{p2egK&8gWVH83G3Cl&16Qg2Id@g>I zOliCH#Okwdunx$g+$-Od-`PZ4!nWIX)h^godyT!-ep2C-qVmw8IXWG0o$H)$U3=X% X?!E5Q?jcV#{$GG5I9R?P86ZCZ-TBT@ delta 496 zcmX>T@WN|?Lj9IoEAKHdFvL7`1qKFX z8z8?XH?g9C!HuB<$ln3vE952SN~YeOP`ex`a0BRoyn_7V5(Z|V6oabA#2w9oK$kE$ z03j=oW@J!!uzj*0qa^dZ7n>*NF{&{=be$Z)C=TXsV^pz{J0KS;^FxL~%1z2n%1X*o zid*uh0Dxrn>l&5OUTUY2vUycxB1Gz%>r^0!;LAEBw_UAJ1XX)wh(c!Bm;;I#9@SDlR^!g# v-p9kk)4|Kd+rg*8cY$Ap-+@1l{~R!!7#M6B+88*%u3`fEO?dNuwO&R5bIo}V diff --git a/fonts/jitsi.woff b/fonts/jitsi.woff index 009c8e38536ad6b49d6999241686ae19f634f8e2..8c35f8c52478f79b57d5578d39cb830264098c88 100755 GIT binary patch delta 982 zcmZ{jU1$?o6vxkAp6Xe}GX6d@qgYEWyf)>bUq zUC;)JA}YG>VCn9IqM%!f4=X8t;wQx?1(Bk@DAsL59(?i(6cNwF$_k5T_;b$vpWmIC z!<`vVjI_&pR=2hS0gUPq5Q}*w5HrolCu%E(mI07u=fd0aThhDw0hkL2IA-PEvi;XC z^u__yq@{GMWukj?dK17r4w*(vzT>y9ccY136RtH&jwRgw?%shx^fuuAktN*6C;kiD z`!*sM!u^o7^eSn*>*`Gp;)6p4G%Abw1rF^<_ihHz@kPiEOV57a`*(let^u53@WiJh zk!l26p&4wz<7kyHF28s%)jBoyuX|dUnV5Mn^Jr!=&*tU)+=5t$7ETp%g-hl*38{!J z{{hxGi@hgWQ^lg-onUAAhjJ2F5m*{n9Eb-b|408@#ZI5mJ#-^YQ-#X3jQZ$L)Jxse zMN4Uk>y7KR>$I63UPY2vPGIWm!r``Hkah|-PLhg^ zSnOUli-6*-Ua2|#0v>V?8_8{Doi;HADRzti@?^)@f4ikZ?sQPlodI*SnhDfr#H9#?wD28Tq(pB=Z ebW`a|*FJZRd!PF+_Z3fd@&9dsgE>hXC0_s}knzy~ delta 575 zcmbOcxW!wn+~3WOfsp|SRJSm2gXs(g#>s_DViR@b>vb3y7l35J~fWS~0b4j{h6x}cDoSOL_i!U7af0An|Xj=aR&RG=8p zFvdI(zB{3Ic|m@03D6HyCjRNx6#y!9076zE&B&neVEaS2hpQe7JmGwLTZbF>Vg!*)Ab7uOmn~p5Nvx12@Qz3=B7>Op=7rlQmS$8Eq#gsESXnRyAR50IJZM zd_Z+$eHudp!!bqeaNGlr1&jcl)Sq|& diff --git a/fonts/selection.json b/fonts/selection.json index 00a713f49..d879577e7 100755 --- a/fonts/selection.json +++ b/fonts/selection.json @@ -1 +1 @@ -{"IcoMoonType":"selection","icons":[{"icon":{"paths":["M768 342v-86h-512v86h512zM598 598v-86h-342v86h342zM256 384v86h512v-86h-512zM854 86c46 0 84 38 84 84v512c0 46-38 86-84 86h-598l-170 170v-768c0-46 38-84 84-84h684z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["chat"],"defaultCode":57527,"grid":24},"attrs":[],"properties":{"ligatures":"chat","id":145,"order":1382,"prevSize":24,"code":57527,"name":"chat-unread"},"setIdx":0,"setId":1,"iconIdx":0},{"icon":{"paths":["M768 470v-44c0-24-18-42-42-42h-128c-24 0-44 18-44 42v172c0 24 20 42 44 42h128c24 0 42-18 42-42v-44h-64v22h-86v-128h86v22h64zM470 470v-44c0-24-20-42-44-42h-128c-24 0-42 18-42 42v172c0 24 18 42 42 42h128c24 0 44-18 44-42v-44h-64v22h-86v-128h86v22h64zM810 170c46 0 86 40 86 86v512c0 46-40 86-86 86h-596c-48 0-86-40-86-86v-512c0-46 38-86 86-86h596z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"tags":["closed_caption"],"grid":24},"attrs":[{}],"properties":{"order":1,"id":0,"prevSize":24,"code":59696,"name":"closed_caption"},"setIdx":0,"setId":1,"iconIdx":1},{"icon":{"paths":["M113.778 0h227.556c62.838 0 113.778 50.94 113.778 113.778v227.556c0 62.838-50.94 113.778-113.778 113.778h-227.556c-62.838 0-113.778-50.94-113.778-113.778v-227.556c0-62.838 50.94-113.778 113.778-113.778zM170.667 113.778c-31.419 0-56.889 25.47-56.889 56.889v113.778c0 31.419 25.47 56.889 56.889 56.889h113.778c31.419 0 56.889-25.47 56.889-56.889v-113.778c0-31.419-25.47-56.889-56.889-56.889h-113.778zM113.778 568.889h227.556c62.838 0 113.778 50.94 113.778 113.778v227.556c0 62.838-50.94 113.778-113.778 113.778h-227.556c-62.838 0-113.778-50.94-113.778-113.778v-227.556c0-62.838 50.94-113.778 113.778-113.778zM170.667 682.667c-31.419 0-56.889 25.47-56.889 56.889v113.778c0 31.419 25.47 56.889 56.889 56.889h113.778c31.419 0 56.889-25.47 56.889-56.889v-113.778c0-31.419-25.47-56.889-56.889-56.889h-113.778zM682.667 0h227.556c62.838 0 113.778 50.94 113.778 113.778v227.556c0 62.838-50.94 113.778-113.778 113.778h-227.556c-62.838 0-113.778-50.94-113.778-113.778v-227.556c0-62.838 50.94-113.778 113.778-113.778zM739.556 113.778c-31.419 0-56.889 25.47-56.889 56.889v113.778c0 31.419 25.47 56.889 56.889 56.889h113.778c31.419 0 56.889-25.47 56.889-56.889v-113.778c0-31.419-25.47-56.889-56.889-56.889h-113.778zM682.667 568.889h227.556c62.838 0 113.778 50.94 113.778 113.778v227.556c0 62.838-50.94 113.778-113.778 113.778h-227.556c-62.838 0-113.778-50.94-113.778-113.778v-227.556c0-62.838 50.94-113.778 113.778-113.778zM739.556 682.667c-31.419 0-56.889 25.47-56.889 56.889v113.778c0 31.419 25.47 56.889 56.889 56.889h113.778c31.419 0 56.889-25.47 56.889-56.889v-113.778c0-31.419-25.47-56.889-56.889-56.889h-113.778z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"grid":24,"tags":["tiles-many"]},"attrs":[{}],"properties":{"order":1377,"id":1065,"name":"tiles-many","prevSize":24,"code":59694},"setIdx":0,"setId":1,"iconIdx":2},{"icon":{"paths":["M810 274l-238 238 238 238-60 60-238-238-238 238-60-60 238-238-238-238 60-60 238 238 238-238z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["close"],"defaultCode":58829,"grid":24},"attrs":[],"properties":{"ligatures":"clear, close","id":157,"order":1313,"prevSize":24,"code":58829,"name":"close"},"setIdx":0,"setId":1,"iconIdx":3},{"icon":{"paths":["M598 128h298v298h-86v-152l-418 418-60-60 418-418h-152v-86zM810 810v-298h86v298c0 46-40 86-86 86h-596c-48 0-86-40-86-86v-596c0-46 38-86 86-86h298v86h-298v596h596z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["open_in_new"],"defaultCode":59550,"grid":24},"attrs":[],"properties":{"ligatures":"launch, open_in_new","id":1047,"order":1314,"prevSize":24,"name":"open_in_new","code":59550},"setIdx":0,"setId":1,"iconIdx":4},{"icon":{"paths":["M512 342h64v180l150 90-32 52-182-110v-212zM554 128c212 0 384 172 384 384s-172 384-384 384c-106 0-200-42-270-112l60-62c54 54 128 88 210 88 166 0 300-132 300-298s-134-298-300-298-298 132-298 298h128l-172 172-4-6-166-166h128c0-212 172-384 384-384z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["restore"],"defaultCode":59571,"grid":24},"attrs":[],"properties":{"ligatures":"history, restore","id":1048,"order":1315,"prevSize":24,"code":59571,"name":"restore"},"setIdx":0,"setId":1,"iconIdx":5},{"icon":{"paths":["M426 256l256 256-256 256-60-60 196-196-196-196z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["navigate_next"],"defaultCode":58377,"grid":24},"attrs":[],"properties":{"ligatures":"chevron_right, navigate_next","id":1049,"order":1316,"prevSize":24,"code":58377,"name":"navigate_next"},"setIdx":0,"setId":1,"iconIdx":6},{"icon":{"paths":["M128 256h768v86h-768v-86zM128 554v-84h768v84h-768zM128 768v-86h768v86h-768z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["menu"],"defaultCode":58834,"grid":24},"attrs":[],"properties":{"ligatures":"menu","id":1050,"order":1317,"prevSize":24,"code":58834,"name":"menu"},"setIdx":0,"setId":1,"iconIdx":7},{"icon":{"paths":["M854 470v84h-520l238 240-60 60-342-342 342-342 60 60-238 240h520z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["arrow_back"],"defaultCode":58820,"grid":24},"attrs":[],"properties":{"ligatures":"arrow_back","id":1051,"order":1318,"prevSize":24,"code":58820,"name":"arrow_back"},"setIdx":0,"setId":1,"iconIdx":8},{"icon":{"paths":["M764 742c56-60 90-142 90-230 0-142-88-266-214-316v18c0 46-40 84-86 84h-84v86c0 24-20 42-44 42h-84v86h256c24 0 42 18 42 42v128h42c38 0 70 26 82 60zM470 850v-82c-46 0-86-40-86-86v-42l-204-204c-6 24-10 50-10 76 0 174 132 318 300 338zM512 86c236 0 426 190 426 426s-190 426-426 426-426-190-426-426 190-426 426-426z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["public"],"defaultCode":59403,"grid":24},"attrs":[],"properties":{"ligatures":"public","id":1053,"order":1320,"prevSize":24,"code":59403,"name":"public"},"setIdx":0,"setId":1,"iconIdx":9},{"icon":{"paths":["M598 598v84h-300v-84h300zM810 810v-468h-596v468h596zM810 128c46 0 86 40 86 86v596c0 46-40 86-86 86h-596c-48 0-86-40-86-86v-596c0-46 38-86 86-86h42v-86h86v86h340v-86h86v86h42zM726 426v86h-428v-86h428z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["event_note"],"defaultCode":58902,"grid":24},"attrs":[],"properties":{"ligatures":"event_note","id":1054,"order":1321,"prevSize":24,"code":58902,"name":"event_note"},"setIdx":0,"setId":1,"iconIdx":10},{"icon":{"paths":["M550 696l-80-82v162zM470 248v162l80-82zM670 328l-184 184 184 184-244 242h-42v-324l-196 196-60-60 238-238-238-238 60-60 196 196v-324h42zM834 286c40 64 62 142 62 222 0 84-24 160-66 226l-50-50c26-52 42-110 42-172s-16-120-42-172zM608 512l98-98c12 30 20 64 20 98s-8 70-20 100z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["bluetooth_searching"],"defaultCode":57770,"grid":24},"attrs":[],"properties":{"ligatures":"bluetooth_audio, bluetooth_searching","id":1056,"order":1323,"prevSize":24,"code":57770,"name":"bluetooth"},"setIdx":0,"setId":1,"iconIdx":11},{"icon":{"paths":["M512 42c212 0 384 172 384 384v300c0 70-58 128-128 128h-128v-342h170v-86c0-166-132-298-298-298s-298 132-298 298v86h170v342h-128c-70 0-128-58-128-128v-300c0-212 172-384 384-384z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["headset"],"defaultCode":58128,"grid":24},"attrs":[],"properties":{"ligatures":"headset","id":1057,"order":1324,"prevSize":24,"code":58128,"name":"headset"},"setIdx":0,"setId":1,"iconIdx":12},{"icon":{"paths":["M640 512c0-70-58-128-128-128v-86c118 0 214 96 214 214h-86zM810 512c0-166-132-298-298-298v-86c212 0 384 172 384 384h-86zM854 662c24 0 42 18 42 42v150c0 24-18 42-42 42-400 0-726-326-726-726 0-24 18-42 42-42h150c24 0 42 18 42 42 0 54 8 104 24 152 4 14 2 32-10 44l-94 94c62 122 162 220 282 282l94-94c12-12 30-14 44-10 48 16 98 24 152 24z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["phone_in_talk"],"defaultCode":58909,"grid":24},"attrs":[],"properties":{"ligatures":"phone_in_talk","id":1058,"order":1325,"prevSize":24,"code":58909,"name":"phone-talk"},"setIdx":0,"setId":1,"iconIdx":13},{"icon":{"paths":["M512 682c46 0 86 40 86 86s-40 86-86 86-86-40-86-86 40-86 86-86zM512 426c46 0 86 40 86 86s-40 86-86 86-86-40-86-86 40-86 86-86zM512 342c-46 0-86-40-86-86s40-86 86-86 86 40 86 86-40 86-86 86z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["more_vert"],"defaultCode":58836,"grid":24},"attrs":[],"properties":{"ligatures":"more_vert","id":1059,"order":1326,"prevSize":24,"code":58836,"name":"thumb-menu"},"setIdx":0,"setId":1,"iconIdx":14},{"icon":{"paths":["M330.667 554.667c-0.427-14.933 6.4-29.44 17.92-39.253 32 6.827 61.867 20.053 88.747 39.253 0 29.013-23.893 52.907-53.333 52.907s-52.907-23.467-53.333-52.907zM586.667 554.667c26.88-18.773 56.747-32 88.747-38.827 11.52 9.813 18.347 24.32 17.92 38.827 0 29.867-23.893 53.76-53.333 53.76s-53.333-23.893-53.333-53.76v0zM512 384c-118.187-1.707-234.667 27.733-338.347 85.333l-2.987 42.667c0 52.48 12.373 104.107 35.84 151.040 101.12-15.36 203.093-23.040 305.493-23.040s204.373 7.68 305.493 23.040c23.467-46.933 35.84-98.56 35.84-151.040l-2.987-42.667c-103.68-57.6-220.16-87.040-338.347-85.333zM512 85.333c235.641 0 426.667 191.025 426.667 426.667s-191.025 426.667-426.667 426.667c-235.641 0-426.667-191.025-426.667-426.667s191.025-426.667 426.667-426.667z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"tags":["ninja"],"grid":24},"attrs":[{}],"properties":{"order":1327,"id":1060,"name":"ninja","prevSize":24,"code":59657},"setIdx":0,"setId":1,"iconIdx":15},{"icon":{"paths":["M810 554h-256v256h-84v-256h-256v-84h256v-256h84v256h256v84z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["invite"],"defaultCode":57669,"grid":24},"attrs":[],"properties":{"ligatures":"add","id":1062,"order":1329,"prevSize":24,"code":57669,"name":"invite"},"setIdx":0,"setId":1,"iconIdx":16},{"icon":{"paths":["M810 554h-256v256h-84v-256h-256v-84h256v-256h84v256h256v84z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["add"],"defaultCode":57669,"grid":24},"attrs":[],"properties":{"order":1383,"id":1066,"prevSize":24,"code":57670,"name":"add"},"setIdx":0,"setId":1,"iconIdx":17},{"icon":{"paths":["M790.857 529.714l-758.857 421.714c-17.714 9.714-32 1.143-32-18.857v-841.143c0-20 14.286-28.571 32-18.857l758.857 421.714c17.714 9.714 17.714 25.714 0 35.429z"],"width":808.5942857142857,"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["play"],"defaultCode":61515,"grid":14},"attrs":[],"properties":{"name":"play","id":75,"order":1380,"prevSize":28,"code":61515},"setIdx":0,"setId":1,"iconIdx":18},{"icon":{"paths":["M877.714 109.714v804.571c0 20-16.571 36.571-36.571 36.571h-804.571c-20 0-36.571-16.571-36.571-36.571v-804.571c0-20 16.571-36.571 36.571-36.571h804.571c20 0 36.571 16.571 36.571 36.571z"],"width":877.7142857142857,"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["stop"],"defaultCode":61517,"grid":14},"attrs":[],"properties":{"name":"stop","id":77,"order":1381,"prevSize":28,"code":61517},"setIdx":0,"setId":1,"iconIdx":19},{"icon":{"paths":["M950.857 365.714c40.571 0 73.143 32.571 73.143 73.143s-32.571 73.143-73.143 73.143v219.429c0 40-33.143 73.143-73.143 73.143-101.714-84.571-265.714-200.571-464-217.143-68 22.857-91.429 102.286-46.857 148-40 65.714 11.429 112 72 159.429-35.429 69.714-182.857 70.857-235.429 22.286-33.143-101.714-82.286-203.429-42.286-332h-69.714c-50.286 0-91.429-41.143-91.429-91.429v-109.714c0-50.286 41.143-91.429 91.429-91.429h274.286c219.429 0 402.286-128 512-219.429 40 0 73.143 33.143 73.143 73.143v219.429zM877.714 710.857v-545.143c-149.143 114.286-293.714 180-438.857 196v154.286c145.143 16 289.714 80.571 438.857 194.857z"],"width":1024,"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["bullhorn"],"defaultCode":61601,"grid":14},"attrs":[],"properties":{"name":"dominant-speaker","id":152,"order":1379,"prevSize":28,"code":61601},"setIdx":0,"setId":1,"iconIdx":20},{"icon":{"paths":["M0 512c0 282.795 229.205 512 512 512s512-229.205 512-512c0-282.795-229.205-512-512-512s-512 229.205-512 512zM525.005 264.638c-20.475-24.944-16.326-61.342 9.268-81.297s62.94-15.911 83.416 9.033c16.036 19.536 38.593 52.97 60.894 97.797 81.621 164.065 89.461 340.992-26.857 506.352-8.384 11.919-17.386 23.69-27.012 35.307-20.593 24.851-57.959 28.727-83.458 8.657s-29.476-56.487-8.882-81.338c7.686-9.275 14.833-18.621 21.455-28.035 88.66-126.041 82.71-260.306 17.953-390.475-10.599-21.305-21.94-40.51-33.198-57.196-6.515-9.657-11.322-16.057-13.578-18.805zM353.479 376.54c-19.353-24.679-15.129-60.448 9.434-79.893s60.164-15.2 79.517 9.479c9.635 12.287 22.577 32.644 35.209 60.034 50.35 109.176 50.35 231.689-33.639 349.612-18.198 25.551-53.566 31.441-78.997 13.157s-31.294-53.819-13.096-79.37c57.564-80.822 57.564-160.581 22.983-235.565-8.601-18.65-16.892-31.691-21.412-37.455z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"grid":0,"tags":["speaker"]},"attrs":[{}],"properties":{"order":1312,"id":1063,"name":"speaker","prevSize":32,"code":59693},"setIdx":0,"setId":1,"iconIdx":21},{"icon":{"paths":["M512 1024c-282.77 0-512-229.23-512-512s229.23-512 512-512c282.77 0 512 229.23 512 512s-229.23 512-512 512zM581.333 590.218h-110.595v-59.233h104.338v-40.332h-104.338v-56.87h110.595v-43.539h-161.665v243.512h161.665v-43.539zM738.771 640c58.849 0 101.802-36.282 106.029-88.933h-49.717c-4.904 26.832-26.888 44.045-56.143 44.045-38.556 0-62.4-31.895-62.4-83.196s23.844-83.027 62.231-83.027c29.086 0 51.239 18.394 56.143 46.407h49.717c-3.72-52.989-48.026-91.296-105.86-91.296-70.855 0-114.485 48.77-114.485 127.916 0 79.314 43.798 128.084 114.485 128.084zM230.27 545.498h41.769l45.489 88.258h57.834l-51.408-96.19c28.072-11.138 44.306-38.138 44.306-69.189 0-48.432-32.976-78.133-86.582-78.133h-102.478v243.512h51.070v-88.258zM230.27 431.42v74.927h44.813c25.704 0 40.754-13.838 40.754-37.295 0-23.119-15.896-37.632-41.262-37.632h-44.306z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"grid":0,"tags":["rec"]},"attrs":[{}],"properties":{"order":1331,"id":1001,"name":"rec","prevSize":32,"code":59691},"setIdx":0,"setId":1,"iconIdx":22},{"icon":{"paths":["M725.333 512c0 117.821-95.513 213.333-213.333 213.333s-213.333-95.513-213.333-213.333c0-117.821 95.513-213.333 213.333-213.333s213.333 95.513 213.333 213.333z","M512 768c141.385 0 256-114.615 256-256s-114.615-256-256-256v0c-141.385 0-256 114.615-256 256s114.615 256 256 256v0zM512 810.667c-164.949 0-298.667-133.718-298.667-298.667s133.718-298.667 298.667-298.667v0c164.949 0 298.667 133.718 298.667 298.667s-133.718 298.667-298.667 298.667v0z"],"attrs":[{},{}],"isMulticolor":false,"isMulticolor2":false,"grid":0,"tags":["camera-take-picture"]},"attrs":[{},{}],"properties":{"order":1332,"id":1002,"name":"camera-take-picture","prevSize":32,"code":59690},"setIdx":0,"setId":1,"iconIdx":23},{"icon":{"paths":["M512 1024c-282.77 0-512-229.23-512-512s229.23-512 512-512c282.77 0 512 229.23 512 512s-229.23 512-512 512zM308.25 636.7h57.225l-87.675-252.525h-62.125l-87.675 252.525h53.025l19.425-60.2h88.725l19.075 60.2zM461.9 384.175h-52.85v165.375c0 56 41.125 93.625 105.7 93.625 64.75 0 105.875-37.625 105.875-93.625v-165.375h-52.85v159.95c0 31.85-19.075 52.15-53.025 52.15-33.775 0-52.85-20.3-52.85-52.15v-159.95zM682.225 384v252.7h99.4c75.6 0 118.475-46.025 118.475-128.1 0-79.1-43.4-124.6-118.475-124.6h-99.4zM735.075 429.15v162.4h38.15c46.725 0 72.975-28.7 72.975-82.075 0-51.1-27.125-80.325-72.975-80.325h-38.15zM243.5 436.675l-31.675 99.050h66.15l-31.325-99.050h-3.15z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"grid":0,"tags":["AUD"]},"attrs":[{}],"properties":{"order":1333,"id":1003,"name":"AUD","prevSize":32,"code":59648},"setIdx":0,"setId":1,"iconIdx":24},{"icon":{"paths":["M512 1024c-282.77 0-512-229.23-512-512s229.23-512 512-512c282.77 0 512 229.23 512 512s-229.23 512-512 512zM481.359 640v-255.823h-54.273v103.18h-116.813v-103.18h-54.273v255.823h54.273v-106.903h116.813v106.903h54.273zM544.258 384v256h102.077c77.636 0 121.665-46.626 121.665-129.773 0-80.133-44.569-126.227-121.665-126.227h-102.077zM598.531 429.74v164.521h39.177c47.983 0 74.94-29.075 74.94-83.147 0-51.767-27.855-81.374-74.94-81.374h-39.177z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"grid":0,"tags":["HD"]},"attrs":[{}],"properties":{"order":1334,"id":1004,"name":"HD","prevSize":32,"code":59687},"setIdx":0,"setId":1,"iconIdx":25},{"icon":{"paths":["M512 1024c-282.77 0-512-229.23-512-512s229.23-512 512-512c282.77 0 512 229.23 512 512s-229.23 512-512 512zM472.4 590.675h-112.35v-206.5h-52.85v252.525h165.2v-46.025zM520.35 384v252.7h99.4c75.6 0 118.475-46.025 118.475-128.1 0-79.1-43.4-124.6-118.475-124.6h-99.4zM573.2 429.15v162.4h38.15c46.725 0 72.975-28.7 72.975-82.075 0-51.1-27.125-80.325-72.975-80.325h-38.15z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"grid":0,"tags":["LD"]},"attrs":[{}],"properties":{"order":1335,"id":1005,"name":"LD","prevSize":32,"code":59688},"setIdx":0,"setId":1,"iconIdx":26},{"icon":{"paths":["M512 1024c-282.77 0-512-229.23-512-512s229.23-512 512-512c282.77 0 512 229.23 512 512s-229.23 512-512 512zM281.6 572.825c1.925 47.075 40.95 76.65 101.15 76.65 63.35 0 102.375-31.15 102.375-82.075 0-39.2-21.875-61.075-72.625-71.75l-30.45-6.475c-29.575-6.3-41.65-15.225-41.65-30.8 0-19.25 17.5-31.5 43.925-31.5 25.55 0 44.1 13.3 46.55 33.25h49.7c-1.575-44.975-40.95-76.125-96.6-76.125-58.275 0-96.6 31.325-96.6 78.925 0 38.5 22.575 62.475 68.6 72.1l32.9 7c30.975 6.65 43.575 15.925 43.575 32.025 0 19.075-19.425 32.375-46.9 32.375-29.75 0-50.4-13.125-52.85-33.6h-51.1zM535 390.3v252.7h99.4c75.6 0 118.475-46.025 118.475-128.1 0-79.1-43.4-124.6-118.475-124.6h-99.4zM587.85 435.45v162.4h38.15c46.725 0 72.975-28.7 72.975-82.075 0-51.1-27.125-80.325-72.975-80.325h-38.15z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"grid":0,"tags":["SD"]},"attrs":[{}],"properties":{"order":1336,"id":1006,"name":"SD","prevSize":32,"code":59689},"setIdx":0,"setId":1,"iconIdx":27},{"icon":{"paths":["M896 0c70.692 0 128 57.308 128 128v768c0 70.692-57.308 128-128 128s-128-57.308-128-128v-768c0-70.692 57.308-128 128-128zM512 256c70.692 0 128 57.308 128 128v512c0 70.692-57.308 128-128 128s-128-57.308-128-128v-512c0-70.692 57.308-128 128-128zM128 640v0c70.692 0 128 57.308 128 128v128c0 70.692-57.308 128-128 128s-128-57.308-128-128v-128c0-70.692 57.308-128 128-128v0z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"grid":0,"tags":["gsm-bars-black"]},"attrs":[{}],"properties":{"order":1384,"id":1007,"name":"gsm-bars","prevSize":32,"code":59686},"setIdx":0,"setId":1,"iconIdx":28},{"icon":{"paths":["M512 85.333c-235.52 0-426.667 191.147-426.667 426.667s191.147 426.667 426.667 426.667 426.667-191.147 426.667-426.667-191.147-426.667-426.667-426.667zM554.667 725.333h-85.333v-256h85.333v256zM554.667 384h-85.333v-85.333h85.333v85.333z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"grid":0,"tags":["ic_info_black_24px"]},"attrs":[{}],"properties":{"order":1338,"id":1008,"name":"info","prevSize":32,"code":59682},"setIdx":0,"setId":1,"iconIdx":29},{"icon":{"paths":["M756.704 395.862l267.296-202.213v635.075l-267.296-202.213v191.923c0 12.085-11.296 21.863-25.216 21.863h-706.272c-13.92 0-25.216-9.777-25.216-21.863v-612.25c0-12.085 11.296-21.863 25.216-21.863h706.272c13.92 0 25.216 9.777 25.216 21.863v189.679zM371.338 647.772c47.817 0 86.529-40.232 86.529-89.811v-184.835c0-49.651-38.713-89.883-86.529-89.883-47.788 0-86.515 40.232-86.515 89.883v184.835c0 49.579 38.756 89.811 86.515 89.811v0zM356.754 709.93v32.78h33.718v-33.412c73.858-9.606 131.235-73.73 131.235-151.351v-88.232h-30.636v88.232c0 67.57-53.696 122.534-119.734 122.534-66.024 0-119.691-54.964-119.691-122.534v-88.232h-30.636v88.232c0 79.215 59.674 144.502 135.744 151.969v0.014z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"tags":["Combined Shape"],"grid":0},"attrs":[{}],"properties":{"order":1339,"id":1009,"name":"mic-camera-combined","prevSize":32,"code":59651},"setIdx":0,"setId":1,"iconIdx":30},{"icon":{"paths":["M42.667 896h170.667v-512h-170.667v512zM981.333 426.667c0-46.933-38.4-85.333-85.333-85.333h-269.227l40.533-194.987 1.28-13.653c0-17.493-7.253-33.707-18.773-45.227l-45.227-44.8-280.747 281.173c-15.787 15.36-25.173 36.693-25.173 60.16v426.667c0 46.933 38.4 85.333 85.333 85.333h384c35.413 0 65.707-21.333 78.507-52.053l128.853-300.8c3.84-9.813 5.973-20.053 5.973-31.147v-81.493l-0.427-0.427 0.427-3.413z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"tags":["ic_thumb_up_black_24px"],"grid":0},"attrs":[{}],"properties":{"order":1340,"id":1010,"name":"feedback","prevSize":32,"code":59677},"setIdx":0,"setId":1,"iconIdx":31},{"icon":{"paths":["M512 384c-68 0-134 10-196 30v132c0 16-10 34-24 40-42 20-80 46-114 78-8 8-18 12-30 12s-22-4-30-12l-106-106c-8-8-12-18-12-30s4-22 12-30c130-124 306-200 500-200s370 76 500 200c8 8 12 18 12 30s-4 22-12 30l-106 106c-8 8-18 12-30 12s-22-4-30-12c-34-32-72-58-114-78-14-6-24-20-24-38v-132c-62-20-128-32-196-32z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["call_end"],"grid":0},"attrs":[],"properties":{"id":1013,"order":1343,"ligatures":"call_end","prevSize":32,"code":59653,"name":"hangup"},"setIdx":0,"setId":1,"iconIdx":32},{"icon":{"paths":["M854 682v-512h-684v598l86-86h598zM854 86c46 0 84 38 84 84v512c0 46-38 86-84 86h-598l-170 170v-768c0-46 38-84 84-84h684z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["chat_bubble_outline"],"grid":0},"attrs":[],"properties":{"id":1014,"order":1344,"ligatures":"chat_bubble_outline","prevSize":32,"code":59654,"name":"chat"},"setIdx":0,"setId":1,"iconIdx":33},{"icon":{"paths":["M554 384h236l-236-234v234zM682 598v-86h-340v86h340zM682 768v-86h-340v86h340zM598 86l256 256v512c0 46-40 84-86 84h-512c-46 0-86-38-86-84l2-684c0-46 38-84 84-84h342z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["description"],"grid":0},"attrs":[],"properties":{"id":1017,"order":1347,"ligatures":"description","prevSize":32,"code":59656,"name":"share-doc"},"setIdx":0,"setId":1,"iconIdx":34},{"icon":{"paths":["M512 214l284 426h-568zM214 726h596v84h-596v-84z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["eject"],"grid":0},"attrs":[],"properties":{"id":1018,"order":1348,"ligatures":"eject","prevSize":32,"code":59652,"name":"kick"},"setIdx":0,"setId":1,"iconIdx":35},{"icon":{"paths":["M512 342l256 256-60 60-196-196-196 196-60-60z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["expand_less"],"grid":0},"attrs":[],"properties":{"id":1019,"order":1349,"ligatures":"expand_less","prevSize":32,"code":59679,"name":"menu-up"},"setIdx":0,"setId":1,"iconIdx":36},{"icon":{"paths":["M708 366l60 60-256 256-256-256 60-60 196 196z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["expand_more"],"grid":0},"attrs":[],"properties":{"id":1020,"order":1350,"ligatures":"expand_more","prevSize":32,"code":59680,"name":"menu-down"},"setIdx":0,"setId":1,"iconIdx":37},{"icon":{"paths":["M598 214h212v212h-84v-128h-128v-84zM726 726v-128h84v212h-212v-84h128zM214 426v-212h212v84h-128v128h-84zM298 598v128h128v84h-212v-212h84z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["fullscreen"],"grid":0},"attrs":[],"properties":{"id":1021,"order":1351,"ligatures":"fullscreen","prevSize":32,"code":59659,"name":"full-screen"},"setIdx":0,"setId":1,"iconIdx":38},{"icon":{"paths":["M682 342h128v84h-212v-212h84v128zM598 810v-212h212v84h-128v128h-84zM342 342v-128h84v212h-212v-84h128zM214 682v-84h212v212h-84v-128h-128z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["fullscreen_exit"],"grid":0},"attrs":[],"properties":{"id":1022,"order":1352,"ligatures":"fullscreen_exit","prevSize":32,"code":59660,"name":"exit-full-screen"},"setIdx":0,"setId":1,"iconIdx":39},{"icon":{"paths":["M768 854v-428h-512v428h512zM768 342c46 0 86 38 86 84v428c0 46-40 84-86 84h-512c-46 0-86-38-86-84v-428c0-46 40-84 86-84h388v-86c0-72-60-132-132-132s-132 60-132 132h-82c0-118 96-214 214-214s214 96 214 214v86h42zM512 726c-46 0-86-40-86-86s40-86 86-86 86 40 86 86-40 86-86 86z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["lock_open"],"grid":0},"attrs":[],"properties":{"id":1024,"order":1354,"ligatures":"lock_open","prevSize":32,"code":59661,"name":"security"},"setIdx":0,"setId":1,"iconIdx":40},{"icon":{"paths":["M768 854v-428h-512v428h512zM380 256v86h264v-86c0-72-60-132-132-132s-132 60-132 132zM768 342c46 0 86 38 86 84v428c0 46-40 84-86 84h-512c-46 0-86-38-86-84v-428c0-46 40-84 86-84h42v-86c0-118 96-214 214-214s214 96 214 214v86h42zM512 726c-46 0-86-40-86-86s40-86 86-86 86 40 86 86-40 86-86 86z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["lock_outline"],"grid":0},"attrs":[],"properties":{"id":1025,"order":1355,"ligatures":"lock_outline","prevSize":32,"code":59662,"name":"security-locked"},"setIdx":0,"setId":1,"iconIdx":41},{"icon":{"paths":["M738 470h72c0 146-116 266-256 286v140h-84v-140c-140-20-256-140-256-286h72c0 128 108 216 226 216s226-88 226-216zM512 598c-70 0-128-58-128-128v-256c0-70 58-128 128-128s128 58 128 128v256c0 70-58 128-128 128z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["mic"],"grid":0},"attrs":[],"properties":{"id":1027,"order":1357,"ligatures":"mic","prevSize":32,"code":59664,"name":"microphone"},"setIdx":0,"setId":1,"iconIdx":42},{"icon":{"paths":["M182 128l714 714-54 54-178-178c-32 20-72 32-110 38v140h-84v-140c-140-20-256-140-256-286h72c0 128 108 216 226 216 34 0 68-8 98-22l-70-70c-8 2-18 4-28 4-70 0-128-58-128-128v-32l-256-256zM640 476l-256-254v-8c0-70 58-128 128-128s128 58 128 128v262zM810 470c0 50-14 98-38 140l-52-54c12-26 18-54 18-86h72z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["mic_off"],"grid":0},"attrs":[],"properties":{"id":1029,"order":1359,"ligatures":"mic_off","prevSize":32,"code":59666,"name":"mic-disabled"},"setIdx":0,"setId":1,"iconIdx":43},{"icon":{"paths":["M982 234v620c0 94-78 170-172 170h-310c-46 0-90-18-122-50l-336-342s54-52 56-52c10-8 22-12 34-12 10 0 18 2 26 6 2 0 184 104 184 104v-508c0-36 28-64 64-64s64 28 64 64v300h42v-406c0-36 28-64 64-64s64 28 64 64v406h42v-364c0-36 28-64 64-64s64 28 64 64v364h44v-236c0-36 28-64 64-64s64 28 64 64z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["pan_tool"],"grid":0},"attrs":[],"properties":{"id":1030,"order":1360,"ligatures":"pan_tool","prevSize":32,"code":59678,"name":"raised-hand"},"setIdx":0,"setId":1,"iconIdx":44},{"icon":{"paths":["M640 598c114 0 342 56 342 170v86h-684v-86c0-114 228-170 342-170zM256 426h128v86h-128v128h-86v-128h-128v-86h128v-128h86v128zM640 512c-94 0-170-76-170-170s76-172 170-172 170 78 170 172-76 170-170 170z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["person_add"],"grid":0},"attrs":[],"properties":{"id":1032,"order":1362,"ligatures":"person_add","prevSize":32,"code":59667,"name":"link"},"setIdx":0,"setId":1,"iconIdx":45},{"icon":{"paths":["M512 854c188 0 342-154 342-342s-154-342-342-342-342 154-342 342 154 342 342 342zM512 86c236 0 426 190 426 426s-190 426-426 426-426-190-426-426 190-426 426-426zM426 704v-384l256 192z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["play_circle_outline"],"grid":0},"attrs":[],"properties":{"id":1033,"order":1363,"ligatures":"play_circle_outline","prevSize":32,"code":59668,"name":"shared-video"},"setIdx":0,"setId":1,"iconIdx":46},{"icon":{"paths":["M512 662c82 0 150-68 150-150s-68-150-150-150-150 68-150 150 68 150 150 150zM830 554l90 70c8 6 10 18 4 28l-86 148c-6 10-16 12-26 8l-106-42c-22 16-46 32-72 42l-16 112c-2 10-10 18-20 18h-172c-10 0-18-8-20-18l-16-112c-26-10-50-24-72-42l-106 42c-10 4-20 2-26-8l-86-148c-6-10-4-22 4-28l90-70c-2-14-2-28-2-42s0-28 2-42l-90-70c-8-6-10-18-4-28l86-148c6-10 16-12 26-8l106 42c22-16 46-32 72-42l16-112c2-10 10-18 20-18h172c10 0 18 8 20 18l16 112c26 10 50 24 72 42l106-42c10-4 20-2 26 8l86 148c6 10 4 22-4 28l-90 70c2 14 2 28 2 42s0 28-2 42z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["settings"],"grid":0},"attrs":[],"properties":{"id":1034,"order":1364,"ligatures":"settings","prevSize":32,"code":59669,"name":"settings"},"setIdx":0,"setId":1,"iconIdx":47},{"icon":{"paths":["M512 658l160 96-42-182 142-124-188-16-72-172-72 172-188 16 142 124-42 182zM938 394l-232 202 70 300-264-160-264 160 70-300-232-202 306-26 120-282 120 282z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["star_border"],"grid":0},"attrs":[],"properties":{"id":1035,"order":1365,"ligatures":"star_border","prevSize":32,"code":59670,"name":"star"},"setIdx":0,"setId":1,"iconIdx":48},{"icon":{"paths":["M640 662l150-150-150-150v108h-256v-108l-150 150 150 150v-108h256v108zM854 170c46 0 84 40 84 86v512c0 46-38 86-84 86h-684c-46 0-84-40-84-86v-512c0-46 38-86 84-86h136l78-84h256l78 84h136z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["switch_camera"],"grid":0},"attrs":[],"properties":{"id":1036,"order":1366,"ligatures":"switch_camera","prevSize":32,"code":59681,"name":"switch-camera"},"setIdx":0,"setId":1,"iconIdx":49},{"icon":{"paths":["M896 726v-512h-768v512h768zM896 128c46 0 86 40 86 86l-2 512c0 46-38 84-84 84h-214v86h-340v-86h-214c-46 0-86-38-86-84v-512c0-46 40-86 86-86h768z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["tv"],"grid":0},"attrs":[],"properties":{"id":1037,"order":1367,"ligatures":"tv","prevSize":32,"code":59671,"name":"share-desktop"},"setIdx":0,"setId":1,"iconIdx":50},{"icon":{"paths":["M726 448l170-170v468l-170-170v150c0 24-20 42-44 42h-512c-24 0-42-18-42-42v-428c0-24 18-42 42-42h512c24 0 44 18 44 42v150z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["videocam"],"grid":0},"attrs":[],"properties":{"id":1038,"order":1368,"ligatures":"videocam","prevSize":32,"code":59672,"name":"camera"},"setIdx":0,"setId":1,"iconIdx":51},{"icon":{"paths":["M140 86l756 756-54 54-136-136c-6 4-16 8-24 8h-512c-24 0-42-18-42-42v-428c0-24 18-42 42-42h32l-116-116zM896 278v456l-478-478h264c24 0 44 18 44 42v150z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["videocam_off"],"grid":0},"attrs":[],"properties":{"id":1039,"order":1369,"ligatures":"videocam_off","prevSize":32,"code":59673,"name":"camera-disabled"},"setIdx":0,"setId":1,"iconIdx":52},{"icon":{"paths":["M598 138c172 38 298 192 298 374s-126 336-298 374v-88c124-36 212-150 212-286s-88-250-212-286v-88zM704 512c0 76-42 140-106 172v-344c64 32 106 96 106 172zM128 384h170l214-214v684l-214-214h-170v-256z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["volume_up"],"grid":0},"attrs":[],"properties":{"id":1040,"order":1370,"ligatures":"volume_up","prevSize":32,"code":59674,"name":"volume"},"setIdx":0,"setId":1,"iconIdx":53},{"icon":{"paths":["M952.495 4.935h-818.689c-72.81 0-132.183 60.63-132.183 135.162v750.719c0 74.473 59.372 135.101 132.183 135.101h818.686c72.936 0 132.314-60.625 132.314-135.101v-750.722c0.003-74.532-59.378-135.159-132.311-135.159zM946.346 884.349h-806.14v-737.822h806.015l0.126 737.822z","M685.753 285.456h216.911v566.758h-216.911v-566.758z","M428.672 413.998h216.911v438.216h-216.911v-438.216z","M172.339 542.54h216.161v309.677h-216.161v-309.677z"],"width":1088,"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["presentation"],"grid":0},"attrs":[],"properties":{"order":1373,"id":1043,"prevSize":32,"code":58883,"name":"presentation","ligatures":""},"setIdx":0,"setId":1,"iconIdx":54},{"icon":{"paths":["M512 384c70 0 128 58 128 128s-58 128-128 128-128-58-128-128 58-128 128-128zM512 726c118 0 214-96 214-214s-96-214-214-214-214 96-214 214 96 214 214 214zM512 192c214 0 396 132 470 320-74 188-256 320-470 320s-396-132-470-320c74-188 256-320 470-320z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["visibility"],"grid":0},"attrs":[],"properties":{"order":1375,"ligatures":"remove_red_eye, visibility","id":1045,"prevSize":32,"code":59683,"name":"visibility"},"setIdx":0,"setId":1,"iconIdx":55},{"icon":{"paths":["M506 384h6c70 0 128 58 128 128v8zM322 418c-14 28-24 60-24 94 0 118 96 214 214 214 34 0 66-10 94-24l-66-66c-8 2-18 4-28 4-70 0-128-58-128-128 0-10 2-20 4-28zM86 182l54-54 756 756-54 54c-47.968-47.365-96.266-94.401-144-142-58 24-120 36-186 36-214 0-396-132-470-320 34-84 90-156 160-212-39.017-38.983-77.307-78.693-116-118zM512 298c-28 0-54 6-78 16l-92-92c52-20 110-30 170-30 214 0 394 132 468 320-32 80-82 148-146 202l-124-124c10-24 16-50 16-78 0-118-96-214-214-214z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["visibility_off"],"grid":0},"attrs":[],"properties":{"order":1376,"ligatures":"visibility_off","id":1046,"prevSize":32,"code":59684,"name":"visibility-off"},"setIdx":0,"setId":1,"iconIdx":56}],"height":1024,"metadata":{"name":"jitsi"},"preferences":{"showGlyphs":true,"showQuickUse":true,"showQuickUse2":true,"showSVGs":true,"fontPref":{"prefix":"icon-","metadata":{"fontFamily":"jitsi","majorVersion":1,"minorVersion":0},"metrics":{"emSize":1024,"baseline":0},"embed":false},"imagePref":{"prefix":"icon-","png":true,"useClassSelector":true,"classSelector":".icon","name":"icomoon"},"historySize":100,"showCodes":false,"search":"","showLiga":false,"gridSize":16}} \ No newline at end of file +{"IcoMoonType":"selection","icons":[{"icon":{"paths":["M282 460c62 120 162 220 282 282l94-94c12-12 30-16 44-10 48 16 100 24 152 24 24 0 42 18 42 42v150c0 24-18 42-42 42-400 0-726-326-726-726 0-24 18-42 42-42h150c24 0 42 18 42 42 0 54 8 104 24 152 4 14 2 32-10 44z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["phone"],"defaultCode":57549,"grid":24},"attrs":[],"properties":{"ligatures":"call, local_phone, phone","id":120,"order":1388,"prevSize":24,"code":57549,"name":"phone"},"setIdx":0,"setId":2,"iconIdx":120},{"icon":{"paths":["M512 854c188 0 342-154 342-342s-154-342-342-342-342 154-342 342 154 342 342 342zM512 86c236 0 426 190 426 426s-190 426-426 426-426-190-426-426 190-426 426-426z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["radio_button_unchecked"],"defaultCode":59446,"grid":24},"attrs":[],"properties":{"ligatures":"panorama_fish_eye, radio_button_unchecked","id":540,"order":1385,"prevSize":24,"code":59446,"name":"radio_button_unchecked"},"setIdx":1,"setId":1,"iconIdx":0},{"icon":{"paths":["M512 854c188 0 342-154 342-342s-154-342-342-342-342 154-342 342 154 342 342 342zM512 86c236 0 426 190 426 426s-190 426-426 426-426-190-426-426 190-426 426-426zM512 298c118 0 214 96 214 214s-96 214-214 214-214-96-214-214 96-214 214-214z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["radio_button_checked"],"defaultCode":59447,"grid":24},"attrs":[],"properties":{"ligatures":"radio_button_checked","id":610,"order":1386,"prevSize":24,"code":59447,"name":"radio_button_checked"},"setIdx":1,"setId":1,"iconIdx":1},{"icon":{"paths":["M406 598c106 0 192-86 192-192s-86-192-192-192-192 86-192 192 86 192 192 192zM662 598l212 212-64 64-212-212v-34l-12-12c-48 42-112 66-180 66-154 0-278-122-278-276s124-278 278-278 276 124 276 278c0 68-24 132-66 180l12 12h34z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["search"],"defaultCode":59574,"grid":24},"attrs":[],"properties":{"ligatures":"search","id":655,"order":1387,"prevSize":24,"code":59574,"name":"search"},"setIdx":1,"setId":1,"iconIdx":2},{"icon":{"paths":["M768 342v-86h-512v86h512zM598 598v-86h-342v86h342zM256 384v86h512v-86h-512zM854 86c46 0 84 38 84 84v512c0 46-38 86-84 86h-598l-170 170v-768c0-46 38-84 84-84h684z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["chat"],"defaultCode":57527,"grid":24},"attrs":[],"properties":{"ligatures":"chat","id":145,"order":1382,"prevSize":24,"code":57527,"name":"chat-unread"},"setIdx":1,"setId":1,"iconIdx":3},{"icon":{"paths":["M768 470v-44c0-24-18-42-42-42h-128c-24 0-44 18-44 42v172c0 24 20 42 44 42h128c24 0 42-18 42-42v-44h-64v22h-86v-128h86v22h64zM470 470v-44c0-24-20-42-44-42h-128c-24 0-42 18-42 42v172c0 24 18 42 42 42h128c24 0 44-18 44-42v-44h-64v22h-86v-128h86v22h64zM810 170c46 0 86 40 86 86v512c0 46-40 86-86 86h-596c-48 0-86-40-86-86v-512c0-46 38-86 86-86h596z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"tags":["closed_caption"],"grid":24},"attrs":[{}],"properties":{"order":1,"id":0,"prevSize":24,"code":59696,"name":"closed_caption"},"setIdx":1,"setId":1,"iconIdx":4},{"icon":{"paths":["M113.778 0h227.556c62.838 0 113.778 50.94 113.778 113.778v227.556c0 62.838-50.94 113.778-113.778 113.778h-227.556c-62.838 0-113.778-50.94-113.778-113.778v-227.556c0-62.838 50.94-113.778 113.778-113.778zM170.667 113.778c-31.419 0-56.889 25.47-56.889 56.889v113.778c0 31.419 25.47 56.889 56.889 56.889h113.778c31.419 0 56.889-25.47 56.889-56.889v-113.778c0-31.419-25.47-56.889-56.889-56.889h-113.778zM113.778 568.889h227.556c62.838 0 113.778 50.94 113.778 113.778v227.556c0 62.838-50.94 113.778-113.778 113.778h-227.556c-62.838 0-113.778-50.94-113.778-113.778v-227.556c0-62.838 50.94-113.778 113.778-113.778zM170.667 682.667c-31.419 0-56.889 25.47-56.889 56.889v113.778c0 31.419 25.47 56.889 56.889 56.889h113.778c31.419 0 56.889-25.47 56.889-56.889v-113.778c0-31.419-25.47-56.889-56.889-56.889h-113.778zM682.667 0h227.556c62.838 0 113.778 50.94 113.778 113.778v227.556c0 62.838-50.94 113.778-113.778 113.778h-227.556c-62.838 0-113.778-50.94-113.778-113.778v-227.556c0-62.838 50.94-113.778 113.778-113.778zM739.556 113.778c-31.419 0-56.889 25.47-56.889 56.889v113.778c0 31.419 25.47 56.889 56.889 56.889h113.778c31.419 0 56.889-25.47 56.889-56.889v-113.778c0-31.419-25.47-56.889-56.889-56.889h-113.778zM682.667 568.889h227.556c62.838 0 113.778 50.94 113.778 113.778v227.556c0 62.838-50.94 113.778-113.778 113.778h-227.556c-62.838 0-113.778-50.94-113.778-113.778v-227.556c0-62.838 50.94-113.778 113.778-113.778zM739.556 682.667c-31.419 0-56.889 25.47-56.889 56.889v113.778c0 31.419 25.47 56.889 56.889 56.889h113.778c31.419 0 56.889-25.47 56.889-56.889v-113.778c0-31.419-25.47-56.889-56.889-56.889h-113.778z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"grid":24,"tags":["tiles-many"]},"attrs":[{}],"properties":{"order":1377,"id":1065,"name":"tiles-many","prevSize":24,"code":59694},"setIdx":1,"setId":1,"iconIdx":5},{"icon":{"paths":["M810 274l-238 238 238 238-60 60-238-238-238 238-60-60 238-238-238-238 60-60 238 238 238-238z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["close"],"defaultCode":58829,"grid":24},"attrs":[],"properties":{"ligatures":"clear, close","id":157,"order":1313,"prevSize":24,"code":58829,"name":"close"},"setIdx":1,"setId":1,"iconIdx":6},{"icon":{"paths":["M598 128h298v298h-86v-152l-418 418-60-60 418-418h-152v-86zM810 810v-298h86v298c0 46-40 86-86 86h-596c-48 0-86-40-86-86v-596c0-46 38-86 86-86h298v86h-298v596h596z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["open_in_new"],"defaultCode":59550,"grid":24},"attrs":[],"properties":{"ligatures":"launch, open_in_new","id":1047,"order":1314,"prevSize":24,"name":"open_in_new","code":59550},"setIdx":1,"setId":1,"iconIdx":7},{"icon":{"paths":["M512 342h64v180l150 90-32 52-182-110v-212zM554 128c212 0 384 172 384 384s-172 384-384 384c-106 0-200-42-270-112l60-62c54 54 128 88 210 88 166 0 300-132 300-298s-134-298-300-298-298 132-298 298h128l-172 172-4-6-166-166h128c0-212 172-384 384-384z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["restore"],"defaultCode":59571,"grid":24},"attrs":[],"properties":{"ligatures":"history, restore","id":1048,"order":1315,"prevSize":24,"code":59571,"name":"restore"},"setIdx":1,"setId":1,"iconIdx":8},{"icon":{"paths":["M426 256l256 256-256 256-60-60 196-196-196-196z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["navigate_next"],"defaultCode":58377,"grid":24},"attrs":[],"properties":{"ligatures":"chevron_right, navigate_next","id":1049,"order":1316,"prevSize":24,"code":58377,"name":"navigate_next"},"setIdx":1,"setId":1,"iconIdx":9},{"icon":{"paths":["M128 256h768v86h-768v-86zM128 554v-84h768v84h-768zM128 768v-86h768v86h-768z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["menu"],"defaultCode":58834,"grid":24},"attrs":[],"properties":{"ligatures":"menu","id":1050,"order":1317,"prevSize":24,"code":58834,"name":"menu"},"setIdx":1,"setId":1,"iconIdx":10},{"icon":{"paths":["M854 470v84h-520l238 240-60 60-342-342 342-342 60 60-238 240h520z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["arrow_back"],"defaultCode":58820,"grid":24},"attrs":[],"properties":{"ligatures":"arrow_back","id":1051,"order":1318,"prevSize":24,"code":58820,"name":"arrow_back"},"setIdx":1,"setId":1,"iconIdx":11},{"icon":{"paths":["M764 742c56-60 90-142 90-230 0-142-88-266-214-316v18c0 46-40 84-86 84h-84v86c0 24-20 42-44 42h-84v86h256c24 0 42 18 42 42v128h42c38 0 70 26 82 60zM470 850v-82c-46 0-86-40-86-86v-42l-204-204c-6 24-10 50-10 76 0 174 132 318 300 338zM512 86c236 0 426 190 426 426s-190 426-426 426-426-190-426-426 190-426 426-426z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["public"],"defaultCode":59403,"grid":24},"attrs":[],"properties":{"ligatures":"public","id":1053,"order":1320,"prevSize":24,"code":59403,"name":"public"},"setIdx":1,"setId":1,"iconIdx":12},{"icon":{"paths":["M598 598v84h-300v-84h300zM810 810v-468h-596v468h596zM810 128c46 0 86 40 86 86v596c0 46-40 86-86 86h-596c-48 0-86-40-86-86v-596c0-46 38-86 86-86h42v-86h86v86h340v-86h86v86h42zM726 426v86h-428v-86h428z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["event_note"],"defaultCode":58902,"grid":24},"attrs":[],"properties":{"ligatures":"event_note","id":1054,"order":1321,"prevSize":24,"code":58902,"name":"event_note"},"setIdx":1,"setId":1,"iconIdx":13},{"icon":{"paths":["M550 696l-80-82v162zM470 248v162l80-82zM670 328l-184 184 184 184-244 242h-42v-324l-196 196-60-60 238-238-238-238 60-60 196 196v-324h42zM834 286c40 64 62 142 62 222 0 84-24 160-66 226l-50-50c26-52 42-110 42-172s-16-120-42-172zM608 512l98-98c12 30 20 64 20 98s-8 70-20 100z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["bluetooth_searching"],"defaultCode":57770,"grid":24},"attrs":[],"properties":{"ligatures":"bluetooth_audio, bluetooth_searching","id":1056,"order":1323,"prevSize":24,"code":57770,"name":"bluetooth"},"setIdx":1,"setId":1,"iconIdx":14},{"icon":{"paths":["M512 42c212 0 384 172 384 384v300c0 70-58 128-128 128h-128v-342h170v-86c0-166-132-298-298-298s-298 132-298 298v86h170v342h-128c-70 0-128-58-128-128v-300c0-212 172-384 384-384z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["headset"],"defaultCode":58128,"grid":24},"attrs":[],"properties":{"ligatures":"headset","id":1057,"order":1324,"prevSize":24,"code":58128,"name":"headset"},"setIdx":1,"setId":1,"iconIdx":15},{"icon":{"paths":["M640 512c0-70-58-128-128-128v-86c118 0 214 96 214 214h-86zM810 512c0-166-132-298-298-298v-86c212 0 384 172 384 384h-86zM854 662c24 0 42 18 42 42v150c0 24-18 42-42 42-400 0-726-326-726-726 0-24 18-42 42-42h150c24 0 42 18 42 42 0 54 8 104 24 152 4 14 2 32-10 44l-94 94c62 122 162 220 282 282l94-94c12-12 30-14 44-10 48 16 98 24 152 24z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["phone_in_talk"],"defaultCode":58909,"grid":24},"attrs":[],"properties":{"ligatures":"phone_in_talk","id":1058,"order":1325,"prevSize":24,"code":58909,"name":"phone-talk"},"setIdx":1,"setId":1,"iconIdx":16},{"icon":{"paths":["M512 682c46 0 86 40 86 86s-40 86-86 86-86-40-86-86 40-86 86-86zM512 426c46 0 86 40 86 86s-40 86-86 86-86-40-86-86 40-86 86-86zM512 342c-46 0-86-40-86-86s40-86 86-86 86 40 86 86-40 86-86 86z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["more_vert"],"defaultCode":58836,"grid":24},"attrs":[],"properties":{"ligatures":"more_vert","id":1059,"order":1326,"prevSize":24,"code":58836,"name":"thumb-menu"},"setIdx":1,"setId":1,"iconIdx":17},{"icon":{"paths":["M330.667 554.667c-0.427-14.933 6.4-29.44 17.92-39.253 32 6.827 61.867 20.053 88.747 39.253 0 29.013-23.893 52.907-53.333 52.907s-52.907-23.467-53.333-52.907zM586.667 554.667c26.88-18.773 56.747-32 88.747-38.827 11.52 9.813 18.347 24.32 17.92 38.827 0 29.867-23.893 53.76-53.333 53.76s-53.333-23.893-53.333-53.76v0zM512 384c-118.187-1.707-234.667 27.733-338.347 85.333l-2.987 42.667c0 52.48 12.373 104.107 35.84 151.040 101.12-15.36 203.093-23.040 305.493-23.040s204.373 7.68 305.493 23.040c23.467-46.933 35.84-98.56 35.84-151.040l-2.987-42.667c-103.68-57.6-220.16-87.040-338.347-85.333zM512 85.333c235.641 0 426.667 191.025 426.667 426.667s-191.025 426.667-426.667 426.667c-235.641 0-426.667-191.025-426.667-426.667s191.025-426.667 426.667-426.667z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"tags":["ninja"],"grid":24},"attrs":[{}],"properties":{"order":1327,"id":1060,"name":"ninja","prevSize":24,"code":59657},"setIdx":1,"setId":1,"iconIdx":18},{"icon":{"paths":["M810 554h-256v256h-84v-256h-256v-84h256v-256h84v256h256v84z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["invite"],"defaultCode":57669,"grid":24},"attrs":[],"properties":{"ligatures":"add","id":1062,"order":1329,"prevSize":24,"code":57669,"name":"invite"},"setIdx":1,"setId":1,"iconIdx":19},{"icon":{"paths":["M810 554h-256v256h-84v-256h-256v-84h256v-256h84v256h256v84z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["add"],"defaultCode":57669,"grid":24},"attrs":[],"properties":{"order":1383,"id":1066,"prevSize":24,"code":57670,"name":"add"},"setIdx":1,"setId":1,"iconIdx":20},{"icon":{"paths":["M790.857 529.714l-758.857 421.714c-17.714 9.714-32 1.143-32-18.857v-841.143c0-20 14.286-28.571 32-18.857l758.857 421.714c17.714 9.714 17.714 25.714 0 35.429z"],"width":808.5942857142857,"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["play"],"defaultCode":61515,"grid":14},"attrs":[],"properties":{"name":"play","id":75,"order":1380,"prevSize":28,"code":61515},"setIdx":1,"setId":1,"iconIdx":21},{"icon":{"paths":["M877.714 109.714v804.571c0 20-16.571 36.571-36.571 36.571h-804.571c-20 0-36.571-16.571-36.571-36.571v-804.571c0-20 16.571-36.571 36.571-36.571h804.571c20 0 36.571 16.571 36.571 36.571z"],"width":877.7142857142857,"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["stop"],"defaultCode":61517,"grid":14},"attrs":[],"properties":{"name":"stop","id":77,"order":1381,"prevSize":28,"code":61517},"setIdx":1,"setId":1,"iconIdx":22},{"icon":{"paths":["M950.857 365.714c40.571 0 73.143 32.571 73.143 73.143s-32.571 73.143-73.143 73.143v219.429c0 40-33.143 73.143-73.143 73.143-101.714-84.571-265.714-200.571-464-217.143-68 22.857-91.429 102.286-46.857 148-40 65.714 11.429 112 72 159.429-35.429 69.714-182.857 70.857-235.429 22.286-33.143-101.714-82.286-203.429-42.286-332h-69.714c-50.286 0-91.429-41.143-91.429-91.429v-109.714c0-50.286 41.143-91.429 91.429-91.429h274.286c219.429 0 402.286-128 512-219.429 40 0 73.143 33.143 73.143 73.143v219.429zM877.714 710.857v-545.143c-149.143 114.286-293.714 180-438.857 196v154.286c145.143 16 289.714 80.571 438.857 194.857z"],"width":1024,"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["bullhorn"],"defaultCode":61601,"grid":14},"attrs":[],"properties":{"name":"dominant-speaker","id":152,"order":1379,"prevSize":28,"code":61601},"setIdx":1,"setId":1,"iconIdx":23},{"icon":{"paths":["M0 512c0 282.795 229.205 512 512 512s512-229.205 512-512c0-282.795-229.205-512-512-512s-512 229.205-512 512zM525.005 264.638c-20.475-24.944-16.326-61.342 9.268-81.297s62.94-15.911 83.416 9.033c16.036 19.536 38.593 52.97 60.894 97.797 81.621 164.065 89.461 340.992-26.857 506.352-8.384 11.919-17.386 23.69-27.012 35.307-20.593 24.851-57.959 28.727-83.458 8.657s-29.476-56.487-8.882-81.338c7.686-9.275 14.833-18.621 21.455-28.035 88.66-126.041 82.71-260.306 17.953-390.475-10.599-21.305-21.94-40.51-33.198-57.196-6.515-9.657-11.322-16.057-13.578-18.805zM353.479 376.54c-19.353-24.679-15.129-60.448 9.434-79.893s60.164-15.2 79.517 9.479c9.635 12.287 22.577 32.644 35.209 60.034 50.35 109.176 50.35 231.689-33.639 349.612-18.198 25.551-53.566 31.441-78.997 13.157s-31.294-53.819-13.096-79.37c57.564-80.822 57.564-160.581 22.983-235.565-8.601-18.65-16.892-31.691-21.412-37.455z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"grid":0,"tags":["speaker"]},"attrs":[{}],"properties":{"order":1312,"id":1063,"name":"speaker","prevSize":32,"code":59693},"setIdx":1,"setId":1,"iconIdx":24},{"icon":{"paths":["M512 1024c-282.77 0-512-229.23-512-512s229.23-512 512-512c282.77 0 512 229.23 512 512s-229.23 512-512 512zM581.333 590.218h-110.595v-59.233h104.338v-40.332h-104.338v-56.87h110.595v-43.539h-161.665v243.512h161.665v-43.539zM738.771 640c58.849 0 101.802-36.282 106.029-88.933h-49.717c-4.904 26.832-26.888 44.045-56.143 44.045-38.556 0-62.4-31.895-62.4-83.196s23.844-83.027 62.231-83.027c29.086 0 51.239 18.394 56.143 46.407h49.717c-3.72-52.989-48.026-91.296-105.86-91.296-70.855 0-114.485 48.77-114.485 127.916 0 79.314 43.798 128.084 114.485 128.084zM230.27 545.498h41.769l45.489 88.258h57.834l-51.408-96.19c28.072-11.138 44.306-38.138 44.306-69.189 0-48.432-32.976-78.133-86.582-78.133h-102.478v243.512h51.070v-88.258zM230.27 431.42v74.927h44.813c25.704 0 40.754-13.838 40.754-37.295 0-23.119-15.896-37.632-41.262-37.632h-44.306z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"grid":0,"tags":["rec"]},"attrs":[{}],"properties":{"order":1331,"id":1001,"name":"rec","prevSize":32,"code":59691},"setIdx":1,"setId":1,"iconIdx":25},{"icon":{"paths":["M725.333 512c0 117.821-95.513 213.333-213.333 213.333s-213.333-95.513-213.333-213.333c0-117.821 95.513-213.333 213.333-213.333s213.333 95.513 213.333 213.333z","M512 768c141.385 0 256-114.615 256-256s-114.615-256-256-256v0c-141.385 0-256 114.615-256 256s114.615 256 256 256v0zM512 810.667c-164.949 0-298.667-133.718-298.667-298.667s133.718-298.667 298.667-298.667v0c164.949 0 298.667 133.718 298.667 298.667s-133.718 298.667-298.667 298.667v0z"],"attrs":[{},{}],"isMulticolor":false,"isMulticolor2":false,"grid":0,"tags":["camera-take-picture"]},"attrs":[{},{}],"properties":{"order":1332,"id":1002,"name":"camera-take-picture","prevSize":32,"code":59690},"setIdx":1,"setId":1,"iconIdx":26},{"icon":{"paths":["M512 1024c-282.77 0-512-229.23-512-512s229.23-512 512-512c282.77 0 512 229.23 512 512s-229.23 512-512 512zM308.25 636.7h57.225l-87.675-252.525h-62.125l-87.675 252.525h53.025l19.425-60.2h88.725l19.075 60.2zM461.9 384.175h-52.85v165.375c0 56 41.125 93.625 105.7 93.625 64.75 0 105.875-37.625 105.875-93.625v-165.375h-52.85v159.95c0 31.85-19.075 52.15-53.025 52.15-33.775 0-52.85-20.3-52.85-52.15v-159.95zM682.225 384v252.7h99.4c75.6 0 118.475-46.025 118.475-128.1 0-79.1-43.4-124.6-118.475-124.6h-99.4zM735.075 429.15v162.4h38.15c46.725 0 72.975-28.7 72.975-82.075 0-51.1-27.125-80.325-72.975-80.325h-38.15zM243.5 436.675l-31.675 99.050h66.15l-31.325-99.050h-3.15z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"grid":0,"tags":["AUD"]},"attrs":[{}],"properties":{"order":1333,"id":1003,"name":"AUD","prevSize":32,"code":59648},"setIdx":1,"setId":1,"iconIdx":27},{"icon":{"paths":["M512 1024c-282.77 0-512-229.23-512-512s229.23-512 512-512c282.77 0 512 229.23 512 512s-229.23 512-512 512zM481.359 640v-255.823h-54.273v103.18h-116.813v-103.18h-54.273v255.823h54.273v-106.903h116.813v106.903h54.273zM544.258 384v256h102.077c77.636 0 121.665-46.626 121.665-129.773 0-80.133-44.569-126.227-121.665-126.227h-102.077zM598.531 429.74v164.521h39.177c47.983 0 74.94-29.075 74.94-83.147 0-51.767-27.855-81.374-74.94-81.374h-39.177z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"grid":0,"tags":["HD"]},"attrs":[{}],"properties":{"order":1334,"id":1004,"name":"HD","prevSize":32,"code":59687},"setIdx":1,"setId":1,"iconIdx":28},{"icon":{"paths":["M512 1024c-282.77 0-512-229.23-512-512s229.23-512 512-512c282.77 0 512 229.23 512 512s-229.23 512-512 512zM472.4 590.675h-112.35v-206.5h-52.85v252.525h165.2v-46.025zM520.35 384v252.7h99.4c75.6 0 118.475-46.025 118.475-128.1 0-79.1-43.4-124.6-118.475-124.6h-99.4zM573.2 429.15v162.4h38.15c46.725 0 72.975-28.7 72.975-82.075 0-51.1-27.125-80.325-72.975-80.325h-38.15z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"grid":0,"tags":["LD"]},"attrs":[{}],"properties":{"order":1335,"id":1005,"name":"LD","prevSize":32,"code":59688},"setIdx":1,"setId":1,"iconIdx":29},{"icon":{"paths":["M512 1024c-282.77 0-512-229.23-512-512s229.23-512 512-512c282.77 0 512 229.23 512 512s-229.23 512-512 512zM281.6 572.825c1.925 47.075 40.95 76.65 101.15 76.65 63.35 0 102.375-31.15 102.375-82.075 0-39.2-21.875-61.075-72.625-71.75l-30.45-6.475c-29.575-6.3-41.65-15.225-41.65-30.8 0-19.25 17.5-31.5 43.925-31.5 25.55 0 44.1 13.3 46.55 33.25h49.7c-1.575-44.975-40.95-76.125-96.6-76.125-58.275 0-96.6 31.325-96.6 78.925 0 38.5 22.575 62.475 68.6 72.1l32.9 7c30.975 6.65 43.575 15.925 43.575 32.025 0 19.075-19.425 32.375-46.9 32.375-29.75 0-50.4-13.125-52.85-33.6h-51.1zM535 390.3v252.7h99.4c75.6 0 118.475-46.025 118.475-128.1 0-79.1-43.4-124.6-118.475-124.6h-99.4zM587.85 435.45v162.4h38.15c46.725 0 72.975-28.7 72.975-82.075 0-51.1-27.125-80.325-72.975-80.325h-38.15z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"grid":0,"tags":["SD"]},"attrs":[{}],"properties":{"order":1336,"id":1006,"name":"SD","prevSize":32,"code":59689},"setIdx":1,"setId":1,"iconIdx":30},{"icon":{"paths":["M896 0c70.692 0 128 57.308 128 128v768c0 70.692-57.308 128-128 128s-128-57.308-128-128v-768c0-70.692 57.308-128 128-128zM512 256c70.692 0 128 57.308 128 128v512c0 70.692-57.308 128-128 128s-128-57.308-128-128v-512c0-70.692 57.308-128 128-128zM128 640v0c70.692 0 128 57.308 128 128v128c0 70.692-57.308 128-128 128s-128-57.308-128-128v-128c0-70.692 57.308-128 128-128v0z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"grid":0,"tags":["gsm-bars-black"]},"attrs":[{}],"properties":{"order":1384,"id":1007,"name":"gsm-bars","prevSize":32,"code":59686},"setIdx":1,"setId":1,"iconIdx":31},{"icon":{"paths":["M512 85.333c-235.52 0-426.667 191.147-426.667 426.667s191.147 426.667 426.667 426.667 426.667-191.147 426.667-426.667-191.147-426.667-426.667-426.667zM554.667 725.333h-85.333v-256h85.333v256zM554.667 384h-85.333v-85.333h85.333v85.333z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"grid":0,"tags":["ic_info_black_24px"]},"attrs":[{}],"properties":{"order":1338,"id":1008,"name":"info","prevSize":32,"code":59682},"setIdx":1,"setId":1,"iconIdx":32},{"icon":{"paths":["M756.704 395.862l267.296-202.213v635.075l-267.296-202.213v191.923c0 12.085-11.296 21.863-25.216 21.863h-706.272c-13.92 0-25.216-9.777-25.216-21.863v-612.25c0-12.085 11.296-21.863 25.216-21.863h706.272c13.92 0 25.216 9.777 25.216 21.863v189.679zM371.338 647.772c47.817 0 86.529-40.232 86.529-89.811v-184.835c0-49.651-38.713-89.883-86.529-89.883-47.788 0-86.515 40.232-86.515 89.883v184.835c0 49.579 38.756 89.811 86.515 89.811v0zM356.754 709.93v32.78h33.718v-33.412c73.858-9.606 131.235-73.73 131.235-151.351v-88.232h-30.636v88.232c0 67.57-53.696 122.534-119.734 122.534-66.024 0-119.691-54.964-119.691-122.534v-88.232h-30.636v88.232c0 79.215 59.674 144.502 135.744 151.969v0.014z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"tags":["Combined Shape"],"grid":0},"attrs":[{}],"properties":{"order":1339,"id":1009,"name":"mic-camera-combined","prevSize":32,"code":59651},"setIdx":1,"setId":1,"iconIdx":33},{"icon":{"paths":["M42.667 896h170.667v-512h-170.667v512zM981.333 426.667c0-46.933-38.4-85.333-85.333-85.333h-269.227l40.533-194.987 1.28-13.653c0-17.493-7.253-33.707-18.773-45.227l-45.227-44.8-280.747 281.173c-15.787 15.36-25.173 36.693-25.173 60.16v426.667c0 46.933 38.4 85.333 85.333 85.333h384c35.413 0 65.707-21.333 78.507-52.053l128.853-300.8c3.84-9.813 5.973-20.053 5.973-31.147v-81.493l-0.427-0.427 0.427-3.413z"],"attrs":[{}],"isMulticolor":false,"isMulticolor2":false,"tags":["ic_thumb_up_black_24px"],"grid":0},"attrs":[{}],"properties":{"order":1340,"id":1010,"name":"feedback","prevSize":32,"code":59677},"setIdx":1,"setId":1,"iconIdx":34},{"icon":{"paths":["M512 384c-68 0-134 10-196 30v132c0 16-10 34-24 40-42 20-80 46-114 78-8 8-18 12-30 12s-22-4-30-12l-106-106c-8-8-12-18-12-30s4-22 12-30c130-124 306-200 500-200s370 76 500 200c8 8 12 18 12 30s-4 22-12 30l-106 106c-8 8-18 12-30 12s-22-4-30-12c-34-32-72-58-114-78-14-6-24-20-24-38v-132c-62-20-128-32-196-32z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["call_end"],"grid":0},"attrs":[],"properties":{"id":1013,"order":1343,"ligatures":"call_end","prevSize":32,"code":59653,"name":"hangup"},"setIdx":1,"setId":1,"iconIdx":35},{"icon":{"paths":["M854 682v-512h-684v598l86-86h598zM854 86c46 0 84 38 84 84v512c0 46-38 86-84 86h-598l-170 170v-768c0-46 38-84 84-84h684z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["chat_bubble_outline"],"grid":0},"attrs":[],"properties":{"id":1014,"order":1344,"ligatures":"chat_bubble_outline","prevSize":32,"code":59654,"name":"chat"},"setIdx":1,"setId":1,"iconIdx":36},{"icon":{"paths":["M554 384h236l-236-234v234zM682 598v-86h-340v86h340zM682 768v-86h-340v86h340zM598 86l256 256v512c0 46-40 84-86 84h-512c-46 0-86-38-86-84l2-684c0-46 38-84 84-84h342z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["description"],"grid":0},"attrs":[],"properties":{"id":1017,"order":1347,"ligatures":"description","prevSize":32,"code":59656,"name":"share-doc"},"setIdx":1,"setId":1,"iconIdx":37},{"icon":{"paths":["M512 214l284 426h-568zM214 726h596v84h-596v-84z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["eject"],"grid":0},"attrs":[],"properties":{"id":1018,"order":1348,"ligatures":"eject","prevSize":32,"code":59652,"name":"kick"},"setIdx":1,"setId":1,"iconIdx":38},{"icon":{"paths":["M512 342l256 256-60 60-196-196-196 196-60-60z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["expand_less"],"grid":0},"attrs":[],"properties":{"id":1019,"order":1349,"ligatures":"expand_less","prevSize":32,"code":59679,"name":"menu-up"},"setIdx":1,"setId":1,"iconIdx":39},{"icon":{"paths":["M708 366l60 60-256 256-256-256 60-60 196 196z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["expand_more"],"grid":0},"attrs":[],"properties":{"id":1020,"order":1350,"ligatures":"expand_more","prevSize":32,"code":59680,"name":"menu-down"},"setIdx":1,"setId":1,"iconIdx":40},{"icon":{"paths":["M598 214h212v212h-84v-128h-128v-84zM726 726v-128h84v212h-212v-84h128zM214 426v-212h212v84h-128v128h-84zM298 598v128h128v84h-212v-212h84z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["fullscreen"],"grid":0},"attrs":[],"properties":{"id":1021,"order":1351,"ligatures":"fullscreen","prevSize":32,"code":59659,"name":"full-screen"},"setIdx":1,"setId":1,"iconIdx":41},{"icon":{"paths":["M682 342h128v84h-212v-212h84v128zM598 810v-212h212v84h-128v128h-84zM342 342v-128h84v212h-212v-84h128zM214 682v-84h212v212h-84v-128h-128z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["fullscreen_exit"],"grid":0},"attrs":[],"properties":{"id":1022,"order":1352,"ligatures":"fullscreen_exit","prevSize":32,"code":59660,"name":"exit-full-screen"},"setIdx":1,"setId":1,"iconIdx":42},{"icon":{"paths":["M768 854v-428h-512v428h512zM768 342c46 0 86 38 86 84v428c0 46-40 84-86 84h-512c-46 0-86-38-86-84v-428c0-46 40-84 86-84h388v-86c0-72-60-132-132-132s-132 60-132 132h-82c0-118 96-214 214-214s214 96 214 214v86h42zM512 726c-46 0-86-40-86-86s40-86 86-86 86 40 86 86-40 86-86 86z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["lock_open"],"grid":0},"attrs":[],"properties":{"id":1024,"order":1354,"ligatures":"lock_open","prevSize":32,"code":59661,"name":"security"},"setIdx":1,"setId":1,"iconIdx":43},{"icon":{"paths":["M768 854v-428h-512v428h512zM380 256v86h264v-86c0-72-60-132-132-132s-132 60-132 132zM768 342c46 0 86 38 86 84v428c0 46-40 84-86 84h-512c-46 0-86-38-86-84v-428c0-46 40-84 86-84h42v-86c0-118 96-214 214-214s214 96 214 214v86h42zM512 726c-46 0-86-40-86-86s40-86 86-86 86 40 86 86-40 86-86 86z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["lock_outline"],"grid":0},"attrs":[],"properties":{"id":1025,"order":1355,"ligatures":"lock_outline","prevSize":32,"code":59662,"name":"security-locked"},"setIdx":1,"setId":1,"iconIdx":44},{"icon":{"paths":["M738 470h72c0 146-116 266-256 286v140h-84v-140c-140-20-256-140-256-286h72c0 128 108 216 226 216s226-88 226-216zM512 598c-70 0-128-58-128-128v-256c0-70 58-128 128-128s128 58 128 128v256c0 70-58 128-128 128z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["mic"],"grid":0},"attrs":[],"properties":{"id":1027,"order":1357,"ligatures":"mic","prevSize":32,"code":59664,"name":"microphone"},"setIdx":1,"setId":1,"iconIdx":45},{"icon":{"paths":["M182 128l714 714-54 54-178-178c-32 20-72 32-110 38v140h-84v-140c-140-20-256-140-256-286h72c0 128 108 216 226 216 34 0 68-8 98-22l-70-70c-8 2-18 4-28 4-70 0-128-58-128-128v-32l-256-256zM640 476l-256-254v-8c0-70 58-128 128-128s128 58 128 128v262zM810 470c0 50-14 98-38 140l-52-54c12-26 18-54 18-86h72z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["mic_off"],"grid":0},"attrs":[],"properties":{"id":1029,"order":1359,"ligatures":"mic_off","prevSize":32,"code":59666,"name":"mic-disabled"},"setIdx":1,"setId":1,"iconIdx":46},{"icon":{"paths":["M982 234v620c0 94-78 170-172 170h-310c-46 0-90-18-122-50l-336-342s54-52 56-52c10-8 22-12 34-12 10 0 18 2 26 6 2 0 184 104 184 104v-508c0-36 28-64 64-64s64 28 64 64v300h42v-406c0-36 28-64 64-64s64 28 64 64v406h42v-364c0-36 28-64 64-64s64 28 64 64v364h44v-236c0-36 28-64 64-64s64 28 64 64z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["pan_tool"],"grid":0},"attrs":[],"properties":{"id":1030,"order":1360,"ligatures":"pan_tool","prevSize":32,"code":59678,"name":"raised-hand"},"setIdx":1,"setId":1,"iconIdx":47},{"icon":{"paths":["M640 598c114 0 342 56 342 170v86h-684v-86c0-114 228-170 342-170zM256 426h128v86h-128v128h-86v-128h-128v-86h128v-128h86v128zM640 512c-94 0-170-76-170-170s76-172 170-172 170 78 170 172-76 170-170 170z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["person_add"],"grid":0},"attrs":[],"properties":{"id":1032,"order":1362,"ligatures":"person_add","prevSize":32,"code":59667,"name":"link"},"setIdx":1,"setId":1,"iconIdx":48},{"icon":{"paths":["M512 854c188 0 342-154 342-342s-154-342-342-342-342 154-342 342 154 342 342 342zM512 86c236 0 426 190 426 426s-190 426-426 426-426-190-426-426 190-426 426-426zM426 704v-384l256 192z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["play_circle_outline"],"grid":0},"attrs":[],"properties":{"id":1033,"order":1363,"ligatures":"play_circle_outline","prevSize":32,"code":59668,"name":"shared-video"},"setIdx":1,"setId":1,"iconIdx":49},{"icon":{"paths":["M512 662c82 0 150-68 150-150s-68-150-150-150-150 68-150 150 68 150 150 150zM830 554l90 70c8 6 10 18 4 28l-86 148c-6 10-16 12-26 8l-106-42c-22 16-46 32-72 42l-16 112c-2 10-10 18-20 18h-172c-10 0-18-8-20-18l-16-112c-26-10-50-24-72-42l-106 42c-10 4-20 2-26-8l-86-148c-6-10-4-22 4-28l90-70c-2-14-2-28-2-42s0-28 2-42l-90-70c-8-6-10-18-4-28l86-148c6-10 16-12 26-8l106 42c22-16 46-32 72-42l16-112c2-10 10-18 20-18h172c10 0 18 8 20 18l16 112c26 10 50 24 72 42l106-42c10-4 20-2 26 8l86 148c6 10 4 22-4 28l-90 70c2 14 2 28 2 42s0 28-2 42z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["settings"],"grid":0},"attrs":[],"properties":{"id":1034,"order":1364,"ligatures":"settings","prevSize":32,"code":59669,"name":"settings"},"setIdx":1,"setId":1,"iconIdx":50},{"icon":{"paths":["M512 658l160 96-42-182 142-124-188-16-72-172-72 172-188 16 142 124-42 182zM938 394l-232 202 70 300-264-160-264 160 70-300-232-202 306-26 120-282 120 282z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["star_border"],"grid":0},"attrs":[],"properties":{"id":1035,"order":1365,"ligatures":"star_border","prevSize":32,"code":59670,"name":"star"},"setIdx":1,"setId":1,"iconIdx":51},{"icon":{"paths":["M640 662l150-150-150-150v108h-256v-108l-150 150 150 150v-108h256v108zM854 170c46 0 84 40 84 86v512c0 46-38 86-84 86h-684c-46 0-84-40-84-86v-512c0-46 38-86 84-86h136l78-84h256l78 84h136z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["switch_camera"],"grid":0},"attrs":[],"properties":{"id":1036,"order":1366,"ligatures":"switch_camera","prevSize":32,"code":59681,"name":"switch-camera"},"setIdx":1,"setId":1,"iconIdx":52},{"icon":{"paths":["M896 726v-512h-768v512h768zM896 128c46 0 86 40 86 86l-2 512c0 46-38 84-84 84h-214v86h-340v-86h-214c-46 0-86-38-86-84v-512c0-46 40-86 86-86h768z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["tv"],"grid":0},"attrs":[],"properties":{"id":1037,"order":1367,"ligatures":"tv","prevSize":32,"code":59671,"name":"share-desktop"},"setIdx":1,"setId":1,"iconIdx":53},{"icon":{"paths":["M726 448l170-170v468l-170-170v150c0 24-20 42-44 42h-512c-24 0-42-18-42-42v-428c0-24 18-42 42-42h512c24 0 44 18 44 42v150z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["videocam"],"grid":0},"attrs":[],"properties":{"id":1038,"order":1368,"ligatures":"videocam","prevSize":32,"code":59672,"name":"camera"},"setIdx":1,"setId":1,"iconIdx":54},{"icon":{"paths":["M140 86l756 756-54 54-136-136c-6 4-16 8-24 8h-512c-24 0-42-18-42-42v-428c0-24 18-42 42-42h32l-116-116zM896 278v456l-478-478h264c24 0 44 18 44 42v150z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["videocam_off"],"grid":0},"attrs":[],"properties":{"id":1039,"order":1369,"ligatures":"videocam_off","prevSize":32,"code":59673,"name":"camera-disabled"},"setIdx":1,"setId":1,"iconIdx":55},{"icon":{"paths":["M598 138c172 38 298 192 298 374s-126 336-298 374v-88c124-36 212-150 212-286s-88-250-212-286v-88zM704 512c0 76-42 140-106 172v-344c64 32 106 96 106 172zM128 384h170l214-214v684l-214-214h-170v-256z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["volume_up"],"grid":0},"attrs":[],"properties":{"id":1040,"order":1370,"ligatures":"volume_up","prevSize":32,"code":59674,"name":"volume"},"setIdx":1,"setId":1,"iconIdx":56},{"icon":{"paths":["M952.495 4.935h-818.689c-72.81 0-132.183 60.63-132.183 135.162v750.719c0 74.473 59.372 135.101 132.183 135.101h818.686c72.936 0 132.314-60.625 132.314-135.101v-750.722c0.003-74.532-59.378-135.159-132.311-135.159zM946.346 884.349h-806.14v-737.822h806.015l0.126 737.822z","M685.753 285.456h216.911v566.758h-216.911v-566.758z","M428.672 413.998h216.911v438.216h-216.911v-438.216z","M172.339 542.54h216.161v309.677h-216.161v-309.677z"],"width":1088,"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["presentation"],"grid":0},"attrs":[],"properties":{"order":1373,"id":1043,"prevSize":32,"code":58883,"name":"presentation","ligatures":""},"setIdx":1,"setId":1,"iconIdx":57},{"icon":{"paths":["M512 384c70 0 128 58 128 128s-58 128-128 128-128-58-128-128 58-128 128-128zM512 726c118 0 214-96 214-214s-96-214-214-214-214 96-214 214 96 214 214 214zM512 192c214 0 396 132 470 320-74 188-256 320-470 320s-396-132-470-320c74-188 256-320 470-320z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["visibility"],"grid":0},"attrs":[],"properties":{"order":1375,"ligatures":"remove_red_eye, visibility","id":1045,"prevSize":32,"code":59683,"name":"visibility"},"setIdx":1,"setId":1,"iconIdx":58},{"icon":{"paths":["M506 384h6c70 0 128 58 128 128v8zM322 418c-14 28-24 60-24 94 0 118 96 214 214 214 34 0 66-10 94-24l-66-66c-8 2-18 4-28 4-70 0-128-58-128-128 0-10 2-20 4-28zM86 182l54-54 756 756-54 54c-47.968-47.365-96.266-94.401-144-142-58 24-120 36-186 36-214 0-396-132-470-320 34-84 90-156 160-212-39.017-38.983-77.307-78.693-116-118zM512 298c-28 0-54 6-78 16l-92-92c52-20 110-30 170-30 214 0 394 132 468 320-32 80-82 148-146 202l-124-124c10-24 16-50 16-78 0-118-96-214-214-214z"],"attrs":[],"isMulticolor":false,"isMulticolor2":false,"tags":["visibility_off"],"grid":0},"attrs":[],"properties":{"order":1376,"ligatures":"visibility_off","id":1046,"prevSize":32,"code":59684,"name":"visibility-off"},"setIdx":1,"setId":1,"iconIdx":59}],"height":1024,"metadata":{"name":"jitsi"},"preferences":{"showGlyphs":true,"showQuickUse":true,"showQuickUse2":true,"showSVGs":true,"fontPref":{"prefix":"icon-","metadata":{"fontFamily":"jitsi","majorVersion":1,"minorVersion":0},"metrics":{"emSize":1024,"baseline":0},"embed":false},"imagePref":{"prefix":"icon-","png":true,"useClassSelector":true,"classSelector":".icon","name":"icomoon"},"historySize":100,"showCodes":false,"search":"","showLiga":false,"gridSize":16}} \ No newline at end of file diff --git a/lang/main.json b/lang/main.json index 7225a026d..44fbdad88 100644 --- a/lang/main.json +++ b/lang/main.json @@ -364,6 +364,16 @@ "title": "Share", "tooltip": "Share link and dial-in info for this meeting" }, + "inviteDialog": { + "alertOk": "Ok", + "alertText": "Failed to invite some participants.", + "alertTitle": "Invite", + "header": "Invite", + "searchCallOnlyPlaceholder": "Enter phone number", + "searchPeopleOnlyPlaceholder": "Search for participants", + "searchPlaceholder": "Participant or phone number", + "send": "Send" + }, "inlineDialogFailure": { "msg": "We stumbled a bit.", "retry": "Try again", diff --git a/react/features/base/react/Types.js b/react/features/base/react/Types.js index 25e9700c7..bd2f223e6 100644 --- a/react/features/base/react/Types.js +++ b/react/features/base/react/Types.js @@ -7,6 +7,11 @@ import type { ComponentType, Element } from 'react'; */ export type Item = { + /** + * The avatar URL or icon name. + */ + avatar: ?string, + /** * the color base of the avatar */ diff --git a/react/features/base/react/components/native/BackButton.js b/react/features/base/react/components/native/BackButton.js index df224d137..289f5119a 100644 --- a/react/features/base/react/components/native/BackButton.js +++ b/react/features/base/react/components/native/BackButton.js @@ -41,7 +41,7 @@ export default class BackButton extends Component { diff --git a/react/features/base/react/components/native/ForwardButton.js b/react/features/base/react/components/native/ForwardButton.js new file mode 100644 index 000000000..96c338f92 --- /dev/null +++ b/react/features/base/react/components/native/ForwardButton.js @@ -0,0 +1,70 @@ +// @flow + +import React, { Component } from 'react'; +import { Text, TouchableOpacity } from 'react-native'; + +import { translate } from '../../../i18n'; + +import styles from './styles'; + +/** + * The type of the React {@code Component} props of {@link ForwardButton} + */ +type Props = { + + /** + * True if the nutton should be disabled. + */ + disabled: boolean; + + /** + * The i18n label key of the button. + */ + labelKey: string, + + /** + * The action to be performed when the button is pressed. + */ + onPress: Function, + + /** + * An external style object passed to the component. + */ + style?: Object, + + /** + * The function to be used to translate i18n labels. + */ + t: Function +}; + +/** + * A component rendering a forward/next/action button. + */ +class ForwardButton extends Component { + /** + * Implements React's {@link Component#render()}, renders the button. + * + * @inheritdoc + * @returns {ReactElement} + */ + render() { + return ( + + + { this.props.t(this.props.labelKey) } + + + ); + } +} + +export default translate(ForwardButton); diff --git a/react/features/base/react/components/native/Header.js b/react/features/base/react/components/native/Header.js index 91797d64f..5346db201 100644 --- a/react/features/base/react/components/native/Header.js +++ b/react/features/base/react/components/native/Header.js @@ -38,7 +38,7 @@ export default class Header extends Component { * @returns {Object} */ static get buttonStyle(): Object { - return styles.headerButton; + return styles.headerButtonIcon; } /** diff --git a/react/features/base/react/components/native/HeaderLabel.js b/react/features/base/react/components/native/HeaderLabel.js index e1d3b129f..c7e28b316 100644 --- a/react/features/base/react/components/native/HeaderLabel.js +++ b/react/features/base/react/components/native/HeaderLabel.js @@ -1,7 +1,7 @@ // @flow import React, { Component } from 'react'; -import { Text } from 'react-native'; +import { Text, View } from 'react-native'; import { translate } from '../../../i18n'; @@ -35,12 +35,16 @@ class HeaderLabel extends Component { */ render() { return ( - - { this.props.t(this.props.labelKey) } - + + + { this.props.t(this.props.labelKey) } + + ); } } diff --git a/react/features/base/react/components/native/index.js b/react/features/base/react/components/native/index.js index a02da2eec..897cc7f57 100644 --- a/react/features/base/react/components/native/index.js +++ b/react/features/base/react/components/native/index.js @@ -3,6 +3,7 @@ export { default as AvatarListItem } from './AvatarListItem'; export { default as BackButton } from './BackButton'; export { default as Container } from './Container'; +export { default as ForwardButton } from './ForwardButton'; export { default as Header } from './Header'; export { default as HeaderLabel } from './HeaderLabel'; export { default as Link } from './Link'; diff --git a/react/features/base/react/components/native/styles.js b/react/features/base/react/components/native/styles.js index 9b3badaf4..e900ef661 100644 --- a/react/features/base/react/components/native/styles.js +++ b/react/features/base/react/components/native/styles.js @@ -19,16 +19,26 @@ export const SIDEBAR_WIDTH = 250; export const UNDERLAY_COLOR = 'rgba(255, 255, 255, 0.2)'; const HEADER_STYLES = { + + disabledButtonText: { + opacity: 0.6 + }, + /** * Platform specific header button (e.g. back, menu, etc). */ - headerButton: { + headerButtonIcon: { alignSelf: 'center', color: ColorPalette.white, fontSize: 26, paddingRight: 22 }, + headerButtonText: { + color: ColorPalette.white, + fontSize: 20 + }, + /** * Style of the header overlay to cover the unsafe areas. */ @@ -44,6 +54,14 @@ const HEADER_STYLES = { fontSize: 20 }, + headerTextWrapper: { + alignItems: 'center', + justifyContent: 'center', + left: 0, + position: 'absolute', + right: 0 + }, + /** * The top-level element of a page. */ @@ -63,7 +81,7 @@ const HEADER_STYLES = { backgroundColor: HEADER_COLOR, flexDirection: 'row', height: HEADER_HEIGHT, - justifyContent: 'flex-start', + justifyContent: 'space-between', padding: HEADER_PADDING } }; diff --git a/react/features/conference/components/native/Conference.js b/react/features/conference/components/native/Conference.js index 1e49593ce..7d9ad8360 100644 --- a/react/features/conference/components/native/Conference.js +++ b/react/features/conference/components/native/Conference.js @@ -22,7 +22,7 @@ import { TileView } from '../../../filmstrip'; import { LargeVideo } from '../../../large-video'; -import { CalleeInfoContainer } from '../../../invite'; +import { AddPeopleDialog, CalleeInfoContainer } from '../../../invite'; import { Captions } from '../../../subtitles'; import { setToolboxVisible, Toolbox } from '../../../toolbox'; import { shouldDisplayTileView } from '../../../video-layout'; @@ -255,6 +255,7 @@ class Conference extends Component { translucent = { true } /> + {/* * The LargeVideo is the lowermost stacking layer. diff --git a/react/features/invite/actionTypes.js b/react/features/invite/actionTypes.js index 955eeca10..dc5ec9026 100644 --- a/react/features/invite/actionTypes.js +++ b/react/features/invite/actionTypes.js @@ -41,6 +41,16 @@ export const REMOVE_PENDING_INVITE_REQUESTS */ export const SET_CALLEE_INFO_VISIBLE = Symbol('SET_CALLEE_INFO_VISIBLE'); +/** + * The type of redux action which sets the invite dialog visible or invisible. + * + * { + * type: SET_INVITE_DIALOG_VISIBLE, + * visible: boolean + * } + */ +export const SET_INVITE_DIALOG_VISIBLE = Symbol('SET_INVITE_DIALOG_VISIBLE'); + /** * The type of the action which signals an error occurred while requesting dial- * in numbers. diff --git a/react/features/invite/actions.js b/react/features/invite/actions.js index 58c36d941..f167cc54c 100644 --- a/react/features/invite/actions.js +++ b/react/features/invite/actions.js @@ -9,6 +9,7 @@ import { BEGIN_ADD_PEOPLE, REMOVE_PENDING_INVITE_REQUESTS, SET_CALLEE_INFO_VISIBLE, + SET_INVITE_DIALOG_VISIBLE, UPDATE_DIAL_IN_NUMBERS_FAILED, UPDATE_DIAL_IN_NUMBERS_SUCCESS } from './actionTypes'; @@ -197,6 +198,22 @@ export function updateDialInNumbers() { }; } +/** + * Sets the visibility of the invite dialog. + * + * @param {boolean} visible - The visibility to set. + * @returns {{ + * type: SET_INVITE_DIALOG_VISIBLE, + * visible: boolean + * }} + */ +export function setAddPeopleDialogVisible(visible: boolean) { + return { + type: SET_INVITE_DIALOG_VISIBLE, + visible + }; +} + /** * Sets the visibility of {@code CalleeInfo}. * diff --git a/react/features/invite/components/AddPeopleDialog.native.js b/react/features/invite/components/AddPeopleDialog.native.js deleted file mode 100644 index e69de29bb..000000000 diff --git a/react/features/invite/components/InviteButton.native.js b/react/features/invite/components/InviteButton.native.js index e23d34d80..5818b9565 100644 --- a/react/features/invite/components/InviteButton.native.js +++ b/react/features/invite/components/InviteButton.native.js @@ -8,29 +8,21 @@ import { AbstractButton } from '../../base/toolbox'; import type { AbstractButtonProps } from '../../base/toolbox'; import { beginShareRoom } from '../../share-room'; -import { beginAddPeople } from '../actions'; +import { setAddPeopleDialogVisible } from '../actions'; import { isAddPeopleEnabled, isDialOutEnabled } from '../functions'; type Props = AbstractButtonProps & { /** - * Whether or not the feature to directly invite people into the + * Whether or not the feature to invite people to join the * conference is available. */ _addPeopleEnabled: boolean, /** - * Whether or not the feature to dial out to number to join the - * conference is available. + * Opens the add people dialog. */ - _dialOutEnabled: boolean, - - /** - * Launches native invite dialog. - * - * @protected - */ - _onAddPeople: Function, + _onOpenAddPeopleDialog: Function, /** * Begins the UI procedure to share the conference/room URL. @@ -54,12 +46,17 @@ class InviteButton extends AbstractButton { * @returns {void} */ _handleClick() { - // FIXME: dispatch _onAddPeople here, when we have a dialog for it. const { + _addPeopleEnabled, + _onOpenAddPeopleDialog, _onShareRoom } = this.props; - _onShareRoom(); + if (_addPeopleEnabled) { + _onOpenAddPeopleDialog(); + } else { + _onShareRoom(); + } } } @@ -69,22 +66,23 @@ class InviteButton extends AbstractButton { * * @param {Function} dispatch - The redux action {@code dispatch} function. * @returns {{ - * _onAddPeople, + * _onOpenAddPeopleDialog, * _onShareRoom * }} * @private */ function _mapDispatchToProps(dispatch: Dispatch<*>) { return { + /** - * Launches the add people dialog. + * Opens the add people dialog. * * @private * @returns {void} * @type {Function} */ - _onAddPeople() { - dispatch(beginAddPeople()); + _onOpenAddPeopleDialog() { + dispatch(setAddPeopleDialogVisible(true)); }, /** @@ -107,25 +105,12 @@ function _mapDispatchToProps(dispatch: Dispatch<*>) { * @param {Object} state - The redux store/state. * @private * @returns {{ + * _addPeopleEnabled: boolean * }} */ function _mapStateToProps(state) { return { - /** - * Whether or not the feature to directly invite people into the - * conference is available. - * - * @type {boolean} - */ - _addPeopleEnabled: isAddPeopleEnabled(state), - - /** - * Whether or not the feature to dial out to number to join the - * conference is available. - * - * @type {boolean} - */ - _dialOutEnabled: isDialOutEnabled(state) + _addPeopleEnabled: isAddPeopleEnabled(state) || isDialOutEnabled(state) }; } diff --git a/react/features/invite/components/add-people-dialog/AbstractAddPeopleDialog.js b/react/features/invite/components/add-people-dialog/AbstractAddPeopleDialog.js new file mode 100644 index 000000000..7abc29e31 --- /dev/null +++ b/react/features/invite/components/add-people-dialog/AbstractAddPeopleDialog.js @@ -0,0 +1,222 @@ +// @flow + +import { Component } from 'react'; + +import { createInviteDialogEvent, sendAnalytics } from '../../../analytics'; + +import { invite } from '../../actions'; +import { + getInviteResultsForQuery, + getInviteTypeCounts, + isAddPeopleEnabled, + isDialOutEnabled +} from '../../functions'; + +const logger = require('jitsi-meet-logger').getLogger(__filename); + +export type Props = { + + /** + * Whether or not to show Add People functionality. + */ + _addPeopleEnabled: boolean, + + /** + * The URL for validating if a phone number can be called. + */ + _dialOutAuthUrl: string, + + /** + * Whether or not to show Dial Out functionality. + */ + _dialOutEnabled: boolean, + + /** + * The JWT token. + */ + _jwt: string, + + /** + * The query types used when searching people. + */ + _peopleSearchQueryTypes: Array, + + /** + * The URL pointing to the service allowing for people search. + */ + _peopleSearchUrl: string, + + /** + * The Redux dispatch function. + */ + dispatch: Function +}; + +export type State = { + + /** + * Indicating that an error occurred when adding people to the call. + */ + addToCallError: boolean, + + /** + * Indicating that we're currently adding the new people to the + * call. + */ + addToCallInProgress: boolean, + + /** + * The list of invite items. + */ + inviteItems: Array, +}; + +/** + * Implements an abstract dialog to invite people to the conference. + */ +export default class AbstractAddPeopleDialog + extends Component { + /** + * Constructor of the component. + * + * @inheritdoc + */ + constructor(props: P) { + super(props); + + this._query = this._query.bind(this); + } + + /** + * Invite people and numbers to the conference. The logic works by inviting + * numbers, people/rooms, and videosipgw in parallel. All invitees are + * stored in an array. As each invite succeeds, the invitee is removed + * from the array. After all invites finish, close the modal if there are + * no invites left to send. If any are left, that means an invite failed + * and an error state should display. + * + * @param {Array} invitees - The items to be invited. + * @returns {Promise>} + */ + _invite(invitees) { + const inviteTypeCounts = getInviteTypeCounts(invitees); + + sendAnalytics(createInviteDialogEvent( + 'clicked', 'inviteButton', { + ...inviteTypeCounts, + inviteAllowed: this._isAddDisabled() + })); + + if (this._isAddDisabled()) { + return Promise.resolve([]); + } + + this.setState({ + addToCallInProgress: true + }); + + const { dispatch } = this.props; + + return dispatch(invite(invitees)) + .then(invitesLeftToSend => { + this.setState({ + addToCallInProgress: false + }); + + // If any invites are left that means something failed to send + // so treat it as an error. + if (invitesLeftToSend.length) { + const erroredInviteTypeCounts + = getInviteTypeCounts(invitesLeftToSend); + + logger.error(`${invitesLeftToSend.length} invites failed`, + erroredInviteTypeCounts); + + sendAnalytics(createInviteDialogEvent( + 'error', 'invite', { + ...erroredInviteTypeCounts + })); + + this.setState({ + addToCallError: true + }); + } + + return invitesLeftToSend; + }); + } + + /** + * Indicates if the Add button should be disabled. + * + * @private + * @returns {boolean} - True to indicate that the Add button should + * be disabled, false otherwise. + */ + _isAddDisabled() { + return !this.state.inviteItems.length + || this.state.addToCallInProgress; + } + + _query: (string) => Promise>; + + /** + * Performs a people and phone number search request. + * + * @param {string} query - The search text. + * @private + * @returns {Promise} + */ + _query(query = '') { + const { + _addPeopleEnabled: addPeopleEnabled, + _dialOutAuthUrl: dialOutAuthUrl, + _dialOutEnabled: dialOutEnabled, + _jwt: jwt, + _peopleSearchQueryTypes: peopleSearchQueryTypes, + _peopleSearchUrl: peopleSearchUrl + } = this.props; + const options = { + addPeopleEnabled, + dialOutAuthUrl, + dialOutEnabled, + jwt, + peopleSearchQueryTypes, + peopleSearchUrl + }; + + return getInviteResultsForQuery(query, options); + } + +} + +/** + * Maps (parts of) the Redux state to the props of this component. + * + * @param {Object} state - The Redux state. + * @private + * @returns {{ + * _addPeopleEnabled: boolean, + * _dialOutAuthUrl: string, + * _dialOutEnabled: boolean, + * _jwt: string, + * _peopleSearchQueryTypes: Array, + * _peopleSearchUrl: string + * }} + */ +export function _mapStateToProps(state: Object) { + const { + dialOutAuthUrl, + peopleSearchQueryTypes, + peopleSearchUrl + } = state['features/base/config']; + + return { + _addPeopleEnabled: isAddPeopleEnabled(state), + _dialOutAuthUrl: dialOutAuthUrl, + _dialOutEnabled: isDialOutEnabled(state), + _jwt: state['features/base/jwt'].jwt, + _peopleSearchQueryTypes: peopleSearchQueryTypes, + _peopleSearchUrl: peopleSearchUrl + }; +} diff --git a/react/features/invite/components/add-people-dialog/index.native.js b/react/features/invite/components/add-people-dialog/index.native.js new file mode 100644 index 000000000..a32ec6061 --- /dev/null +++ b/react/features/invite/components/add-people-dialog/index.native.js @@ -0,0 +1,3 @@ +// @flow + +export * from './native'; diff --git a/react/features/invite/components/add-people-dialog/index.web.js b/react/features/invite/components/add-people-dialog/index.web.js new file mode 100644 index 000000000..40d5f4652 --- /dev/null +++ b/react/features/invite/components/add-people-dialog/index.web.js @@ -0,0 +1,3 @@ +// @flow + +export * from './web'; diff --git a/react/features/invite/components/add-people-dialog/native/AddPeopleDialog.js b/react/features/invite/components/add-people-dialog/native/AddPeopleDialog.js new file mode 100644 index 000000000..002bfc6d0 --- /dev/null +++ b/react/features/invite/components/add-people-dialog/native/AddPeopleDialog.js @@ -0,0 +1,469 @@ +// @flow + +import _ from 'lodash'; +import React from 'react'; +import { + ActivityIndicator, + Alert, + FlatList, + SafeAreaView, + TextInput, + TouchableOpacity, + View +} from 'react-native'; +import { connect } from 'react-redux'; + +import { Icon } from '../../../../base/font-icons'; +import { translate } from '../../../../base/i18n'; +import { + AvatarListItem, + BackButton, + ForwardButton, + Header, + HeaderLabel, + Modal, + type Item +} from '../../../../base/react'; + +import { setAddPeopleDialogVisible } from '../../../actions'; + +import AbstractAddPeopleDialog, { + type Props as AbstractProps, + type State as AbstractState, + _mapStateToProps as _abstractMapStateToProps +} from '../AbstractAddPeopleDialog'; + +import styles, { + AVATAR_SIZE, + DARK_GREY +} from './styles'; + +type Props = AbstractProps & { + + /** + * True if the invite dialog should be open, false otherwise. + */ + _isVisible: boolean, + + /** + * Function used to translate i18n labels. + */ + t: Function +}; + +type State = AbstractState & { + + /** + * True if a search is in progress, false otherwise. + */ + searchInprogress: boolean, + + /** + * An array of items that are selectable on this dialog. This is usually + * populated by an async search. + */ + selectableItems: Array +}; + +/** + * Implements a special dialog to invite people from a directory service. + */ +class AddPeopleDialog extends AbstractAddPeopleDialog { + /** + * Default state object to reset the state to when needed. + */ + defaultState = { + addToCallError: false, + addToCallInProgress: false, + inviteItems: [], + searchInprogress: false, + selectableItems: [] + }; + + /** + * Ref of the search field. + */ + inputFieldRef: ?TextInput; + + /** + * TimeoutID to delay the search for the time the user is probably typing. + */ + searchTimeout: TimeoutID; + + /** + * Contrustor of the component. + * + * @inheritdoc + */ + constructor(props: Props) { + super(props); + + this.state = this.defaultState; + + this._keyExtractor = this._keyExtractor.bind(this); + this._renderItem = this._renderItem.bind(this); + this._renderSeparator = this._renderSeparator.bind(this); + this._onCloseAddPeopleDialog = this._onCloseAddPeopleDialog.bind(this); + this._onInvite = this._onInvite.bind(this); + this._onPressItem = this._onPressItem.bind(this); + this._onTypeQuery = this._onTypeQuery.bind(this); + this._setFieldRef = this._setFieldRef.bind(this); + } + + /** + * Implements {@code Component#componentDidUpdate}. + * + * @inheritdoc + */ + componentDidUpdate(prevProps) { + if (prevProps._isVisible !== this.props._isVisible) { + // Clear state + this._clearState(); + } + } + + /** + * Implements {@code Component#render}. + * + * @inheritdoc + */ + render() { + const { + _addPeopleEnabled, + _dialOutEnabled + } = this.props; + const { inviteItems } = this.state; + + let placeholderKey = 'searchPlaceholder'; + + if (!_addPeopleEnabled) { + placeholderKey = 'searchCallOnlyPlaceholder'; + } else if (!_dialOutEnabled) { + placeholderKey = 'searchPeopleOnlyPlaceholder'; + } + + return ( + +
+ + + +
+ + + + { this.state.searchInprogress + ? + : } + + + + + +
+ ); + } + + /** + * Clears the dialog content. + * + * @returns {void} + */ + _clearState() { + this.setState(this.defaultState); + } + + _invite: Array => Promise> + + _isAddDisabled: () => boolean; + + _keyExtractor: Object => string + + /** + * Key extractor for the flatlist. + * + * @param {Object} item - The flatlist item that we need the key to be + * generated for. + * @returns {string} + */ + _keyExtractor(item) { + return item.type === 'user' ? item.user_id : item.number; + } + + _onCloseAddPeopleDialog: () => void + + /** + * Closes the dialog. + * + * @returns {void} + */ + _onCloseAddPeopleDialog() { + this.props.dispatch(setAddPeopleDialogVisible(false)); + } + + _onInvite: () => void + + /** + * Invites the selected entries. + * + * @returns {void} + */ + _onInvite() { + this._invite(this.state.inviteItems) + .then(invitesLeftToSend => { + if (invitesLeftToSend.length) { + this.setState({ + inviteItems: invitesLeftToSend + }); + this._showFailedInviteAlert(); + } else { + this._onCloseAddPeopleDialog(); + } + }); + } + + _onPressItem: Item => Function + + /** + * Function to preapre a callback for the onPress event of the touchable. + * + * @param {Item} item - The item on which onPress was invoked. + * @returns {Function} + */ + _onPressItem(item) { + return () => { + const { inviteItems } = this.state; + const finderKey = item.type === 'phone' ? 'number' : 'user_id'; + + if (inviteItems.find( + _.matchesProperty(finderKey, item[finderKey]))) { + // Item is already selected, need to unselect it. + this.setState({ + inviteItems: inviteItems.filter( + element => item[finderKey] !== element[finderKey]) + }); + } else { + // Item is not selected yet, need to add to the list. + this.setState({ + inviteItems: _.orderBy( + inviteItems.concat(item), [ 'name' ], [ 'asc' ]) + }); + } + }; + } + + _onTypeQuery: string => void + + /** + * Handles the typing event of the text field on the dialog and performs the + * search. + * + * @param {string} query - The query that is typed in the field. + * @returns {void} + */ + _onTypeQuery(query) { + clearTimeout(this.searchTimeout); + this.searchTimeout = setTimeout(() => { + this.setState({ + searchInprogress: true + }, () => { + this._performSearch(query); + }); + }, 500); + } + + /** + * Performs the actual search. + * + * @param {string} query - The query to search for. + * @returns {void} + */ + _performSearch(query) { + this._query(query).then(results => { + const { inviteItems } = this.state; + + let selectableItems = results.filter(result => { + switch (result.type) { + case 'phone': + return result.allowed && result.number + && !inviteItems.find( + _.matchesProperty('number', result.number)); + case 'user': + return result.user_id && !inviteItems.find( + _.matchesProperty('user_id', result.user_id)); + default: + return false; + } + }); + + selectableItems + = _.orderBy( + this.state.inviteItems.concat(selectableItems), + [ 'name' ], [ 'asc' ]); + + this.setState({ + selectableItems + }); + }) + .finally(() => { + this.setState({ + searchInprogress: false + }, () => { + this.inputFieldRef && this.inputFieldRef.focus(); + }); + }); + } + + _query: (string) => Promise>; + + _renderItem: Object => ?React$Element<*> + + /** + * Renders a single item in the {@code FlatList}. + * + * @param {Object} flatListItem - An item of the data array of the + * {@code FlatList}. + * @param {number} index - The index of the currently rendered item. + * @returns {?React$Element<*>} + */ + _renderItem(flatListItem, index) { + const { item } = flatListItem; + const { inviteItems } = this.state; + let selected = false; + let renderableItem; + + switch (item.type) { + case 'phone': + selected + = inviteItems.find(_.matchesProperty('number', item.number)); + renderableItem = { + avatar: 'phone', + key: item.number, + title: item.number + }; + break; + case 'user': + selected + = inviteItems.find(_.matchesProperty('user_id', item.user_id)); + renderableItem = { + avatar: item.avatar, + key: item.user_id, + title: item.name + }; + break; + default: + return null; + } + + return ( + + + + + + + ); + } + + _renderSeparator: () => ?React$Element<*> + + /** + * Renders the item separator. + * + * @returns {?React$Element<*>} + */ + _renderSeparator() { + return ( + + ); + } + + _setFieldRef: ?TextInput => void + + /** + * Sets a reference to the input field for later use. + * + * @param {?TextInput} input - The reference to the input field. + * @returns {void} + */ + _setFieldRef(input) { + this.inputFieldRef = input; + } + + /** + * Shows an alert telling the user that some invitees were failed to be + * invited. + * + * NOTE: We're using an Alert here because we're on a modal and it makes + * using our dialogs a tad more difficult. + * + * @returns {void} + */ + _showFailedInviteAlert() { + const { t } = this.props; + + Alert.alert( + t('inviteDialog.alertTitle'), + t('inviteDialog.alertText'), + [ + { + text: t('inviteDialog.alertOk') + } + ] + ); + } +} + +/** + * Maps part of the Redux state to the props of this component. + * + * @param {Object} state - The Redux state. + * @returns {{ + * _isVisible: boolean + * }} + */ +function _mapStateToProps(state: Object) { + return { + ..._abstractMapStateToProps(state), + _isVisible: state['features/invite'].inviteDialogVisible + }; +} + +export default translate(connect(_mapStateToProps)(AddPeopleDialog)); diff --git a/react/features/invite/components/add-people-dialog/native/index.js b/react/features/invite/components/add-people-dialog/native/index.js new file mode 100644 index 000000000..f2e67e631 --- /dev/null +++ b/react/features/invite/components/add-people-dialog/native/index.js @@ -0,0 +1,3 @@ +// @flow + +export { default as AddPeopleDialog } from './AddPeopleDialog'; diff --git a/react/features/invite/components/add-people-dialog/native/styles.js b/react/features/invite/components/add-people-dialog/native/styles.js new file mode 100644 index 000000000..8ef0e155c --- /dev/null +++ b/react/features/invite/components/add-people-dialog/native/styles.js @@ -0,0 +1,91 @@ +// @flow + +import { ColorPalette } from '../../../../base/styles'; + +export const AVATAR_SIZE = 40; +export const DARK_GREY = 'rgb(28, 32, 37)'; +export const LIGHT_GREY = 'rgb(209, 219, 232)'; +export const ICON_SIZE = 15; + +export default { + avatar: { + backgroundColor: LIGHT_GREY + }, + + avatarText: { + color: 'rgb(28, 32, 37)', + fontSize: 12 + }, + + dialogWrapper: { + alignItems: 'stretch', + backgroundColor: ColorPalette.white, + flex: 1, + flexDirection: 'column' + }, + + itemLinesStyle: { + color: 'rgb(118, 136, 152)', + fontSize: 13 + }, + + itemText: { + color: DARK_GREY, + fontSize: 14, + fontWeight: 'normal' + }, + + itemWrapper: { + alignItems: 'center', + flexDirection: 'row', + paddingLeft: 5 + }, + + radioButton: { + color: DARK_GREY, + fontSize: 16, + padding: 2 + }, + + resultList: { + padding: 5 + }, + + searchField: { + backgroundColor: 'rgb(240, 243, 247)', + borderBottomRightRadius: 10, + borderTopRightRadius: 10, + flex: 1, + fontSize: 17, + paddingVertical: 7 + }, + + separator: { + borderBottomColor: LIGHT_GREY, + borderBottomWidth: 1, + marginLeft: 85 + }, + + searchFieldWrapper: { + alignItems: 'stretch', + flexDirection: 'row', + height: 52, + paddingHorizontal: 15, + paddingVertical: 8 + }, + + searchIcon: { + color: DARK_GREY, + fontSize: ICON_SIZE + }, + + searchIconWrapper: { + alignItems: 'center', + backgroundColor: 'rgb(240, 243, 247)', + borderBottomLeftRadius: 10, + borderTopLeftRadius: 10, + flexDirection: 'row', + justifyContent: 'center', + width: ICON_SIZE + 16 + } +}; diff --git a/react/features/invite/components/AddPeopleDialog.web.js b/react/features/invite/components/add-people-dialog/web/AddPeopleDialog.js similarity index 70% rename from react/features/invite/components/AddPeopleDialog.web.js rename to react/features/invite/components/add-people-dialog/web/AddPeopleDialog.js index b6e506121..c0b93e7be 100644 --- a/react/features/invite/components/AddPeopleDialog.web.js +++ b/react/features/invite/components/add-people-dialog/web/AddPeopleDialog.js @@ -2,26 +2,27 @@ import Avatar from '@atlaskit/avatar'; import InlineMessage from '@atlaskit/inline-message'; -import React, { Component } from 'react'; +import React from 'react'; import { connect } from 'react-redux'; -import { createInviteDialogEvent, sendAnalytics } from '../../analytics'; -import { Dialog, hideDialog } from '../../base/dialog'; -import { translate, translateToHTML } from '../../base/i18n'; -import { getLocalParticipant } from '../../base/participants'; -import { MultiSelectAutocomplete } from '../../base/react'; +import { createInviteDialogEvent, sendAnalytics } from '../../../../analytics'; +import { Dialog, hideDialog } from '../../../../base/dialog'; +import { translate, translateToHTML } from '../../../../base/i18n'; +import { getLocalParticipant } from '../../../../base/participants'; +import { MultiSelectAutocomplete } from '../../../../base/react'; -import { invite } from '../actions'; -import { getInviteResultsForQuery, getInviteTypeCounts } from '../functions'; - -const logger = require('jitsi-meet-logger').getLogger(__filename); +import AbstractAddPeopleDialog, { + type Props as AbstractProps, + type State, + _mapStateToProps as _abstractMapStateToProps +} from '../AbstractAddPeopleDialog'; declare var interfaceConfig: Object; /** * The type of the React {@code Component} props of {@link AddPeopleDialog}. */ -type Props = { +type Props = AbstractProps & { /** * The {@link JitsiMeetConference} which will be used to invite "room" @@ -29,41 +30,11 @@ type Props = { */ _conference: Object, - /** - * The URL for validating if a phone number can be called. - */ - _dialOutAuthUrl: string, - /** * Whether to show a footer text after the search results as a last element. */ _footerTextEnabled: boolean, - /** - * The JWT token. - */ - _jwt: string, - - /** - * The query types used when searching people. - */ - _peopleSearchQueryTypes: Array, - - /** - * The URL pointing to the service allowing for people search. - */ - _peopleSearchUrl: string, - - /** - * Whether or not to show Add People functionality. - */ - addPeopleEnabled: boolean, - - /** - * Whether or not to show Dial Out functionality. - */ - dialOutEnabled: boolean, - /** * The redux {@code dispatch} function. */ @@ -75,32 +46,10 @@ type Props = { t: Function, }; -/** - * The type of the React {@code Component} state of {@link AddPeopleDialog}. - */ -type State = { - - /** - * Indicating that an error occurred when adding people to the call. - */ - addToCallError: boolean, - - /** - * Indicating that we're currently adding the new people to the - * call. - */ - addToCallInProgress: boolean, - - /** - * The list of invite items. - */ - inviteItems: Array -}; - /** * The dialog that allows to invite people to the call. */ -class AddPeopleDialog extends Component { +class AddPeopleDialog extends AbstractAddPeopleDialog { _multiselect = null; _resourceClient: Object; @@ -121,12 +70,10 @@ class AddPeopleDialog extends Component { super(props); // Bind event handlers so they are only bound once per instance. - this._isAddDisabled = this._isAddDisabled.bind(this); this._onItemSelected = this._onItemSelected.bind(this); this._onSelectionChange = this._onSelectionChange.bind(this); this._onSubmit = this._onSubmit.bind(this); this._parseQueryResults = this._parseQueryResults.bind(this); - this._query = this._query.bind(this); this._setMultiSelectElement = this._setMultiSelectElement.bind(this); this._resourceClient = { @@ -183,25 +130,27 @@ class AddPeopleDialog extends Component { * @returns {ReactElement} */ render() { - const { _footerTextEnabled, - addPeopleEnabled, - dialOutEnabled, - t } = this.props; + const { + _addPeopleEnabled, + _dialOutEnabled, + _footerTextEnabled, + t + } = this.props; let isMultiSelectDisabled = this.state.addToCallInProgress || false; let placeholder; let loadingMessage; let noMatches; let footerText; - if (addPeopleEnabled && dialOutEnabled) { + if (_addPeopleEnabled && _dialOutEnabled) { loadingMessage = 'addPeople.loading'; noMatches = 'addPeople.noResults'; placeholder = 'addPeople.searchPeopleAndNumbers'; - } else if (addPeopleEnabled) { + } else if (_addPeopleEnabled) { loadingMessage = 'addPeople.loadingPeople'; noMatches = 'addPeople.noResults'; placeholder = 'addPeople.searchPeople'; - } else if (dialOutEnabled) { + } else if (_dialOutEnabled) { loadingMessage = 'addPeople.loadingNumber'; noMatches = 'addPeople.noValidNumbers'; placeholder = 'addPeople.searchNumbers'; @@ -250,19 +199,9 @@ class AddPeopleDialog extends Component { ); } - _isAddDisabled: () => boolean; + _invite: Array => Promise<*> - /** - * Indicates if the Add button should be disabled. - * - * @private - * @returns {boolean} - True to indicate that the Add button should - * be disabled, false otherwise. - */ - _isAddDisabled() { - return !this.state.inviteItems.length - || this.state.addToCallInProgress; - } + _isAddDisabled: () => boolean; _onItemSelected: (Object) => Object; @@ -300,12 +239,7 @@ class AddPeopleDialog extends Component { _onSubmit: () => void; /** - * Invite people and numbers to the conference. The logic works by inviting - * numbers, people/rooms, and videosipgw in parallel. All invitees are - * stored in an array. As each invite succeeds, the invitee is removed - * from the array. After all invites finish, close the modal if there are - * no invites left to send. If any are left, that means an invite failed - * and an error state should display. + * Submits the selection for inviting. * * @private * @returns {void} @@ -313,45 +247,10 @@ class AddPeopleDialog extends Component { _onSubmit() { const { inviteItems } = this.state; const invitees = inviteItems.map(({ item }) => item); - const inviteTypeCounts = getInviteTypeCounts(invitees); - sendAnalytics(createInviteDialogEvent( - 'clicked', 'inviteButton', { - ...inviteTypeCounts, - inviteAllowed: this._isAddDisabled() - })); - - if (this._isAddDisabled()) { - return; - } - - this.setState({ - addToCallInProgress: true - }); - - const { dispatch } = this.props; - - dispatch(invite(invitees)) + this._invite(invitees) .then(invitesLeftToSend => { - // If any invites are left that means something failed to send - // so treat it as an error. if (invitesLeftToSend.length) { - const erroredInviteTypeCounts - = getInviteTypeCounts(invitesLeftToSend); - - logger.error(`${invitesLeftToSend.length} invites failed`, - erroredInviteTypeCounts); - - sendAnalytics(createInviteDialogEvent( - 'error', 'invite', { - ...erroredInviteTypeCounts - })); - - this.setState({ - addToCallInProgress: false, - addToCallError: true - }); - const unsentInviteIDs = invitesLeftToSend.map(invitee => invitee.id || invitee.number); @@ -362,15 +261,9 @@ class AddPeopleDialog extends Component { if (this._multiselect) { this._multiselect.setSelectedItems(itemsToSelect); } - - return; + } else { + this.props.dispatch(hideDialog()); } - - this.setState({ - addToCallInProgress: false - }); - - dispatch(hideDialog()); }); } @@ -442,34 +335,6 @@ class AddPeopleDialog extends Component { _query: (string) => Promise>; - /** - * Performs a people and phone number search request. - * - * @param {string} query - The search text. - * @private - * @returns {Promise} - */ - _query(query = '') { - const { - addPeopleEnabled, - dialOutEnabled, - _dialOutAuthUrl, - _jwt, - _peopleSearchQueryTypes, - _peopleSearchUrl - } = this.props; - const options = { - dialOutAuthUrl: _dialOutAuthUrl, - addPeopleEnabled, - dialOutEnabled, - jwt: _jwt, - peopleSearchQueryTypes: _peopleSearchQueryTypes, - peopleSearchUrl: _peopleSearchUrl - }; - - return getInviteResultsForQuery(query, options); - } - /** * Renders the error message if the add doesn't succeed. * @@ -557,10 +422,7 @@ class AddPeopleDialog extends Component { */ function _mapStateToProps(state) { const { - dialOutAuthUrl, - enableFeaturesBasedOnToken, - peopleSearchQueryTypes, - peopleSearchUrl + enableFeaturesBasedOnToken } = state['features/base/config']; let footerTextEnabled = false; @@ -573,11 +435,8 @@ function _mapStateToProps(state) { } return { - _dialOutAuthUrl: dialOutAuthUrl, - _footerTextEnabled: footerTextEnabled, - _jwt: state['features/base/jwt'].jwt, - _peopleSearchQueryTypes: peopleSearchQueryTypes, - _peopleSearchUrl: peopleSearchUrl + ..._abstractMapStateToProps(state), + _footerTextEnabled: footerTextEnabled }; } diff --git a/react/features/invite/components/add-people-dialog/web/index.js b/react/features/invite/components/add-people-dialog/web/index.js new file mode 100644 index 000000000..f2e67e631 --- /dev/null +++ b/react/features/invite/components/add-people-dialog/web/index.js @@ -0,0 +1,3 @@ +// @flow + +export { default as AddPeopleDialog } from './AddPeopleDialog'; diff --git a/react/features/invite/components/index.js b/react/features/invite/components/index.js index 06f471205..b5335af1d 100644 --- a/react/features/invite/components/index.js +++ b/react/features/invite/components/index.js @@ -1,4 +1,6 @@ -export { default as AddPeopleDialog } from './AddPeopleDialog'; +// @flow + +export * from './add-people-dialog'; export { DialInSummary } from './dial-in-summary'; export { default as InfoDialogButton } from './InfoDialogButton'; export { default as InviteButton } from './InviteButton'; diff --git a/react/features/invite/middleware.web.js b/react/features/invite/middleware.web.js index 5684ead49..d67008b24 100644 --- a/react/features/invite/middleware.web.js +++ b/react/features/invite/middleware.web.js @@ -5,7 +5,6 @@ import { MiddlewareRegistry } from '../base/redux'; import { BEGIN_ADD_PEOPLE } from './actionTypes'; import { AddPeopleDialog } from './components'; -import { isAddPeopleEnabled, isDialOutEnabled } from './functions'; import './middleware.any'; /** @@ -36,15 +35,10 @@ MiddlewareRegistry.register(store => next => action => { * @private * @returns {*} The value returned by {@code next(action)}. */ -function _beginAddPeople({ dispatch, getState }, next, action) { +function _beginAddPeople({ dispatch }, next, action) { const result = next(action); - const state = getState(); - - dispatch(openDialog(AddPeopleDialog, { - addPeopleEnabled: isAddPeopleEnabled(state), - dialOutEnabled: isDialOutEnabled(state) - })); + dispatch(openDialog(AddPeopleDialog)); return result; } diff --git a/react/features/invite/reducer.js b/react/features/invite/reducer.js index fd56d68ea..35dbe8329 100644 --- a/react/features/invite/reducer.js +++ b/react/features/invite/reducer.js @@ -6,6 +6,7 @@ import { ADD_PENDING_INVITE_REQUEST, REMOVE_PENDING_INVITE_REQUESTS, SET_CALLEE_INFO_VISIBLE, + SET_INVITE_DIALOG_VISIBLE, UPDATE_DIAL_IN_NUMBERS_FAILED, UPDATE_DIAL_IN_NUMBERS_SUCCESS } from './actionTypes'; @@ -20,7 +21,7 @@ const DEFAULT_STATE = { * @type {boolean|undefined} */ calleeInfoVisible: false, - + inviteDialogVisible: false, numbersEnabled: true, pendingInviteRequests: [] }; @@ -49,6 +50,12 @@ ReducerRegistry.register('features/invite', (state = DEFAULT_STATE, action) => { initialCalleeInfo: action.initialCalleeInfo }; + case SET_INVITE_DIALOG_VISIBLE: + return { + ...state, + inviteDialogVisible: action.visible + }; + case UPDATE_DIAL_IN_NUMBERS_FAILED: return { ...state,