Compare commits

..

172 Commits

Author SHA1 Message Date
xdrm-brackets 010160e109 test prod@releaser@1 2017-12-10 23:39:36 +01:00
xdrm-brackets 51dab68805 watch position over time instead of getCurrent 2017-12-08 05:40:21 +01:00
xdrm-brackets d534f1f37c fix: geoloc with HIGH accuracy 2017-12-08 05:33:22 +01:00
xdrm-brackets fad2ac4696 upd: added google Maps link 2017-12-08 05:24:28 +01:00
xdrm-brackets cea356fb66 Merge branch 'master' of https://git.xdrm.io/ndli1718/main 2017-12-08 05:05:11 +01:00
xdrm-brackets 5a8cc4ddb7 ADDED update client (js) 2017-12-08 05:04:49 +01:00
Guillaume FAUVET 972dc6f86d add: public_html.css.accueil (add css for home page)
add: public_html.image.* (add new images for types )
upd: view.vue.container.dashboard (add some content)
upd: view.vue.home (add css reference for home page)
2017-12-08 04:54:59 +01:00
xdrm-brackets 1463253b86 DELETE msg btn now below message box 2017-12-08 04:50:09 +01:00
xdrm-brackets 7cb932335c upd: vue.emergency (user can now DELETE its own messages) 2017-12-08 04:47:23 +01:00
xdrm-brackets 044abf22e4 upd: api.message (UPT message/emergency) 2017-12-08 04:30:43 +01:00
xdrm-brackets 741656e6f1 now send string to ws-server 2017-12-08 04:24:55 +01:00
xdrm-brackets 2b53f076bc removed apache error 2017-12-08 04:22:34 +01:00
xdrm-brackets 855cfa023a 'id' is now of type 'id' 2017-12-08 04:22:27 +01:00
xdrm-brackets 11761e16e2 upd: api.message (DELETE message/emergency) 2017-12-08 04:17:41 +01:00
xdrm-brackets 512bd699de fix ridicule (2char) 2017-12-08 03:46:42 +01:00
xdrm-brackets 2da458ad31 FUCK YES -> api: POST message/emergency (now works with DB FINALLY) 2017-12-08 03:39:29 +01:00
xdrm-brackets 8e78142119 Added api: POST message/emergency (with db) 2017-12-08 03:18:29 +01:00
xdrm-brackets ec59cde080 fix: fix con 2017-12-08 03:04:57 +01:00
xdrm-brackets 60a6ec10bf debug@2 2017-12-08 03:02:22 +01:00
xdrm-brackets 89520180c7 debug 2017-12-08 02:58:17 +01:00
xdrm-brackets dd4ae7e748 Merge branch 'api-with-db' of https://git.xdrm.io/ndli1718/main into api-with-db 2017-12-08 02:54:32 +01:00
xdrm-brackets 81449426a5 Removed 'username' from POST message/emergency + POST message/event (because already in session) 2017-12-08 02:54:21 +01:00
xdrm-brackets 27942b8b82 fix: $_SESSION['name'] is now ok with API calls (tokens, etc) 2017-12-08 02:50:47 +01:00
xdrm-brackets a073f5632d clean modules.json 2017-12-08 02:50:47 +01:00
Guillaume FAUVET d2b54f431b add: build.router.controller.loader
upd: build.router.controller.api
upd: build.router.controller.page
2017-12-08 02:50:47 +01:00
xdrm-brackets aa5b97dcc8 add: repo.event (event default 'getAll()' with limit 'getById', 'create', 'update', 'remove') 2017-12-08 02:50:47 +01:00
xdrm-brackets 69df30d57c add: repo.emergency (emergency default 'getAll()' with limit 'getById', 'create', 'update', 'remove') 2017-12-08 02:50:47 +01:00
SeekDaSky 26c6a6bb22 Merge branch 'master' of https://git.xdrm.io/ndli1718/main 2017-12-08 02:45:32 +01:00
SeekDaSky 3c68e0a100 fix date 2017-12-08 02:45:23 +01:00
Guillaume FAUVET b1bafa61a8 fix: view.vue.signup-form (correct invalid username argument + secure sign up) 2017-12-08 02:35:16 +01:00
xdrm-brackets 87504efc0a add: repo.event (event default 'getAll()' with limit 'getById', 'create', 'update', 'remove') 2017-12-08 02:22:23 +01:00
xdrm-brackets d8156b3f55 add: repo.emergency (emergency default 'getAll()' with limit 'getById', 'create', 'update', 'remove') 2017-12-08 02:20:05 +01:00
SeekDaSky f468536e13 Merge branch 'master' of https://git.xdrm.io/ndli1718/main 2017-12-08 02:01:03 +01:00
SeekDaSky f3437d8db9 add: Interop pour le channel event 2017-12-08 01:56:52 +01:00
Guillaume FAUVET 65ad834bd8 add: public_html/image/header (missing logout icon) 2017-12-08 01:56:52 +01:00
Guillaume FAUVET c0013f25b0 upd: build.router.controller (add _SERVER.session.connected)
upd: public_html.header = (add icon logout)
upd: public_html.signup-form (add backlink to login)
upd: view.vue.header = (change icon if connected or not)
upd: view.vue.signup-form = (add backling to login)
2017-12-08 01:56:52 +01:00
xdrm-brackets 90c05624ab fix: view.main (added geolocation) | upd: vue.emergency|vue.event (added geolocation use) 2017-12-08 01:56:52 +01:00
Guillaume FAUVET a04a0ede20 Merge remote-tracking branch 'origin/dev-logout' into dev-logout 2017-12-08 01:25:28 +01:00
Guillaume FAUVET 8d62ed08e5 add: public_html/image/header (missing logout icon) 2017-12-08 01:25:10 +01:00
Guillaume FAUVET dbdc578ea3 upd: build.router.controller (add _SERVER.session.connected)
upd: public_html.header = (add icon logout)
upd: public_html.signup-form (add backlink to login)
upd: view.vue.header = (change icon if connected or not)
upd: view.vue.signup-form = (add backling to login)
2017-12-08 01:22:32 +01:00
Guillaume FAUVET 438607a1e6 upd: build.router.controller (add _SERVER.session.connected)
upd: public_html.header = (add icon logout)
upd: public_html.signup-form (add backlink to login)
upd: view.vue.header = (change icon if connected or not)
upd: view.vue.signup-form = (add backling to login)
2017-12-08 01:22:03 +01:00
xdrm-brackets 66d8eb39eb fix: view.main (added geolocation) | upd: vue.emergency|vue.event (added geolocation use) 2017-12-08 01:02:52 +01:00
SeekDaSky a906da7266 Merge branch 'master' of https://git.xdrm.io/ndli1718/main 2017-12-08 00:47:06 +01:00
SeekDaSky a297a89287 merge 2017-12-08 00:45:16 +01:00
xdrm-brackets 94ad405dee fix: view.websocket (fixed update) 2017-12-08 00:45:16 +01:00
xdrm-brackets 1400d445ee BIG FIX: session_name with logout .... 2017-12-08 00:45:16 +01:00
xdrm-brackets bdf119700c fix: view.websocket (object length fixes '/event' notification count) 2017-12-08 00:45:16 +01:00
xdrm-brackets 97c6dcf8be fix: view.websocket (object length fixes '/emergency' notification count) 2017-12-08 00:45:16 +01:00
xdrm-brackets f3e3f1496b IMPORTANT fix: websocket (now will work also for '/event' channel 2017-12-08 00:45:16 +01:00
Guillaume FAUVET e8d385f1f6 upt: public_html.css.layout (css for sign up form)
upt: public_html.css.login-form (add new css for sign up button)
upt: view.vue.header (close sign up form on menu click)
upt: view.vue.login-form (add sign up button in the login form authentication)
upt: view.vue.wrapper (add new popup for sign up)
upt: view.home (add reference css for sign up)
upt: view.vue-config (add gstore.add.signupform for popup sign up visibility)
2017-12-08 00:45:16 +01:00
Guillaume FAUVET 0596380219 add: public_html.css.signup-form (css for sign up form authentication)
add: view.vue.signup-form (vue for sign up form authentication)
2017-12-08 00:45:16 +01:00
Guillaume FAUVET db00a1cdc3 fix: config.modules (user mail & admin mail must be of mail type instead of text) 2017-12-08 00:45:16 +01:00
Guillaume FAUVET 7f183ed8ea fix: view.vue-config (boolean must be initialize with false) 2017-12-08 00:45:16 +01:00
Guillaume FAUVET 067ef7de6a upt: public_html.css.header (add new background-image for user authentication)
upt: public_html.css.layout (add new css for user authentication)
upt: view.vue.header (add a button for showing login interface)
upt: view.vue.wrapper (add a button for showing login interface)
upt: view.home (add a reference to user authentication css)
upt: view.vue-config (add boolean gstore.data.loginform to display user authentication interface)
2017-12-08 00:45:16 +01:00
Guillaume FAUVET 35129d49f0 add: public_html.css.login-form (css for user authentication)
add: public_html.image.header.notif.login (icon for user authentication for header)
add: view.vue.login-form (vue for user authentication)
2017-12-08 00:45:16 +01:00
xdrm-brackets d7710a2b92 fix: view.websocket (fixed update) 2017-12-08 00:39:43 +01:00
xdrm-brackets f856b67f7e BIG FIX: session_name with logout .... 2017-12-08 00:32:18 +01:00
xdrm-brackets 965b634f72 fix: view.websocket (object length fixes '/event' notification count) 2017-12-08 00:06:34 +01:00
xdrm-brackets d7a5e57a22 fix: view.websocket (object length fixes '/emergency' notification count) 2017-12-08 00:05:52 +01:00
xdrm-brackets 56b4327184 IMPORTANT fix: websocket (now will work also for '/event' channel 2017-12-08 00:01:25 +01:00
Guillaume FAUVET b12eb46939 upt: public_html.css.layout (css for sign up form)
upt: public_html.css.login-form (add new css for sign up button)
upt: view.vue.header (close sign up form on menu click)
upt: view.vue.login-form (add sign up button in the login form authentication)
upt: view.vue.wrapper (add new popup for sign up)
upt: view.home (add reference css for sign up)
upt: view.vue-config (add gstore.add.signupform for popup sign up visibility)
2017-12-07 23:44:09 +01:00
Guillaume FAUVET 514f56db18 add: public_html.css.signup-form (css for sign up form authentication)
add: view.vue.signup-form (vue for sign up form authentication)
2017-12-07 23:44:09 +01:00
Guillaume FAUVET 11895fb875 fix: config.modules (user mail & admin mail must be of mail type instead of text) 2017-12-07 23:44:09 +01:00
Guillaume FAUVET 2791dda887 fix: view.vue-config (boolean must be initialize with false) 2017-12-07 23:44:09 +01:00
Guillaume FAUVET d0dc02e53f upt: public_html.css.header (add new background-image for user authentication)
upt: public_html.css.layout (add new css for user authentication)
upt: view.vue.header (add a button for showing login interface)
upt: view.vue.wrapper (add a button for showing login interface)
upt: view.home (add a reference to user authentication css)
upt: view.vue-config (add boolean gstore.data.loginform to display user authentication interface)
2017-12-07 23:43:13 +01:00
Guillaume FAUVET 0406689523 add: public_html.css.login-form (css for user authentication)
add: public_html.image.header.notif.login (icon for user authentication for header)
add: view.vue.login-form (vue for user authentication)
2017-12-07 23:40:58 +01:00
SeekDaSky d5078b9bc9 Merge branch 'master' of https://git.xdrm.io/ndli1718/main 2017-12-07 23:40:15 +01:00
SeekDaSky e82f192f8e Implémentation de l'interop pour la suppression de message (promis c'est le dernier commit sur master) 2017-12-07 23:40:05 +01:00
xdrm-brackets 96b92e02cb lolfix 2017-12-07 23:38:55 +01:00
xdrm-brackets 48f9be4f3c minfix 2017-12-07 23:37:06 +01:00
SeekDaSky ce31a026c5 minfix 2017-12-07 23:36:10 +01:00
SeekDaSky 1327cfebda merge 2017-12-07 23:32:22 +01:00
xdrm-brackets 8875440602 minfix 2017-12-07 23:31:07 +01:00
xdrm-brackets 4699fe9e70 minfix 2017-12-07 23:27:39 +01:00
xdrm-brackets ec45b1c13a fix: view.websocket (object to data) 2017-12-07 23:19:49 +01:00
xdrm-brackets ca3e25b0e7 upd: view.websocket (not array contat, now object merging) 2017-12-07 22:48:39 +01:00
xdrm-brackets dc167766fa tmp: geolocation to test through https (must push to master) sorry .. 2017-12-07 22:36:04 +01:00
xdrm-brackets b7d22fad31 upd: vue.emergency (now send with api) 2017-12-07 22:25:39 +01:00
xdrm-brackets ab1b3080c7 upd: view.websocket (now managing 'add', 'del', 'upd') 2017-12-07 22:16:15 +01:00
xdrm-brackets cddb82a8b5 Merge branch 'master' of https://git.xdrm.io/ndli1718/main 2017-12-07 21:53:52 +01:00
xdrm-brackets 9f0f82c521 removed 'module.authentication' to 'user/login' and 'admin/login' + ADDED 'user/signup' and 'admin/signup' 2017-12-07 21:52:11 +01:00
xdrm-brackets 216412f26a upd: error.core.{Error,Err} (Added management for Err::AlreadyExists) 2017-12-07 21:52:11 +01:00
SeekDaSky cb5482950f upd: Postmessage channel emergency interop 2017-12-07 21:52:11 +01:00
SeekDaSky d5c713de6c Merge branch 'master' of https://git.xdrm.io/ndli1718/main 2017-12-07 21:07:31 +01:00
SeekDaSky 79c74e9832 upd: Postmessage channel emergency interop 2017-12-07 21:06:35 +01:00
xdrm-brackets e30b4a6098 fix: vue.emergency (now detect session.name instead of session.user) 2017-12-07 21:06:35 +01:00
xdrm-brackets c01cbb89a7 refactor bbcode() from container/*.vue to view.vue-config 2017-12-07 21:06:35 +01:00
xdrm-brackets a5a89be961 fix: vue.inbox (now takes the right msg content) 2017-12-07 21:06:35 +01:00
xdrm-brackets 3434ac229c fix: vue.emergency (now detect session.name instead of session.user) 2017-12-07 20:51:06 +01:00
xdrm-brackets 0861185a8e refactor bbcode() from container/*.vue to view.vue-config 2017-12-07 20:47:03 +01:00
xdrm-brackets a166ecc004 fix: vue.inbox (now takes the right msg content) 2017-12-07 20:41:20 +01:00
SeekDaSky 63b5c3afa8 add: Interop pour l'envoi de message + upd: Interop pour la connection 2017-12-07 20:24:59 +01:00
xdrm-brackets 602d72f361 upd: view.vue-config (removed global sendMessage()) 2017-12-07 20:17:50 +01:00
xdrm-brackets 62b353eea9 added local time to event 2017-12-07 20:17:04 +01:00
xdrm-brackets 8a649dbf0b upd: vue.container.inbox (fix submit trigger) 2017-12-07 20:11:28 +01:00
xdrm-brackets 037057cc8a upd: vue.container.event (fix message send) 2017-12-07 20:10:38 +01:00
xdrm-brackets 5ecb15048a upd: vue.container.emergency (fix submit sendin' with param) 2017-12-07 20:09:08 +01:00
xdrm-brackets a20335c045 upd: view.websocket (added subchannel 31 RPZ) 2017-12-07 20:06:45 +01:00
xdrm-brackets 9a9af7373e upd: vue.container.event (fix message send) 2017-12-07 20:04:55 +01:00
xdrm-brackets 978d920fec upd: vue.container.emergency (fix 2) 2017-12-07 20:04:14 +01:00
xdrm-brackets f4c59b11a6 upd: vue.container.emergency (fix) 2017-12-07 20:03:51 +01:00
xdrm-brackets 629df98a36 upd: vue.container.emergency (fix message send) 2017-12-07 20:02:27 +01:00
xdrm-brackets cf08a98b9e upd: css.container|vue.container.emergency (added timestamp + date display) 2017-12-07 19:49:57 +01:00
xdrm-brackets ad575c3697 upd: view.websocket (updated 'response.data' instead of 'response.msg' for channels: /event AND /emergency 2017-12-07 19:15:20 +01:00
xdrm-brackets ece78fa1bd upd: vue.container.emergency (copy of 'vue.container.inbox' for 'emergency' channel) | upd: vue.container.event (same) | upd: vue.container.inbox (setup in order for all to work) | upd: view.vue-config (updated 'gstore.func.sendMessage' second argument takes the WSClient object)" 2017-12-07 19:12:43 +01:00
xdrm-brackets 84cabd92eb upd: view.main (removed websocket management) | add: view.websocket (dispatched from 'view.main') 2017-12-07 19:11:23 +01:00
xdrm-brackets ea6d21634d fix: css.container (loader did not keep its ratio) 2017-12-07 18:42:08 +01:00
xdrm-brackets 78439ec878 Added sending loader + 'new_msg'/'msg_pending' have a value for each channel 2017-12-07 18:38:27 +01:00
xdrm-brackets 40598a5418 UPD: reset page list (menu.items + header.notifs) + UPD: notif now isn't array but object which key is the link + added proper CSS instead of VueJS inline style='...' 2017-12-07 18:17:32 +01:00
xdrm-brackets 97bb6de0cf fix: api.module.dev (managed output) #2 2017-12-07 17:20:40 +01:00
xdrm-brackets d824ae38f0 fix: api.module.dev (managed output) 2017-12-07 17:19:02 +01:00
xdrm-brackets 1c34b59231 fix: api.module.dev (added npm management) 2017-12-07 17:14:44 +01:00
xdrm-brackets 29cb835400 upd: config.modules|api.module.dev (added auto-release (git pull) with url trigger) 2017-12-07 16:34:36 +01:00
SeekDaSky 7f4b481bb6 Merge branch 'master' of https://git.xdrm.io/ndli1718/main 2017-12-07 15:35:52 +01:00
SeekDaSky 4f6fa13155 fix: Interop not closing socket + discard keepalive packets 2017-12-07 15:35:07 +01:00
Guillaume FAUVET 95e90bef20 Merge remote-tracking branch 'origin/master' 2017-12-07 15:33:28 +01:00
Guillaume FAUVET 3c442e48a5 upd: view.main (api et wsclientbuilder en fonction de si local ou pas)
upd: view.vue-config (gstore.data.is_local : bool)
2017-12-07 15:33:01 +01:00
xdrm-brackets 4cfb4a7f4d upd: packages.json (added commands: 'ws-start', 'ws-stop', 'ws-restart') | add: ndli1718.jar (added to .gitignore) 2017-12-07 15:27:15 +01:00
xdrm-brackets ff129222b9 upd: ... (added component 'notification-stack' to wrapper, can be shown with 'gstore.data.nstack=true' + its css) 2017-12-06 21:38:04 +01:00
xdrm-brackets 7092a5f9c8 fix: view.main (added remote notification sound) 2017-12-06 20:05:26 +01:00
xdrm-brackets c107e6c38b fix: view.main (fixed no notification if on current page, added '/' before router path check) 2017-12-06 19:10:28 +01:00
xdrm-brackets 926f5d1224 upd: view.main (removed websocket closing protocol (PING/PONG will destroy it automatically)) 2017-12-06 18:23:48 +01:00
xdrm-brackets 5d9e6ef83f upd: config.modules (added GET dev/session_destroy) | add: api.module.dev (added session_destroy() to clean the variable) 2017-12-06 17:41:25 +01:00
SeekDaSky 27bb422aca fix: wsInterop (namespace + move interop code from index to controller 2017-12-06 17:12:08 +01:00
SeekDaSky 3ba539e9de Merge branch 'master' of https://git.xdrm.io/ndli1718/main 2017-12-06 16:40:41 +01:00
SeekDaSky 5ccdc2e804 update: .gitignore 2017-12-06 16:40:19 +01:00
xdrm-brackets 1945158724 add: build.kwebsocket.core.wsinterop (added SeekDaSky websocket-interop lib) | upd: public.index ( added name gathering through websocket-interop) 2017-12-06 16:36:55 +01:00
xdrm-brackets 40967db18b upd: view.main (added /connect ws-client management (connected: [], disconnected: []) + list unicity + notifications + sound (mp3 not pushed for now) 2017-12-06 16:23:21 +01:00
xdrm-brackets 6a483539f5 upd: config.modules (added signup + password update into config) | TODO: implement body 2017-12-06 13:23:37 +01:00
xdrm-brackets adcaf1a72f upd: view.vue.container.inbox (minmod: cleaned code 'msg[0]' instead of 'gstore.notif[1].data[id][0]') 2017-12-06 09:44:25 +01:00
xdrm-brackets 9b67c15a6b upd: css.container|view.vue.container.inbox (only display name on first message from same user) 2017-12-05 23:42:18 +01:00
xdrm-brackets 372d532f1b upd: css.container (vertical message margin (only top, not bottom) for first in order no for :before to be out) 2017-12-05 23:33:24 +01:00
xdrm-brackets 1db7f17830 upd: css.container (self messages less spaced (vertically)) 2017-12-05 23:10:54 +01:00
xdrm-brackets 8c919acc4b upd: css.container (now author up from message: outside ; self messages not in color, white as other messages) 2017-12-05 23:07:42 +01:00
xdrm-brackets b7c307a852 update: smileys+emojis colors + size ehancement 2017-12-05 22:53:37 +01:00
xdrm-brackets d61476d302 Added common smileys + some emojis 2017-12-05 22:45:55 +01:00
xdrm-brackets 54a95d481c Added *bbcode* filter (escape html + bold + italic + underlined + code) + its css + fix: css.container (message list do not go under new-msg input) 2017-12-05 22:30:03 +01:00
xdrm-brackets 7b5c057da6 fix: view.vue-config (cannot send empty messages; empty means if trimmed message has a length of 0) 2017-12-05 20:57:39 +01:00
xdrm-brackets 49b4e0a914 fix: README (display errors) 2017-12-05 14:33:54 -05:00
xdrm-brackets 21d4be378e tmp: view.main (removed temporarily websocket/connect to clean network log and SeekDaSky websocket logs) 2017-12-05 18:58:27 +01:00
xdrm-brackets fe1ab69cf0 fix: view.vue-config|view.main (do not show notification if already on the target page) 2017-12-05 18:55:07 +01:00
xdrm-brackets 3fd5fdfa97 fix: *.js|*.vue (removed 'window.' when accessing window.* variables because 'window.' is implicit) 2017-12-05 18:41:39 +01:00
xdrm-brackets 69a6be7c2d upd: css.header (updated notification puce color) 2017-12-05 18:21:35 +01:00
xdrm-brackets 18a20ca7b4 fix: css.container (now on toggleMenuSize() same transition as the menu) 2017-12-05 18:16:43 +01:00
xdrm-brackets 3f646bcd6c fix: view.vue.container.inbox (empty input when message sent) 2017-12-05 18:12:26 +01:00
xdrm-brackets ba14390582 fix: now msg input have same font-family 2017-12-05 18:06:42 +01:00
xdrm-brackets ee05d5f432 fix message input on menu side toggle size 2017-12-05 15:12:29 +01:00
xdrm-brackets 3862675b1d fix: new close protocol (close: true) because GoogleChrome does not send the close handshake (test@1) 2017-12-05 14:40:08 +01:00
xdrm-brackets 0f1d995c94 Removed log 2017-12-05 14:17:24 +01:00
xdrm-brackets dd7bad469c Fix notification associated pages count=0 2017-12-05 14:00:27 +01:00
xdrm-brackets 47d9dfac0b Now message input 2017-12-05 13:32:42 +01:00
xdrm-brackets 7363f6ea1a fix: vue-router now works (require(...).default) 2017-12-05 08:39:24 +01:00
xdrm-brackets 3b524fbe93 Added vue-router 2017-12-05 00:00:22 +01:00
xdrm-brackets 092836359b maxmod + router-like system with URL 2017-12-04 23:29:02 +01:00
xdrm-brackets 6bcc725d31 updated ''router'' engine (without vue-router) 2017-12-04 22:57:24 +01:00
xdrm-brackets 19a9ab9dc4 upd: view.main (fixed websocket close 'onbeforeunload') 2017-12-04 22:56:30 +01:00
xdrm-brackets dc02f564be No more router(redirect:home nor page:load) only page:load by default to allow JS use 2017-12-04 22:55:41 +01:00
xdrm-brackets e0debfed54 Close sockets 'beforeunload' 2017-12-04 19:44:30 +01:00
xdrm-brackets c02253dc11 Added gstore func to send a message 2017-12-04 19:19:15 +01:00
xdrm-brackets 64d04d83b9 ADD: container/message message viewer according to wss://...../chat 2017-12-04 19:13:49 +01:00
xdrm-brackets 8b6e616a1f Make viewport to 40% of screen 2017-12-04 17:52:29 +01:00
xdrm-brackets 2ae283987a minmod: header rotation on transition 2017-12-04 17:50:18 +01:00
xdrm-brackets add5e16625 upd: css.header (Cannot user-select header-icon) 2017-12-04 17:46:19 +01:00
xdrm-brackets 6d894c456f upd: fixed transition (2-way) for menu size 2017-12-04 17:44:43 +01:00
xdrm-brackets 7db3f2e3f8 upd: css.layout (fix menu height (too low)) 2017-12-04 17:36:07 +01:00
xdrm-brackets 2a791d0401 add: view.lib.infobox (infobox management with stack + timeout chain) | upd:view.main (now right ws-client management) 2017-12-04 17:30:33 +01:00
xdrm-brackets 9fdec3c2db fix: minfix 2017-12-04 17:07:20 +01:00
xdrm-brackets 360c2f7133 Now ws-client only targets _onmessage when same URL+URI 2017-12-04 16:38:34 +01:00
xdrm-brackets 7e2714222d Make infobox great again (visible) 2017-12-04 16:30:26 +01:00
xdrm-brackets 54757ef460 minmod (debug ws-client response) 2017-12-04 14:59:36 +01:00
xdrm-brackets dfe9843845 remove /*TMP*/ to test websocket.jar 2017-12-04 14:53:16 +01:00
xdrm-brackets c2f3f0ce15 upd: view.vue.header (only header-icon not HEADER toggles the menu size) 2017-12-04 11:56:02 +01:00
70 changed files with 3646 additions and 206 deletions

4
.gitignore vendored
View File

@ -1,3 +1,5 @@
websocket.out
ndli1718.jar
.vscode .vscode
.DS_Store .DS_Store
node_modules/ node_modules/
@ -7,6 +9,7 @@ yarn-error.log
public_html/js/bundle@*.js public_html/js/bundle@*.js
public_html/js/bundle@*.js* public_html/js/bundle@*.js*
package-lock.json package-lock.json
yarn.lock
# Editor directories and files # Editor directories and files
.idea .idea
@ -14,3 +17,4 @@ package-lock.json
*.ntvs* *.ntvs*
*.njsproj *.njsproj
*.sln *.sln
/.gtm/

View File

@ -43,9 +43,9 @@ Toujours dans le dossier parent (celui qui contient `ndli1718-web`)
### 3-1. Configuration Apache ### 3-1. Configuration Apache
> Si vous n'avez pas apache > Si vous n'avez pas apache
> ```bash ```bash
> sudo apt-get install apache2 libapache2-mod-php mysql-server php-mysql php; > sudo apt-get install apache2 libapache2-mod-php mysql-server php-mysql php;
> ``` ```
##### 1. Créer l'hôte virtuel ##### 1. Créer l'hôte virtuel

View File

@ -25,11 +25,13 @@
public static function check(){ public static function check(){
/* (1) Initialisation /* (1) Initialisation
---------------------------------------------------------*/ ---------------------------------------------------------*/
if( !isset($_SESSION['TOKEN']) ) $_SESSION['TOKEN'] = []; if( !isset($_SESSION['TOKEN']) ) $_SESSION['TOKEN'] = [];
if( !isset($_SESSION['AUTH']) ) $_SESSION['AUTH'] = []; if( !isset($_SESSION['AUTH']) ) $_SESSION['AUTH'] = [];
if( !isset($_SESSION['PERM']) ) $_SESSION['PERM'] = []; if( !isset($_SESSION['PERM']) ) $_SESSION['PERM'] = [];
if( !isset($_SESSION['USER']) ) $_SESSION['USER'] = []; if( !isset($_SESSION['USER']) ) $_SESSION['USER'] = [];
if( !isset($_SESSION['ADMIN']) ) $_SESSION['ADMIN'] = []; if( !isset($_SESSION['ADMIN']) ) $_SESSION['ADMIN'] = [];
if( !isset($_SESSION['NAME']) ) $_SESSION['NAME'] = '';
if( !isset($_SESSION['WS']) ) $_SESSION['WS'] = true;
/* (2) Gestion de AUTH (authentification) /* (2) Gestion de AUTH (authentification)
@ -37,8 +39,10 @@
$AUTH = ''; $AUTH = '';
/* (1) Si Auth dans HEADER, on le récupère */ /* (1) Si Auth dans HEADER, on le récupère */
if( isset($_SERVER['PHP_AUTH_DIGEST']) && is_string($_SERVER['PHP_AUTH_DIGEST']) ) if( isset($_SERVER['PHP_AUTH_DIGEST']) && is_string($_SERVER['PHP_AUTH_DIGEST']) ){
$AUTH = $_SERVER['PHP_AUTH_DIGEST']; $AUTH = $_SERVER['PHP_AUTH_DIGEST'];
$_SESSION['WS'] = true;
}
/* (2) Si SESSION déja connectée -> no récupère le token */ /* (2) Si SESSION déja connectée -> no récupère le token */
elseif( isset($_SESSION['TOKEN']) && is_string($_SESSION['TOKEN']) ) elseif( isset($_SESSION['TOKEN']) && is_string($_SESSION['TOKEN']) )

View File

@ -141,6 +141,10 @@
return $checker && (is_numeric($value) || $value == null || $value == 'null'); return $checker && (is_numeric($value) || $value == null || $value == 'null');
break; break;
case "float":
return $checker && is_float($value);
break;
default: default:
return false; return false;
break; break;

View File

@ -119,7 +119,8 @@
// On rajoute l'erreur au message // On rajoute l'erreur au message
$returnData = array_merge([ $returnData = array_merge([
'error' => $this->error->get(), 'error' => $this->error->get(),
'ErrorDescription' => $this->error->explicit() 'ErrorDescription' => $this->error->explicit(),
'name' => $_SESSION['NAME']
], ],
$this->data $this->data
); );
@ -127,6 +128,7 @@
return json_encode($returnData); return json_encode($returnData);
} }
}
}
?> ?>

View File

@ -9,7 +9,7 @@ use \database\core\Repo;
use \api\core\AuthSystemDefault; use \api\core\AuthSystemDefault;
class authentication{ class admin{
public function __construct(){} public function __construct(){}
@ -17,7 +17,7 @@ class authentication{
public function POST_admin($argv){ public function POST_login($argv){
extract($argv); extract($argv);
/* (1) Logout by default /* (1) Logout by default
@ -52,6 +52,7 @@ class authentication{
---------------------------------------------------------*/ ---------------------------------------------------------*/
/* (1) Update session */ /* (1) Update session */
$_SESSION['TOKEN'] = 'a'.$fetched_admin['token']; $_SESSION['TOKEN'] = 'a'.$fetched_admin['token'];
$_SESSION['WS'] = true; // to tell websocket we are connected
new AuthSystemDefault; new AuthSystemDefault;
/* (2) Return status */ /* (2) Return status */
@ -59,7 +60,10 @@ class authentication{
} }
public function POST_user($argv){
public function POST_signup($argv){
extract($argv); extract($argv);
@ -68,37 +72,44 @@ class authentication{
$_SESSION['TOKEN'] = []; $_SESSION['TOKEN'] = [];
/* (2) Search for @id_user from username /* (2) Check if @username is unique
---------------------------------------------------------*/ ---------------------------------------------------------*/
/* (1) Fetch by username */ /* (1) Fetch by username */
$fetched_user = Repo::request('user', 'getByUsername', $username); $fetched_admin = Repo::request('admin', 'getByUsername', $username);
/* (2) If not found -> error */ /* (2) If found -> error */
if( !is_array($fetched_user) || !isset($fetched_user['id_user']) || !is_numeric($fetched_user['id_user']) ) if( $fetched_admin !== false )
return ['connected' => false]; return ['error' => new Error(Err::AlreadyExists)];
/* (3) Extract @id_user */
$id_user = intval( $fetched_user['id_user'] );
/* (3) Check password for user /* (3) Check if @mail is unique
---------------------------------------------------------*/ ---------------------------------------------------------*/
/* (1) Check password */ /* (1) Fetch by mail */
$valid_pass = Repo::request('user', 'checkPassword', $id_user, $password); $fetched_admin = Repo::request('admin', 'getByMail', $mail);
/* (2) If wrong password -> error */ /* (2) If found -> error */
if( !$valid_pass ) if( $fetched_admin !== false )
return ['connected' => false]; return ['error' => new Error(Err::AlreadyExists)];
/* (4) Update session to be connected /* (4) Create user
---------------------------------------------------------*/ ---------------------------------------------------------*/
/* (1) Update session */ /* (1) Create repo request */
$_SESSION['TOKEN'] = 'u'.$fetched_user['token']; $id_created = Repo::request('admin', 'create', $username, $mail, $password);
new AuthSystemDefault;
/* (2) Return status */ /* (2) If error -> dispatch */
return ['connected' => true]; if( $id_created === false )
return [ 'error' => new Error(Err::RepoError) ];
/* (3) Return status */
return [ 'registered' => $id_created ];
}
public function DELETE_logout(){
$_SESSION = [];
} }
} }

39
build/api/module/dev.php Normal file
View File

@ -0,0 +1,39 @@
<?php
namespace api\module;
use \error\core\Error;
use \error\core\Err;
use \database\core\Repo;
use \api\core\AuthSystemDefault;
class dev{
public function __construct(){}
public function __destruct(){}
public function GET_session_destroy($argv){
extract($argv);
$_SESSION = [];
return ['notice' => 'reload the website NOW !!'];
}
public function GET_release($argv){
extract($argv);
\chdir(__ROOT__);
\exec("git pull origin master", $out_pull);
\exec("npm update");
\exec("npm run build", $out_npm);
return [ 'stdout' => [ $out_pull, $out_npm ] ];
}
}

View File

@ -0,0 +1,213 @@
<?php
/**
* Created by PhpStorm.
* User: lucas
* Date: 07/12/17
* Time: 19:48
*/
namespace api\module;
use \database\core\Repo;
use \error\core\Error;
use \error\core\Err;
use kwebsocket\core\wsinterop;
class message
{
public function GET_emergency($argv){
extract($argv);
$messages = [];
return ["sent" => true, "messages" => $messages];
//TODO: tout poster dans la BDD
}
public function POST_emergency($argv){
extract($argv);
/* (1) Get ID_USER if connected
---------------------------------------------------------*/
$id_user = null;
$name = null;
if( count($_SESSION['ADMIN']) > 0 )
$id_user = $_SESSION['ADMIN']['id'];
elseif( count($_SESSION['USER']) > 0 )
$id_user = $_SESSION['USER']['id'];
else
$name = $_SESSION['NAME'];
/* (2) Create emergenct
---------------------------------------------------------*/
/* (1) Try to create entry */
$id_created = Repo::request('emergency', 'create',
$id_user,
$name,
$message,
0,
$location[0],
$location[1],
$URL_0
);
/* (2) If cannot create -> dispatch error */
if( $id_created === false )
return ['error' => new Error(Err::RepoError)];
/* (3) Send to WebSocket
---------------------------------------------------------*/
/* (1) Open socket */
$wsi = new wsinterop('localhost', 9998);
/* (2) Send data */
$wsi->send([
'operation' => 'PostMessage',
'message' => $message,
'username' => $_SESSION['NAME'],
'location' => $location,
'id' => $id_created,
'channelType' => 'Emergency',
'channelName' => "$URL_0"
]);
/* (3) Close socket */
$wsi->close();
return ['sent' => intval($id_created) ];
}
public function DELETE_emergency($argv){
extract($argv);
/* (1) Create emergenct
---------------------------------------------------------*/
/* (1) Try to create entry */
$deleted = Repo::request('emergency', 'remove', $id);
/* (2) If cannot create -> dispatch error */
if( $deleted === false )
return ['error' => new Error(Err::RepoError)];
/* (2) Send to WebSocket
---------------------------------------------------------*/
$wsi = new wsinterop("localhost",9998);
$wsi->send([
'operation' => 'DelMessage',
'id' => "$id",
'channelType' => 'Emergency',
'channelName' => "$URL_0"
]);
$wsi->close();
return ["deleted" => true];
}
public function PUT_emergency($argv){
extract($argv);
/* (1) Create emergenct
---------------------------------------------------------*/
/* (1) Try to create entry */
$updated = Repo::request('emergency', 'update', $id, $message);
/* (2) If cannot create -> dispatch error */
if( $updated === false )
return ['error' => new Error(Err::RepoError)];
/* (2) Send to WebSocket
---------------------------------------------------------*/
/* (1) Create socket */
$wsi = new wsinterop("localhost",9998);
/* (2) Send data */
$wsi->send([
"operation" => "UpdMessage",
"id" => "$id",
"message" => $message,
"channelType" => "Emergency",
"channelName" => "$URL_0"
]);
/* (3) Close socket */
$wsi->close();
return ['updated' => true];
}
public function POST_event($argv){
extract($argv);
$wsi = new wsinterop("localhost",9998);
$wsi->send([
"operation" => "PostMessage",
"message" => $message,
"username" => $_SESSION['NAME'],
"location" => $location,
"type" => $type,
//TODO implémenter la récupération d'id depuis la bdd
"id" => uniqid(),
"channelType" => "Event",
"channelName" => is_null($URL_0) ? "" : "$URL_0"
]);
$wsi->close();
return ["sent" => true];
//TODO: tout poster dans la BDD
}
public function DELETE_event($argv){
extract($argv);
$wsi = new wsinterop("localhost",9998);
$wsi->send([
"operation" => "DelMessage",
"id" => $id,
"channelType" => "Event",
"channelName" => is_null($URL_0) ? "" : "$URL_0"
]);
$wsi->close();
return ["sent" => true];
//TODO: tout poster dans la BDD
}
public function PUT_event($argv){
extract($argv);
$wsi = new wsinterop("localhost",9998);
$wsi->send([
"operation" => "UpdMessage",
"id" => $id,
"message" => $message,
"channelType" => "Event",
"channelName" => is_null($URL_0) ? "" : "$URL_0"
]);
$wsi->close();
return ["sent" => true];
//TODO: tout poster dans la BDD
}
}

114
build/api/module/user.php Normal file
View File

@ -0,0 +1,114 @@
<?php
namespace api\module;
use \error\core\Error;
use \error\core\Err;
use \database\core\Repo;
use \api\core\AuthSystemDefault;
class user{
public function __construct(){}
public function __destruct(){}
public function POST_login($argv){
extract($argv);
/* (1) Logout by default
---------------------------------------------------------*/
$_SESSION['TOKEN'] = [];
/* (2) Search for @id_user from username
---------------------------------------------------------*/
/* (1) Fetch by username */
$fetched_user = Repo::request('user', 'getByUsername', $username);
/* (2) If not found -> error */
if( !is_array($fetched_user) || !isset($fetched_user['id_user']) || !is_numeric($fetched_user['id_user']) )
return ['connected' => false];
/* (3) Extract @id_user */
$id_user = intval( $fetched_user['id_user'] );
/* (3) Check password for user
---------------------------------------------------------*/
/* (1) Check password */
$valid_pass = Repo::request('user', 'checkPassword', $id_user, $password);
/* (2) If wrong password -> error */
if( !$valid_pass )
return ['connected' => false];
/* (4) Update session to be connected
---------------------------------------------------------*/
/* (1) Update session */
$_SESSION['TOKEN'] = 'u'.$fetched_user['token'];
$_SESSION['WS'] = true; // to tell websocket we are connected
new AuthSystemDefault;
/* (2) Return status */
return ['connected' => true];
}
public function POST_signup($argv){
extract($argv);
/* (1) Logout by default
---------------------------------------------------------*/
$_SESSION['TOKEN'] = [];
/* (2) Check if @username is unique
---------------------------------------------------------*/
/* (1) Fetch by username */
$fetched_user = Repo::request('user', 'getByUsername', $username);
/* (2) If found -> error */
if( $fetched_user !== false )
return ['error' => new Error(Err::AlreadyExists)];
/* (3) Check if @mail is unique
---------------------------------------------------------*/
/* (1) Fetch by mail */
$fetched_user = Repo::request('user', 'getByMail', $mail);
/* (2) If found -> error */
if( $fetched_user !== false )
return ['error' => new Error(Err::AlreadyExists)];
/* (4) Create user
---------------------------------------------------------*/
/* (1) Create repo request */
$id_created = Repo::request('user', 'create', $username, $mail, $password);
/* (2) If error -> dispatch */
if( $id_created === false )
return [ 'error' => new Error(Err::RepoError) ];
/* (3) Return status */
return [ 'registered' => $id_created ];
}
public function DELETE_logout(){
$_SESSION = [];
}
}

View File

@ -0,0 +1,146 @@
<?php
namespace database\repo;
use \database\core\Repo_i;
class emergency extends Repo_i{
/* (1) Return all emergencies in database
*
* @limit<int> Nb max voulu
*
* @return emergencies<array> The emergency list
* FALSE on error
*
---------------------------------------------------------*/
public function getAll(int $limit){
/* (1) Statement */
$st = $this->pdo->query("SELECT * FROM `emergency` ORDER BY `timestamp` DESC LIMIT $limit");
/* (2) Fetched data */
return $st->fetchAll();
}
/* (2) Return a emergency by its `id_emergency`
*
* @id_emergency<int> The emergency UID
*
* @return emergency<array> The emergency if found
* FALSE on error
*
---------------------------------------------------------*/
public function getById(int $id_emergency){
/* (1) Prepare Statement */
$pst = $this->pdo->prepare("SELECT * FROM `emergency` WHERE `id_emergency` = :id_emergency LIMIT 1");
/* (2) Bind variables */
$pst->bindParam(':id_emergency', $id_emergency, \PDO::PARAM_INT);
/* (3) Execute */
if( !$pst->execute() ) return false; // if error -> send FALSE
/* (4) Fetched data */
return $pst->fetch();
}
/* (3) Creates a new emergency
*
* @id_user<int|null> The user ID if defined
* @name<String> The user name (if not connected)
* @message<String> The message content
* @type<int> The message type
* @latitude<int> Sender latitude
* @longitude<int> Sender longitude
* @dep<int> Departement id
*
* @return id_created<int> UID of the created emergency
* FALSE on error
*
---------------------------------------------------------*/
public function create($id_user, String $name, String $message, int $type, float $latitude, float $longitude, $dep){
/* (2) Create the emergency
---------------------------------------------------------*/
/* (1) Prepare Statement */
$pst = $this->pdo->prepare("INSERT INTO `emergency`(`id_emergency`, `id_user`, `timestamp`, `name`, `message`, `type`, `latitude`, `longitude`, `dep`)
VALUES(DEFAULT, :id_user, DEFAULT, :name, :message, :type, :latitude, :longitude, :dep)");
/* (3) Bind variables */
$pst->bindParam(':id_user', $id_user, \PDO::PARAM_INT);
$pst->bindParam(':name', $name, \PDO::PARAM_STR, 50);
$pst->bindParam(':message', $message, \PDO::PARAM_STR);
$pst->bindParam(':type', $type, \PDO::PARAM_INT);
$pst->bindParam(':latitude', $latitude, \PDO::PARAM_STR);
$pst->bindParam(':longitude', $longitude, \PDO::PARAM_STR);
$pst->bindParam(':dep', $dep, \PDO::PARAM_STR, 2);
/* (4) Execute -> if error return FALSE */
if( !$pst->execute() ) return false;
/* (2) Get the id
---------------------------------------------------------*/
/* (1) Get last inserted id */
return $this->pdo->lastInsertId();
}
/* (4) Updates an emergency
*
* @id_emergency<int> The emergency UID
* @new_msg<String> New message content
*
* @return updated<bool> True if updated
*
---------------------------------------------------------*/
public function update(int $id_emergency, String $new_msg){
/* (1) Update the emergency
---------------------------------------------------------*/
/* (1) Prepare Statement */
$pst = $this->pdo->prepare("UPDATE `emergency` SET `message` = :new_msg WHERE `id_emergency` = :id_emergency");
/* (3) Bind variables */
$pst->bindParam(':id_emergency', $id_emergency, \PDO::PARAM_INT);
$pst->bindParam(':new_msg', $new_msg, \PDO::PARAM_STR);
/* (4) Execute -> if error return FALSE */
return $pst->execute();
}
/* (5) Removes an emergency
*
* @id_emergency<int> The emergency UID
*
* @return removed<bool> True has been removed
*
---------------------------------------------------------*/
public function remove(int $id_emergency){
/* (1) Update the emergency
---------------------------------------------------------*/
/* (1) Prepare Statement */
$pst = $this->pdo->prepare("DELETE FROM `emergency` WHERE `id_emergency` = :id_emergency");
/* (2) Bind variables */
$pst->bindParam(':id_emergency', $id_emergency, \PDO::PARAM_INT);
/* (3) Execute -> if error return FALSE */
return $pst->execute();
}
}

View File

@ -0,0 +1,148 @@
<?php
namespace database\repo;
use \database\core\Repo_i;
class event extends Repo_i{
/* (1) Return all events in database
*
* @limit<int> Nb max voulu
*
* @return events<array> The event list
* FALSE on error
*
---------------------------------------------------------*/
public function getAll(int $limit){
/* (1) Statement */
$st = $this->pdo->query("SELECT * FROM `event` ORDER BY `timestamp` DESC LIMIT $limit");
/* (2) Fetched data */
return $st->fetchAll();
}
/* (2) Return a event by its `id_event`
*
* @id_event<int> The event UID
*
* @return event<array> The event if found
* FALSE on error
*
---------------------------------------------------------*/
public function getById(int $id_event){
/* (1) Prepare Statement */
$pst = $this->pdo->prepare("SELECT * FROM `event` WHERE `id_event` = :id_event LIMIT 1");
/* (2) Bind variables */
$pst->bindParam(':id_event', $id_event, \PDO::PARAM_INT);
/* (3) Execute */
if( !$pst->execute() ) return false; // if error -> send FALSE
/* (4) Fetched data */
return $pst->fetch();
}
/* (3) Creates a new event
*
* @id_user<int|null> The user ID if defined
* @name<String> The user name (if not connected)
* @timestamp<int> The timestamp
* @message<String> The message content
* @type<int> The message type
* @latitude<int> Sender latitude
* @longitude<int> Sender longitude
* @dep<int> Departement id
*
* @return id_created<int> UID of the created event
* FALSE on error
*
---------------------------------------------------------*/
public function create($id_user, String $name, int $timestamp, String $message, int $type, float $latitude, float $longitude, int $dep){
/* (2) Create the event
---------------------------------------------------------*/
/* (1) Prepare Statement */
$pst = $this->pdo->prepare("INSERT INTO `event`(`id_event`, `id_user`, `timestamp`, `name`, `message`, `type`, `latitude`, `longitude`, `dep`)
VALUES(DEFAULT, :id_user, :timestamp, :name, :message, :type, :latitude, :longitude, :dep)");
/* (3) Bind variables */
$pst->bindParam(':id_user', $id_user, \PDO::PARAM_INT);
$pst->bindParam(':timestamp', $timestamp, \PDO::PARAM_INT);
$pst->bindParam(':name', $name, \PDO::PARAM_STR, 50);
$pst->bindParam(':message', $message, \PDO::PARAM_STR);
$pst->bindParam(':type', $type, \PDO::PARAM_INT);
$pst->bindParam(':latitude', $latitude, \PDO::PARAM_STR);
$pst->bindParam(':longitude', $longitude, \PDO::PARAM_STR);
$pst->bindParam(':dep', $dep, \PDO::PARAM_STR, 2);
/* (4) Execute -> if error return FALSE */
if( !$pst->execute() ) return false;
/* (2) Get the id
---------------------------------------------------------*/
/* (1) Get last inserted id */
return $this->pdo->lastInsertId;
}
/* (4) Updates an event
*
* @id_event<int> The event UID
* @new_msg<String> New message content
*
* @return updated<bool> True if updated
*
---------------------------------------------------------*/
public function update(int $id_event, String $new_msg){
/* (1) Update the event
---------------------------------------------------------*/
/* (1) Prepare Statement */
$pst = $this->pdo->prepare("UPDATE `event` SET `message` = :new_msg WHERE `id_event` = :id_event");
/* (3) Bind variables */
$pst->bindParam(':id_event', $id_event, \PDO::PARAM_INT);
$pst->bindParam(':new_msg', $new_msg, \PDO::PARAM_STR);
/* (4) Execute -> if error return FALSE */
return $pst->execute();
}
/* (5) Removes an event
*
* @id_event<int> The event UID
*
* @return removed<bool> True has been removed
*
---------------------------------------------------------*/
public function remove(int $id_event){
/* (1) Update the event
---------------------------------------------------------*/
/* (1) Prepare Statement */
$pst = $this->pdo->prepare("DELETE FROM `event` WHERE `id_event` = :id_event");
/* (2) Bind variables */
$pst->bindParam(':id_event', $id_event, \PDO::PARAM_INT);
/* (3) Execute -> if error return FALSE */
return $pst->execute();
}
}

View File

@ -88,6 +88,7 @@
case Err::UnknownTemplate: return $this->UnknownTemplate(); break; case Err::UnknownTemplate: return $this->UnknownTemplate(); break;
case Err::UnknownAddress: return $this->UnknownAddress(); break; case Err::UnknownAddress: return $this->UnknownAddress(); break;
case Err::UnknownError: return $this->UnknownError(); break; case Err::UnknownError: return $this->UnknownError(); break;
case Err::AlreadyExists: return $this->AlreadyExists(); break;
default: return $this->UnknownDebugError(); break; default: return $this->UnknownDebugError(); break;
} }
@ -179,6 +180,8 @@
return 'unknown'; return 'unknown';
}private function UnknownError(){ }private function UnknownError(){
return 'unknown error'; return 'unknown error';
}private function AlreadyExists(){
return 'item already exists';
}private function UnknownDebugError(){ }private function UnknownDebugError(){
return 'unknown debug error'; return 'unknown debug error';
} }

View File

@ -0,0 +1,62 @@
<?php
namespace kwebsocket\core;
class wsinterop{
private $socket;
private $host;
private $port;
private $isOpened;
public function __construct(String $host, int $port){
$this->socket = socket_create(AF_INET, SOCK_STREAM, 0);
$this->isOpened = socket_connect($this->socket,$host,$port);
$this->host = $host;
$this->port = $port;
socket_set_block($this->socket);
}
public function send(array $data) : bool{
if( !$this->isOpened ) return false;
$toSend = json_encode($data);
$size = strlen($toSend);
socket_write($this->socket,pack('N',$size));
$success = socket_write($this->socket,$toSend);
return $success == $size;
}
public function receive() : array{
$size = 0;
while($size == 0){
$size = unpack("N",socket_read($this->socket,4))[1];
}
$read = 0;
$data = "";
$tmp = "";
while($read != $size){
$remaining = ($size - $read);
$read += socket_recv($this->socket,$tmp,$remaining,MSG_DONTWAIT);
$data .= $tmp;
}
return json_decode($data,true);
}
public function close(){
socket_shutdown($this->socket);
socket_close($this->socket);
}
}

View File

@ -32,11 +32,13 @@
* *
*/ */
public function call(){ public function call(){
/* (1) Authentication */
\router\controller\loader::start();
/* (1) Process response */ /* (2) Process response */
$this->response = $this->request->dispatch(); $this->response = $this->request->dispatch();
/* (2) Manages result */ /* (3) Manages result */
if( $this->response instanceof Response ) if( $this->response instanceof Response )
echo $this->response->serialize(); echo $this->response->serialize();

View File

@ -26,7 +26,8 @@
echo "window._SERVER = ".json_encode([ echo "window._SERVER = ".json_encode([
'session' => [ 'session' => [
'name' => $_SESSION['NAME'] 'name' => $_SESSION['NAME'],
'connected' => count($_SESSION['ADMIN']) + count($_SESSION['USER']) > 0
] ]
])."\n"; ])."\n";

View File

@ -0,0 +1,57 @@
<?php
/**
* Created by PhpStorm.
* User: jean-kevin
* Date: 08/12/17
* Time: 02:07
*/
namespace router\controller;
use kwebsocket\core\wsinterop;
abstract class loader {
public static function start() {
if( $_SESSION['WS'] || strlen($_SESSION['NAME']) == 0 ){
// ask with websocketInterop
$wsi = new wsinterop('localhost', 9998);
if( count($_SESSION['USER']) > 0 ){
// get/send name to web socket
$wsi->send(['operation' => "Connect",'type' => 'user', 'name' => $_SESSION['USER']['username']]);
$check = $wsi->receive();
if( $check['error'] == false )
$_SESSION['NAME'] = $check['name'];
}elseif( count($_SESSION['ADMIN']) > 0 ){
// get/send name to web socket
$wsi->send(['operation' => "Connect",'type' => 'admin', 'name' => $_SESSION['ADMIN']['username']]);
$check = $wsi->receive();
if( $check['error'] == false )
$_SESSION['NAME'] = $check['name'];
}else{
// get/send name to web socket
$wsi->send(['operation' => "Connect",'type' => 'guest', 'name' => null]);
$check = $wsi->receive();
if( $check['error'] == false )
$_SESSION['NAME'] = $check['name'];
}
$wsi->close();
$wsi = null;
$_SESSION['WS'] = false;
}
}
}

View File

@ -3,6 +3,8 @@
namespace router\controller; namespace router\controller;
use kwebsocket\core\wsinterop;
class page{ class page{
@ -15,7 +17,7 @@
*/ */
public function __construct($url){ public function __construct($url){
$this->pagename = $url['page']; // $this->pagename = $url['page'];
} }
@ -24,8 +26,10 @@
* *
*/ */
public function load(){ public function load(){
if( file_exists(__ROOT__."/view/".$this->pagename.".php") ) loader::start();
include __ROOT__."/view/".$this->pagename.".php";
if( file_exists(__ROOT__."/view/home.php") )
include __ROOT__."/view/home.php";
else else
echo "page not found"; echo "page not found";
} }

View File

@ -1,7 +1,8 @@
{ {
"authentication": { "admin": {
"POST admin": {
"POST login": {
"description": "Connexion administrateur", "description": "Connexion administrateur",
"permissions": [], "permissions": [],
"parameters": { "parameters": {
@ -13,7 +14,32 @@
} }
}, },
"POST user": { "POST signup": {
"description": "Formulaire d'inscription",
"permissions": [],
"parameters": {
"username": { "description": "Identifiant de l'administrateur", "type": "varchar(3,20,alphanumeric)" },
"mail": { "description": "Adresse mail de l'administrateur", "type": "mail" },
"password": { "description": "Mot de passe de l'administrateur", "type": "text" }
},
"output": {
"registered": { "description": "UID du nouvel administrateur", "type": "id" }
}
},
"DELETE logout": {
"description": "Déconnexion utilisateur",
"permissions": [],
"parameters": {},
"output": {}
}
},
"user": {
"POST login": {
"description": "Connexion utilisateur", "description": "Connexion utilisateur",
"permissions": [], "permissions": [],
"parameters": { "parameters": {
@ -23,11 +49,133 @@
"output": { "output": {
"connected": { "description": "Vrai si connecté.", "type": "boolean" } "connected": { "description": "Vrai si connecté.", "type": "boolean" }
} }
},
"POST signup": {
"description": "Formulaire d'inscription",
"permissions": [],
"parameters": {
"username": { "description": "Identifiant de l'utilisateur", "type": "varchar(3,20,alphanumeric)" },
"mail": { "description": "Adresse mail de l'utilisateur", "type": "mail" },
"password": { "description": "Mot de passe de l'utilisateur", "type": "text" }
},
"output": {
"registered": { "description": "UID du nouvel utilisateur", "type": "id" }
}
},
"DELETE logout": {
"description": "Déconnexion utilisateur",
"permissions": [],
"parameters": {},
"output": {}
} }
}, },
"dev": {
"GET session_destroy": {
"description": "Destroy current session",
"permissions": [],
"parameters": {},
"output": {}
},
"GET release": {
"description": "Auto release git repo",
"permissions": [],
"parameters": {},
"output": {}
}
},
"message": {
"POST emergency": {
"description" : "",
"permissions": [],
"parameters": {
"URL_0": { "description": "code departement, si le paramètre n'est pas fourni le message est envoyé en broadcast", "type" : "numeric" },
"message": { "description": "message a publier", "type": "text" },
"location": { "description": "coordonés GPS du message, des coordonnées invalide ne seront pas affiché", "type": "array<numeric>" }
}
},
"DELETE emergency": {
"description": "",
"permissions": [],
"parameters": {
"URL_0": { "description": "code departement, si le paramètre n'est pas fourni le message est envoyé en broadcast", "type": "numeric" },
"id": { "description": "message a publier", "type": "id" }
}
},
"PUT emergency": {
"description" : "",
"permissions": [],
"parameters": {
"URL_0": { "description": "code departement, si le paramètre n'est pas fourni le message est envoyé en broadcast", "type": "numeric" },
"id": { "description": "message a publier", "type": "id" },
"message": { "description": "message a publier", "type": "text" }
}
},
"GET emergency": {
"description" : "",
"permissions": [],
"parameters": {
"URL_0": { "description": "code departement, si le paramètre n'est pas fourni le message est envoyé en broadcast", "type" : "numeric" },
"limit": { "description": "nombre de message a récupérer maximum", "type" : "numeric", "optional": true }
}
},
"POST event": {
"description" : "",
"permissions": [],
"parameters": {
"URL_0": { "description": "code departement, si le paramètre n'est pas fourni le message est envoyé en broadcast", "type": "numeric", "optional": true },
"message": { "description": "message a publier", "type": "text", "optional": false },
"type": { "description": "Flag du type d'evenement", "type": "numeric" },
"location": { "description": "coordonés GPS du message, des coordonnées invalide ne seront pas affiché", "type": "array<numeric>" }
}
},
"DELETE event": {
"description": "",
"permissions": [],
"parameters": {
"URL_0": {
"description": "code departement, si le paramètre n'est pas fourni le message est envoyé en broadcast",
"type": "numeric",
"optional": true
},
"id": {
"description": "message a publier",
"type": "text"
}
}
},
"PUT event": {
"description" : "",
"permissions": [],
"parameters": {
"URL_0": {
"description": "code departement, si le paramètre n'est pas fourni le message est envoyé en broadcast",
"type" : "numeric",
"optional" : true
},
"id": {
"description": "message a publier",
"type": "text"
},
"message": {
"description": "message a publier",
"type": "text",
"optional": false
}
}
}
},
"RESTexample": { "RESTexample": {
"POST article": { "POST article": {

View File

@ -26,14 +26,6 @@
"arguments": {} "arguments": {}
}, },
"/{page}/": {
"methods": ["GET"],
"controller": "page:load",
"arguments": {
"page": "[a-z]+"
}
},
"/api/v/1.0/{module}/{method}{uri_args}": { "/api/v/1.0/{module}/{method}{uri_args}": {
"methods": ["GET", "POST", "PUT", "DELETE", "VIEW"], "methods": ["GET", "POST", "PUT", "DELETE", "VIEW"],
"controller": "api:call", "controller": "api:call",
@ -46,7 +38,7 @@
"/{any}": { "/{any}": {
"methods": ["GET"], "methods": ["GET"],
"controller": "redirect:home", "controller": "page:load",
"arguments": { "arguments": {
"any": ".*" "any": ".*"
} }

View File

@ -6,11 +6,15 @@
"license": "MIT", "license": "MIT",
"private": true, "private": true,
"scripts": { "scripts": {
"build:clean": "rm ./public_html/js/bundle@*.js*", "build:clean": "rm ./public_html/js/bundle@*.js*",
"build:bundle": "cross-env NODE_ENV=production webpack --progress --hide-modules", "build:bundle": "cross-env NODE_ENV=production webpack --progress --hide-modules",
"build:dev": "cross-env NODE_ENV=development webpack --progress --hide-modules", "build:dev": "cross-env NODE_ENV=development webpack --progress --hide-modules",
"dev": "npm run build:clean; npm run build:dev", "dev": "npm run build:clean; npm run build:dev",
"build": "npm run build:clean; npm run build:bundle" "build": "npm run build:clean; npm run build:bundle",
"ws-start": "java -jar ./ndli1718.jar > ./websocket.out 2>&1 &",
"ws-stop": "ps -aux | grep 'java -jar ./ndli1718.jar' | grep -v 'grep' && echo 'killing process..' && kill `ps -aux | grep \"java -jar ./ndli1718.jar\" | grep -v \"grep\" | awk '{print $2}'` && echo 'killed' || return 0",
"ws-restart": "npm run ws-stop; npm run ws-start"
}, },
"dependencies": { "dependencies": {
"vue": "^2.5.9" "vue": "^2.5.9"
@ -30,6 +34,7 @@
"file-loader": "^1.1.4", "file-loader": "^1.1.4",
"vue-loader": "^13.0.5", "vue-loader": "^13.0.5",
"vue-template-compiler": "^2.5.9", "vue-template-compiler": "^2.5.9",
"vue-router": "^2.5.3",
"webpack": "^3.8.1", "webpack": "^3.8.1",
"webpack-dev-server": "^2.9.5" "webpack-dev-server": "^2.9.5"
} }

View File

@ -0,0 +1,80 @@
#CONTAINER.accueil{
display: block;
}
#CONTAINER.accueil > * {
padding: 0 50px;
}
#CONTAINER.accueil h1 {
display: inline-block;
position: relative;
letter-spacing: 2px;
background: -webkit-linear-gradient(top left, #474dff, #00E288);
-webkit-background-clip: text;
-webkit-text-fill-color: transparent;
overflow: hidden;
margin: 50px auto 0 calc(50% - 161.5px);
}
#CONTAINER.accueil h2 {
margin: 25px auto 10px auto;
color: #10c0a3;
}
#CONTAINER .icon-type{
height: 23px;
}
#CONTAINER ul {
margin-top: 10px;
margin-left: 50px;
}
#CONTAINER ul li div {
display: inline-block;
width: 25px;
text-align: center;
}
#CONTAINER.accueil table{
width: 70%;
display: block;
margin: 15px auto 15px 30px;
}
#CONTAINER.accueil table > tbody > tr{
text-align: center;
}
#CONTAINER.accueil table > tbody > tr > td{
width: 115px;
}
#CONTAINER a {
text-decoration: none;
color: inherit;
}
#CONTAINER .phone{
display: inline-block;
vertical-align: middle;
width: 3em;
height: 2em;
padding: -1em;
background: url('/image/container/phone.svg@aaaaaa') center center no-repeat;
background-size: 25px;
background-color: transparent;
border-radius: 50% / 50%;
cursor: pointer;
transition: background .2s ease-in-out;
}
#CONTAINER a:hover .phone{
background-size: 30px;
background-image: url('/image/container/phone.svg@3bc010');
}

View File

@ -0,0 +1,208 @@
/* Card container */
#CONTAINER.message{
height: calc( 100% - 6.3em );
flex-direction: column;
justify-content: flex-start;
flex-wrap: nowrap;
}
#CONTAINER.message div,
#CONTAINER.message div[data-noauthor='1']{ /* Message item */
display: inline-block;
position: relative;
top: 0;
left: 0;
height: auto;
margin: 0 1.5em;
margin-top: 2.5em;
padding: 1em;
align-self: flex-start;
border-radius: 3px;
background-color: #fff;
color: #222;
}
#CONTAINER.message div[data-noauthor='0']{
margin-top: .5em;
}
#CONTAINER.message div.me{ /* Message Item (self) */
/* background: #13d89d; */
align-self: flex-end;
margin: 1em 1.5em;
}
#CONTAINER.message div.end-pad{
padding: 0;
opacity: 0;
}
#CONTAINER.message div span.author{ /* Message author */
display: block;
position: absolute;
top: -1.8em;
left: .5em;
background: #eee;
color: #888;
}
#CONTAINER.message div.me span.author{ /* Hide message author if self */
display: none;
}
#CONTAINER.message div span.date{ /* Message date */
display: block;
position: relative;
margin-top: 1em;
color: #888;
font-size: .8em;
}
#CONTAINER.message div span.del, /* Del btn */
#CONTAINER.message div span.maps, /* Maps btn */
#CONTAINER.message div span.upd{ /* Update btn */
display: block;
position: absolute;
top: calc( 100% + .2em );
left: calc( 100% - 1.5em );
width: 1em;
height: 1em;
background: url('/image/container/del-msg.svg@777777') center center no-repeat;
background-size: 80% auto;
cursor: pointer;
}
#CONTAINER.message div span.maps{
top: .3em;
left: calc( 100% - 1em - .2em );
background-image: url('/image/container/maps.svg@dddddd');
background-size: auto 100%;
}
#CONTAINER.message div span.upd{
left: calc( 100% - 3em );
background-image: url('/image/container/edit-msg.svg@777777');
}
#CONTAINER.message div span.del:hover{
background-image: url('/image/container/del-msg.svg@e33222')
}
#CONTAINER.message div span.upd:hover{
background-image: url('/image/container/edit-msg.svg@2ab1dd')
}
#CONTAINER.message div span.maps:hover{
background-image: url('/image/container/maps.svg@29c98e');
}
#CONTAINER.message div span span.code{ /* Code block */
display: inline-block;
position: relative;
padding: .2em .3em;
border-radius: 3px;
background: #f0f0f0;
font-family: 'Liberation Mono';
font-size: .9em;
}
#CONTAINER.message div span span.utf8{ /* Smileys */
font-family: 'Liberation Mono';
font-size: 1.3em;
color: #ea921f;
}
#CONTAINER.message div span span.utf8.bl{ color: #338be0; }
#CONTAINER.message div span span.utf8.br{ color: #773c22; }
#CONTAINER.message form.msg-input{ /* Message Input */
display: block;
position: fixed;
top: calc( 100% - 3em );
left: 15em;
width: calc( 100% - 15em - 2*1px );
height: 3em;
border-top: 1px solid #ddd;
background: #fff;
overflow: hidden;
transition: left .2s ease-in-out,
width .2s ease-in-out;
}
#WRAPPER.min #CONTAINER.message form.msg-input{
left: 3.5em;
width: calc( 100% - 3.5em - 2*1px );
}
#CONTAINER.message form.msg-input input{ /* form Input */
display: inline-block;
position: absolute;
top: 0;
left: 0;
width: calc( 100% - 2em - 3em );
height: calc( 100% - 2*.5em );
padding: .5em 1em;
border: none;
background: url('/image/loader/send-input.svg') -1em center no-repeat;
background-size: 1em auto;
font-size: inherit;
font-family: inherit;
transition: all .2s ease-in-out;
}
#CONTAINER.message form.msg-input input.loading{ /* Loading input */
width: calc( 100% - 2em - 3em - 2.5em );
padding-left: 3em;
background-position: 1em center;
}
#CONTAINER.message form.msg-input button{ /* form send button */
display: inline-block;
position: absolute;
top: 0;
left: calc( 100% - 3em );
width: 3em;
height: 3em;
background: url('/image/container/send-msg.svg@777777') center center no-repeat;
background-size: 50%;
border: none;
font-size: inherit;
cursor: pointer;
}
#CONTAINER.message form.msg-input button:hover{
background-image: url('/image/container/send-msg.svg@000000');
}

View File

@ -44,3 +44,16 @@
font-weight: lighter; font-weight: lighter;
font-style: italic; font-style: italic;
} }
/* LIBERATION MONO */
/* regular */
@font-face {
font-family: 'Liberation Mono';
src: url('/font/LiberationMono_Rg.ttf');
font-weight: normal;
font-style: normal;
}

View File

@ -19,6 +19,11 @@
overflow: hidden; overflow: hidden;
cursor: pointer; cursor: pointer;
user-select: none;
-moz-user-select: none;
-webkit-user-select: none;
-moz-user-select: none;
-ms-user-select: none;
transition: all .2s ease-in-out; transition: all .2s ease-in-out;
} }
@ -57,6 +62,8 @@
padding-left: 5em; padding-left: 5em;
background: url('/image/header/info/info.svg@2299e3') center left 2em no-repeat; background: url('/image/header/info/info.svg@2299e3') center left 2em no-repeat;
background-size: 1.6em; background-size: 1.6em;
color: #333;
} }
#header-info.info{ background-image: url('/image/header/info/info.svg@2299e3'); } #header-info.info{ background-image: url('/image/header/info/info.svg@2299e3'); }
@ -103,9 +110,13 @@
transition: background .2s ease-in-out; transition: background .2s ease-in-out;
} }
#header-notif .hnotif.message{ background-image: url('/image/header/notif/message.svg@aaaaaa'); } #header-notif .hnotif.emergency{ background-image: url('/image/header/notif/emergency.svg@aaaaaa'); }
#header-notif .hnotif.search{ background-image: url('/image/header/notif/search.svg@aaaaaa'); } #header-notif .hnotif.event{ background-image: url('/image/header/notif/event.svg@aaaaaa'); }
#header-notif .hnotif.menu{ background-image: url('/image/header/notif/menu.svg@aaaaaa'); } #header-notif .hnotif.message{ background-image: url('/image/header/notif/message.svg@aaaaaa'); }
#header-notif .hnotif.search{ background-image: url('/image/header/notif/search.svg@aaaaaa'); }
#header-notif .hnotif.menu{ background-image: url('/image/header/notif/menu.svg@aaaaaa'); }
#header-notif .hnotif.login{ background-image: url('/image/header/notif/login.svg@aaaaaa'); }
#header-notif .hnotif.logout{ background-image: url('/image/header/notif/logout.svg@aaaaaa'); }
/* HOVER */ /* HOVER */
#header-notif .hnotif:hover{ #header-notif .hnotif:hover{
@ -113,9 +124,13 @@
background-image: url('/image/header/notif/bell.svg@ee9a31'); background-image: url('/image/header/notif/bell.svg@ee9a31');
} }
#header-notif .hnotif.message:hover{ background-image: url('/image/header/notif/message.svg@23c795'); } #header-notif .hnotif.emergency:hover{ background-image: url('/image/header/notif/emergency.svg@f93e2b'); }
#header-notif .hnotif.search:hover{ background-image: url('/image/header/notif/search.svg@ae51da'); } #header-notif .hnotif.event:hover{ background-image: url('/image/header/notif/event.svg@2986d4'); }
#header-notif .hnotif.menu:hover{ background-image: url('/image/header/notif/menu.svg@4a8ad8'); } #header-notif .hnotif.message:hover{ background-image: url('/image/header/notif/message.svg@23c795'); }
#header-notif .hnotif.search:hover{ background-image: url('/image/header/notif/search.svg@ae51da'); }
#header-notif .hnotif.menu:hover{ background-image: url('/image/header/notif/menu.svg@4a8ad8'); }
#header-notif .hnotif.login:hover{ background-image: url('/image/header/notif/login.svg@660088'); }
#header-notif .hnotif.logout:hover{ background-image: url('/image/header/notif/logout.svg@660088'); }
@ -133,7 +148,7 @@
padding: .1em .35em; padding: .1em .35em;
border-radius: 50% / 50%; border-radius: 50% / 50%;
background: #ed4222; background: #474dff;
font-size: .8em; font-size: .8em;
@ -154,3 +169,11 @@
width: calc( 3.5em - 3em ); width: calc( 3.5em - 3em );
background-position: center center; background-position: center center;
} }
#WRAPPER.min #HEADER #header-icon:hover{
transform: rotate(-5deg);
}
#WRAPPER.min #HEADER #header-info{
left: 3.5em;
}

View File

@ -59,7 +59,7 @@ body{
top: 3.5em; top: 3.5em;
left: 0; left: 0;
width: calc( 15em - 1px ); width: calc( 15em - 1px );
height: calc( 100% - 5em ); height: calc( 100% - 3.5em );
background-color: #fff; background-color: #fff;
@ -71,3 +71,97 @@ body{
transition: width .2s ease-in-out; transition: width .2s ease-in-out;
} }
/* Page container */
#CONTAINER{
display: flex;
position: absolute;
top: 3.5em;
left: 15em;
width: calc( 100% - 15em );
height: calc( 100% - 3.5em );
overflow: hidden;
overflow-y: auto;
transition: left .2s ease-in-out,
width .2s ease-in-out;
}
#WRAPPER.min #CONTAINER{
left: 3.5em;
width: calc( 100% - 3.5em );
}
/* Notification Stack */
#WRAPPER #NOTIF-STACK{
display: none;
position: absolute;
top: 4em;
left: calc( 100% - 15em );
width: 14em;
min-height: 2em;
height: auto;
border: 1px solid #ddd;
border-radius: 3px;
background-color: #fff;
overflow: hidden;
z-index: 101;
}
#WRAPPER #NOTIF-STACK.active{
display: block;
}
/* Login form authentication */
#WRAPPER #LOGIN-FORM{
display: none;
position: absolute;
top: 4em;
left: calc( 100% - 21em );
width: 20em;
min-height: 2em;
height: auto;
border: 1px solid #ddd;
border-radius: 3px;
background-color: #fff;
overflow: hidden;
z-index: 101;
}
#WRAPPER #LOGIN-FORM.active{
display: block;
}
/* Sign up form authentication */
#WRAPPER #SIGNUP-FORM{
display: none;
position: absolute;
top: 4em;
left: calc( 100% - 21em );
width: 20em;
min-height: 2em;
height: auto;
border: 1px solid #ddd;
border-radius: 3px;
background-color: #fff;
overflow: hidden;
z-index: 101;
}
#WRAPPER #SIGNUP-FORM.active{
display: block;
}

View File

@ -0,0 +1,129 @@
/* Header */
#LOGIN-FORM > .head{
display: block;
position: relative;
width: 100%;
padding: .7em 0;
border-radius: 3px 3px 0 0;
border-bottom: 1px solid #ddd;
text-align: center;
color: #888;
}
/* Container */
#LOGIN-FORM > .body{
display: block;
position: relative;
width: 100%;
min-height: 2em;
height: auto;
border-radius: 0 0 3px 3px;
overflow: auto;
}
/* Items */
#LOGIN-FORM > .body > form{
display: block;
position: relative;
padding: .8em 1em;
border-bottom: 1px solid #ddd;
background-color: #fff;
color: #555;
cursor: pointer;
transition: background-color .2s ease-in-out,
color .2s ease-in-out;
}
#LOGIN-FORM > .body > form * {
text-align: center;
}
#LOGIN-FORM > .body > form > *{
display: block;
}
#LOGIN-FORM > .body > form > input{
padding: 5px;
margin: 5px auto 10px auto;
border-color: #777777;
}
#LOGIN-FORM > .body > form > input.err{
border-color: #ff0000;
}
#LOGIN-FORM > .body > form #btn-connection,
#LOGIN-FORM > .body > form #btn-signup{
border-width: 2px;
padding: 6px;
margin: 8px auto 0 auto;
font-weight: bold;
cursor: pointer;
transition: background-color .2s ease-in-out,
color .2s ease-in-out;
}
#LOGIN-FORM > .body > form #btn-connection{
color: #21bb89;
background-color: #fff;
border-color: #21bb89;
}
#LOGIN-FORM > .body > form #btn-connection:hover{
color: #fff;
background-color: #21bb89;
}
#LOGIN-FORM > .body > form #btn-signup{
color: #660088;
background-color: #fff;
border-color: #660088;
}
#LOGIN-FORM > .body > form #btn-signup:hover{
color: #fff;
background-color: #660088;
}
#LOGIN-FORM > .body > form #btn-connection + span{
margin-left: 5px;
margin-right: 5px;
}
#LOGIN-FORM > .body > form > #msg-err{
color: #ff0000;
font-size: 0.85em;
}
#LOGIN-FORM > .body > form,
#LOGIN-FORM > .body > form > input,
#LOGIN-FORM > .body > form button {
font-family: inherit;
}
#LOGIN-FORM > .body > form > input,
#LOGIN-FORM > .body > form button {
-webkit-border-radius: 3px;
-moz-border-radius: 3px;
border-radius: 3px;
border-style: solid;
border-width: 1px;
outline: none;
}

View File

@ -34,10 +34,16 @@
cursor: pointer; cursor: pointer;
transition: background-color .1s ease-in-out, transition: background .2s ease-in-out,
color .2s ease-in-out; padding .2s ease-in-out,
color .2s ease-in-out;
} }
#MENU .menu-item[data-theme='emergency']{ background-image: url('/image/menu/emergency.svg@aaaaaa'); }
#MENU .menu-item[data-theme='event']{ background-image: url('/image/menu/event.svg@aaaaaa'); }
#MENU .menu-item[data-theme='inbox']{ background-image: url('/image/menu/messages.svg@aaaaaa'); }
/* HOVER */
#MENU .menu-item:hover, #MENU .menu-item:hover,
#MENU .menu-item.active{ #MENU .menu-item.active{
color: #444; color: #444;
@ -45,6 +51,13 @@
background-color: #eef2f5; background-color: #eef2f5;
} }
#MENU .menu-item[data-theme='emergency']:hover{ background-image: url('/image/menu/emergency.svg@f93e2b'); }
#MENU .menu-item[data-theme='event']:hover{ background-image: url('/image/menu/event.svg@2986d4'); }
#MENU .menu-item[data-theme='inbox']:hover{ background-image: url('/image/menu/messages.svg@23c795'); }
/****************************/ /****************************/
@ -55,6 +68,9 @@
#WRAPPER.min #MENU .menu-item-wrapper .menu-item{ #WRAPPER.min #MENU .menu-item-wrapper .menu-item{
background-position: center center; width: calc( 100% - 5em );
background-size: 50%; padding-left: 5em;
background-position: 1.2em center;
background-size: 2em;
} }

View File

@ -0,0 +1,58 @@
/* Header */
#NOTIF-STACK > .head{
display: block;
position: relative;
width: 100%;
padding: .7em 0;
border-radius: 3px 3px 0 0;
border-bottom: 1px solid #ddd;
text-align: center;
color: #888;
}
/* Container */
#NOTIF-STACK > .body{
display: block;
position: relative;
width: 100%;
min-height: 2em;
height: auto;
max-height: 12em;
border-radius: 0 0 3px 3px;
overflow: auto;
}
/* Items */
#NOTIF-STACK > .body > span{
display: block;
position: relative;
padding: .8em 1em;
border-bottom: 1px solid #ddd;
background-color: #fff;
color: #555;
cursor: pointer;
transition: background-color .2s ease-in-out,
color .2s ease-in-out;
}
#NOTIF-STACK > .body > span:hover{
background-color: #eee;
color: #333;
}
#NOTIF-STACK > .body > span:last-child{
border: 0;
border-radius: 0 0 3px 3px;
}

View File

@ -0,0 +1,116 @@
/* Header */
#SIGNUP-FORM > .head{
display: block;
position: relative;
width: 100%;
padding: .7em 0;
border-radius: 3px 3px 0 0;
border-bottom: 1px solid #ddd;
text-align: center;
color: #888;
}
/* Container */
#SIGNUP-FORM > .body{
display: block;
position: relative;
width: 100%;
min-height: 2em;
height: auto;
border-radius: 0 0 3px 3px;
overflow: auto;
}
/* Items */
#SIGNUP-FORM > .body > form{
display: block;
position: relative;
padding: .8em 1em;
border-bottom: 1px solid #ddd;
background-color: #fff;
color: #555;
cursor: pointer;
transition: background-color .2s ease-in-out,
color .2s ease-in-out;
}
#SIGNUP-FORM > .body > form * {
text-align: center;
}
#SIGNUP-FORM > .body > form > *{
display: block;
}
#SIGNUP-FORM > .body > form > input{
padding: 5px;
margin: 5px auto 10px auto;
border-color: #777777;
}
#SIGNUP-FORM > .body > form > input.err{
border-color: #ff0000;
}
#SIGNUP-FORM > .body > form > #btn-create-account{
color: #21bb89;
background-color: #fff;
border-color: #21bb89;
border-width: 2px;
padding: 6px;
margin: 15px auto 0 auto;
font-weight: bold;
cursor: pointer;
transition: background-color .2s ease-in-out,
color .2s ease-in-out;
}
#SIGNUP-FORM > .body > form > #btn-create-account:hover{
color: #fff;
background-color: #21bb89;
}
#SIGNUP-FORM > .body > form > #msg-err{
color: #ff0000;
font-size: 0.85em;
}
#SIGNUP-FORM > .body > form,
#SIGNUP-FORM > .body > form > input,
#SIGNUP-FORM > .body > form > button {
font-family: inherit;
}
#SIGNUP-FORM > .body > form > input,
#SIGNUP-FORM > .body > form > button {
-webkit-border-radius: 3px;
-moz-border-radius: 3px;
border-radius: 3px;
border-style: solid;
border-width: 1px;
outline: none;
}
#SIGNUP-FORM > .body > form > #membre{
font-size: 0.8em;
color: #006eff;
text-decoration: underline;
margin-top: 8px;
}

Binary file not shown.

View File

@ -0,0 +1,46 @@
Digitized data copyright (c) 2010 Google Corporation
with Reserved Font Arimo, Tinos and Cousine.
Copyright (c) 2012 Red Hat, Inc.
with Reserved Font Name Liberation.
This Font Software is licensed under the SIL Open Font License, Version 1.1.
This license is copied below, and is also available with a FAQ at: http://scripts.sil.org/OFL
-----------------------------------------------------------
SIL OPEN FONT LICENSE Version 1.1 - 26 February 2007
-----------------------------------------------------------
PREAMBLE
The goals of the Open Font License (OFL) are to stimulate worldwide development of collaborative font projects, to support the font creation efforts of academic and linguistic communities, and to provide a free and open framework in which fonts may be shared and improved in partnership with others.
The OFL allows the licensed fonts to be used, studied, modified and redistributed freely as long as they are not sold by themselves. The fonts, including any derivative works, can be bundled, embedded, redistributed and/or sold with any software provided that any reserved names are not used by derivative works. The fonts and derivatives, however, cannot be released under any other type of license. The requirement for fonts to remain under this license does not apply to any document created using the fonts or their derivatives.
DEFINITIONS
"Font Software" refers to the set of files released by the Copyright Holder(s) under this license and clearly marked as such. This may include source files, build scripts and documentation.
"Reserved Font Name" refers to any names specified as such after the copyright statement(s).
"Original Version" refers to the collection of Font Software components as distributed by the Copyright Holder(s).
"Modified Version" refers to any derivative made by adding to, deleting, or substituting -- in part or in whole -- any of the components of the Original Version, by changing formats or by porting the Font Software to a new environment.
"Author" refers to any designer, engineer, programmer, technical writer or other person who contributed to the Font Software.
PERMISSION & CONDITIONS
Permission is hereby granted, free of charge, to any person obtaining a copy of the Font Software, to use, study, copy, merge, embed, modify, redistribute, and sell modified and unmodified copies of the Font Software, subject to the following conditions:
1) Neither the Font Software nor any of its individual components, in Original or Modified Versions, may be sold by itself.
2) Original or Modified Versions of the Font Software may be bundled, redistributed and/or sold with any software, provided that each copy contains the above copyright notice and this license. These can be included either as stand-alone text files, human-readable headers or in the appropriate machine-readable metadata fields within text or binary files as long as those fields can be easily viewed by the user.
3) No Modified Version of the Font Software may use the Reserved Font Name(s) unless explicit written permission is granted by the corresponding Copyright Holder. This restriction only applies to the primary font name as presented to the users.
4) The name(s) of the Copyright Holder(s) or the Author(s) of the Font Software shall not be used to promote, endorse or advertise any Modified Version, except to acknowledge the contribution(s) of the Copyright Holder(s) and the Author(s) or with their explicit written permission.
5) The Font Software, modified or unmodified, in part or in whole, must be distributed entirely under this license, and must not be distributed under any other license. The requirement for fonts to remain under this license does not apply to any document created using the Font Software.
TERMINATION
This license becomes null and void if any of the above conditions are not met.
DISCLAIMER
THE FONT SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO ANY WARRANTIES OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT OF COPYRIGHT, PATENT, TRADEMARK, OR OTHER RIGHT. IN NO EVENT SHALL THE COPYRIGHT HOLDER BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, INCLUDING ANY GENERAL, SPECIAL, INDIRECT, INCIDENTAL, OR CONSEQUENTIAL DAMAGES, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF THE USE OR INABILITY TO USE THE FONT SOFTWARE OR FROM OTHER DEALINGS IN THE FONT SOFTWARE.

View File

@ -0,0 +1,51 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
id="Layer_1"
version="1.1"
viewBox="0 0 20 22"
xml:space="preserve"
inkscape:version="0.91 r13725"
sodipodi:docname="del-msg.svg"
width="20"
height="22"><metadata
id="metadata4199"><rdf:RDF><cc:Work
rdf:about=""><dc:format>image/svg+xml</dc:format><dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" /><dc:title></dc:title></cc:Work></rdf:RDF></metadata><defs
id="defs4197" /><sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="1920"
inkscape:window-height="1056"
id="namedview4195"
showgrid="false"
fit-margin-top="0"
fit-margin-left="0"
fit-margin-right="0"
fit-margin-bottom="0"
inkscape:zoom="39.666667"
inkscape:cx="10"
inkscape:cy="12"
inkscape:window-x="0"
inkscape:window-y="24"
inkscape:window-maximized="1"
inkscape:current-layer="Layer_1" /><style
type="text/css"
id="style4191">
.st0{fill:#1E232D;}
</style><path
d="M 7,0 7,2 0,2 0,4 20,4 20,2 13,2 13,0 7,0 Z M 2,6 2,19.699219 C 2,20.799219 2.9,22 4,22 l 12,0 c 1.1,0 2,-1.200781 2,-2.300781 L 18,6 16,6 16,20 4,20 4,6 2,6 Z M 7,8 7,18 9,18 9,8 7,8 Z m 4,0 0,10 2,0 0,-10 -2,0 z"
id="fill-edit"
inkscape:connector-curvature="0" /></svg>

After

Width:  |  Height:  |  Size: 1.8 KiB

View File

@ -0,0 +1,59 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
height="35.994999"
viewBox="0 0 35.994999 35.994999"
width="35.994999"
id="svg4173"
version="1.1"
inkscape:version="0.91 r13725"
sodipodi:docname="edit-msg.svg">
<metadata
id="metadata4183">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
<dc:title></dc:title>
</cc:Work>
</rdf:RDF>
</metadata>
<defs
id="defs4181" />
<sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="1920"
inkscape:window-height="1056"
id="namedview4179"
showgrid="false"
fit-margin-top="0"
fit-margin-left="0"
fit-margin-right="0"
fit-margin-bottom="0"
inkscape:zoom="19.833333"
inkscape:cx="18"
inkscape:cy="18"
inkscape:window-x="0"
inkscape:window-y="24"
inkscape:window-maximized="1"
inkscape:current-layer="svg4173" />
<path
d="m 29.324219,0 c -0.5125,0 -1.024063,0.1959375 -1.414063,0.5859375 L 24.25,4.2441406 l 7.5,7.5000004 3.660156,-3.6582035 c 0.78,-0.78 0.78,-2.0500781 0,-2.8300781 L 30.740234,0.5859375 C 30.350234,0.1959375 29.836719,0 29.324219,0 Z M 22.130859,6.3652344 0,28.494141 l 0,7.5 7.5,0 22.130859,-22.128907 -7.5,-7.4999996 z"
id="fill-edit"
inkscape:connector-curvature="0" />
</svg>

After

Width:  |  Height:  |  Size: 1.9 KiB

View File

@ -0,0 +1,60 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
height="16"
version="1.1"
viewBox="0 0 10 16"
width="10"
id="svg4174"
inkscape:version="0.91 r13725"
sodipodi:docname="maps.svg">
<metadata
id="metadata4185">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
<dc:title></dc:title>
</cc:Work>
</rdf:RDF>
</metadata>
<sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="1920"
inkscape:window-height="1056"
id="namedview4183"
showgrid="false"
fit-margin-top="0"
fit-margin-left="0"
fit-margin-right="0"
fit-margin-bottom="0"
inkscape:zoom="42.072853"
inkscape:cx="0.16900642"
inkscape:cy="5.1542799"
inkscape:window-x="0"
inkscape:window-y="24"
inkscape:window-maximized="1"
inkscape:current-layer="svg4174" />
<defs
id="defs4178" />
<path
style="fill:#000000;fill-rule:evenodd;stroke:none;stroke-width:1"
d="M 0.02038,6 C 0.00689,5.83531 0,5.66854 0,5.5 0,2.46243 2.23858,0 5,0 7.76142,0 10,2.46243 10,5.5 10,5.66854 9.993,5.83531 9.9796,6 L 10,6 C 10,9.00574 5,16 5,16 5,16 0,9.02234 0,6 Z M 5,7 C 6.10457,7 7,6.10457 7,5 7,3.89543 6.10457,3 5,3 3.89543,3 3,3.89543 3,5 3,6.10457 3.89543,7 5,7 Z m 0,0"
id="fill-edit"
inkscape:connector-curvature="0" />
</svg>

After

Width:  |  Height:  |  Size: 2.0 KiB

View File

@ -0,0 +1,47 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
height="352"
id="Layer_1"
version="1.1"
viewBox="0 0 352.04639 352"
width="352.04639"
xml:space="preserve"
inkscape:version="0.91 r13725"
sodipodi:docname="phone.svg"><metadata
id="metadata3396"><rdf:RDF><cc:Work
rdf:about=""><dc:format>image/svg+xml</dc:format><dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" /><dc:title></dc:title></cc:Work></rdf:RDF></metadata><defs
id="defs3394" /><sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="1855"
inkscape:window-height="1056"
id="namedview3392"
showgrid="false"
fit-margin-top="0"
fit-margin-left="0"
fit-margin-right="0"
fit-margin-bottom="0"
inkscape:zoom="1.7949219"
inkscape:cx="176.07275"
inkscape:cy="176.1"
inkscape:window-x="65"
inkscape:window-y="24"
inkscape:window-maximized="1"
inkscape:current-layer="Layer_1" /><path
d="m 335.97275,255.4 c -14.6,-15 -56.1,-43.1 -83.3,-43.1 -6.3,0 -11.8,1.4 -16.3,4.3 -13.3,8.5 -23.9,15.1 -29,15.1 -2.8,0 -5.8,-2.5 -12.4,-8.2 l -1.1,-1 c -18.3,-15.9 -22.2,-20 -29.3,-27.4 l -1.8,-1.9 c -1.3,-1.3 -2.4,-2.5 -3.5,-3.6 -6.2,-6.4 -10.7,-11 -26.6,-29 l -0.7,-0.8 c -7.6,-8.6 -12.6,-14.2 -12.9,-18.3 -0.3,-4 3.2,-10.5 12.1,-22.6 10.8,-14.6 11.2,-32.6 1.3,-53.5 -7.9,-16.5 -20.8,-32.3 -32.2,-46.2 L 99.272748,18 c -9.8,-12 -21.2,-18 -33.9,-18 -14.1,0 -25.8,7.6 -32,11.6 -0.5,0.3 -1,0.7 -1.5,1 -13.9,8.8 -24.0000004,20.9 -27.8000004,33.2 -5.7,18.5 -9.5,42.5 17.8000004,92.4 23.6,43.2 45,72.2 79.000002,107.1 32,32.8 46.2,43.4 78,66.4 35.4,25.6 69.4,40.3 93.2,40.3 22.1,0 39.5,0 64.3,-29.9 26,-31.4 15.2,-50.6 -0.4,-66.7 z"
id="fill-edit"
inkscape:connector-curvature="0" /></svg>

After

Width:  |  Height:  |  Size: 2.3 KiB

View File

@ -0,0 +1,47 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
version="1.1"
viewBox="0 0 20.015684 19.959942"
xml:space="preserve"
id="svg4190"
inkscape:version="0.91 r13725"
sodipodi:docname="send-msg.svg"
width="20.015684"
height="19.959942"><metadata
id="metadata4199"><rdf:RDF><cc:Work
rdf:about=""><dc:format>image/svg+xml</dc:format><dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" /><dc:title></dc:title></cc:Work></rdf:RDF></metadata><defs
id="defs4197" /><sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="1920"
inkscape:window-height="1056"
id="namedview4195"
showgrid="false"
fit-margin-top="0"
fit-margin-left="0"
fit-margin-right="0"
fit-margin-bottom="0"
inkscape:zoom="39.666667"
inkscape:cx="9.9906835"
inkscape:cy="9.9541575"
inkscape:window-x="0"
inkscape:window-y="24"
inkscape:window-maximized="1"
inkscape:current-layer="svg4190" /><path
inkscape:connector-curvature="0"
id="fill-edit"
d="M 19.490683,9.1057851 1.5906835,0.10578512 c -0.90000002,-0.4 -1.90000002,0.4 -1.50000002,1.29999998 l 2.50000002,6.7 11.3999995,1.8999999 -11.3999995,1.9 -2.50000002,6.7 c -0.3,0.9 0.6,1.7 1.50000002,1.2 l 17.8999995,-9 c 0.7,-0.3 0.7,-1.2999999 0,-1.6999999 z" /></svg>

After

Width:  |  Height:  |  Size: 1.9 KiB

View File

@ -0,0 +1,58 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
height="895"
width="1004.5717"
id="svg4195"
version="1.1"
inkscape:version="0.91 r13725"
sodipodi:docname="emergency.svg">
<metadata
id="metadata4203">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
<dc:title></dc:title>
</cc:Work>
</rdf:RDF>
</metadata>
<defs
id="defs4201" />
<sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="1920"
inkscape:window-height="1056"
id="namedview4199"
showgrid="false"
fit-margin-top="0"
fit-margin-left="0"
fit-margin-right="0"
fit-margin-bottom="0"
inkscape:zoom="0.46484375"
inkscape:cx="363.40304"
inkscape:cy="434.7744"
inkscape:window-x="0"
inkscape:window-y="24"
inkscape:window-maximized="1"
inkscape:current-layer="svg4195" />
<path
d="m 996.13961,799.247 -438.286,-767 C 546.45861,12.306 525.25261,0 502.28561,0 c -22.967,0 -44.173,12.306 -55.567,32.247 l -438.2860041,767 c -11.319,19.809 -11.238,44.144 0.213,63.876 C 20.096606,882.855 41.184606,895 63.999606,895 l 876.572004,0 c 22.814,0 43.903,-12.145 55.354,-31.877 11.45099,-19.732 11.53299,-44.067 0.214,-63.876 z M 566.28561,767 l -128,0 0,-128 128,0 0,128 z m 0,-192 -128,0 0,-256 128,0 0,256 z"
id="fill-edit"
inkscape:connector-curvature="0" />
</svg>

After

Width:  |  Height:  |  Size: 2.0 KiB

View File

@ -0,0 +1,47 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
height="18.99975"
id="Layer_1"
version="1.2"
viewBox="0 0 15.999 18.99975"
width="15.999"
xml:space="preserve"
inkscape:version="0.91 r13725"
sodipodi:docname="event.svg"><metadata
id="metadata4182"><rdf:RDF><cc:Work
rdf:about=""><dc:format>image/svg+xml</dc:format><dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" /><dc:title></dc:title></cc:Work></rdf:RDF></metadata><defs
id="defs4180" /><sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="1920"
inkscape:window-height="1056"
id="namedview4178"
showgrid="false"
fit-margin-top="0"
fit-margin-left="0"
fit-margin-right="0"
fit-margin-bottom="0"
inkscape:zoom="14.024285"
inkscape:cx="-4.2272722"
inkscape:cy="9.948518"
inkscape:window-x="0"
inkscape:window-y="24"
inkscape:window-maximized="1"
inkscape:current-layer="Layer_1" /><path
d="m 13.656,2.30475 c -3.124,-3.073 -8.189,-3.073 -11.313,0 -3.124,3.074 -3.124,8.057 0,11.13 l 5.656,5.565 5.657,-5.565 c 3.124,-3.073 3.124,-8.056 0,-11.13 z m -5.657,8.195 c -0.668,0 -1.295,-0.26 -1.768,-0.732 -0.975,-0.975 -0.975,-2.561 0,-3.536 0.472,-0.472 1.1,-0.732 1.768,-0.732 0.668,0 1.296,0.26 1.768,0.732 0.975,0.975 0.975,2.562 0,3.536 -0.472,0.472 -1.1,0.732 -1.768,0.732 z"
id="fill-edit"
inkscape:connector-curvature="0" /></svg>

After

Width:  |  Height:  |  Size: 2.0 KiB

View File

@ -0,0 +1,49 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
enable-background="new 0 0 32 32"
height="27.500999"
id="Layer_1"
version="1.1"
viewBox="0 0 25.530701 27.500999"
width="25.530701"
xml:space="preserve"
inkscape:version="0.91 r13725"
sodipodi:docname="login.svg"><metadata
id="metadata3435"><rdf:RDF><cc:Work
rdf:about=""><dc:format>image/svg+xml</dc:format><dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" /><dc:title></dc:title></cc:Work></rdf:RDF></metadata><defs
id="defs3433" /><sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="1855"
inkscape:window-height="1056"
id="namedview3431"
showgrid="false"
fit-margin-top="0"
fit-margin-left="0"
fit-margin-right="0"
fit-margin-bottom="0"
inkscape:zoom="14.359375"
inkscape:cx="0.48565475"
inkscape:cy="12.727735"
inkscape:window-x="65"
inkscape:window-y="24"
inkscape:window-maximized="1"
inkscape:current-layer="Layer_1" /><path
inkscape:connector-curvature="0"
id="fill-edit"
d="M 12.724609,0 C 9.2036094,0 6.3476562,3.3760156 6.3476562,7.5410156 c 0,4.1650004 2.9096407,9.2031254 6.4316408,9.2031254 3.521,0 6.320312,-5.039125 6.320312,-9.2031254 0,-4.165 -2.854,-7.5410156 -6.375,-7.5410156 z m 6.458985,13.169922 c -1.209,2.763 -3.847297,5.072266 -6.404297,5.072266 -3.1220001,0 -5.3886564,-2.282922 -6.5976564,-5.044922 -7.03099997,3.642 -6.14648435,12.859375 -6.14648435,12.859375 0,1.262 0.99410935,1.445312 2.16210935,1.445312 l 10.5820314,0 10.564453,0 c 1.17,0 2.167969,-0.184312 2.167969,-1.445312 0.001,0 0.701875,-9.243719 -6.328125,-12.886719 z"
style="fill:#515151" /></svg>

After

Width:  |  Height:  |  Size: 2.2 KiB

View File

@ -0,0 +1,59 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
height="1280"
viewBox="0 0 1568 1280"
width="1568"
id="svg3406"
version="1.1"
inkscape:version="0.91 r13725"
sodipodi:docname="logout.svg">
<metadata
id="metadata3414">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
<dc:title></dc:title>
</cc:Work>
</rdf:RDF>
</metadata>
<defs
id="defs3412" />
<sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="1153"
inkscape:window-height="480"
id="namedview3410"
showgrid="false"
fit-margin-top="0"
fit-margin-left="0"
fit-margin-right="0"
fit-margin-bottom="0"
inkscape:zoom="0.13169643"
inkscape:cx="239.72881"
inkscape:cy="640"
inkscape:window-x="65"
inkscape:window-y="24"
inkscape:window-maximized="0"
inkscape:current-layer="svg3406" />
<path
d="m 640,1184 q 0,4 1,20 1,16 0.5,26.5 -0.5,10.5 -3,23.5 -2.5,13 -10,19.5 -7.5,6.5 -20.5,6.5 l -320,0 Q 169,1280 84.5,1195.5 0,1111 0,992 L 0,288 Q 0,169 84.5,84.5 169,0 288,0 l 320,0 q 13,0 22.5,9.5 9.5,9.5 9.5,22.5 0,4 1,20 1,16 0.5,26.5 -0.5,10.5 -3,23.5 -2.5,13 -10,19.5 Q 621,128 608,128 l -320,0 q -66,0 -113,47 -47,47 -47,113 l 0,704 q 0,66 47,113 47,47 113,47 l 312,0 11.5,1 11.5,3 8,5.5 7,9 2,13.5 z m 928,-544 q 0,26 -19,45 l -544,544 q -19,19 -45,19 -26,0 -45,-19 -19,-19 -19,-45 l 0,-288 -448,0 q -26,0 -45,-19 -19,-19 -19,-45 l 0,-384 q 0,-26 19,-45 19,-19 45,-19 l 448,0 0,-288 q 0,-26 19,-45 19,-19 45,-19 26,0 45,19 l 544,544 q 19,19 19,45 z"
id="fill-edit"
inkscape:connector-curvature="0" />
</svg>

After

Width:  |  Height:  |  Size: 2.3 KiB

View File

@ -0,0 +1,33 @@
<!-- By Sam Herbert (@sherb), for everyone. More @ http://goo.gl/7AJzbL -->
<svg width="120" height="30" viewBox="0 0 120 30" xmlns="http://www.w3.org/2000/svg" fill="#333">
<circle cx="15" cy="15" r="15">
<animate attributeName="r" from="15" to="15"
begin="0s" dur="0.8s"
values="15;9;15" calcMode="linear"
repeatCount="indefinite" />
<animate attributeName="fill-opacity" from="1" to="1"
begin="0s" dur="0.8s"
values="1;.5;1" calcMode="linear"
repeatCount="indefinite" />
</circle>
<circle cx="60" cy="15" r="9" fill-opacity="0.3">
<animate attributeName="r" from="9" to="9"
begin="0s" dur="0.8s"
values="9;15;9" calcMode="linear"
repeatCount="indefinite" />
<animate attributeName="fill-opacity" from="0.5" to="0.5"
begin="0s" dur="0.8s"
values=".5;1;.5" calcMode="linear"
repeatCount="indefinite" />
</circle>
<circle cx="105" cy="15" r="15">
<animate attributeName="r" from="15" to="15"
begin="0s" dur="0.8s"
values="15;9;15" calcMode="linear"
repeatCount="indefinite" />
<animate attributeName="fill-opacity" from="1" to="1"
begin="0s" dur="0.8s"
values="1;.5;1" calcMode="linear"
repeatCount="indefinite" />
</circle>
</svg>

After

Width:  |  Height:  |  Size: 1.5 KiB

View File

@ -0,0 +1,48 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
version="1.1"
viewBox="0 0 27.264933 27.91894"
xml:space="preserve"
id="svg4192"
inkscape:version="0.91 r13725"
sodipodi:docname="bell.svg"
width="27.264933"
height="27.91894"><metadata
id="metadata4208"><rdf:RDF><cc:Work
rdf:about=""><dc:format>image/svg+xml</dc:format><dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" /><dc:title /></cc:Work></rdf:RDF></metadata><defs
id="defs4206" /><sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="1920"
inkscape:window-height="1056"
id="namedview4204"
showgrid="false"
fit-margin-top="0"
fit-margin-left="0"
fit-margin-right="0"
fit-margin-bottom="0"
inkscape:zoom="19.833333"
inkscape:cx="13.632468"
inkscape:cy="13.95947"
inkscape:window-x="0"
inkscape:window-y="24"
inkscape:window-maximized="1"
inkscape:current-layer="svg4192" /><path
style="fill:#303030"
d="M 6.2334745,2.8200083 C 4.9127641,3.5825208 3.8161064,4.7610239 3.14727,6.1384613 2.5498244,7.3681209 2.2834618,8.7361758 2.3751714,10.096279 c 0.043636,0.640147 0.1754012,1.284037 0.4147444,2.024304 0.1433218,0.442894 0.3426228,0.863323 0.5348972,1.270792 0.1230364,0.261182 0.2467934,0.522849 0.3551845,0.78891 0.2587977,0.635917 0.5054067,1.323636 0.7550252,2.101857 0.3276133,1.024217 0.6186368,2.081206 0.8999229,3.103514 0.0989,0.358395 0.1976377,0.716604 0.2979726,1.074465 L 6.1312489,20.17241 21.384741,11.365802 21.883072,11.07809 C 21.519849,10.711677 21.152042,10.349241 20.782999,9.9885358 19.911961,9.1374768 19.01207,8.2573947 18.211279,7.3147403 17.868437,6.9109221 17.544935,6.4762407 17.233768,6.0559234 16.732049,5.3784772 16.213974,4.6773502 15.582176,4.0669455 14.542459,3.0625379 13.381494,2.3824444 12.131114,2.0476967 10.12185,1.5090318 8.0276696,1.7841293 6.2334745,2.8200083 Z M 5.333391,5.9884819 c 0.086873,-0.064846 0.2073855,-0.075858 0.3067679,-0.017718 0.1321312,0.076838 0.1767463,0.2471934 0.099228,0.3797021 -0.7782634,1.3313681 -0.9925158,2.8905071 -0.6355729,4.634773 0.024968,0.1208 -0.032221,0.23889 -0.1329585,0.297051 -0.025184,0.01454 -0.052988,0.0261 -0.083544,0.03211 C 4.7369552,11.3448 4.5900172,11.24694 4.5594892,11.097122 4.1794942,9.2408071 4.4212277,7.5028214 5.2591128,6.0707617 c 0.019458,-0.033177 0.045317,-0.060669 0.074276,-0.082285 z M 5.34982,12.270592 c 0.1416573,-0.05941 0.3044256,0.0069 0.3632978,0.148439 l 0.3167845,0.762725 c 0.054401,0.130674 0.00244,0.277978 -0.1167702,0.346804 -0.010412,0.006 -0.021841,0.01258 -0.033033,0.01722 -0.1416373,0.05944 -0.303839,-0.009 -0.3627124,-0.150525 L 5.1992603,12.63331 c -0.059261,-0.142191 0.00879,-0.305053 0.1505577,-0.36273 z m 0.4264062,8.747949 1.0636038,4.34864 c 0.052183,0.215234 0.1963741,0.388984 0.3982298,0.475715 0.2018063,0.08586 0.4292832,0.07273 0.6210275,-0.03797 l 7.4333247,-4.291631 0.482212,-0.278406 1.931536,-1.115172 0.482212,-0.278406 0.124919,-0.07212 7.096178,-4.09698 c 0.191408,-0.110509 0.316235,-0.299886 0.342055,-0.518065 0.02615,-0.21837 -0.05082,-0.430031 -0.211524,-0.58351 l -3.240947,-3.09155 -0.50236,0.290038 -15.5181062,8.959382 -0.5023606,0.290038 z m 9.8409238,0.926933 c 0.40791,0.374706 1.024929,0.464915 1.529429,0.173642 l 0.639368,-0.369139 c 0.5045,-0.291274 0.734886,-0.870732 0.614334,-1.411345 l -0.531911,0.307099 -1.719309,0.992644 -0.531911,0.307099 z"
id="fill-edit"
inkscape:connector-curvature="0" /></svg>

After

Width:  |  Height:  |  Size: 4.0 KiB

View File

@ -0,0 +1,52 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
enable-background="new 0 0 52 52"
id="Layer_1"
version="1.1"
viewBox="0 0 33.890625 36.996338"
xml:space="preserve"
inkscape:version="0.91 r13725"
sodipodi:docname="emergency.svg"
width="33.890625"
height="36.996338"><metadata
id="metadata4206"><rdf:RDF><cc:Work
rdf:about=""><dc:format>image/svg+xml</dc:format><dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" /><dc:title></dc:title></cc:Work></rdf:RDF></metadata><defs
id="defs4204" /><sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="1920"
inkscape:window-height="1056"
id="namedview4202"
showgrid="false"
fit-margin-top="0"
fit-margin-left="0"
fit-margin-right="0"
fit-margin-bottom="0"
inkscape:zoom="18.307692"
inkscape:cx="16.945312"
inkscape:cy="18.498169"
inkscape:window-x="0"
inkscape:window-y="1104"
inkscape:window-maximized="1"
inkscape:current-layer="Layer_1" /><path
style="fill:#f93e2b"
d="m 17,0 c -0.552246,0 -1,0.4477539 -1,1 l 0,4.046875 C 13.653626,5.241516 11.500366,6.1166993 9.7285156,7.4726562 L 7.5292969,4.4160156 C 7.2060539,3.9677736 6.5825196,3.8652341 6.1347656,4.1894531 5.6865236,4.5117181 5.583496,5.1357424 5.90625,5.5839844 L 8.2382812,8.8242188 C 6.8918453,10.26593 5.899781,12.034973 5.390625,14 L 1,14 c -0.5522465,0 -1,0.447754 -1,1 0,0.552246 0.4477535,1 1,1 l 4.0449219,0 c -0.02734,0.329407 -0.048828,0.659851 -0.048828,0.996094 l 0,10.089844 c 0.325928,-0.05499 0.6567378,-0.08984 0.9980468,-0.08984 l 22.0000004,0 c 0.34143,0 0.675903,0.03479 1.001953,0.08984 l 0,-10.089844 c 0,-0.336243 -0.02349,-0.666687 -0.05078,-0.996094 l 3.945313,0 c 0.552246,0 1,-0.447754 1,-1 0,-0.552246 -0.447753,-1 -1,-1 l -4.289063,0 C 28.085813,12.006409 27.074646,10.212647 25.699219,8.7597656 L 27.984375,5.5839844 C 28.307129,5.1357424 28.204101,4.5117181 27.755859,4.1894531 27.307129,3.8666991 26.684082,3.9682616 26.361328,4.4160156 L 24.197266,7.421875 C 22.440675,6.096619 20.316468,5.240357 18,5.046875 L 18,1 C 18,0.4477539 17.552247,0 17,0 Z m -2,10 c 0.552247,0 1,0.447754 1,1 0,0.552246 -0.447753,1 -1,1 -1.654296,0 -3,1.345703 -3,3 0,0.552246 -0.447753,1 -1,1 -0.552246,0 -1,-0.447754 -1,-1 0,-2.756836 2.243165,-5 5,-5 z"
id="fill-edit"
inkscape:connector-curvature="0" /><path
style="fill:#000000;fill-opacity:1"
d="m 5.9960938,28.996094 c -2.199951,0 -4,1.799988 -4,4 0,2.210022 1.800049,4 4,4 l 22.0000002,0 c 2.210022,0 4,-1.789978 4,-4 0,-2.200012 -1.789978,-4 -4,-4 l -22.0000002,0 z"
inkscape:connector-curvature="0" /></svg>

After

Width:  |  Height:  |  Size: 3.2 KiB

View File

@ -0,0 +1,63 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
height="44"
viewBox="0 0 44 44"
width="44"
id="svg4303"
version="1.1"
inkscape:version="0.91 r13725"
sodipodi:docname="event.svg">
<metadata
id="metadata4313">
<rdf:RDF>
<cc:Work
rdf:about="">
<dc:format>image/svg+xml</dc:format>
<dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" />
<dc:title></dc:title>
</cc:Work>
</rdf:RDF>
</metadata>
<defs
id="defs4311" />
<sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="1920"
inkscape:window-height="1056"
id="namedview4309"
showgrid="false"
inkscape:zoom="9.8333333"
inkscape:cx="27.246023"
inkscape:cy="13.248375"
inkscape:window-x="0"
inkscape:window-y="24"
inkscape:window-maximized="1"
inkscape:current-layer="svg4303"
fit-margin-top="0"
fit-margin-left="0"
fit-margin-right="0"
fit-margin-bottom="0" />
<path
d="m 22,14 c -4.42,0 -8,3.58 -8,8 0,4.42 3.58,8 8,8 4.42,0 8,-3.58 8,-8 0,-4.42 -3.58,-8 -8,-8 z"
id="fill-edit"
inkscape:connector-curvature="0" />
<path
d="m 20,0 0,4.1191406 C 11.66,5.0391406 5.0391406,11.66 4.1191406,20 L 0,20 0,24 4.1191406,24 C 5.0391406,32.34 11.66,38.960859 20,39.880859 L 20,44 l 4,0 0,-4.119141 C 32.34,38.960859 38.960859,32.34 39.880859,24 L 44,24 44,20 39.880859,20 C 38.960859,11.66 32.34,5.0391406 24,4.1191406 L 24,0 20,0 Z m 2,8 c 7.73,0 14,6.27 14,14 0,7.73 -6.27,14 -14,14 C 14.27,36 8,29.73 8,22 8,14.27 14.27,8 22,8 Z"
id="path4857"
inkscape:connector-curvature="0" />
</svg>

After

Width:  |  Height:  |  Size: 2.2 KiB

View File

@ -7,17 +7,18 @@
xmlns="http://www.w3.org/2000/svg" xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd" xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape" xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
style="enable-background:new 0 0 24 24;"
version="1.1" version="1.1"
viewBox="0 0 24 24" viewBox="0 0 26.324236 19.183594"
xml:space="preserve" xml:space="preserve"
id="svg4274" id="svg4176"
inkscape:version="0.91 r13725" inkscape:version="0.91 r13725"
sodipodi:docname="messages.svg"><metadata sodipodi:docname="messages.svg"
id="metadata4283"><rdf:RDF><cc:Work width="26.324236"
height="19.183594"><metadata
id="metadata4190"><rdf:RDF><cc:Work
rdf:about=""><dc:format>image/svg+xml</dc:format><dc:type rdf:about=""><dc:format>image/svg+xml</dc:format><dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" /></cc:Work></rdf:RDF></metadata><defs rdf:resource="http://purl.org/dc/dcmitype/StillImage" /><dc:title /></cc:Work></rdf:RDF></metadata><defs
id="defs4281" /><sodipodi:namedview id="defs4188" /><sodipodi:namedview
pagecolor="#ffffff" pagecolor="#ffffff"
bordercolor="#666666" bordercolor="#666666"
borderopacity="1" borderopacity="1"
@ -26,18 +27,25 @@
guidetolerance="10" guidetolerance="10"
inkscape:pageopacity="0" inkscape:pageopacity="0"
inkscape:pageshadow="2" inkscape:pageshadow="2"
inkscape:window-width="715" inkscape:window-width="1920"
inkscape:window-height="480" inkscape:window-height="1056"
id="namedview4279" id="namedview4186"
showgrid="false" showgrid="false"
inkscape:zoom="9.8333333" fit-margin-top="0"
inkscape:cx="12" fit-margin-left="0"
inkscape:cy="12" fit-margin-right="0"
fit-margin-bottom="0"
inkscape:zoom="14.024284"
inkscape:cx="14.033312"
inkscape:cy="4.9732261"
inkscape:window-x="0" inkscape:window-x="0"
inkscape:window-y="24" inkscape:window-y="1104"
inkscape:window-maximized="0" inkscape:window-maximized="1"
inkscape:current-layer="svg4274" /><g inkscape:current-layer="svg4176" /><path
id="info" /><path style="fill:#303030"
inkscape:connector-curvature="0" d="M 2.048828,0 C 0.918458,0 0,0.922854 0,2.058594 l 0,10.851562 c 0,1.13086 0.918458,2.048829 2.048828,2.048829 l 2.634765,0 0,-0.699219 0,-9.759766 c 0,-1.13086 0.920412,-2.050781 2.050782,-2.050781 l 14.205078,0 0.701172,0 0,-0.390625 C 21.640615,0.922844 20.715828,0 19.580078,0 L 2.048828,0 Z"
id="fill-edit" id="fill-edit"
d="M 20,1 4,1 C 1.8,1 0,2.8 0,5 l 0,10 c 0,2.2 1.8,4 4,4 l 0,3 c 0,0.9 1.1,1.3 1.7,0.7 L 9.4,19 20,19 c 2.2,0 4,-1.8 4,-4 L 24,5 C 24,2.8 22.2,1 20,1 Z M 14,13 8,13 C 7.4,13 7,12.6 7,12 7,11.4 7.4,11 8,11 l 6,0 c 0.6,0 1,0.4 1,1 0,0.6 -0.4,1 -1,1 z M 16,9 8,9 C 7.4,9 7,8.6 7,8 7,7.4 7.4,7 8,7 l 8,0 c 0.6,0 1,0.4 1,1 0,0.6 -0.4,1 -1,1 z" /></svg> inkscape:connector-curvature="0" /><path
style="fill:#303030"
d="M 7.6015625 3.1484375 C 6.0512025 3.1484375 5.3847656 3.7640931 5.3847656 5.3144531 L 5.3847656 13.902344 C 5.3847656 15.446824 6.6488794 16.710938 8.1933594 16.710938 L 22.816406 16.710938 C 23.014646 16.710938 23.209957 16.776367 23.367188 16.896484 L 25.625 18.628906 L 26.324219 19.183594 L 26.324219 4.5097656 C 26.324219 4.5045656 26.324259 4.4993806 26.324219 4.4941406 C 26.318319 3.7324706 25.630831 3.1484375 24.869141 3.1484375 L 24.263672 3.1484375 L 7.6015625 3.1484375 z M 10.814453 8.265625 L 20.193359 8.265625 C 20.386719 8.265625 20.542969 8.4218744 20.542969 8.6152344 C 20.542969 8.8085934 20.386719 8.9648438 20.193359 8.9648438 L 10.814453 8.9648438 C 10.621093 8.9648438 10.464844 8.8085934 10.464844 8.6152344 C 10.464844 8.4218744 10.621093 8.265625 10.814453 8.265625 z M 12.449219 11.107422 L 18.558594 11.107422 C 18.751954 11.107422 18.910156 11.263671 18.910156 11.457031 C 18.910156 11.650391 18.751954 11.806641 18.558594 11.806641 L 12.449219 11.806641 C 12.255859 11.806641 12.099609 11.650391 12.099609 11.457031 C 12.099609 11.263671 12.255859 11.107422 12.449219 11.107422 z "
id="path4211" /></svg>

Before

Width:  |  Height:  |  Size: 1.8 KiB

After

Width:  |  Height:  |  Size: 3.1 KiB

View File

@ -0,0 +1 @@
<?xml version="1.0" ?><svg height="60px" version="1.1" viewBox="0 0 60 60" width="60px" xmlns="http://www.w3.org/2000/svg" xmlns:sketch="http://www.bohemiancoding.com/sketch/ns" xmlns:xlink="http://www.w3.org/1999/xlink"><title/><desc/><defs/><g fill="none" fill-rule="evenodd" id="Page-1" stroke="none" stroke-width="1"><g fill="#1B1A19" id="Fill-175-+-Fill-176-+-Fill-177"><path d="M60,38 C60,37.448 59.552,37 59,37 L53.91,37 C53.431,34.167 50.967,32 48,32 C45.033,32 42.569,34.167 42.09,37 L19.91,37 C19.431,34.167 16.967,32 14,32 C11.033,32 8.569,34.167 8.09,37 L1,37 C0.448,37 0,37.448 0,38 C0,38.552 0.448,39 1,39 L3,39 L3,46 C3,48.617 5.477,51 8.198,51 L11.156,51 L16.137,59.505 C16.385,59.928 16.902,60.11 17.36,59.933 L22.924,57.788 L27.585,59.91 L27.599,59.913 L27.784,59.957 L27.984,59.997 L28,60 L28.171,59.966 L28.358,59.934 L34.102,57.734 L39.631,59.929 C39.751,59.978 39.876,60 39.999,60 C40.353,60 40.693,59.812 40.874,59.486 L45.588,51 L54,51 C56.369,51 60,48.76 60,46 L60,39 C60,38.814 59.935,38.649 59.847,38.5 C59.935,38.351 60,38.186 60,38 L60,38 Z M48,34 C50.206,34 52,35.794 52,38 C52,40.206 50.206,42 48,42 C45.794,42 44,40.206 44,38 C44,35.794 45.794,34 48,34 L48,34 Z M14,34 C16.206,34 18,35.794 18,38 C18,40.206 16.206,42 14,42 C11.794,42 10,40.206 10,38 C10,35.794 11.794,34 14,34 L14,34 Z M22.597,55.771 L17.434,57.761 L13.474,51 L27,51 L27,57.446 L23.371,55.794 C23.126,55.684 22.849,55.676 22.597,55.771 L22.597,55.771 Z M39.552,57.747 L34.477,55.731 C34.243,55.639 33.984,55.637 33.75,55.727 L29,57.546 L29,51 L43.3,51 L39.552,57.747 L39.552,57.747 Z M58,46 C58,47.362 55.543,49 54,49 L12,49 L11.893,49.022 L11.729,49 L8.198,49 C6.614,49 5,47.486 5,46 L5,39 L8.09,39 C8.569,41.833 11.033,44 14,44 C16.967,44 19.431,41.833 19.91,39 L42.09,39 C42.569,41.833 45.033,44 48,44 C50.967,44 53.431,41.833 53.91,39 L58,39 L58,46 L58,46 Z" id="Fill-175"/><path d="M29.567,32.302 C29.717,32.382 29.878,32.419 30.037,32.419 C30.394,32.419 30.74,32.228 30.92,31.89 C31.18,31.403 30.996,30.797 30.508,30.537 C23.63,26.869 25.251,23.28 27.304,18.737 C28.185,16.788 29.087,14.789 29.18,12.777 C31.258,14.095 33,16.007 33,18 C33,18.464 33.319,18.867 33.77,18.973 C34.225,19.078 34.687,18.862 34.894,18.447 C36.686,14.863 38.696,10.844 34.298,2.877 C42.521,6.311 46.877,13.37 45.03,20.757 C44.939,21.12 45.058,21.502 45.338,21.75 C45.619,21.997 46.013,22.069 46.361,21.933 C47.843,21.359 49.981,19.289 50.873,15.691 C51.909,17.67 53.019,20.658 52.74,23.266 C52.557,24.984 51.806,26.261 50.445,27.168 C49.986,27.474 49.862,28.095 50.168,28.555 C50.474,29.014 51.095,29.139 51.555,28.832 C53.414,27.593 54.482,25.792 54.729,23.479 C55.22,18.884 52.21,13.517 50.984,12.251 C50.706,11.966 50.286,11.872 49.915,12.011 C49.543,12.151 49.289,12.498 49.268,12.895 C49.125,15.589 48.273,17.412 47.399,18.553 C47.968,10.457 41.994,2.935 32.286,0.042 C31.887,-0.076 31.45,0.066 31.199,0.401 C30.948,0.737 30.933,1.194 31.162,1.545 C35.585,8.348 35.423,12.012 34.231,15.108 C33.022,12.859 30.589,11.087 28.417,10.091 C28.064,9.928 27.649,9.986 27.353,10.237 C27.057,10.488 26.933,10.888 27.035,11.263 C27.581,13.267 26.561,15.524 25.481,17.914 C23.501,22.297 21.037,27.753 29.567,32.302" id="Fill-176"/><path d="M40.628,30.071 C40.116,30.277 39.866,30.858 40.071,31.372 C40.228,31.762 40.603,32 41,32 C41.124,32 41.249,31.977 41.372,31.929 C43.311,31.153 44.407,29.276 44.457,26.645 C44.535,22.484 42.034,17.254 39.406,16.086 C39.04,15.923 38.607,15.996 38.315,16.272 C38.021,16.548 37.922,16.974 38.063,17.351 C39.428,20.989 38.767,23.496 37.408,24.092 C36.305,24.577 34.958,23.705 34.058,21.925 C33.875,21.563 33.488,21.347 33.087,21.379 C32.683,21.412 32.338,21.684 32.214,22.07 C30.967,25.944 30.96,28.375 34.293,31.707 C34.684,32.098 35.316,32.098 35.707,31.707 C36.098,31.316 36.098,30.684 35.707,30.293 C33.672,28.258 33.176,26.851 33.575,24.715 C35.07,26.282 36.857,26.519 38.212,25.923 C39.81,25.222 40.98,23.347 40.809,20.473 C41.764,22.233 42.495,24.578 42.456,26.606 C42.422,28.434 41.807,29.6 40.628,30.071" id="Fill-177"/></g></g></svg>

After

Width:  |  Height:  |  Size: 4.0 KiB

View File

@ -0,0 +1,62 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
height="20"
version="1.2"
viewBox="0 0 20 20"
width="20"
xml:space="preserve"
id="svg3422"
inkscape:version="0.91 r13725"
sodipodi:docname="rain.svg"><metadata
id="metadata3445"><rdf:RDF><cc:Work
rdf:about=""><dc:format>image/svg+xml</dc:format><dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" /><dc:title></dc:title></cc:Work></rdf:RDF></metadata><defs
id="defs3443" /><sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="1855"
inkscape:window-height="1056"
id="namedview3441"
showgrid="false"
fit-margin-top="0"
fit-margin-left="0"
fit-margin-right="0"
fit-margin-bottom="0"
inkscape:zoom="38.291667"
inkscape:cx="8.7725789"
inkscape:cy="12"
inkscape:window-x="65"
inkscape:window-y="24"
inkscape:window-maximized="1"
inkscape:current-layer="svg3422" /><g
id="Layer_1"
transform="translate(-2,-4)"><g
id="g3425"><path
d="m 15,22 c -0.552,0 -1,-0.447 -1,-1 l 0,-6 c 0,-0.553 0.448,-1 1,-1 0.552,0 1,0.447 1,1 l 0,6 c 0,0.553 -0.448,1 -1,1 z"
id="path3427"
inkscape:connector-curvature="0" /></g><g
id="g3429"><path
d="M 9,22 C 8.448,22 8,21.553 8,21 l 0,-6 c 0,-0.553 0.448,-1 1,-1 0.552,0 1,0.447 1,1 l 0,6 c 0,0.553 -0.448,1 -1,1 z"
id="path3431"
inkscape:connector-curvature="0" /></g><g
id="g3433"><path
d="m 12,24 c -0.552,0 -1,-0.447 -1,-1 l 0,-6 c 0,-0.553 0.448,-1 1,-1 0.552,0 1,0.447 1,1 l 0,6 c 0,0.553 -0.448,1 -1,1 z"
id="path3435"
inkscape:connector-curvature="0" /></g><g
id="g3437"><path
d="M 6,18 C 3.794,18 2,16.206 2,14 2,12.139 3.277,10.571 5.001,10.126 5,10.084 5,10.042 5,10 5,6.691 7.691,4 11,4 13.587,4 15.824,5.639 16.65,8.015 19.586,7.771 22,10.128 22,13 c 0,2.241 -1.507,4.223 -3.666,4.819 -0.535,0.146 -1.083,-0.166 -1.23,-0.697 -0.147,-0.532 0.165,-1.083 0.698,-1.23 C 19.096,15.534 20,14.345 20,13 c 0,-1.654 -1.346,-3 -3,-3 -0.242,0 -0.499,0.041 -0.811,0.13 L 15.115,10.436 14.93,9.334 C 14.604,7.402 12.952,6 11,6 8.794,6 7,7.794 7,10 c 0,0.272 0.027,0.545 0.082,0.808 L 7.33,12.01 5.908,11.994 C 4.897,12 4,12.897 4,14 c 0,1.103 0.897,2 2,2 0.552,0 1,0.447 1,1 0,0.553 -0.448,1 -1,1 z"
id="path3439"
inkscape:connector-curvature="0" /></g></g></svg>

After

Width:  |  Height:  |  Size: 2.9 KiB

View File

@ -0,0 +1 @@
<?xml version="1.0" ?><!DOCTYPE svg PUBLIC '-//W3C//DTD SVG 1.1//EN' 'http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd'><svg enable-background="new -0.71 -1.337 141.732 141.732" height="141.732px" id="Livello_1" version="1.1" viewBox="-0.71 -1.337 141.732 141.732" width="141.732px" xml:space="preserve" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink"><g id="Livello_66"><path d="M136.314,53.739L136.314,53.739l-16.896-4.931l12.231-7.688c2.58-1.622,3.465-5.218,1.976-8.024 c-1.486-2.81-4.787-3.771-7.367-2.149l-12.269,7.715l4.541-18.456c0.771-3.137-0.938-6.354-3.813-7.194 c-2.877-0.839-5.838,1.02-6.605,4.154l-7.336,29.803L75.662,62.75l-0.084-0.056H75.57l-0.002-24.781l20.039-21.818 c2.104-2.294,2.104-6.013-0.002-8.307c-2.104-2.294-5.521-2.294-7.627,0L75.57,21.3L75.568,5.875c0-3.244-2.414-5.874-5.396-5.875 c-2.979,0.001-5.395,2.631-5.395,5.875v15.382L52.411,7.788c-2.105-2.294-5.521-2.294-7.63,0s-2.107,6.013,0,8.307L64.78,37.871 V62.8l-0.053-0.104l-0.076,0.05l-25.104-15.78L32.214,17.16c-0.771-3.138-3.729-4.994-6.604-4.154 c-2.879,0.84-4.586,4.061-3.813,7.191l4.541,18.457l-12.269-7.714c-2.582-1.621-5.881-0.655-7.369,2.15 c-1.489,2.81-0.604,6.403,1.975,8.021l12.234,7.69l-16.9,4.936c-2.878,0.842-4.587,4.062-3.812,7.194 c0.771,3.134,3.729,4.993,6.607,4.154l27.318-7.974l19.739,12.41L34.11,81.942l-27.314-7.97c-2.882-0.84-5.837,1.021-6.606,4.153 C-0.584,81.259,1.125,84.479,4,85.317l16.897,4.934L8.663,97.94c-2.58,1.622-3.466,5.215-1.978,8.024s4.791,3.771,7.371,2.147 l12.266-7.713l-4.538,18.456c-0.771,3.134,0.938,6.354,3.813,7.194s5.836-1.021,6.605-4.153l7.334-29.804l25.11-15.787l0.084,0.053 l0.043-0.084l0.002,0.084h0.011l0.002,24.785l-20.04,21.817c-2.104,2.294-2.104,6.014,0,8.307c2.107,2.294,5.521,2.294,7.629,0 l12.41-13.509v15.424c0,3.245,2.416,5.875,5.396,5.875c2.979,0,5.393-2.63,5.393-5.874l0.002-15.382l12.368,13.468 c2.105,2.294,5.521,2.294,7.63,0c2.104-2.294,2.104-6.013,0-8.307l-20-21.775V76.344l0.01,0.018l0.074-0.047l25.104,15.781 l7.334,29.803c0.771,3.138,3.729,4.994,6.605,4.154s4.586-4.06,3.812-7.194l-4.541-18.456l12.269,7.712 c2.58,1.622,5.883,0.66,7.368-2.146c1.49-2.812,0.607-6.402-1.973-8.024l-12.233-7.688l16.896-4.934c0,0,0,0,0.002,0 c2.877-0.839,4.584-4.06,3.812-7.19c-0.771-3.134-3.729-4.993-6.604-4.153l-27.32,7.97L86.453,69.539l19.75-12.417l27.317,7.97 v0.001c2.879,0.839,5.836-1.021,6.605-4.154C140.898,57.8,139.191,54.579,136.314,53.739"/></g><g id="Livello_1_1_"/></svg>

After

Width:  |  Height:  |  Size: 2.4 KiB

View File

@ -0,0 +1,53 @@
<?xml version="1.0" encoding="UTF-8" standalone="no"?>
<svg
xmlns:dc="http://purl.org/dc/elements/1.1/"
xmlns:cc="http://creativecommons.org/ns#"
xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
xmlns:svg="http://www.w3.org/2000/svg"
xmlns="http://www.w3.org/2000/svg"
xmlns:sodipodi="http://sodipodi.sourceforge.net/DTD/sodipodi-0.dtd"
xmlns:inkscape="http://www.inkscape.org/namespaces/inkscape"
height="19"
version="1.2"
viewBox="0 0 20 19"
width="20"
xml:space="preserve"
id="svg3562"
inkscape:version="0.91 r13725"
sodipodi:docname="storm.svg"><metadata
id="metadata3577"><rdf:RDF><cc:Work
rdf:about=""><dc:format>image/svg+xml</dc:format><dc:type
rdf:resource="http://purl.org/dc/dcmitype/StillImage" /><dc:title></dc:title></cc:Work></rdf:RDF></metadata><defs
id="defs3575" /><sodipodi:namedview
pagecolor="#ffffff"
bordercolor="#666666"
borderopacity="1"
objecttolerance="10"
gridtolerance="10"
guidetolerance="10"
inkscape:pageopacity="0"
inkscape:pageshadow="2"
inkscape:window-width="735"
inkscape:window-height="480"
id="namedview3573"
showgrid="false"
fit-margin-top="0"
fit-margin-left="0"
fit-margin-right="0"
fit-margin-bottom="0"
inkscape:zoom="9.8333333"
inkscape:cx="10"
inkscape:cy="11"
inkscape:window-x="65"
inkscape:window-y="24"
inkscape:window-maximized="0"
inkscape:current-layer="svg3562" /><g
id="Layer_1"
transform="translate(-2,-4)"><g
id="g3565"><path
d="m 17,18 c -0.553,0 -1,-0.447 -1,-1 0,-0.553 0.447,-1 1,-1 1.654,0 3,-1.346 3,-3 0,-1.654 -1.346,-3 -3,-3 -0.238,0 -0.496,0.042 -0.813,0.131 L 15.116,10.432 14.93,9.334 C 14.604,7.402 12.951,6 11,6 8.795,6 7,7.794 7,10 c 0,0.274 0.027,0.545 0.082,0.806 l 0.26,1.24 -1.436,-0.052 C 4.896,12 4,12.897 4,14 c 0,1.103 0.896,2 2,2 0.553,0 1,0.447 1,1 0,0.553 -0.447,1 -1,1 C 3.795,18 2,16.206 2,14 2,12.139 3.277,10.571 5.002,10.126 5,10.084 5,10.042 5,10 5,6.691 7.691,4 11,4 13.587,4 15.824,5.638 16.649,8.015 19.574,7.774 22,10.127 22,13 c 0,2.757 -2.243,5 -5,5 z"
id="path3567"
inkscape:connector-curvature="0" /></g><g
id="g3569"><polygon
points="9.639,23 14.139,18.95 11.139,17.5 12.639,14 8.139,18.051 11.139,19.5 "
id="polygon3571" /></g></g></svg>

After

Width:  |  Height:  |  Size: 2.3 KiB

View File

@ -0,0 +1 @@
<?xml version="1.0" ?><!DOCTYPE svg PUBLIC '-//W3C//DTD SVG 1.1//EN' 'http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd'><svg height="64px" id="Layer_1" style="enable-background:new 0 0 44 64;" version="1.1" viewBox="0 0 44 64" width="44px" xml:space="preserve" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink"><g id="Body_7_"><g><path d="M32,0H12C9.791,0,8,1.791,8,4v56c0,2.209,1.791,4,4,4h20c2.209,0,4-1.791,4-4V4 C36,1.791,34.209,0,32,0z" style="fill:#666666;"/></g></g><g id="Tunnel_Visor"><g><path d="M0,8c2.938,0,6,10,6,10h2V6H0V8z M0,26c2.938,0,6,10,6,10h2 V24H0V26z M0,44c2.938,0,6,9.999,6,9.999h2v-12H0V44z M36,6v12h2c0,0,3.063-10,6-10V6H36z M36,36h2c0,0,3.063-10,6-10v-2h-8V36z M36,53.999h2c0,0,3.063-9.999,6-9.999v-2.001h-8V53.999z" style="fill-rule:evenodd;clip-rule:evenodd;fill:#333333;"/></g></g><g id="Green"><g><ellipse cx="22" cy="49.982" rx="6" ry="6.006" style="fill:#88C057;"/></g></g><g id="Yellow_2_"><g><ellipse cx="22" cy="31.982" rx="6" ry="6.006" style="fill:#FFCC66;"/></g></g><g id="Red_2_"><g><ellipse cx="22" cy="13.982" rx="6" ry="6.006" style="fill:#ED7161;"/></g></g><g/><g/><g/><g/><g/><g/><g/><g/><g/><g/><g/><g/><g/><g/><g/></svg>

After

Width:  |  Height:  |  Size: 1.2 KiB

View File

@ -0,0 +1 @@
<?xml version="1.0" ?><!DOCTYPE svg PUBLIC '-//W3C//DTD SVG 1.1//EN' 'http://www.w3.org/Graphics/SVG/1.1/DTD/svg11.dtd'><svg height="60px" id="Layer_1" style="enable-background:new 0 0 64.001 60;" version="1.1" viewBox="0 0 64.001 60" width="64.001px" xml:space="preserve" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink"><g id="Stand_1_"><g><rect height="8" style="fill:#B3B3B3;" width="32" x="16.001" y="44"/></g></g><g id="Leg"><g><path d="M8.001,56c0,2.209,1.791,4,4,4s4-1.791,4-4V6h-8V56z M48.001,6v50c0,2.209,1.79,4,4,4 c2.209,0,4-1.791,4-4V6H48.001z" style="fill:#CCCCCC;"/></g></g><g id="Bar"><g><path d="M60.445,15.999H3.556C1.592,15.999,0,17.609,0,19.596v8.789c0,1.986,1.592,3.597,3.556,3.597h56.89 c1.963,0,3.555-1.61,3.555-3.597v-8.789C64,17.609,62.408,15.999,60.445,15.999z" style="fill:#E6E6E6;"/></g></g><g id="Stripes_1_"><g><path d="M10.001,16l-10,10v2.395c0.005,1.981,1.594,3.587,3.555,3.587 H6.02L22.001,16H10.001z M60.455,16h-2.454L42.02,31.981h12l9.98-9.98v-2.405C64,17.612,62.413,16.006,60.455,16z M34.001,16 l-16,16h12l16-16H34.001z" style="fill-rule:evenodd;clip-rule:evenodd;fill:#FF8833;"/></g></g><g id="Lights"><g><path d="M12.001,0c-3.313,0-6,2.686-6,6c0,3.313,2.687,6,6,6 s6-2.687,6-6C18.001,2.686,15.314,0,12.001,0z M52.001,0c-3.313,0-6,2.686-6,6c0,3.313,2.687,6,6,6s6-2.687,6-6 C58.001,2.686,55.314,0,52.001,0z" style="fill-rule:evenodd;clip-rule:evenodd;fill:#FFCC66;"/></g></g><g/><g/><g/><g/><g/><g/><g/><g/><g/><g/><g/><g/><g/><g/><g/></svg>

After

Width:  |  Height:  |  Size: 1.5 KiB

View File

@ -8,12 +8,6 @@
/* (1) Start session */ /* (1) Start session */
session_start(); session_start();
if( count($_SESSION['USER']) > 0 )
$_SESSION['NAME'] = $_SESSION['USER']['username'];
elseif( count($_SESSION['ADMIN']) > 0 )
$_SESSION['NAME'] = $_SESSION['ADMIN']['username'];
elseif( !isset($_SESSION['NAME']) || strlen($_SESSION['NAME']) == 0 )
$_SESSION['NAME'] = 'guest'.uniqid();
/* (2) Set default Driver for Repos */ /* (2) Set default Driver for Repos */
Repo::setDriver(DatabaseDriver::get()); Repo::setDriver(DatabaseDriver::get());

1
test@release Normal file
View File

@ -0,0 +1 @@
test prod-releaser@1

View File

@ -3,7 +3,7 @@
<head> <head>
<meta charset="UTF-8"> <meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0"> <meta name="viewport" content="width=device-width, initial-scale=0.4">
<meta http-equiv="X-UA-Compatible" content="ie=edge"> <meta http-equiv="X-UA-Compatible" content="ie=edge">
@ -17,6 +17,11 @@
<link rel='stylesheet' type='text/css' href='/css/layout.css'> <link rel='stylesheet' type='text/css' href='/css/layout.css'>
<link rel='stylesheet' type='text/css' href='/css/menu.css'> <link rel='stylesheet' type='text/css' href='/css/menu.css'>
<link rel='stylesheet' type='text/css' href='/css/header.css'> <link rel='stylesheet' type='text/css' href='/css/header.css'>
<link rel='stylesheet' type='text/css' href='/css/container.css'>
<link rel='stylesheet' type='text/css' href='/css/accueil.css'>
<link rel='stylesheet' type='text/css' href='/css/notification-stack.css'>
<link rel='stylesheet' type='text/css' href='/css/login-form.css'>
<link rel='stylesheet' type='text/css' href='/css/signup-form.css'>
<!-- JS dependencies --> <!-- JS dependencies -->
<script type='text/javascript' src='/js/_SERVER.js'></script> <script type='text/javascript' src='/js/_SERVER.js'></script>

64
view/lib/infobox-es6.js Normal file
View File

@ -0,0 +1,64 @@
/* classe InfoBox */
export class InfoBox{
constructor(msgObject){
/* (1) get reference target */
this.target = msgObject;
/* (2) Init useful variables */
this.stack = []; // message stack
this.pending = false; // if currently waiting/showing
}
show(msg, type, timeout=2000){
/* (1) If pending -> add to stack */
if( this.pending )
this.stack.push( {message: msg, type: type, to: timeout} );
/* (2) Else -> display message */
else
this._display(msg, type, timeout);
}
_next(){
/* (1) Init */
this.target.active = false;
/* (2) Get last active message + pop stack */
var buf = this.stack.pop();
/* (3) If no more msg -> exit */
if( buf == null )
return (this.pending = false);
/* (4) Send current message */
this._display(buf.message, buf.type, buf.to);
}
_display(msg, type, timeout=2000){
/* (1) Set pending */
this.pending = true;
/* (2) Set message data */
this.target.message = msg;
this.target.type = type;
this.target.active = true;
/* (3) Timeout to next */
setTimeout(this._next.bind(this), timeout);
}
}

View File

@ -14,6 +14,7 @@ class WSClient{
/* (1) Store the arguments */ /* (1) Store the arguments */
this.server_url = server_url; this.server_url = server_url;
this.channel_uri = channel_uri; this.channel_uri = channel_uri;
this.built_url = this.server_url+'/'+this.channel_uri;
/* (2) Initialise event data */ /* (2) Initialise event data */
this.is_opened = false; // Set to TRUE when connection opened this.is_opened = false; // Set to TRUE when connection opened
@ -21,7 +22,7 @@ class WSClient{
this.handler = []; // On reveice handlers this.handler = []; // On reveice handlers
/* (3) Create the websocket connection */ /* (3) Create the websocket connection */
this.ws = new WebSocket(this.server_url+'/'+channel_uri); this.ws = new WebSocket(this.built_url);
/* (2) Bind events /* (2) Bind events
@ -132,6 +133,10 @@ class WSClient{
return; return;
} }
/* (3) If not for this channel -> exit */
if( msg_event.target.url != this.built_url )
return;
/* (3) Try to JSON parse */ /* (3) Try to JSON parse */
var parsedMsg = null; var parsedMsg = null;
try{ try{

View File

@ -2,10 +2,13 @@
---------------------------------------------------------*/ ---------------------------------------------------------*/
/* (1) NPM libs */ /* (1) NPM libs */
import Vue from 'vue' import Vue from 'vue'
import VueRouter from 'vue-router'
/* (2) Internal libs */ /* (2) Internal libs */
import {API} from './lib/api-es6' import {API} from './lib/api-es6'
import {InfoBox} from './lib/infobox-es6'
import {WSClient,WSClientBuilder} from './lib/ws-client-es6' import {WSClient,WSClientBuilder} from './lib/ws-client-es6'
import routes from './routes'
/* (3) Vues */ /* (3) Vues */
import wrapper_vue from './vue/wrapper.vue' import wrapper_vue from './vue/wrapper.vue'
@ -13,69 +16,50 @@ import wrapper_vue from './vue/wrapper.vue'
/* (2) Initialisation /* (2) Initialisation
---------------------------------------------------------*/ ---------------------------------------------------------*/
/* (1) API */ /* (1) global store init */
window.api = new API("http://ndli1718/api/v/1.0/");
/* (2) wsclient */
window.wsc = new WSClientBuilder("wss://websocket.xdrm.io");
/* (3) global store init */
require('./vue-config'); require('./vue-config');
window.gstore.add('server', window._SERVER); window.gstore.add('server', window._SERVER);
window.infobox = new InfoBox(gstore.data.info);
/* (4) Render view */ /* (2) API */
window.api = new API(gstore.data.is_local ? 'http://ndli1718/api/v/1.0/' : 'https://ndli1718.xdrm.io/api/v/1.0/');
/* (3) wsclient */
window.wsc = new WSClientBuilder(gstore.data.is_local ? 'ws://localhost:9999' : 'wss://websocket.xdrm.io');
/* (4) Init vue router */
Vue.use(VueRouter);
const router = new VueRouter({
mode: 'history',
routes: routes[0]
});
/* (5) Render view */
new Vue({ new Vue({
el: '#main-vue', el: '#main-vue',
render: h => h(wrapper_vue), router,
data: { render: h => h(wrapper_vue)
gstore: window.gstore.data });
}
}) /* (6) Navigate at page load (to update notifications count) */
gstore.data.func.nav(router, null);
/* (3) Set WebSocket channels /* (3) Set WebSocket channels
---------------------------------------------------------*/ ---------------------------------------------------------*/
/* (1) Connection channel */ /* (1) Make router globally available */
window.wsc_connect = window.wsc.channel('connect').listen(function(msg, err){ window._router_ = router;
// {1} Manage error // /* (2) Create/Manage web socket clients */
if( msg == null && err != null ){ require('./websocket');
console.warn(err);
/*TEMP*///return;
/*TEMP*/msg = {error: 0, connected: ['guest123', 'guest456', 'guest789']};
}
// {2} Manage wsclient error // /* (3) Remove global ref to router */
if( msg.connected == null || msg.error == null || msg.error !== 0 ){ delete window._router_;
console.warn('websocket error: '+msg.error);
return;
}
// {3} Manage notification //
window.gstore.data.notif[0].data = window.gstore.data.notif[0].data.concat( msg.connected );
}).send({name: window._SERVER.session.name});
/* (2) Message channel */
window.wsc_chat = window.wsc.channel('chat').listen(function(msg, err){
// {1} Manage error //
if( msg == null && err != null ){
console.warn(err);
/*TEMP*///return;
/*TEMP*/msg = {error: 0, msg: [['guest123', 'message 1'], ['guest456', 'message 2'], ['guest789', 'message 3']]};
}
// {2} Manage wsclient error //
if( msg.msg == null || msg.error == null || msg.error !== 0 ){
console.warn('websocket error: '+msg.error);
return;
}
// {3} Manage notification //
window.gstore.data.notif[1].data = window.gstore.data.notif[1].data.concat( msg.msg );
}).send({name: window._SERVER.session.name});
/* (4) Get geolocation
---------------------------------------------------------*/
navigator.geolocation && navigator.geolocation.watchPosition(function(loc){
gstore.data.loc = [ loc.coords.latitude, loc.coords.longitude ];
}, null, { enableHighAccuracy: true });

19
view/routes.js Normal file
View File

@ -0,0 +1,19 @@
export default { 0: [
{
path: '/dashboard/',
component: require('./vue/container/dashboard.vue').default
}, {
path: '/emergency/',
component: require('./vue/container/emergency.vue').default
}, {
path: '/inbox/',
component: require('./vue/container/inbox.vue').default
}, {
path: '/event/',
component: require('./vue/container/event.vue').default
}, {
path: '*',
redirect: '/dashboard/'
}
]}

View File

@ -3,37 +3,153 @@ import {GlobalStore} from './lib/gstore-es6'
window.gstore = new GlobalStore(); window.gstore = new GlobalStore();
// Header // Header
window.gstore.add('header_title', 'ndli1718'); gstore.add('header_title', 'ndli1718');
window.gstore.add('info', { gstore.add('info', {
active: false, active: false,
type: 'warning', type: 'warning',
message: 'Warning! blabla' message: 'Warning! blabla'
}); });
window.gstore.add('notif', [ gstore.add('notif', {
{ class: 'bell', data: ['guest1224934 connected', 'guest2349329042 connected'] }, emergency: { class: 'emergency', data: [], count: 0 },
{ class: 'message', data: [['guestsdfljd, \"blabla bloblo\"']] }, event: { class: 'event', data: [], count: 0 },
{ class: 'search', data: [] }, inbox: { class: 'message', data: [], count: 0 },
{ class: 'menu', data: [] } dashboard: { class: 'menu', data: [], count: 0 }
]) });
// Menu // Menu
window.gstore.add('menu_item', { gstore.add('menu_item', {
dashboard: { dashboard: {
label: 'Dashboard', label: 'Accueil',
icon: 'dashboard' theme: 'dashboard'
}, profile: { }, emergency: {
label: 'Profil', label: 'Urgences',
icon: 'profile' theme: 'emergency'
}, event: {
label: 'Signalements',
theme: 'event'
}, inbox: { }, inbox: {
label: 'Boîte de réception', label: 'Messagerie',
icon: 'messages' theme: 'inbox'
} }
}); });
window.gstore.add('menu_item_active', 'dashboard');
window.gstore.add('min_menu', true);
gstore.add('URI', document.URL.replace(/^(?:\/\/|[^\/]+)*/, ''));
gstore.add('is_local', document.URL.replace(/^http:\/\/([^\/]+).*$/, '$1') == 'ndli1718');
gstore.add('min_menu', false);
// Proccess current page from url
if( /^\/(\w+)(?:\/?.*)$/.test(gstore.data.URI) ){
var mi_keys = Object.keys( gstore.data.menu_item );
// if current page exists
if( !!~mi_keys.indexOf(RegExp.$1) ) gstore.add('menu_item_active', RegExp.$1);
else gstore.add('menu_item_active', 'dashboard');
}else
gstore.add('menu_item_active', 'dashboard');
// Functions // Functions
window.gstore.add('func', { gstore.add('func', {
toggleMenuSize: function(){ window.gstore.data.min_menu=!window.gstore.data.min_menu; } nav: function(router, uri){
// {1} Update view (vue-router) //
if( typeof uri == 'string' )
router.push('/'+uri);
// {2} if no @uri -> Extract route from @router //
else if( /^\/([^\/]+).*$/.test( router.app.$route.path ) )
uri = RegExp.$1;
// {3} If no @uri -> exit //
else
return;
// {4} Activate current menu_item //
gstore.data.menu_item_active = uri;
// {5} Manage notifications //
for( var id in gstore.data.notif )
if( id == uri ) // if notif links to current page
gstore.data.notif[id].count = 0;
},
toggleMenuSize: function(){ gstore.data.min_menu=!gstore.data.min_menu; },
bbcode: function(msg){
/* (1) Escape HTML
---------------------------------------------------------*/
msg = msg.replace(/&/g, '&amp;');
msg = msg.replace(/</g, '&lt;');
msg = msg.replace(/>/g, '&gt;');
/* (2) Manage text format
---------------------------------------------------------*/
/* (1) Manage bold */
msg = msg.replace(/\*([^\*]+)\*/g, "<b>$1</b>");
/* (2) italic */
msg = msg.replace(/_([^_]+)_/g, "<i>$1</i>");
/* (3) underline */
msg = msg.replace(/\[([^\]]+)\]/g, "<ins>$1</ins>");
/* (4) Code */
msg = msg.replace(/`([^`]+)`/g, "<span class='code'>$1</span>");
/* (3) Manage emojis
---------------------------------------------------------*/
/* (1) Smileys */
msg = msg.replace(/:D/g, "<span class='utf8'>😃</span>");
msg = msg.replace(/:\)/g, "<span class='utf8'>🙂</span>");
msg = msg.replace(/:B/g, "<span class='utf8'>😎</span>");
msg = msg.replace(/:3/g, "<span class='utf8'>😗</span>");
msg = msg.replace(/;\)/g, "<span class='utf8'>😉</span>");
msg = msg.replace(/:P/g, "<span class='utf8'>😋</span>");
msg = msg.replace(/;P/g, "<span class='utf8'>😜</span>");
msg = msg.replace(/xD/g, "<span class='utf8'>😆</span>");
msg = msg.replace(/:O/ig, "<span class='utf8'>😲</span>");
msg = msg.replace(/:S/g, "<span class='utf8'>😖</span>");
msg = msg.replace(/\^\^/g, "<span class='utf8'>😊</span>");
/* (2) Emojis */
msg = msg.replace(/:poop:/g, "<span class='utf8 br'>💩</span>");
msg = msg.replace(/:fuck:/g, "<span class='utf8'>🖕</span>");
msg = msg.replace(/\+1/g, "<span class='utf8 bl'>👍</span>");
msg = msg.replace(/-1/g, "<span class='utf8 bl'>👎</span>");
return msg;
}
}); });
// new-message container
gstore.add('new_msg', {
inbox: '',
emergency: '',
event: ''
});
// edit-message container
gstore.add('upd_msg', {
inbox: null,
emergency: null,
event: null
});
// if message loader
gstore.add('msg_pending', {
inbox: true,
emergency: true,
event: true
}); // true when message send pending
// notification stack visibility
gstore.add('nstack', false);
// location
gstore.add('loc', [0, 0]);
// login form authentication visibility
gstore.add('loginform', false);
// sign up form visibility
gstore.add('signupform', false);

View File

@ -0,0 +1,54 @@
<template>
<div id='CONTAINER' class='accueil'>
<h1>{{ nom_app.toUpperCase() }}</h1>
<h2>Ayez les bons réflexes !</h2>
<p>Parce que chaque seconde gagnée est précieuse pour augmenter la chance de survie de la personne accidentée,
voici les principaux numéros d'urgences ouvert 24/7 : </p>
<table>
<tbody>
<tr>
<td><a href="tel:15">15<div class='phone'></div></a></td>
<td><a href="tel:17">17<div class='phone'></div></a></td>
<td><a href="tel:18">18<div class='phone'></div></a></td>
<td><a href="tel:112">112<div class='phone'></div></a></td>
</tr>
<tr>
<td>SAMU</td>
<td>Police</td>
<td>Pompier</td>
<td>Urgence<br>européenne</td>
</tr>
</tbody>
</table>
<h2>Le concept</h2>
<div>
<p>{{ nom_app }} est la toute dernière application de prévention routière. C'est également une manière simple
d'échanger sur le traffic, et de prévenir l'accident. Parmi les 3 centre de discussion, vous retrouverez
les icônes suivants : </p>
<ul>
<li><div><img class='icon-type' src="/public_html/image/type/rain.svg"/></div> : forte pluie</li>
<li><div><img class='icon-type' src="/public_html/image/type/snow.svg"/></div> : neige ou verglas</li>
<li><div><img class='icon-type' src="/public_html/image/type/storm.svg"/></div> : tempête ou orage</li>
<li><div><img class='icon-type' src="/public_html/image/type/accident.svg"/></div> : accident de voiture</li>
<li><div><img class='icon-type' src="/public_html/image/type/traffic.svg"/></div> : ralentissements</li>
<li><div><img class='icon-type' src="/public_html/image/type/work.svg"/></div> : travaux sur la route</li>
</ul>
</div>
</div>
</template>
<script>
export default {
name: 'CONTAINER_ACCUEIL',
data(){
return {
gstore: gstore.data,
nom_app: 'Ndli1718'
};
}
}
</script>

View File

@ -0,0 +1,147 @@
<template>
<div id='CONTAINER' class='message'>
<div v-for='(msg, id) in gstore.notif.emergency.data' :class="msg.user == gstore.server.session.name ? 'me' : ''" :data-noauthor='id == 0 || gstore.notif.emergency.data[id-1].user != msg.user ? "1" : "0"'>
<span class='author' v-text='msg.user' v-if='id == 0 || gstore.notif.emergency.data[id-1].user != msg.user'></span>
<span class='content' v-html='bbcode(msg.message)'></span>
<span class='date' v-text='local_date(id)'></span>
<span @click='del_message(msg.id)' class='del' v-if='msg.user == gstore.server.session.name'></span>
<span @click='upd_message(msg.id, msg.message)' class='upd' v-if='msg.user == gstore.server.session.name'></span>
<span @click='maps(msg.location)' class='maps' v-if='msg.user != gstore.server.session.name && msg.location[0] != 0 && msg.location[1] != 0'></span>
</div>
<div class='end-pad'></div> <!-- End Spacing -->
<form class='msg-input' @submit.prevent='new_message(gstore.new_msg.emergency)'>
<input type='text' placeholder='Nouveau message..' id='msg-new-content' v-model='gstore.new_msg.emergency' :class='gstore.msg_pending.emergency ? "loading" : ""'>
<button></button>
</form>
</div>
</template>
<script>
export default {
name: 'CONTAINER_EMERGENCY',
data(){ return {
gstore: gstore.data,
dep: "31"
}; },
methods: {
maps(coord){
window.open('https://www.google.com/maps/?q=-'+coord[0]+','+coord[1]);
},
local_date: function(id){
/* (1) Get current date (convert unix timestamp to javascript timestamp */
var cur = new Date( gstore.data.notif.emergency.data[id].timestamp * 1000);
/* (2) First line -> show whole date */
if( id < 1 )
return cur.toLocaleString();
/* (3) Get previous date */
var pre = new Date( gstore.data.notif.emergency.data[id-1].timestamp );
/* (2) If same day -> show time only */
if( cur.toLocaleDateString() == pre.toLocaleDateString() )
return cur.toLocaleTimeString();
return cur.toLocaleString();
},
new_message(msg){
/* (1) If empty message -> abort */
if( msg.trim().length == 0 )
return;
/* (1) If in EDIT_MODE
---------------------------------------------------------*/
if( gstore.data.upd_msg.emergency != null ){
/* (2) Prepare request */
var rq = {
id: this.gstore.upd_msg.emergency,
message: msg
};
/* (3) Add loader */
gstore.data.msg_pending.emergency = true;
/* (4) Send request */
api.call("PUT message/emergency/"+this.dep, rq, function(rs){
// {1} If error -> exit //
if( rs.error != 0 )
return;
// {2} Update message content //
for( var id in gstore.data.notif.emergency.data )
if( gstore.data.notif.emergency.data[id].id == gstore.data.upd_msg.emergency )
gstore.data.notif.emergency.data[id].message = msg;
// {3} exit EDIT_MODE //
gstore.data.upd_msg.emergency = null;
// {4} Empty input //
gstore.data.new_msg.emergency = '';
});
/* (2) If IN NEW_MSG_MODE
---------------------------------------------------------*/
}else{
/* (2) Prepare request */
var rq = {
message: this.gstore.new_msg.emergency,
location: this.gstore.loc,
username: this.gstore.server.session.name
};
/* (3) Add loader */
gstore.data.msg_pending.emergency = true;
/* (4) Send request */
api.call("POST message/emergency/"+this.dep, rq, function(rs){
// {1} If error -> exit //
if( rs.error != 0 )
return;
// {2} Empty input //
gstore.data.new_msg.emergency = '';
});
}
},
del_message(id_msg){
api.call("DELETE message/emergency/"+this.dep, { id: id_msg }, function(rs){});
},
upd_message(id_msg, msg_content){
/* (1) Move to 'edit_mode' */
this.gstore.upd_msg.emergency = id_msg;
/* (2) Copy message content to INPUT */
this.gstore.new_msg.emergency = msg_content;
},
bbcode: function(msg){
return this.gstore.func.bbcode(msg);
}
}
}
</script>

View File

@ -0,0 +1,80 @@
<template>
<div id='CONTAINER' class='message'>
<div v-for='(msg, id) in gstore.notif.event.data' :class="msg[0] == gstore.server.session.name ? 'me' : ''" :data-noauthor='id == 0 || gstore.notif.event.data[id-1][0] != gstore.notif.event.data[id][0] ? "1" : "0"'>
<span class='author' v-text='msg[0]' v-if='id == 0 || gstore.notif.event.data[id-1][0] != msg[0]'></span>
<span class='content' v-html='bbcode(msg[1])'></span>
<span class='date' v-text='local_date(id)'></span>
</div>
<div class='end-pad'></div> <!-- End Spacing -->
<form class='msg-input' @submit.prevent='new_message(gstore.new_msg.event)'>
<input type='text' placeholder='Nouveau message..' id='msg-new-content' v-model='gstore.new_msg.event' :class='gstore.msg_pending.event ? "loading" : ""'>
<button></button>
</form>
</div>
</template>
<script>
export default {
name: 'CONTAINER_EVENT',
data(){ return { gstore: gstore.data }; },
methods: {
local_date: function(id){
/* (1) Get current date */
var cur = new Date( gstore.data.notif.event.data[id].timestamp * 1000 );
/* (2) First line -> show whole date */
if( id < 1 )
return cur.toLocaleString();
/* (3) Get previous date */
var pre = new Date( gstore.data.notif.event.data[id-1].timestamp );
/* (2) If same day -> show time only */
if( cur.toLocaleDateString() == pre.toLocaleDateString() )
return cur.toLocaleTimeString();
return cur.toLocaleString();
},
new_message(msg){
/* (1) If empty message -> abort */
if( msg.trim().length == 0 )
return;
/* (2) Prepare request */
var rq = {
message: this.gstore.new_msg.event,
location: this.gstore.loc,
username: this.gstore.server.session.name
};
/* (3) Add loader */
gstore.data.msg_pending.event = true;
/* (4) Send request */
api.call("POST message/event/"+this.dep, rq, function(rs){
// {1} If error -> exit //
if( rs.error != 0 )
return;
// {2} Empty input //
gstore.data.new_msg.event = '';
});
},
bbcode: function(msg){
return this.gstore.func.bbcode(msg);
}
}
}
</script>

View File

@ -0,0 +1,49 @@
<template>
<div id='CONTAINER' class='message'>
<div v-for='(msg, id) in gstore.notif.inbox.data' :class="msg[0] == gstore.server.session.name ? 'me' : ''" :data-noauthor='id == 0 || gstore.notif.inbox.data[id-1][0] != gstore.notif.inbox.data[id][0] ? "1" : "0"'>
<span class='author' v-text='msg[0]' v-if='id == 0 || gstore.notif.inbox.data[id-1][0] != msg[0]'></span>
<span class='content' v-html='bbcode(msg[1])'></span>
</div>
<div class='end-pad'></div> <!-- End Spacing -->
<form class='msg-input' @submit.prevent='new_message(gstore.new_msg.inbox)'>
<input type='text' placeholder='Nouveau message..' id='msg-new-content' v-model='gstore.new_msg.inbox' :class='gstore.msg_pending.inbox ? "loading" : ""'>
<button></button>
</form>
</div>
</template>
<script>
export default {
name: 'CONTAINER_INBOX',
data(){ return { gstore: gstore.data }; },
methods: {
new_message(msg){
/* (1) If empty message -> abort */
if( msg.trim().length == 0 )
return;
/* (2) Send message to WebSocket */
wsc_chat.send(JSON.stringify({message: msg}));
/* (3) Add loader */
gstore.data.msg_pending.inbox = true;
/* (4) Empty input */
this.gstore.new_msg.inbox = '';
},
bbcode: function(msg){
return this.gstore.func.bbcode(msg);
}
}
}
</script>

View File

@ -1,9 +1,9 @@
<template> <template>
<div id='HEADER' @click='gstore.func.toggleMenuSize'> <div id='HEADER'>
<!-- Header Icon+Title --> <!-- Header Icon+Title -->
<div id='header-icon'> <div id='header-icon' @click='gstore.func.toggleMenuSize'>
<div class='header-title'>{{ gstore.header_title }}</div> <div class='header-title'>{{ gstore.header_title }}</div>
</div> </div>
@ -12,7 +12,9 @@
<!-- Header Notif --> <!-- Header Notif -->
<div id='header-notif'> <div id='header-notif'>
<div v-for='notif in gstore.notif' :class='"hnotif " + notif.class' :data-count='notif.data.length'></div> <div v-for='(notif, link) in gstore.notif' @click='show_notif(link)' :class='"hnotif " + notif.class' :data-count='notif.count'></div>
<div v-if='!is_connected' @click='show_login()' class='hnotif login'></div>
<div v-if='is_connected' @click='logout()' class='hnotif logout'></div>
</div> </div>
</div> </div>
@ -23,10 +25,24 @@
<script> <script>
export default { export default {
name: 'HEADER', name: 'HEADER',
data(){ return { gstore: window.gstore.data }; }, data(){
return {
gstore: gstore.data,
is_connected: _SERVER.session.connected
};
},
methods: { methods: {
show_notif(){ show_notif(uri){
this.gstore.func.nav(this.$router, uri);
},
show_login() {
this.gstore.signupform = false;
this.gstore.loginform = !this.gstore.loginform;
},
logout() {
api.call('DELETE user/logout', null, function() {
document.location = '';
});
} }
} }
} }

66
view/vue/login-form.vue Normal file
View File

@ -0,0 +1,66 @@
<template>
<div id='LOGIN-FORM' :class='gstore.loginform ? "active" : ""'>
<!-- Header -->
<div class='head'>
<span>Connexion au compte</span>
<i></i>
</div>
<!-- Body -->
<div class='body'>
<form @submit.prevent='authentification'>
<label for='username'>Nom d'utilisateur</label>
<input :class='err_connection ? "err" : ""' v-model='username_val' type='text' id='username'>
<label for='password'>Mot de passe</label>
<input :class='err_connection ? "err" : ""' v-model='password_val' type='password' id='password'>
<p v-if='err_connection' id='msg-err'>Identifiant ou mot de passe incorrect</p>
<div>
<button id='btn-connection'>Se connecter</button>
<span>ou</span>
<button @click='signup' id='btn-signup'>S'inscrire</button>
</div>
</form>
</div>
</div>
</template>
<script>
export default {
name: 'LOGIN_FORM',
data(){
return {
gstore: gstore.data,
username_val: '',
password_val: '',
err_connection: false
};
},
methods: {
authentification() {
let request = {
username: this.username_val,
password: this.password_val
};
api.call("POST user/login", request, function (response) {
/* (1) Check if is there an error and display theme that goes with */
if (response.error != 0 || !response.connected) {
this.err_connection = true;
}
/* (2) Close the login form authentication */
else {
document.location = '';
}
}.bind(this));
},
signup(evt) {
evt.preventDefault();
this.gstore.signupform = true;
}
}
}
</script>

View File

@ -4,8 +4,8 @@
<div v-for='(item, index) in gstore.menu_item' class='menu-item-wrapper'> <div v-for='(item, index) in gstore.menu_item' class='menu-item-wrapper'>
<div :class="(index == gstore.menu_item_active) ? 'menu-item active' : 'menu-item'" @click='navigate_menu(index)' :style='"background-image: url(/image/menu/" + item.icon + ".svg@333333"'> <div :class="(index == gstore.menu_item_active) ? 'menu-item active' : 'menu-item'" @click='navigate(index)' :data-theme='item.theme'>
<span v-show='!gstore.min_menu'>{{ item.label }}</span> <span>{{ item.label }}</span>
</div> </div>
</div> </div>
@ -18,16 +18,10 @@
<script> <script>
export default { export default {
name: 'MENU', name: 'MENU',
data(){ return { gstore: window.gstore.data }; }, data(){ return { gstore: gstore.data }; },
methods: { methods: {
navigate_menu(page){ navigate(uri){
this.gstore.func.nav(this.$router, uri);
// (1) Manage action
console.log('Loading page \''+page+'\'');
// (2) Activate current element
this.gstore.menu_item_active = page;
} }
} }
} }

View File

@ -0,0 +1,24 @@
<template>
<div id='NOTIF-STACK' :class='gstore.nstack ? "active" : ""'>
<!-- Header -->
<div class='head'>Notifications</div>
<!-- Body -->
<div class='body'>
<span v-for='n in gstore.notif.emergency.data'><b>{{ n }}</b> est connecté</span>
</div>
</div>
</template>
<script>
export default {
name: 'NOTIFICATION_STACK',
data(){ return { gstore: gstore.data }; },
methods: {}
}
</script>

104
view/vue/signup-form.vue Normal file
View File

@ -0,0 +1,104 @@
<template>
<div id='SIGNUP-FORM' :class='gstore.signupform ? "active" : ""'>
<!-- Header -->
<div class='head'>
<span>Création d'un compte</span>
<i></i>
</div>
<!-- Body -->
<div class='body'>
<form @submit.prevent='create_account'>
<label for='username'>Nom d'utilisateur</label>
<input :class='err_username ? "err" : ""' v-model='username_val' type='text' id='username'>
<label for='mail'>Adresse mail</label>
<input :class='err_mail ? "err" : ""' v-model='mail_val' type='email' id='mail'>
<label for='password'>Mot de passe</label>
<input v-model='password_val' type='password' id='password'>
<p v-if='err_username || err_mail || err_unknow' id='msg-err'>{{ err_message }}</p>
<button id='btn-create-account'>Créer mon compte</button>
<p @click='redirect_login' id='membre'>Déjà membre ? Connectez-vous !</p>
</form>
</div>
</div>
</template>
<script>
export default {
name: 'SIGNUP_FORM',
data(){
return {
gstore: gstore.data,
username_val: '',
mail_val: '',
password_val: '',
err_username: false,
err_mail: false,
err_unknow: false,
err_message: ''
};
},
methods: {
create_account() {
const const_username = this.username_val;
const const_mail = this.mail_val;
const const_password = this.password_val;
let request = {
username: const_username,
mail: const_mail,
password: const_password
};
api.call("POST user/signup", request, function (response) {
/* (1) Check if is there an error and display theme that goes with */
if (response.error == 17 && response.ErrorDescription.indexOf('mail') !== -1) {
this.err_username = false;
this.err_mail = true;
this.err_unknow = false;
this.err_message = 'Le mail est invalide';
}
else if (response.error == 17 && response.ErrorDescription.indexOf('username') !== -1) {
this.err_username = true;
this.err_mail = false;
this.err_unknow = false;
this.err_message = 'Le nom d\'utilisateur a des caractères invalides';
}
else if (response.error == 29) {
this.err_username = true;
this.err_mail = true;
this.err_unknow = false;
this.err_message = 'Le nom d\'utilisateur ou le mail est déjà pris';
}
else if (!response.registered) {
this.err_username = false;
this.err_mail = false;
this.err_unknow = true;
this.err_message = 'Impossible de créer le compte pour le moment, veuillez réessayer plus tard';
}
/* (2) Close the sign up form authentication */
else {
infobox._display('Inscription terminée ! Connexion en cours ...', 'info', 3000);
let request = {
username: const_username,
password: const_password
};
api.call("POST user/login", request, function (response) {
document.location = '';
});
}
}.bind(this));
},
redirect_login() {
this.gstore.signupform = false;
this.gstore.loginform = true;
}
}
}
</script>

View File

@ -7,30 +7,41 @@
<!-- Menu --> <!-- Menu -->
<menu-comp></menu-comp> <menu-comp></menu-comp>
<span>message: {{ msg }}</span> <!-- Container -->
<router-view></router-view>
<!-- Notification Stack -->
<notifstack-comp></notifstack-comp>
<!-- Login form -->
<loginform-comp></loginform-comp>
<!--Sign pu form-->
<signupform-comp></signupform-comp>
</div> </div>
</template> </template>
<script> <script>
import header_vue from './header.vue'; import header_vue from './header.vue'
import menu_vue from './menu.vue'; import menu_vue from './menu.vue'
import notifstack_vue from './notification-stack.vue'
import loginform_vue from './login-form.vue'
import signupform_vue from './signup-form.vue';
export default {
export default { name: 'wrapper',
name: 'wrapper', data(){ return { gstore: gstore.data }; },
data(){ return { components: {
msg: 'Main vue component', 'HeaderComp': header_vue,
gstore: window.gstore.data 'MenuComp': menu_vue,
}; }, 'NotifstackComp': notifstack_vue,
components: { 'LoginformComp': loginform_vue,
'HeaderComp': header_vue, 'SignupformComp': signupform_vue
'MenuComp': menu_vue }
} }
}
</script> </script>

165
view/websocket.js Normal file
View File

@ -0,0 +1,165 @@
// make router usable as it
const router = window._router_;
/* (1) Emergency channel
---------------------------------------------------------*/
window.wsc_emergency = wsc.channel('emergency/31').listen(function(msg, err){
/* (1) Manage error */
if( msg == null && err != null )
return infobox.show('Erreur de connexion WebSocket@emergency ('+err+')', 'error', 3000);
/* (2) Manage wsclient error */
if( typeof msg.error != 'boolean' || msg.error !== false )
return infobox.show('Erreur de connexion WebSocket@emergency', 'warning', 3000);
/* (3) If message(s) to add */
if( msg.add != null ){
// {1} Play sound if 1msg received + not already on page //
// note: 1msg means a new message but not the page load past buffer
if( msg.add.length == 1 && router.app.$route.path != '/emergency' )
( new Audio('https://notificationsounds.com/message-tones/communication-channel-519/download/mp3') ).play();
// {2} Add messages to stack //
for( var id in msg.add ){
var tmp = msg.add[id]; // add id to data
tmp.id = id;
gstore.data.notif.emergency.data.push(tmp);
}
// {3} Add notification count if not already on page //
if( router.app.$route.path != '/emergency' )
gstore.data.notif.emergency.count += Object.keys(msg.add).length;
}
/* (4) If message(s) to del */
if( msg.del != null ){
// {1} Rem messages from stack //
for( var id in gstore.data.notif.emergency.data )
if( msg.del[ gstore.data.notif.emergency.data[id].id ] != null )
gstore.data.notif.emergency.data[id].message = 'L\'auteur n\'a pas assumé ce message.. Honte à lui !';
}
/* (5) If message(s) to update */
if( msg.upd != null ){
// {1} Update messages in stack //
for( var id in gstore.data.notif.emergency.data )
if( msg.upd[ gstore.data.notif.emergency.data[id].id ] != null )
gstore.data.notif.emergency.data[id].message = msg.upd[ gstore.data.notif.emergency.data[id].id ].message;
}
/* (6) Remove loader */
gstore.data.msg_pending.emergency = false;
}).send({name: _SERVER.session.name});
/* (2) Event channel
---------------------------------------------------------*/
window.wsc_event = wsc.channel('event/31').listen(function(msg, err){
/* (1) Manage error */
if( msg == null && err != null )
return infobox.show('Erreur de connexion WebSocket@event ('+err+')', 'error', 3000);
/* (2) Manage wsclient error */
if( typeof msg.error != 'boolean' || msg.error !== false )
return infobox.show('Erreur de connexion WebSocket@event', 'warning', 3000);
/* (3) If message(s) to add */
if( msg.add != null ){
// {1} Play sound if 1msg received + not already on page //
// note: 1msg means a new message but not the page load past buffer
if( msg.add.length == 1 && router.app.$route.path != '/event' )
( new Audio('https://notificationsounds.com/message-tones/communication-channel-519/download/mp3') ).play();
// {2} Add messages to stack //
for( var id in msg.add ){
var tmp = msg.add[id]; // add id to data
tmp.id = id;
gstore.data.notif.event.data.push(tmp);
}
// {3} Add notification count if not already on page //
if( router.app.$route.path != '/event' )
gstore.data.notif.event.count += Object.keys(msg.add).length;
}
/* (4) If message(s) to del */
if( msg.del != null ){
// {1} Rem messages from stack //
for( var id in gstore.data.notif.event.data )
if( msg.del[ gstore.data.notif.event.data[id].id ] != null )
gstore.data.notif.event.data[id].message = 'L\'auteur n\'a pas assumé ce message.. Honte à lui !';
}
/* (5) If message(s) to update */
if( msg.upd != null ){
// {1} Update messages in stack //
for( var id in gstore.data.notif.event.data )
if( msg.upd[ gstore.data.notif.event.data[id].id ] != null )
gstore.data.notif.event.data[id].message = msg.upd[ gstore.data.notif.event.data[id].id ].message;
}
/* (6) Remove loader */
gstore.data.msg_pending.event = false;
}).send({name: _SERVER.session.name});
/* (3) Message channel
---------------------------------------------------------*/
window.wsc_chat = wsc.channel('chat').listen(function(msg, err){
/* (1) Manage error */
if( msg == null && err != null )
return infobox.show('Erreur de connexion WebSocket@chat ('+err+')', 'error', 3000);
/* (2) Manage wsclient error */
if( typeof msg.error != 'boolean' || msg.error !== false )
return infobox.show('Erreur de connexion WebSocket@chat', 'warning', 3000);
/* (3) If no message -> exit */
if( msg.msg == null )
return;
/* (4) Play sound if 1msg received + not already on page */
// note: 1msg means a new message but not the page load past buffer
if( msg.msg.length == 1 && router.app.$route.path != '/inbox' )
( new Audio('https://notificationsounds.com/message-tones/communication-channel-519/download/mp3') ).play();
/* (5) Add messages to stack */
gstore.data.notif.inbox.data = gstore.data.notif.inbox.data.concat( msg.msg );
/* (6) Add notification count if not already on page */
if( router.app.$route.path != '/inbox' )
gstore.data.notif.inbox.count += msg.msg.length;
/* (7) Remove loader */
gstore.data.msg_pending.inbox = false;
}).send({name: _SERVER.session.name});