Commit 67fbbbe2088f5137b15e396b7defe60e8cb121ac
Exists in
master
and in
8 other branches
Merge branch 'refact-home'
Showing
169 changed files
with
4690 additions
and
1213 deletions
Show diff stats
Too many changes.
To preserve performance only 100 of 169 files displayed.
bower.json
... | ... | @@ -11,7 +11,10 @@ |
11 | 11 | "bootstrap-sass-official": "~3.3.4", |
12 | 12 | "animate.css": "~3.3.0", |
13 | 13 | "angular": "~1.4.0", |
14 | - "modernizr": "~2.8.3" | |
14 | + "modernizr": "~2.8.3", | |
15 | + "angular-slugify": "~1.0.1", | |
16 | + "open-sans-fontface": "~1.4.2", | |
17 | + "angular-social-links": "~0.0.19" | |
15 | 18 | }, |
16 | 19 | "devDependencies": { |
17 | 20 | "angular-mocks": "~1.4.0" | ... | ... |
... | ... | @@ -0,0 +1,738 @@ |
1 | +/** | |
2 | + * Use https://github.com/typicode/json-server for fake endpoint server. | |
3 | + * Example: $ json-server data.js -p 9000 -w data.js | |
4 | + */ | |
5 | +module.exports = function () { | |
6 | + 'use strict'; | |
7 | + var data = {}; | |
8 | + | |
9 | + // add /api/v1/articles path | |
10 | + // data.api = {}; | |
11 | + // data.api.v1 = {}; | |
12 | + // data.api.v1.articles = []; | |
13 | + | |
14 | + // add data to articles path | |
15 | + // data.api.v1.articles.push({ | |
16 | + data.articles = []; | |
17 | + | |
18 | + // json get from hom on 26/08/2015 | |
19 | + var articleHome = { | |
20 | + id: 103358, | |
21 | + "article":{ | |
22 | + "id": 103358, | |
23 | + "abstract": "<p style=\"text-align: center;\"><iframe src=\"https://www.youtube.com/embed/kpAdrO-emV0?rel=0&showinfo=0&iv_load_policy=3&controls=1\" style=\"max-width: 1000px; left: 5%;\" width=\"275\" height=\"200\"></iframe></p>", | |
24 | + | |
25 | + "title": "Dialoga Brasil", | |
26 | + "categories": [ | |
27 | + { | |
28 | + "name": "Saúde", | |
29 | + "id": 180, | |
30 | + "slug": "saude", | |
31 | + "image": null | |
32 | + }, | |
33 | + { | |
34 | + "name": "Segurança Pública", | |
35 | + "id": 182, | |
36 | + "slug": "seguranca-publica", | |
37 | + "image": null | |
38 | + }, | |
39 | + { | |
40 | + "name": "Educação", | |
41 | + "id": 181, | |
42 | + "slug": "educacao", | |
43 | + "image": null | |
44 | + }, | |
45 | + { | |
46 | + "name": "Redução da Pobreza", | |
47 | + "id": 183, | |
48 | + "slug": "reducao-da-pobreza", | |
49 | + "image": null | |
50 | + }, | |
51 | + { | |
52 | + "name": "Cultura", | |
53 | + "id": 194, | |
54 | + "slug": "cultura", | |
55 | + "image": null | |
56 | + } | |
57 | + ], | |
58 | + "image": null, | |
59 | + "setting": { | |
60 | + "custom_body_label": "Corpo", | |
61 | + "phase": "proposals", | |
62 | + "allow_topics": true, | |
63 | + "moderate_comments": false, | |
64 | + "comment_paragraph_plugin_activate": false, | |
65 | + "author_name": "Leandro Nunes dos Santos", | |
66 | + "moderate_proposals": true, | |
67 | + "allow_members_to_edit": false | |
68 | + }, | |
69 | + "position": null, | |
70 | + "children": [ | |
71 | + { | |
72 | + "id": 103390, | |
73 | + "abstract": "<p>Prevenção, tratamento e enfrentamento ao tráfico.</p>", | |
74 | + "title": "Crack, é possível vencer!", | |
75 | + "categories": [ | |
76 | + { | |
77 | + "name": "Segurança Pública", | |
78 | + "id": 182, | |
79 | + "slug": "seguranca-publica", | |
80 | + "image": null | |
81 | + } | |
82 | + ], | |
83 | + "image": { | |
84 | + "url": "/image_uploads/dialoga/0000/0104/crack.jpg" | |
85 | + }, | |
86 | + "setting": { | |
87 | + "color": "#00ff00", | |
88 | + "moderate_comments": false, | |
89 | + "comment_paragraph_plugin_activate": false, | |
90 | + "author_name": "Ronald Emerson Scherolt da Costa", | |
91 | + "allow_members_to_edit": false | |
92 | + }, | |
93 | + "position": 14 | |
94 | + }, | |
95 | + { | |
96 | + "id": 103521, | |
97 | + "abstract": "<p>Mais atendimento nos municípios, mais saúde para quem mais precisa.</p>", | |
98 | + "title": "Mais Médicos", | |
99 | + "categories": [ | |
100 | + { | |
101 | + "name": "Saúde", | |
102 | + "id": 180, | |
103 | + "slug": "saude", | |
104 | + "image": null | |
105 | + } | |
106 | + ], | |
107 | + "image": { | |
108 | + "url": "/image_uploads/dialoga/0000/0025/Mais_M_dicos.jpg" | |
109 | + }, | |
110 | + "setting": { | |
111 | + "color": "#ffe599", | |
112 | + "moderate_comments": false, | |
113 | + "comment_paragraph_plugin_activate": false, | |
114 | + "author_name": "Ronald Emerson Scherolt da Costa", | |
115 | + "allow_members_to_edit": false | |
116 | + }, | |
117 | + "position": 1 | |
118 | + }, | |
119 | + { | |
120 | + "id": 103457, | |
121 | + "abstract": "<p>Ação conjunta e cooperação transfronteiriça.</p>", | |
122 | + "title": "Proteção das Fronteiras", | |
123 | + "categories": [ | |
124 | + { | |
125 | + "name": "Segurança Pública", | |
126 | + "id": 182, | |
127 | + "slug": "seguranca-publica", | |
128 | + "image": null | |
129 | + } | |
130 | + ], | |
131 | + "image": { | |
132 | + "url": "/image_uploads/dialoga/0000/0110/fronteira_redim.jpg" | |
133 | + }, | |
134 | + "setting": { | |
135 | + "color": "#a64d79", | |
136 | + "moderate_comments": false, | |
137 | + "comment_paragraph_plugin_activate": false, | |
138 | + "author_name": "Ronald Emerson Scherolt da Costa", | |
139 | + "allow_members_to_edit": false | |
140 | + }, | |
141 | + "position": 15 | |
142 | + }, | |
143 | + { | |
144 | + "id": 103612, | |
145 | + "abstract": "<p>Garantir água para beber e produzir.</p>", | |
146 | + "title": "Cisternas", | |
147 | + "categories": [ | |
148 | + { | |
149 | + "name": "Redução da Pobreza", | |
150 | + "id": 183, | |
151 | + "slug": "reducao-da-pobreza", | |
152 | + "image": null | |
153 | + } | |
154 | + ], | |
155 | + "image": { | |
156 | + "url": "/image_uploads/dialoga/0000/0039/cisterna_redim.jpg" | |
157 | + }, | |
158 | + "setting": { | |
159 | + "color": "#0000ff", | |
160 | + "moderate_comments": false, | |
161 | + "comment_paragraph_plugin_activate": false, | |
162 | + "author_name": "Ronald Emerson Scherolt da Costa", | |
163 | + "allow_members_to_edit": false | |
164 | + }, | |
165 | + "position": 20 | |
166 | + }, | |
167 | + { | |
168 | + "id": 103442, | |
169 | + "abstract": "<p>Complemento à renda e acompanhamento em educação e saúde.</p>", | |
170 | + "title": "Bolsa Família", | |
171 | + "categories": [ | |
172 | + { | |
173 | + "name": "Redução da Pobreza", | |
174 | + "id": 183, | |
175 | + "slug": "reducao-da-pobreza", | |
176 | + "image": null | |
177 | + } | |
178 | + ], | |
179 | + "image": { | |
180 | + "url": "/image_uploads/dialoga/0000/0013/bolsa_familia_redim.jpg" | |
181 | + }, | |
182 | + "setting": { | |
183 | + "color": "#ff9900", | |
184 | + "moderate_comments": false, | |
185 | + "comment_paragraph_plugin_activate": false, | |
186 | + "author_name": "Ronald Emerson Scherolt da Costa", | |
187 | + "allow_members_to_edit": false | |
188 | + }, | |
189 | + "position": 17 | |
190 | + }, | |
191 | + { | |
192 | + "id": 103673, | |
193 | + "abstract": "<p>A melhor escolha é se informar.</p>", | |
194 | + "title": "Incentivo ao Parto Normal", | |
195 | + "categories": [ | |
196 | + { | |
197 | + "name": "Saúde", | |
198 | + "id": 180, | |
199 | + "slug": "saude", | |
200 | + "image": null | |
201 | + } | |
202 | + ], | |
203 | + "image": { | |
204 | + "url": "/image_uploads/dialoga/0000/0092/parto-normal.jpg" | |
205 | + }, | |
206 | + "setting": { | |
207 | + "color": "#ff0000", | |
208 | + "moderate_comments": false, | |
209 | + "comment_paragraph_plugin_activate": false, | |
210 | + "author_name": "Ronald Emerson Scherolt da Costa", | |
211 | + "allow_members_to_edit": false | |
212 | + }, | |
213 | + "position": 6 | |
214 | + }, | |
215 | + { | |
216 | + "id": 103397, | |
217 | + "abstract": "<p>Renda, inclusão produtiva e acesso a serviços.</p>", | |
218 | + "title": "Brasil Sem Miséria", | |
219 | + "categories": [ | |
220 | + { | |
221 | + "name": "Redução da Pobreza", | |
222 | + "id": 183, | |
223 | + "slug": "reducao-da-pobreza", | |
224 | + "image": null | |
225 | + } | |
226 | + ], | |
227 | + "image": { | |
228 | + "url": "/image_uploads/dialoga/0000/0116/bsm_redim.jpg" | |
229 | + }, | |
230 | + "setting": { | |
231 | + "color": "", | |
232 | + "moderate_comments": false, | |
233 | + "comment_paragraph_plugin_activate": false, | |
234 | + "author_name": "Ronald Emerson Scherolt da Costa", | |
235 | + "allow_members_to_edit": false | |
236 | + }, | |
237 | + "position": 18 | |
238 | + }, | |
239 | + { | |
240 | + "id": 121505, | |
241 | + "abstract": "<p>Um novo jeito de ver e de fazer cultura</p>", | |
242 | + "title": "Agenda Seculo XXI", | |
243 | + "categories": [ | |
244 | + { | |
245 | + "name": "Cultura", | |
246 | + "id": 194, | |
247 | + "slug": "cultura", | |
248 | + "image": null | |
249 | + } | |
250 | + ], | |
251 | + "image": { | |
252 | + "url": "/image_uploads/dialoga/0000/0166/Abertura_AGENDA_SECULO_XXI-v4.jpg" | |
253 | + }, | |
254 | + "setting": { | |
255 | + "color": "", | |
256 | + "allow_members_to_edit": false, | |
257 | + "moderate_comments": false, | |
258 | + "comment_paragraph_plugin_activate": false, | |
259 | + "author_name": "leonardo.merlin" | |
260 | + }, | |
261 | + "position": null | |
262 | + }, | |
263 | + { | |
264 | + "id": 121526, | |
265 | + "abstract": "<p>Cultura e arte como base para a educação integral</p>", | |
266 | + "title": "Cultura e Educação", | |
267 | + "categories": [ | |
268 | + { | |
269 | + "name": "Cultura", | |
270 | + "id": 194, | |
271 | + "slug": "cultura", | |
272 | + "image": null | |
273 | + } | |
274 | + ], | |
275 | + "image": { | |
276 | + "url": "/image_uploads/dialoga/0000/0177/Abertura-cultura-e-educacao-v2.jpg" | |
277 | + }, | |
278 | + "setting": { | |
279 | + "color": "", | |
280 | + "allow_members_to_edit": false, | |
281 | + "moderate_comments": false, | |
282 | + "comment_paragraph_plugin_activate": false, | |
283 | + "author_name": "leonardo.merlin" | |
284 | + }, | |
285 | + "position": null | |
286 | + }, | |
287 | + { | |
288 | + "id": 103485, | |
289 | + "abstract": "<p>Caminho para uma educação de qualidade.</p>", | |
290 | + "title": "Valorização dos Professores", | |
291 | + "categories": [ | |
292 | + { | |
293 | + "name": "Educação", | |
294 | + "id": 181, | |
295 | + "slug": "educacao", | |
296 | + "image": null | |
297 | + } | |
298 | + ], | |
299 | + "image": { | |
300 | + "url": "/image_uploads/dialoga/0000/0140/valorizacao_professor.jpg" | |
301 | + }, | |
302 | + "setting": { | |
303 | + "color": "#ffff00", | |
304 | + "moderate_comments": false, | |
305 | + "comment_paragraph_plugin_activate": false, | |
306 | + "author_name": "Ronald Emerson Scherolt da Costa", | |
307 | + "allow_members_to_edit": false | |
308 | + }, | |
309 | + "position": 11 | |
310 | + }, | |
311 | + { | |
312 | + "id": 103663, | |
313 | + "abstract": "<p>Mais educação profissional e tecnológica, mais desenvolvimento</p>", | |
314 | + "title": "Ensino Técnico", | |
315 | + "categories": [ | |
316 | + { | |
317 | + "name": "Educação", | |
318 | + "id": 181, | |
319 | + "slug": "educacao", | |
320 | + "image": null | |
321 | + } | |
322 | + ], | |
323 | + "image": { | |
324 | + "url": "/image_uploads/dialoga/0000/0134/Ensino_tecnico.jpg" | |
325 | + }, | |
326 | + "setting": { | |
327 | + "color": "#d0e0e3", | |
328 | + "moderate_comments": false, | |
329 | + "comment_paragraph_plugin_activate": false, | |
330 | + "author_name": "Ronald Emerson Scherolt da Costa", | |
331 | + "allow_members_to_edit": false | |
332 | + }, | |
333 | + "position": 10 | |
334 | + }, | |
335 | + { | |
336 | + "id": 121514, | |
337 | + "abstract": "<p>Reconhecimento, fortalecimento e mobilização das comunidades que fazem cultura no Brasil</p>", | |
338 | + "title": "Cultura Viva", | |
339 | + "categories": [ | |
340 | + { | |
341 | + "name": "Cultura", | |
342 | + "id": 194, | |
343 | + "slug": "cultura", | |
344 | + "image": null | |
345 | + } | |
346 | + ], | |
347 | + "image": { | |
348 | + "url": "/image_uploads/dialoga/0000/0167/Abertura_Cultura_Viva.jpg" | |
349 | + }, | |
350 | + "setting": { | |
351 | + "color": "", | |
352 | + "allow_members_to_edit": false, | |
353 | + "moderate_comments": false, | |
354 | + "comment_paragraph_plugin_activate": false, | |
355 | + "author_name": "leonardo.merlin" | |
356 | + }, | |
357 | + "position": null | |
358 | + }, | |
359 | + { | |
360 | + "id": 103592, | |
361 | + "abstract": "<p>Garantir acesso à proteção social.</p>", | |
362 | + "title": "Assistência Social", | |
363 | + "categories": [ | |
364 | + { | |
365 | + "name": "Redução da Pobreza", | |
366 | + "id": 183, | |
367 | + "slug": "reducao-da-pobreza", | |
368 | + "image": null | |
369 | + } | |
370 | + ], | |
371 | + "image": { | |
372 | + "url": "/image_uploads/dialoga/0000/0122/assistencia_social.jpg" | |
373 | + }, | |
374 | + "setting": { | |
375 | + "color": "#a61c00", | |
376 | + "moderate_comments": false, | |
377 | + "comment_paragraph_plugin_activate": false, | |
378 | + "author_name": "Ronald Emerson Scherolt da Costa", | |
379 | + "allow_members_to_edit": false | |
380 | + }, | |
381 | + "position": 19 | |
382 | + }, | |
383 | + { | |
384 | + "id": 103426, | |
385 | + "abstract": "<p>Da saúde se cuida todos os dias.</p>", | |
386 | + "title": "Vida saudável", | |
387 | + "categories": [ | |
388 | + { | |
389 | + "name": "Saúde", | |
390 | + "id": 180, | |
391 | + "slug": "saude", | |
392 | + "image": null | |
393 | + } | |
394 | + ], | |
395 | + "image": { | |
396 | + "url": "/image_uploads/dialoga/0000/0046/vida_saudavel.jpg" | |
397 | + }, | |
398 | + "setting": { | |
399 | + "color": "#d9d2e9", | |
400 | + "moderate_comments": false, | |
401 | + "comment_paragraph_plugin_activate": false, | |
402 | + "author_name": "Ronald Emerson Scherolt da Costa", | |
403 | + "allow_members_to_edit": false | |
404 | + }, | |
405 | + "position": 7 | |
406 | + }, | |
407 | + { | |
408 | + "id": 103507, | |
409 | + "abstract": "<p>Tecnologia a serviço da segurança do cidadão.</p>", | |
410 | + "title": "Sinesp", | |
411 | + "categories": [ | |
412 | + { | |
413 | + "name": "Segurança Pública", | |
414 | + "id": 182, | |
415 | + "slug": "seguranca-publica", | |
416 | + "image": null | |
417 | + } | |
418 | + ], | |
419 | + "image": { | |
420 | + "url": "/image_uploads/dialoga/0000/0098/sinesp.png" | |
421 | + }, | |
422 | + "setting": { | |
423 | + "color": "#00ff00", | |
424 | + "moderate_comments": false, | |
425 | + "comment_paragraph_plugin_activate": false, | |
426 | + "author_name": "Ronald Emerson Scherolt da Costa", | |
427 | + "allow_members_to_edit": false | |
428 | + }, | |
429 | + "position": 12 | |
430 | + }, | |
431 | + { | |
432 | + "id": 103359, | |
433 | + "abstract": "<p>Acesso a exames e consultas com especialistas.</p>", | |
434 | + "title": "Mais Especialidades", | |
435 | + "categories": [ | |
436 | + { | |
437 | + "name": "Saúde", | |
438 | + "id": 180, | |
439 | + "slug": "saude", | |
440 | + "image": null | |
441 | + } | |
442 | + ], | |
443 | + "image": { | |
444 | + "url": "/image_uploads/dialoga/0000/0083/mais_especialidades1.png" | |
445 | + }, | |
446 | + "setting": { | |
447 | + "color": "#ea9999", | |
448 | + "moderate_comments": false, | |
449 | + "comment_paragraph_plugin_activate": false, | |
450 | + "author_name": "Ronald Emerson Scherolt da Costa", | |
451 | + "allow_members_to_edit": false | |
452 | + }, | |
453 | + "position": 2 | |
454 | + }, | |
455 | + { | |
456 | + "id": 103683, | |
457 | + "abstract": "<p>Saúde não tem preço.</p>", | |
458 | + "title": "Aqui tem Farmácia Popular", | |
459 | + "categories": [ | |
460 | + { | |
461 | + "name": "Saúde", | |
462 | + "id": 180, | |
463 | + "slug": "saude", | |
464 | + "image": null | |
465 | + } | |
466 | + ], | |
467 | + "image": { | |
468 | + "url": "/image_uploads/dialoga/0000/0019/saude_nao_tem_preco.jpg" | |
469 | + }, | |
470 | + "setting": { | |
471 | + "color": "#e69138", | |
472 | + "moderate_comments": false, | |
473 | + "comment_paragraph_plugin_activate": false, | |
474 | + "author_name": "Ronald Emerson Scherolt da Costa", | |
475 | + "allow_members_to_edit": false | |
476 | + }, | |
477 | + "position": 5 | |
478 | + }, | |
479 | + { | |
480 | + "id": 103695, | |
481 | + "abstract": "<p>Novo modelo de atuação em Segurança Pública.</p>", | |
482 | + "title": "Segurança Pública Integrada", | |
483 | + "categories": [ | |
484 | + { | |
485 | + "name": "Segurança Pública", | |
486 | + "id": 182, | |
487 | + "slug": "seguranca-publica", | |
488 | + "image": null | |
489 | + } | |
490 | + ], | |
491 | + "image": { | |
492 | + "url": "/image_uploads/dialoga/0000/0152/policiaintegrada.jpg" | |
493 | + }, | |
494 | + "setting": { | |
495 | + "color": "#ff00ff", | |
496 | + "moderate_comments": false, | |
497 | + "comment_paragraph_plugin_activate": false, | |
498 | + "author_name": "Ronald Emerson Scherolt da Costa", | |
499 | + "allow_members_to_edit": false | |
500 | + }, | |
501 | + "position": 13 | |
502 | + }, | |
503 | + { | |
504 | + "id": 103379, | |
505 | + "abstract": "<p>Resgate e atendimento 24 horas, sete dias da semana.</p>", | |
506 | + "title": "SAMU 192 e UPAs", | |
507 | + "categories": [ | |
508 | + { | |
509 | + "name": "Saúde", | |
510 | + "id": 180, | |
511 | + "slug": "saude", | |
512 | + "image": null | |
513 | + } | |
514 | + ], | |
515 | + "image": { | |
516 | + "url": "/image_uploads/dialoga/0000/0060/SAMU.jpg" | |
517 | + }, | |
518 | + "setting": { | |
519 | + "color": "#45818e", | |
520 | + "moderate_comments": false, | |
521 | + "comment_paragraph_plugin_activate": false, | |
522 | + "author_name": "Ronald Emerson Scherolt da Costa", | |
523 | + "allow_members_to_edit": false | |
524 | + }, | |
525 | + "position": 4 | |
526 | + }, | |
527 | + { | |
528 | + "id": 103494, | |
529 | + "abstract": "<p>Da Educação Infantil ao Ensino Médio.</p>", | |
530 | + "title": "Educação Básica", | |
531 | + "categories": [ | |
532 | + { | |
533 | + "name": "Educação", | |
534 | + "id": 181, | |
535 | + "slug": "educacao", | |
536 | + "image": null | |
537 | + } | |
538 | + ], | |
539 | + "image": { | |
540 | + "url": "/image_uploads/dialoga/0000/0076/Educa__o_B_sica.jpg" | |
541 | + }, | |
542 | + "setting": { | |
543 | + "color": "#fce5cd", | |
544 | + "moderate_comments": false, | |
545 | + "comment_paragraph_plugin_activate": false, | |
546 | + "author_name": "Ronald Emerson Scherolt da Costa", | |
547 | + "allow_members_to_edit": false | |
548 | + }, | |
549 | + "position": 8 | |
550 | + }, | |
551 | + { | |
552 | + "id": 103644, | |
553 | + "abstract": "<p>Um caminho de oportunidades com o Enem: Sisu, Prouni, Fies, Ciência sem Fronteiras</p>", | |
554 | + "title": "Ensino Superior", | |
555 | + "categories": [ | |
556 | + { | |
557 | + "name": "Educação", | |
558 | + "id": 181, | |
559 | + "slug": "educacao", | |
560 | + "image": null | |
561 | + } | |
562 | + ], | |
563 | + "image": { | |
564 | + "url": "/image_uploads/dialoga/0000/0128/enem.jpg" | |
565 | + }, | |
566 | + "setting": { | |
567 | + "color": "#cfe2f3", | |
568 | + "moderate_comments": false, | |
569 | + "comment_paragraph_plugin_activate": false, | |
570 | + "author_name": "Ronald Emerson Scherolt da Costa", | |
571 | + "allow_members_to_edit": false | |
572 | + }, | |
573 | + "position": 9 | |
574 | + }, | |
575 | + { | |
576 | + "id": 121499, | |
577 | + "abstract": "<p>Valorização da arte e da cultura em suas múltiplas possibilidades</p>", | |
578 | + "title": "Política Nacional das Artes", | |
579 | + "categories": [ | |
580 | + { | |
581 | + "name": "Cultura", | |
582 | + "id": 194, | |
583 | + "slug": "cultura", | |
584 | + "image": null | |
585 | + } | |
586 | + ], | |
587 | + "image": { | |
588 | + "url": "/image_uploads/dialoga/0000/0159/Banner_Pol_tica_Nacional_das_Artes.jpg" | |
589 | + }, | |
590 | + "setting": { | |
591 | + "color": "", | |
592 | + "allow_members_to_edit": false, | |
593 | + "moderate_comments": false, | |
594 | + "comment_paragraph_plugin_activate": false, | |
595 | + "author_name": "leonardo.merlin" | |
596 | + }, | |
597 | + "position": null | |
598 | + }, | |
599 | + { | |
600 | + "id": 103472, | |
601 | + "abstract": "<p>Polícia Federal, Polícia Rodoviária Federal e Força Nacional de Segurança Pública.</p>", | |
602 | + "title": "Forças Federais de Segurança", | |
603 | + "categories": [ | |
604 | + { | |
605 | + "name": "Segurança Pública", | |
606 | + "id": 182, | |
607 | + "slug": "seguranca-publica", | |
608 | + "image": null | |
609 | + } | |
610 | + ], | |
611 | + "image": { | |
612 | + "url": "/image_uploads/dialoga/0000/0031/federais2.png" | |
613 | + }, | |
614 | + "setting": { | |
615 | + "color": "", | |
616 | + "moderate_comments": false, | |
617 | + "comment_paragraph_plugin_activate": false, | |
618 | + "author_name": "Ronald Emerson Scherolt da Costa", | |
619 | + "allow_members_to_edit": false | |
620 | + }, | |
621 | + "position": 16 | |
622 | + }, | |
623 | + { | |
624 | + "id": 121492, | |
625 | + "abstract": "<p>Apoio ao audiovisual brasileiro: ampliação da produção, da difusão e do acesso</p>", | |
626 | + "title": "Brasil de Todas as Telas", | |
627 | + "categories": [ | |
628 | + { | |
629 | + "name": "Cultura", | |
630 | + "id": 194, | |
631 | + "slug": "cultura", | |
632 | + "image": null | |
633 | + } | |
634 | + ], | |
635 | + "image": { | |
636 | + "url": "/image_uploads/dialoga/0000/0165/brasil-de-todas-telas-banner.jpg" | |
637 | + }, | |
638 | + "setting": { | |
639 | + "color": "", | |
640 | + "allow_members_to_edit": false, | |
641 | + "moderate_comments": false, | |
642 | + "comment_paragraph_plugin_activate": false, | |
643 | + "author_name": "leonardo.merlin" | |
644 | + }, | |
645 | + "position": null | |
646 | + }, | |
647 | + { | |
648 | + "id": 121521, | |
649 | + "abstract": "<p>Mais acesso a cultura para trabalhadores e trabalhadoras</p>", | |
650 | + "title": "Vale-Cultura", | |
651 | + "categories": [ | |
652 | + { | |
653 | + "name": "Cultura", | |
654 | + "id": 194, | |
655 | + "slug": "cultura", | |
656 | + "image": null | |
657 | + } | |
658 | + ], | |
659 | + "image": { | |
660 | + "url": "/image_uploads/dialoga/0000/0175/Abertura_Vale_cultura-v3.jpg" | |
661 | + }, | |
662 | + "setting": { | |
663 | + "color": "", | |
664 | + "allow_members_to_edit": false, | |
665 | + "moderate_comments": false, | |
666 | + "comment_paragraph_plugin_activate": false, | |
667 | + "author_name": "leonardo.merlin" | |
668 | + }, | |
669 | + "position": null | |
670 | + }, | |
671 | + { | |
672 | + "id": 103416, | |
673 | + "abstract": "<p>Estrutura adequada para atender melhor a população na atenção básica.</p>", | |
674 | + "title": "Melhorar os Postos de Saúde", | |
675 | + "categories": [ | |
676 | + { | |
677 | + "name": "Saúde", | |
678 | + "id": 180, | |
679 | + "slug": "saude", | |
680 | + "image": null | |
681 | + } | |
682 | + ], | |
683 | + "image": { | |
684 | + "url": "/image_uploads/dialoga/0000/0053/requalif_redim.jpg" | |
685 | + }, | |
686 | + "setting": { | |
687 | + "color": "#cc4125", | |
688 | + "moderate_comments": false, | |
689 | + "comment_paragraph_plugin_activate": false, | |
690 | + "author_name": "Ronald Emerson Scherolt da Costa", | |
691 | + "allow_members_to_edit": false | |
692 | + }, | |
693 | + "position": 3 | |
694 | + }, | |
695 | + { | |
696 | + "id": 121501, | |
697 | + "abstract": "<p>Preservação do patrimônio e qualidade de vida para os cidadãos</p>", | |
698 | + "title": "PAC Cidades Históricas", | |
699 | + "categories": [ | |
700 | + { | |
701 | + "name": "Cultura", | |
702 | + "id": 194, | |
703 | + "slug": "cultura", | |
704 | + "image": null | |
705 | + } | |
706 | + ], | |
707 | + "image": { | |
708 | + "url": "/image_uploads/dialoga/0000/0168/Abertura__PAC_Cidades_Historicas-v3.JPG" | |
709 | + }, | |
710 | + "setting": { | |
711 | + "color": "", | |
712 | + "allow_members_to_edit": false, | |
713 | + "moderate_comments": false, | |
714 | + "comment_paragraph_plugin_activate": false, | |
715 | + "author_name": "leonardo.merlin" | |
716 | + }, | |
717 | + "position": null | |
718 | + } | |
719 | + ] | |
720 | + } | |
721 | + }; | |
722 | + data.articles.push(articleHome); | |
723 | + | |
724 | + data.articles.push({ | |
725 | + "id":103521, | |
726 | + "article":{"id":103521,"body":"\u003Cdiv class=\"container\"\u003E\r\n\u003Cdiv class=\"row\"\u003E\r\n\u003Cdiv class=\"col-md-12\"\u003E\r\n\u003Ch2\u003EMais M\u00e9dicos\u003Csmall\u003E Mais atendimento nos munic\u00edpios, mais sa\u00fade para quem mais precisa.\u003C/small\u003E\u003C/h2\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003Cdiv class=\"row\"\u003E\r\n\u003Cdiv class=\"col-md-6\"\u003E\u003Cimg class=\"center-block img-responsive\" src=\"http://dialoga.gov.br/dialoga/dialoga-brasil/mais-medicos/imagens/mais-medicos-foto1.jpg\" alt=\"Foto colorida mostra um M\u00e9dico examinando uma menina. Ele est\u00e1 com uma lanterna na m\u00e3o e ela est\u00e1 com a l\u00edngua para fora.\" width=\"640\" height=\"373\" /\u003E\u003C/div\u003E\r\n\u003Cdiv class=\"col-md-6\"\u003E\r\n\u003Cp\u003EEste programa garante m\u00e9dicos nos postos de sa\u00fade de todo o Pa\u00eds. O\u00a0Mais M\u00e9dicos come\u00e7ou em 2013 e j\u00e1 mostra resultados positivos: \u00e9 muito bem avaliado por 95% dos usu\u00e1rios, segundo pesquisa feita pela UFMG / Ipespe, em 2014.\u003C/p\u003E\r\n\u003Cp\u003EO programa veio para enfrentar uma car\u00eancia hist\u00f3rica de m\u00e9dicos em muitos munic\u00edpios do Brasil. Antes do lan\u00e7amento do Mais M\u00e9dicos, 22 estados tinham um n\u00famero de m\u00e9dicos abaixo da m\u00e9dia nacional. Cinco desses estados tinham menos de 1 m\u00e9dico para cada mil habitantes.\u003C/p\u003E\r\n\u003Cp\u003EEntre 2013 e 2014, o governo federal selecionou e levou 14.462 m\u00e9dicos para 3.785 munic\u00edpios. Assim, garantiu atendimento para 50 milh\u00f5es de pessoas que precisavam se deslocar a outras cidades, nem sempre pr\u00f3ximas, para ter atendimento m\u00e9dico.\u003C/p\u003E\r\n\u003Cp\u003EEm 2015, chegamos a 18 mil vagas para m\u00e9dicos no programa. Beneficiamos 63 milh\u00f5es de pessoas, em mais de 4 mil munic\u00edpios. N\u00e3o h\u00e1 um \u00fanico munic\u00edpio brasileiro sem atendimento m\u00e9dico.\u003C/p\u003E\r\n\u003Cp\u003EOs m\u00e9dicos brasileiros se destacaram, em 2015: 92% dos m\u00e9dicos que aderiram ao programa s\u00e3o brasileiros.\u003C/p\u003E\r\n\u003Cp\u003ETodos os m\u00e9dicos rec\u00e9m-formados que participam do Mais M\u00e9dicos recebem um b\u00f4nus de 10% em sua nota na prova de resid\u00eancia, como incentivo a sua atua\u00e7\u00e3o nesta tarefa de levar atendimento \u00e0 sa\u00fade a nossa popula\u00e7\u00e3o.\u003C/p\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003Cdiv class=\"row\"\u003E\r\n\u003Cdiv class=\"col-md-12\"\u003E\r\n\u003Cdiv class=\"text-center\"\u003E\u003Cimg class=\"img-responsive center-block\" src=\"http://dialoga.gov.br/dialoga/dialoga-brasil/mais-medicos/imagens/mais-medicos-foto2.jpg\" alt=\"Infogr\u00e1fico mostra a aceita\u00e7\u00e3o do Mais M\u00e9dico de 95% dos usu\u00e1rios.\" width=\"501\" height=\"135\" /\u003E\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003Cdiv class=\"container\"\u003E\r\n\u003Cdiv class=\"row\"\u003E\r\n\u003Cdiv class=\"col-md-12\"\u003E\r\n\u003Ch3\u003EEvolu\u00e7\u00e3o do programa\u003C/h3\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003Cdiv class=\"row\"\u003E\r\n\u003Cdiv class=\"col-md-12\"\u003E\u003Cimg class=\"center-block img-responsive\" src=\"http://dialoga.gov.br/dialoga/dialoga-brasil/mais-medicos/imagens/mais-medicos-foto3.jpg\" alt=\"Dois mapas do Brasil mostrando a evolu\u00e7\u00e3o do programa, um com o n\u00famero de m\u00e9dicos do programa em 2013 com 1.136 m\u00e9dicos e o outro em 2015 com 18.247 m\u00e9dicos.\" width=\"752\" height=\"548\" /\u003E\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003Cdiv class=\"row bloco-destaque\"\u003E\r\n\u003Cdiv class=\"col-md-12\"\u003E\r\n\u003Ch4\u003EForam criadas 4.600 vagas de gradua\u00e7\u00e3o e 2.586 vagas de resid\u00eancia\u003C/h4\u003E\r\n\u003Cdiv class=\"row\"\u003E\r\n\u003Cdiv class=\"col-md-5 col-sm-5\"\u003E\r\n\u003Cp\u003EO Programa Mais M\u00e9dicos leva para o interior novas vagas em cursos de medicina, investindo na qualidade da forma\u00e7\u00e3o de m\u00e9dicos no Brasil e aumentando o n\u00famero de novos profissionais.\u003C/p\u003E\r\n\u003Cp\u003ES\u00e3o oferecidas, tamb\u00e9m, mais vagas de resid\u00eancia m\u00e9dica na rede de sa\u00fade, para formar especialistas que atendam \u00e0s necessidades de todas as regi\u00f5es do pa\u00eds.\u003Cimg class=\"center-block img-responsive\" src=\"http://dialoga.gov.br/dialoga/dialoga-brasil/mais-medicos/imagens/mais-medicos-foto5.jpg\" alt=\"Gr\u00e1fico de barra, com duas colunas. Uma mostra o crescimento de bolsas em outras especialidades de sa\u00fade. Em 2010 o n\u00famero de 499 e 2.875 em 2015. A outra barra mostra o crescimento de bolsas em resid\u00eancia. 788 vagas de resid\u00eancia em 2010 e 4.952 bolsas em 2015. Ao lado do gr\u00e1fico tem o texto : A cada ano, o Minist\u00e9rio da Sa\u00fade financia um n\u00famero maior de bolsas para forma\u00e7\u00e3o e especializa\u00e7\u00e3o. Ao lado foto mostra quatro m\u00e9dicos, duas mulheres e dois homens de jaleco branco e estetosc\u00f3pio no pesco\u00e7o e sorrindo.\" width=\"756\" height=\"397\" /\u003E\u003C/p\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003Cdiv class=\"row\"\u003E\r\n\u003Cdiv class=\"col-md-12\"\u003E\r\n\u003Ch3 class=\"titulo-destaque\"\u003EHoje, das 22.344 vagas em cursos de medicina, 52% est\u00e3o localizados no interior.\u003C/h3\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003Cdiv class=\"row\"\u003E\r\n\u003Cdiv class=\"col-md-12\"\u003E\u003Cimg class=\"center-block img-responsive\" src=\"http://dialoga.gov.br/dialoga/dialoga-brasil/mais-medicos/imagens/maismedicos-graficointeriorv3.jpg\" alt=\"Gr\u00e1fico de linha mostra a evolu\u00e7\u00e3o no n\u00famero de vagas nos cursos de medicina. A linha cinza mostra que em 1994 tinha 4.884 vagas na capital e 10.637 vagas em 2015. A linha azul mostra 3.878 vagas no interior em 1994 e 14.522 em 2015\" width=\"748\" height=\"435\" /\u003E\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003Cdiv class=\"container\"\u003E\r\n\u003Cdiv class=\"row\"\u003E\r\n\u003Cdiv class=\"col-md-12\"\u003E\r\n\u003Ch3\u003ECompromissos\u003C/h3\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003Cdiv class=\"row\"\u003E\r\n\u003Cdiv class=\"col-md-6 col-sm-6\"\u003E\u003Cimg class=\"center-block img-responsive\" src=\"http://dialoga.gov.br/dialoga/dialoga-brasil/mais-medicos/imagens/mais-medicos-foto7.png\" alt=\"Foto mostra uma m\u00e3o de mulher segurando um Estetosc\u00f3pio com a sigla do SUS (Sistema \u00danico de Sa\u00fade).\" width=\"327\" height=\"327\" /\u003E\u003C/div\u003E\r\n\u003Cdiv class=\"col-md-6 col-sm-6\"\u003E\r\n\u003Cul class=\"list-unstyled\"\u003E\r\n\u003Cli\u003ELevar atendimento m\u00e9dico a 70 milh\u00f5es de pessoas at\u00e9 2018.\u003C/li\u003E\r\n\u003Cli\u003EAt\u00e9 2017, criar mais 6,8 mil novas vagas em faculdades de medicina, chegando a 11,5 mil.\u003C/li\u003E\r\n\u003Cli\u003EAt\u00e9 2018, criar mais 9,8 mil vagas de resid\u00eancia m\u00e9dica chegando a 12,4 mil.\u003C/li\u003E\r\n\u003C/ul\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E"} | |
727 | + }); | |
728 | + data.articles.push({ | |
729 | + id: 103507, | |
730 | + "article": {"id":103507,"body":"\u003Cdiv class=\"container\"\u003E\r\n\u003Cdiv class=\"row\"\u003E\r\n\u003Cdiv class=\"col-md-12\"\u003E\r\n\u003Ch2\u003ESINESP\u003Csmall\u003ETecnologia a servi\u00e7o da seguran\u00e7a do cidad\u00e3o.\u003C/small\u003E\u003C/h2\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003Cdiv class=\"container\"\u003E\r\n\u003Cdiv class=\"row\"\u003E\r\n\u003Cdiv class=\"col-md-6 col-sm-6\"\u003E\u003Cimg class=\"img-responsive center-block\" src=\"http://dialoga.gov.br/dialoga/dialoga-brasil/sinesp/imagens/grafico-sinesp-2.jpg\" alt=\"Infogr\u00e1fico com o mapa do Brasil ligado por pontilhados a um monitor com o texto: base de dados. Outro pontilhado liga o monitor a cinco pictogramas, o primeiro a figura de uma engrenagem com o texto: pain\u00e9is gerenciais; o segundo um gr\u00e1fico de barras com o texto: gr\u00e1ficos anal\u00edticos; o terceiro uma folha de papel com escrito e o texto: relat\u00f3rios; a quarta um mapa do Brasil com o texto: mapas estat\u00edsticos e o quinto com tr\u00eas pessoas e o texto: planos de a\u00e7\u00e3o. Ao lado desse infogr\u00e1fico o texto: Sinesp \u2013 Sistema Nacional de Informa\u00e7\u00f5es de Seguran\u00e7a P\u00fablica, Prisionais e sobre Drogas. Atendimentos a emerg\u00eancias municipais, estaduais e federais (190, 191, 192, 193 e 197). Dados centralizados e consolidados. Atualiza\u00e7\u00e3o em tempo real. Sincroniza\u00e7\u00e3o das bases. Boletins de ocorr\u00eancia. Inqu\u00e9ritos policiais civis estaduais e federais. \" width=\"784\" height=\"598\" /\u003E\u003C/div\u003E\r\n\u003Cdiv class=\"col-md-6 col-sm-6\"\u003E\r\n\u003Cp\u003EO \u003Cstrong\u003ESINESP - Sistema Nacional de Informa\u00e7\u00f5es de Seguran\u00e7a P\u00fablica, Prisionais e sobre Drogas\u003C/strong\u003E \u00e9 um servi\u00e7o in\u00e9dito no Brasil. Re\u00fane, sistematiza, analisa e coloca \u00e0 disposi\u00e7\u00e3o dos cidad\u00e3os informa\u00e7\u00f5es sobre seguran\u00e7a p\u00fablica, justi\u00e7a, drogas e sistema prisional.\u003C/p\u003E\r\n\u003Cp\u003EImplementado pelo governo federal, em parceria com os 26 estados e o Distrito Federal, o sistema est\u00e1 ajudando a \u003Cstrong\u003Emelhorar a qualidade dos servi\u00e7os prestados \u003C/strong\u003E pela seguran\u00e7a p\u00fablica.\u003C/p\u003E\r\n\u003Cp\u003EO SINESP ajuda gestores a planejar e executar a\u00e7\u00f5es integradas contra o crime e a viol\u00eancia. Al\u00e9m disso, d\u00e1 mais \u003Cstrong\u003Etranspar\u00eancia\u003C/strong\u003E aos \u00edndices de criminalidade para toda a sociedade, pois os relat\u00f3rios com todas as\u00a0 informa\u00e7\u00f5es dispon\u00edveis no SINESP podem ser lidos e consultados pela popula\u00e7\u00e3o via \u003Cem\u003Einternet\u003C/em\u003E.\u003C/p\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003Cdiv class=\"container\"\u003E\r\n\u003Cdiv class=\"row\"\u003E\r\n\u003Cdiv class=\"col-md-6 col-sm-6\"\u003E\r\n\u003Ch3\u003ESINESP Cidad\u00e3o\u003C/h3\u003E\r\n\u003Cp\u003EDispon\u00edvel para qualquer pessoa, \u00e9 um aplicativo de consulta r\u00e1pida via \u003Cem\u003Einternet \u003C/em\u003Eque oferece informa\u00e7\u00f5es sobre \u003Cstrong\u003Eve\u00edculos roubados ou furtados, pessoas desaparecidas ou com mandatos de pris\u00e3o expedidos contra elas.\u003C/strong\u003E\u003C/p\u003E\r\n\u003Cp\u003EA ferramenta pode ser acessada, \u003Cstrong\u003Egratuitamente\u003C/strong\u003E, pelo endere\u00e7o \u003Cstrong\u003Ewww.sinesp.gov.br\u003C/strong\u003E e nas lojas de aplicativos, tanto para IOS, Android e Windows Phone.\u003C/p\u003E\r\n\u003Cp\u003EEm breve, um novo m\u00f3dulo ser\u00e1 disponibilizado no aplicativo: a localiza\u00e7\u00e3o de unidades policiais pr\u00f3ximas do usu\u00e1rio.\u003C/p\u003E\r\n\u003C/div\u003E\r\n\u003Cdiv class=\"col-md-6 col-sm-6\"\u003E\u003Cimg class=\"img-responsive center-block\" src=\"http://dialoga.gov.br/dialoga/dialoga-brasil/sinesp/imagens/tecnologia-sinesp-imagem2.jpg\" alt=\"Foto mostra m\u00e3o de uma pessoa com celular na m\u00e3o acessando o aplicativo. Ao fundo carros passando na rua. \" width=\"326\" height=\"327\" /\u003E\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003Cdiv class=\"container\"\u003E\r\n\u003Cdiv class=\"row\"\u003E\r\n\u003Cdiv class=\"col-md-12 col-sm-12\"\u003E\u003Cimg class=\"img-responsive center-block\" src=\"http://dialoga.gov.br/dialoga/dialoga-brasil/sinesp/imagens/tecnologia-sinesp-imagem3.jpg\" alt=\"Tr\u00eas pictogramas um ao lado do outro. O primeiro uma nuvem com uma seta para baixo com o texto: mais de 4,5 milh\u00f5es de downloads. O segundo uma lupa e o texto: mais de 150 milh\u00f5es de consulta. E o terceiro um carro com o texto: mais de 100 mil ve\u00edculos recuperados. \" width=\"773\" height=\"176\" /\u003E\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E"} | |
731 | + }); | |
732 | + data.articles.push({ | |
733 | + id: 121521, | |
734 | + "article":{"id":121521,"body":"\u003Cdiv class=\"col-xs-12\"\u003E\r\n\u003Cdiv class=\"row\"\u003E\r\n\u003Cdiv class=\"col-md-12\"\u003E\r\n\u003Ch2\u003EVale-Cultura\u003Csmall\u003EMais acesso \u00e0 cultura para trabalhadores e trabalhadoras\u003C/small\u003E\u003C/h2\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003Cdiv class=\"row\"\u003E\r\n\u003Cdiv class=\"col-md-12\"\u003E\r\n\u003Ch3\u003ELivros, shows e espet\u00e1culos para todos.\u003C/h3\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003Cdiv class=\"row\"\u003E\r\n\u003Cdiv class=\"col-md-6 col-sm-6 vcenter\"\u003E\u003Cimg class=\"img-responsive\" src=\"http://gestao.dialoga.gov.br/dialoga/dialoga-brasil/vale-cultura/imagens/vale-cultura1.jpg\" alt=\"\" /\u003E\u003C/div\u003E\r\n\u003Cdiv class=\"col-md-6 col-sm-6 vcenter\"\u003E\r\n\u003Cp\u003EO Vale-Cultura incentiva as empresas a oferecer aos seus funcion\u00e1rios acesso a livros, revistas, ingressos para cinemas, teatros, shows, instrumentos musicais e cursos de arte e cultura.\u003C/p\u003E\r\n\u003Cp\u003EO benef\u00edcio \u00e9 garantido por meio de um cart\u00e3o magn\u00e9tico pr\u00e9-pago, v\u00e1lido em todo os pa\u00eds. Mensalmente, esse cart\u00e3o recebe cr\u00e9dito de R$ 50, que pode ser acumulado para despesas maiores.\u003C/p\u003E\r\n\u003Cp\u003EA ades\u00e3o das empresas \u00e9 facultativa e os custos s\u00e3o livres de encargos sociais e trabalhistas. Aquelas que t\u00eam lucro real podem deduzir at\u00e9 1% do Imposto de Renda devido.\u003C/p\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003Cbr /\u003E\r\n\u003Cdiv class=\"row\"\u003E\r\n\u003Cdiv class=\"col-md-6 col-sm-6 vcenter\"\u003E\r\n\u003Cblockquote\u003E\r\n\u003Cp class=\"text-center\"\u003EEm pouco mais de um ano, o Vale-Cultura j\u00e1 mobiliza mais de R$140 milh\u00f5es e beneficia cerca de 420 mil trabalhadores e trabalhadoras.\u003C/p\u003E\r\n\u003C/blockquote\u003E\r\n\u003C/div\u003E\r\n\u003Cdiv class=\"col-md-6 col-sm-6 vcenter\"\u003E\r\n\u003Cdiv class=\"embed-responsive embed-responsive-16by9\"\u003E\u003Ciframe src=\"https://www.youtube.com/embed/KKmZh5T46g8?rel=0\" frameborder=\"0\" width=\"560\" height=\"315\"\u003E\u003C/iframe\u003E\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003Cdiv class=\"row\"\u003E\r\n\u003Cdiv class=\"col-md-12\"\u003E\r\n\u003Ch3\u003ECompromissos\u003C/h3\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003Cdiv class=\"row\"\u003E\r\n\u003Cdiv class=\"col-md-6 col-sm-6 vcenter\"\u003E\u003Cimg class=\"img-responsive\" src=\"http://gestao.dialoga.gov.br/dialoga/dialoga-brasil/vale-cultura/imagens/vale-cultura3.jpg\" alt=\"\" /\u003E\u003C/div\u003E\r\n\u003Cdiv class=\"col-md-6 col-sm-6 vcenter\"\u003E\r\n\u003Cul class=\"list-unstyled\"\u003E\r\n\u003Cli class=\"bullet\"\u003E\u003Cstrong\u003EAmpliar a ades\u00e3o de empresas e trabalhadores\u003C/strong\u003E\u003C/li\u003E\r\n\u003Cli class=\"bullet\"\u003E\u003Cstrong\u003EAmpliar a rede de estabelecimentos que recebem o Vale-Cultura.\u003C/strong\u003E\u003C/li\u003E\r\n\u003C/ul\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E\r\n\u003C/div\u003E"} | |
735 | + }); | |
736 | + | |
737 | + return data; | |
738 | +}; | ... | ... |
e2e/.jshintrc
e2e/main.po.js
... | ... | @@ -1,15 +0,0 @@ |
1 | -/** | |
2 | - * This file uses the Page Object pattern to define the main page for tests | |
3 | - * https://docs.google.com/presentation/d/1B6manhG0zEXkC-H-tPo2vwU06JhL8w9-XCF9oehXzAQ | |
4 | - */ | |
5 | - | |
6 | -'use strict'; | |
7 | - | |
8 | -var MainPage = function() { | |
9 | - this.jumbEl = element(by.css('.jumbotron')); | |
10 | - this.h1El = this.jumbEl.element(by.css('h1')); | |
11 | - this.imgEl = this.jumbEl.element(by.css('img')); | |
12 | - this.thumbnailEls = element(by.css('body')).all(by.repeater('awesomeThing in main.awesomeThings')); | |
13 | -}; | |
14 | - | |
15 | -module.exports = new MainPage(); |
e2e/main.spec.js
... | ... | @@ -1,21 +0,0 @@ |
1 | -'use strict'; | |
2 | - | |
3 | -describe('The main view', function () { | |
4 | - var page; | |
5 | - | |
6 | - beforeEach(function () { | |
7 | - browser.get('/index.html'); | |
8 | - page = require('./main.po'); | |
9 | - }); | |
10 | - | |
11 | - it('should include jumbotron with correct data', function() { | |
12 | - expect(page.h1El.getText()).toBe('\'Allo, \'Allo!'); | |
13 | - expect(page.imgEl.getAttribute('src')).toMatch(/assets\/images\/yeoman.png$/); | |
14 | - expect(page.imgEl.getAttribute('alt')).toBe('I\'m Yeoman'); | |
15 | - }); | |
16 | - | |
17 | - it('should list more than 5 awesome things', function () { | |
18 | - expect(page.thumbnailEls.count()).toBeGreaterThan(5); | |
19 | - }); | |
20 | - | |
21 | -}); |
... | ... | @@ -0,0 +1,16 @@ |
1 | +(function(){ | |
2 | + 'use strict'; | |
3 | + | |
4 | + describe('The index page', function () { | |
5 | + var page = browser.get('/'); | |
6 | + | |
7 | + // beforeEach(function () { | |
8 | + // browser.get('/'); | |
9 | + // }); | |
10 | + | |
11 | + describe('Common layout', function (){ | |
12 | + require('./layout.js')(); | |
13 | + }); | |
14 | + | |
15 | + }); | |
16 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,124 @@ |
1 | +/* global require */ | |
2 | +(function(){ | |
3 | + 'use strict'; | |
4 | + | |
5 | + describe('The index page', function () { | |
6 | + var page = require('./inicio.po.js'); | |
7 | + // beforeEach(function () { | |
8 | + // browser.get('/'); | |
9 | + // }); | |
10 | + | |
11 | + describe('Common layout', function (){ | |
12 | + require('./layout.js')(); | |
13 | + }); | |
14 | + | |
15 | + describe('Component: Main Video', function(){ | |
16 | + it('should have a thumb background image (for async)', function() { | |
17 | + expect(page.video.element(by.css('.video-thumbnail'))).toBeDefined(); | |
18 | + expect(page.video.element(by.css('.video-thumbnail')).getCssValue('background-image')).toContain('youtube-background.png'); | |
19 | + expect(page.video.element(by.css('.video-thumbnail')).getAttribute('aria-hidden')).toBe('true'); | |
20 | + }); | |
21 | + | |
22 | + it('should have a button play trigger', function() { | |
23 | + expect(page.video.element(by.css('.video-play-button'))).toBeDefined(); | |
24 | + expect(page.video.element(by.css('.video-play-button')).getAttribute('aria-label')).toBeDefined(); | |
25 | + }); | |
26 | + }); | |
27 | + | |
28 | + describe('Component: Agenda', function(){ | |
29 | + it('should have a tab-trigger', function() { | |
30 | + expect(page.agenda.element(by.css('.event-tab--trigger'))).toBeDefined(); | |
31 | + expect(page.agenda.element(by.css('.event-tab--title'))).toBeDefined(); | |
32 | + expect(page.agenda.element(by.css('.event-tab--icon'))).toBeDefined(); | |
33 | + expect(page.agenda.element(by.css('.event-tab--icon')).element(by.css('.glyphicon'))).toBeDefined(); | |
34 | + expect(page.agenda.element(by.css('.event-tab--icon')).element(by.css('.glyphicon')).getAttribute('aria-hidden')).toBe('true'); | |
35 | + expect(page.agenda.element(by.css('.event-tab--button'))).toBeDefined(); | |
36 | + expect(page.agenda.element(by.css('.event-tab--total-scheduled'))).toBeDefined(); | |
37 | + expect(page.agenda.element(by.css('.event-tab--total-scheduled'))).toMatch(/(\d)*/); | |
38 | + }); | |
39 | + | |
40 | + describe('Component: Agenda / Open-panel', function(){ | |
41 | + it('should have a header', function() { | |
42 | + // the 2 lines below need to open panel and make elements visibles | |
43 | + expect(page.agenda.element(by.model('eventListCtrl.isListVisible'))).toBeDefined(); | |
44 | + page.agenda.element(by.css('.event-tab--trigger')).click(); | |
45 | + | |
46 | + expect(page.agenda.element(by.css('.event-list--title'))).toBeDefined(); | |
47 | + expect(page.agenda.element(by.css('.event-list--title')).getText()).toEqual('Bate-papo com ministr@s'); | |
48 | + expect(page.agenda.element(by.css('.event-list--icon'))).toBeDefined(); | |
49 | + expect(page.agenda.element(by.css('.event-list--icon')).element(by.css('.glyphicon'))).toBeDefined(); | |
50 | + expect(page.agenda.element(by.css('.event-list--icon')).element(by.css('.glyphicon')).getAttribute('aria-hidden')).toBe('true'); | |
51 | + expect(page.agenda.element(by.css('.event-list--minimize'))).toBeDefined(); | |
52 | + expect(page.agenda.element(by.css('.event-list--minimize')).element(by.css('.glyphicon'))).toBeDefined(); | |
53 | + expect(page.agenda.element(by.css('.event-list--minimize')).element(by.css('.glyphicon')).getAttribute('aria-hidden')).toBe('true'); | |
54 | + }); | |
55 | + | |
56 | + it('should have a table with content', function() { | |
57 | + // date/time | |
58 | + expect(page.agenda.element(by.css('.event-list--minimize')).element(by.css('.glyphicon')).getAttribute('aria-hidden')).toBe('true'); | |
59 | + // title | |
60 | + // subscribe button | |
61 | + // total of subscribers | |
62 | + // show only 5 itens | |
63 | + }); | |
64 | + // it('should have the title of scheduled chat', function() {}); | |
65 | + // it('should have a subscribe button to scheduled chat', function() {}); | |
66 | + // it('should show the number of subscribers on each item', function() {}); | |
67 | + // it('should show 5 itens at most', function() {}); | |
68 | + // it('should be accessible', function() {}); | |
69 | + }); | |
70 | + | |
71 | + describe('Component: Agenda / with Hangout', function(){ | |
72 | + it('should have a title', function() {}); | |
73 | + it('should have a thumb background image (for async)', function() {}); | |
74 | + it('should have a button trigger to start the video', function() {}); | |
75 | + it('should have a description', function() { | |
76 | + // PATTERN: %DATETIME - %TITLE, %CATEGORY, ? | |
77 | + // Get it from the endpoint or assembly-it ? | |
78 | + }); | |
79 | + it('should have a open trigger', function() { | |
80 | + // with: | |
81 | + // - total of scheduled events | |
82 | + // - icon: arrow down | |
83 | + }); | |
84 | + }); | |
85 | + }); | |
86 | + | |
87 | + describe('Component: Category List', function(){ | |
88 | + it('should have a title', function() {}); | |
89 | + it('should have list of category', function() {}); | |
90 | + it('should have the icon of each category', function() {}); | |
91 | + it('should have the name of each category', function() {}); | |
92 | + it('should be accessible', function() {}); | |
93 | + // what expect on hover or focus? Material Desgn likes? | |
94 | + // | |
95 | + }); | |
96 | + | |
97 | + describe('Component: Article List | Box (each) ', function(){ | |
98 | + it('should have a category label', function() {}); | |
99 | + it('should have a banner image', function() {}); | |
100 | + it('should have a alternatve text for the banner image', function() {}); | |
101 | + it('should have a title', function() {}); | |
102 | + it('should have 50 letters at most on title', function() {}); | |
103 | + it('should have a abstract', function() {}); | |
104 | + it('should have 200 letters at most on abstract', function() {}); | |
105 | + it('should have the number of sent proposals', function() {}); | |
106 | + it('should have a call-to-action button', function() {}); | |
107 | + it('should have the same color of the category-color at call-to-action button', function() {}); | |
108 | + it('should be accessible', function() {}); | |
109 | + // what colors on what? | |
110 | + // what are links/clickable/focusable | |
111 | + }); | |
112 | + | |
113 | + describe('Component: Search ', function(){ | |
114 | + it('should have a hidden label', function() {}); | |
115 | + it('should have a html5 search input', function() {}); | |
116 | + it('should have be focusable by a11y link', function() {}); | |
117 | + it('should have a more filters?', function() {}); | |
118 | + it('should be accessible', function() {}); | |
119 | + // what behaviours? | |
120 | + // more filters? ordering by alphabet: name, category, random. | |
121 | + // show results at another page | |
122 | + }); | |
123 | + }); | |
124 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,80 @@ |
1 | +module.exports = function(){ | |
2 | + 'use strict'; | |
3 | + | |
4 | + describe('The common layout', function () { | |
5 | + | |
6 | + var page = require('./layout.po.js'); | |
7 | + | |
8 | + describe('Accessibility (a11y) top bar', function(){ | |
9 | + it('should have a "skip-to-content" anchor', function() { | |
10 | + expect(page.skipToContent.getText()).toEqual('Ir para o conteúdo 1'); | |
11 | + }); | |
12 | + it('should have a "skip-to-navigation" anchor', function() { | |
13 | + expect(page.skipToNavigation.getText()).toEqual('Ir para o menu 2'); | |
14 | + }); | |
15 | + it('should have a "skip-to-search" anchor', function() { | |
16 | + expect(page.skipToSearch.getText()).toEqual('Ir para a busca 3'); | |
17 | + }); | |
18 | + it('should have a "skip-to-footer" anchor', function() { | |
19 | + expect(page.skipToFooter.getText()).toEqual('Ir para o rodapé 4'); | |
20 | + }); | |
21 | + | |
22 | + it('should have a accessibility anchor', function() { | |
23 | + expect(page.actionAccessibility.getText()).toEqual('Acessibilidade'); | |
24 | + }); | |
25 | + it('should have a adjust contrast anchor', function() { | |
26 | + expect(page.actionContrast.getText()).toEqual('Alto Contraste'); | |
27 | + }); | |
28 | + it('should have a sitemap anchor', function() { | |
29 | + expect(page.actionSitemap.getText()).toEqual('Mapa do Site'); | |
30 | + }); | |
31 | + }); | |
32 | + | |
33 | + describe('Header', function(){ | |
34 | + it('should have a logo', function() {}); | |
35 | + it('should have a navigation', function() {}); | |
36 | + it('should have a social share area', function() {}); | |
37 | + it('should have a "CADASTRAR" anchor', function() {}); | |
38 | + it('should have a "ENTRAR" anchor', function() {}); | |
39 | + it('should have a "Veja mais" area', function() {}); | |
40 | + it('should have a valid ARIA', function() {}); | |
41 | + | |
42 | + describe('Header / Navigation', function(){ | |
43 | + it('should have a "SOBRE" anchor', function() {}); | |
44 | + it('should have a "PROGRAMAS" anchor', function() {}); | |
45 | + it('should have a "PROPOSTAS" anchor', function() {}); | |
46 | + it('should have a "DÚVIDAS" anchor', function() {}); | |
47 | + it('should be condensed on mobile', function() {}); | |
48 | + it('should have a valid ARIA', function() {}); | |
49 | + // it('should have a "ENTRAR?" anchor on MOBILE?', function() {}); | |
50 | + // it('should have a "RANKING?" anchor on MOBILE?', function() {}); | |
51 | + // it('should have a "RESPOSTAS?" anchor on MOBILE?', function() {}); | |
52 | + // it('should have a "PARTICIPE?" anchor on MOBILE?', function() {}); | |
53 | + }); | |
54 | + | |
55 | + describe('Header / Social Share', function(){ | |
56 | + it('should have a facebook share button', function() {}); | |
57 | + it('should have a twitter share button', function() {}); | |
58 | + it('should have a gplus share button', function() {}); | |
59 | + it('should have a whatsapp share button', function() {}); | |
60 | + it('should be condensed on mobile', function() {}); | |
61 | + it('should have a email share button', function() {}); | |
62 | + it('should have a valid ARIA', function() {}); | |
63 | + // what to do when on mobile? | |
64 | + // too small on mobile? point issues | |
65 | + }); | |
66 | + | |
67 | + describe('Header / "Veja mais"', function(){ | |
68 | + it('should have a youtube link', function() {}); | |
69 | + // it('should have a flicker? link', function() {}); | |
70 | + it('should have a valid ARIA', function() {}); | |
71 | + // what to do when on mobile? | |
72 | + }); | |
73 | + }); | |
74 | + | |
75 | + describe('Footer', function(){ | |
76 | + it('should have a ?', function() {}); | |
77 | + it('should have a valid ARIA', function() {}); | |
78 | + }); | |
79 | + }); | |
80 | +}; | ... | ... |
... | ... | @@ -0,0 +1,16 @@ |
1 | +module.exports = (function() { | |
2 | + 'use strict'; | |
3 | + | |
4 | + var PageObject = function() { | |
5 | + this.skipToContent = element(by.id('skip-to-content')); | |
6 | + this.skipToNavigation = element(by.id('skip-to-navigation')); | |
7 | + this.skipToSearch = element(by.id('skip-to-search')); | |
8 | + this.skipToFooter = element(by.id('skip-to-footer')); | |
9 | + | |
10 | + this.actionAccessibility = element(by.id('siteaction-accessibility')); | |
11 | + this.actionContrast = element(by.id('siteaction-contrast')); | |
12 | + this.actionSitemap = element(by.id('siteaction-sitemap')); | |
13 | + }; | |
14 | + | |
15 | + return (new PageObject()); | |
16 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,55 @@ |
1 | +(function(){ | |
2 | + 'use strict'; | |
3 | + | |
4 | + describe('The "Programa" page', function () { | |
5 | + var page = browser.get('/'); | |
6 | + | |
7 | + // beforeEach(function () { | |
8 | + // browser.get('/'); | |
9 | + // }); | |
10 | + | |
11 | + describe('Common layout', function (){ | |
12 | + require('./layout.js')(); | |
13 | + }); | |
14 | + | |
15 | + describe('Component: article-preview', function (){}); | |
16 | + | |
17 | + describe('Component: article-content', function (){}); | |
18 | + | |
19 | + // describe('Component: article-template-1', function (){}); | |
20 | + | |
21 | + describe('Component: proposal-random', function (){ | |
22 | + it('should have a loading state', function() {}); | |
23 | + it('should have a breadcrumb', function() {}); | |
24 | + it('should have the text-content of proposal', function() {}); | |
25 | + it('should have a vote up button', function() {}); | |
26 | + it('should have a vote skip button', function() {}); | |
27 | + it('should have a vote down button', function() {}); | |
28 | + it('should have a social share area', function() {}); | |
29 | + it('should have the ranking position', function() {}); | |
30 | + it('should have a ranking button trigger', function() {}); | |
31 | + it('should be accessible', function() {}); | |
32 | + }); | |
33 | + | |
34 | + describe('Component: proposal-ranking', function (){ | |
35 | + it('should have a loading state', function() {}); | |
36 | + it('should have a close button trigger', function() {}); | |
37 | + it('should have the ranking position of proposal', function() {}); | |
38 | + it('should have the text-content of proposal', function() {}); | |
39 | + it('should have the number of views', function() {}); | |
40 | + it('should have the number of votes up', function() {}); | |
41 | + it('should have the number of votes down', function() {}); | |
42 | + it('should have a link to proposal', function() {}); | |
43 | + it('should have a link to all proposals', function() {}); | |
44 | + it('should be accessible', function() {}); | |
45 | + }); | |
46 | + | |
47 | + describe('Component: proposal-maker', function (){ | |
48 | + it('should be accessible', function() {}); | |
49 | + }); | |
50 | + | |
51 | + describe('Component: proposal-ranking', function (){ | |
52 | + it('should be accessible', function() {}); | |
53 | + }); | |
54 | + }); | |
55 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,29 @@ |
1 | +(function(){ | |
2 | + 'use strict'; | |
3 | + | |
4 | + describe('The "Sobre" page', function () { | |
5 | + var page = browser.get('/'); | |
6 | + | |
7 | + // beforeEach(function () { | |
8 | + // browser.get('/'); | |
9 | + // }); | |
10 | + | |
11 | + describe('Common layout', function (){ | |
12 | + require('./layout.js')(); | |
13 | + }); | |
14 | + | |
15 | + describe('Breadcrumb', function(){ | |
16 | + it('should have two itens', function() {}); | |
17 | + }); | |
18 | + | |
19 | + describe('Content', function(){ | |
20 | + it('should have a main video', function() {}); | |
21 | + it('should have a main video thumb image', function() {}); | |
22 | + it('should have a main video thumb image alternative text', function() {}); | |
23 | + | |
24 | + it('should have a "Programas" description', function() {}); | |
25 | + it('should have a "Propostas" tutorial', function() {}); | |
26 | + it('should be accessible', function() {}); | |
27 | + }); | |
28 | + }); | |
29 | +})(); | ... | ... |
gulp/build.js
... | ... | @@ -48,6 +48,7 @@ gulp.task('html', ['inject', 'partials'], function () { |
48 | 48 | .pipe(jsFilter.restore()) |
49 | 49 | .pipe(cssFilter) |
50 | 50 | .pipe($.replace('../../bower_components/bootstrap-sass-official/assets/fonts/bootstrap/', '../fonts/')) |
51 | + .pipe($.replace('../../bower_components/open-sans-fontface/fonts/', '../fonts/')) | |
51 | 52 | .pipe($.csso()) |
52 | 53 | .pipe(cssFilter.restore()) |
53 | 54 | .pipe(assets.restore()) |
... | ... | @@ -68,7 +69,10 @@ gulp.task('html', ['inject', 'partials'], function () { |
68 | 69 | // Only applies for fonts from bower dependencies |
69 | 70 | // Custom fonts are handled by the "other" task |
70 | 71 | gulp.task('fonts', function () { |
71 | - return gulp.src($.mainBowerFiles().concat('bower_components/bootstrap-sass-official/assets/fonts/bootstrap/*')) | |
72 | + return gulp.src([ | |
73 | + $.mainBowerFiles().concat('bower_components/bootstrap-sass-official/assets/fonts/bootstrap/*'), | |
74 | + $.mainBowerFiles().concat('bower_components/open-sans-fontface/fonts/*') | |
75 | + ]) | |
72 | 76 | .pipe($.filter('**/*.{eot,svg,ttf,woff,woff2}')) |
73 | 77 | .pipe($.flatten()) |
74 | 78 | .pipe(gulp.dest(path.join(conf.paths.dist, '/fonts/'))); | ... | ... |
... | ... | @@ -0,0 +1,24 @@ |
1 | +'use strict'; | |
2 | + | |
3 | +var path = require('path'); | |
4 | +var gulp = require('gulp'); | |
5 | +var conf = require('./conf'); | |
6 | + | |
7 | +var gulpif = require('gulp-if'); | |
8 | +var sprity = require('sprity'); | |
9 | + | |
10 | +gulp.task('sprites', function () { | |
11 | + var src = [ | |
12 | + path.join(conf.paths.src, '/assets/images/icons/*.png'), | |
13 | + path.join('!' + conf.paths.src, '/assets/images/icons/sprite.png') | |
14 | + ]; | |
15 | + var destCss = path.join(conf.paths.tmp, '/serve/app/'); | |
16 | + var destImg = path.join(conf.paths.src, '/assets/images/icons'); | |
17 | + | |
18 | + return sprity.src({ | |
19 | + src: src, | |
20 | + style: 'sprite.css', | |
21 | + cssPath: '../assets/images/icons/' | |
22 | + }) | |
23 | + .pipe(gulpif('*.png', gulp.dest(destImg), gulp.dest(destCss))); | |
24 | +}); | ... | ... |
gulp/inject.js
... | ... | @@ -9,7 +9,7 @@ var $ = require('gulp-load-plugins')(); |
9 | 9 | var wiredep = require('wiredep').stream; |
10 | 10 | var _ = require('lodash'); |
11 | 11 | |
12 | -gulp.task('inject', ['scripts', 'styles'], function () { | |
12 | +gulp.task('inject', ['scripts', 'styles', 'sprites'], function () { | |
13 | 13 | var injectStyles = gulp.src([ |
14 | 14 | path.join(conf.paths.tmp, '/serve/app/**/*.css'), |
15 | 15 | path.join('!' + conf.paths.tmp, '/serve/app/vendor.css') | ... | ... |
gulp/server.js
... | ... | @@ -8,6 +8,7 @@ var browserSync = require('browser-sync'); |
8 | 8 | var browserSyncSpa = require('browser-sync-spa'); |
9 | 9 | |
10 | 10 | var util = require('util'); |
11 | +var gutil = require('gulp-util'); | |
11 | 12 | |
12 | 13 | var proxyMiddleware = require('http-proxy-middleware'); |
13 | 14 | |
... | ... | @@ -33,7 +34,25 @@ function browserSyncInit(baseDir, browser) { |
33 | 34 | * |
34 | 35 | * For more details and option, https://github.com/chimurai/http-proxy-middleware/blob/v0.0.5/README.md |
35 | 36 | */ |
36 | - // server.middleware = proxyMiddleware('/users', {target: 'http://jsonplaceholder.typicode.com', proxyHost: 'jsonplaceholder.typicode.com'}); | |
37 | + if(gutil.env.target) { | |
38 | + server.middleware = proxyMiddleware('/api', {target: gutil.env.target}); | |
39 | + } else { | |
40 | + // no target! Point to localhost | |
41 | + server.middleware = proxyMiddleware('/api', { | |
42 | + target: 'http://0.0.0.0:9000/', | |
43 | + pathRewrite: { | |
44 | + // rewrite paths | |
45 | + '^/api/v1/articles' : '/articles' | |
46 | + }, | |
47 | + proxyTable: { | |
48 | + // when request.headers.host == 'dev.localhost:3000', | |
49 | + // override target 'http://www.example.org' to 'http://localhost:8000' | |
50 | + // 'dev.localhost:3000' : 'http://localhost:8000' | |
51 | + 'hom.dialoga.gov.br' : 'http://localhost:9000', | |
52 | + 'login.dialoga.gov.br' : 'http://localhost:9000' | |
53 | + } | |
54 | + }); | |
55 | + } | |
37 | 56 | |
38 | 57 | browserSync.instance = browserSync.init({ |
39 | 58 | startPath: '/', | ... | ... |
gulp/styles.js
... | ... | @@ -39,7 +39,10 @@ gulp.task('styles', function () { |
39 | 39 | .pipe(wiredep(_.extend({}, conf.wiredep))) |
40 | 40 | .pipe($.sourcemaps.init()) |
41 | 41 | .pipe($.sass(sassOptions)).on('error', conf.errorHandler('Sass')) |
42 | - .pipe($.autoprefixer()).on('error', conf.errorHandler('Autoprefixer')) | |
42 | + .pipe($.autoprefixer({ | |
43 | + browsers: ['last 3 versions', 'ie >= 9', 'ff > 20', 'Chrome > 30', 'Android', 'Edge', 'Opera', 'Safari', 'iOS'], | |
44 | + cascade: false | |
45 | + })).on('error', conf.errorHandler('Autoprefixer')) | |
43 | 46 | .pipe($.sourcemaps.write()) |
44 | 47 | .pipe(gulp.dest(path.join(conf.paths.tmp, '/serve/app/'))) |
45 | 48 | .pipe(browserSync.reload({ stream: true })); | ... | ... |
gulp/watch.js
... | ... | @@ -25,6 +25,16 @@ gulp.task('watch', ['inject'], function () { |
25 | 25 | } |
26 | 26 | }); |
27 | 27 | |
28 | + gulp.watch([ | |
29 | + path.join(conf.paths.src, '/assets/images/icons/*.png') | |
30 | + ], function(event) { | |
31 | + if(isOnlyChange(event)) { | |
32 | + gulp.start('sprites'); | |
33 | + } else { | |
34 | + gulp.start('inject'); | |
35 | + } | |
36 | + }); | |
37 | + | |
28 | 38 | gulp.watch(path.join(conf.paths.src, '/app/**/*.js'), function(event) { |
29 | 39 | if(isOnlyChange(event)) { |
30 | 40 | gulp.start('scripts'); | ... | ... |
package.json
... | ... | @@ -6,47 +6,49 @@ |
6 | 6 | "test": "gulp test" |
7 | 7 | }, |
8 | 8 | "devDependencies": { |
9 | + "browser-sync": "~2.7.12", | |
10 | + "browser-sync-spa": "~1.0.2", | |
11 | + "chalk": "~1.0.0", | |
12 | + "concat-stream": "~1.5.0", | |
13 | + "del": "~1.2.0", | |
9 | 14 | "gulp": "~3.9.0", |
10 | - "gulp-autoprefixer": "~2.3.1", | |
15 | + "gulp-angular-filesort": "~1.1.1", | |
11 | 16 | "gulp-angular-templatecache": "~1.6.0", |
12 | - "del": "~1.2.0", | |
13 | - "lodash": "~3.9.3", | |
17 | + "gulp-autoprefixer": "~2.3.1", | |
14 | 18 | "gulp-csso": "~1.0.0", |
15 | 19 | "gulp-filter": "~2.0.2", |
16 | 20 | "gulp-flatten": "~0.0.4", |
21 | + "gulp-if": "^1.2.5", | |
22 | + "gulp-inject": "~1.3.1", | |
17 | 23 | "gulp-jshint": "~1.11.0", |
18 | 24 | "gulp-load-plugins": "~0.10.0", |
19 | - "gulp-size": "~1.2.1", | |
20 | - "gulp-uglify": "~1.2.0", | |
21 | - "gulp-useref": "~1.2.0", | |
22 | - "gulp-util": "~3.0.5", | |
25 | + "gulp-minify-html": "~1.0.3", | |
23 | 26 | "gulp-ng-annotate": "~1.0.0", |
24 | - "gulp-replace": "~0.5.3", | |
27 | + "gulp-protractor": "~1.0.0", | |
25 | 28 | "gulp-rename": "~1.2.2", |
29 | + "gulp-replace": "~0.5.3", | |
26 | 30 | "gulp-rev": "~5.0.0", |
27 | 31 | "gulp-rev-replace": "~0.4.2", |
28 | - "gulp-minify-html": "~1.0.3", | |
29 | - "gulp-inject": "~1.3.1", | |
30 | - "gulp-protractor": "~1.0.0", | |
31 | - "gulp-sourcemaps": "~1.5.2", | |
32 | 32 | "gulp-sass": "~2.0.1", |
33 | - "gulp-angular-filesort": "~1.1.1", | |
34 | - "main-bower-files": "~2.8.0", | |
35 | - "merge-stream": "~0.1.7", | |
33 | + "gulp-size": "~1.2.1", | |
34 | + "gulp-sourcemaps": "~1.5.2", | |
35 | + "gulp-uglify": "~1.2.0", | |
36 | + "gulp-useref": "~1.2.0", | |
37 | + "gulp-util": "~3.0.5", | |
38 | + "http-proxy-middleware": "^0.7.0", | |
36 | 39 | "jshint-stylish": "~2.0.0", |
37 | - "wiredep": "~2.2.2", | |
38 | 40 | "karma": "~0.12.36", |
39 | - "karma-jasmine": "~0.3.5", | |
40 | - "karma-phantomjs-launcher": "~0.2.0", | |
41 | 41 | "karma-angular-filesort": "~0.1.0", |
42 | + "karma-jasmine": "~0.3.5", | |
42 | 43 | "karma-ng-html2js-preprocessor": "~0.1.2", |
43 | - "concat-stream": "~1.5.0", | |
44 | + "karma-phantomjs-launcher": "~0.2.0", | |
45 | + "lodash": "~3.10.1", | |
46 | + "main-bower-files": "~2.8.0", | |
47 | + "merge-stream": "^1.0.0", | |
44 | 48 | "require-dir": "~0.3.0", |
45 | - "browser-sync": "~2.7.12", | |
46 | - "browser-sync-spa": "~1.0.2", | |
47 | - "http-proxy-middleware": "~0.0.5", | |
48 | - "chalk": "~1.0.0", | |
49 | + "sprity": "^1.0.7", | |
49 | 50 | "uglify-save-license": "~0.4.1", |
51 | + "wiredep": "~2.2.2", | |
50 | 52 | "wrench": "~1.5.8" |
51 | 53 | }, |
52 | 54 | "engines": { | ... | ... |
protractor.conf.js
1 | -'use strict'; | |
2 | - | |
3 | -var paths = require('./.yo-rc.json')['generator-gulp-angular'].props.paths; | |
4 | - | |
5 | -// An example configuration file. | |
6 | -exports.config = { | |
7 | - // The address of a running selenium server. | |
8 | - //seleniumAddress: 'http://localhost:4444/wd/hub', | |
9 | - //seleniumServerJar: deprecated, this should be set on node_modules/protractor/config.json | |
10 | - | |
11 | - // Capabilities to be passed to the webdriver instance. | |
12 | - capabilities: { | |
13 | - 'browserName': 'chrome' | |
14 | - }, | |
15 | - | |
16 | - baseUrl: 'http://localhost:3000', | |
17 | - | |
18 | - // Spec patterns are relative to the current working directly when | |
19 | - // protractor is called. | |
20 | - specs: [paths.e2e + '/**/*.js'], | |
21 | - | |
22 | - // Options to be passed to Jasmine-node. | |
23 | - jasmineNodeOpts: { | |
24 | - showColors: true, | |
25 | - defaultTimeoutInterval: 30000 | |
26 | - } | |
27 | -}; | |
1 | +/* globals require, exports*/ | |
2 | +(function(){ | |
3 | + 'use strict'; | |
4 | + | |
5 | + var paths = require('./.yo-rc.json')['generator-gulp-angular'].props.paths; | |
6 | + | |
7 | + // An example configuration file. | |
8 | + exports.config = { | |
9 | + // The address of a running selenium server. | |
10 | + //seleniumAddress: 'http://0.0.0.0:4444/wd/hub', | |
11 | + //seleniumServerJar: deprecated, this should be set on node_modules/protractor/config.json | |
12 | + | |
13 | + // Capabilities to be passed to the webdriver instance. | |
14 | + capabilities: { | |
15 | + 'browserName': 'chrome' | |
16 | + }, | |
17 | + | |
18 | + chromeOnly: true, | |
19 | + | |
20 | + onPrepare: function() { | |
21 | + /* global angular: false, browser: false */ | |
22 | + | |
23 | + // Disable animations so e2e tests run more quickly | |
24 | + var disableNgAnimate = function() { | |
25 | + angular.module('disableNgAnimate', []).run(['$animate', function($animate) { | |
26 | + $animate.enabled(false); | |
27 | + }]); | |
28 | + }; | |
29 | + | |
30 | + browser.addMockModule('disableNgAnimate', disableNgAnimate); | |
31 | + | |
32 | + // Disable debug info | |
33 | + // var disableDebugInfo = function() { | |
34 | + // angular.module('disableDebugInfo', []).run(['$compileProvider', function($compileProvider) { | |
35 | + // $compileProvider.debugInfoEnabled(false); | |
36 | + // }]); | |
37 | + // }; | |
38 | + // browser.addMockModule('disableDebugInfo', disableDebugInfo); | |
39 | + | |
40 | + // Store the name of the browser that's currently being used. | |
41 | + browser.getCapabilities().then(function(caps) { | |
42 | + browser.params.browser = caps.get('browserName'); | |
43 | + }); | |
44 | + | |
45 | + browser.driver.manage().window().setSize(1400, 400); | |
46 | + }, | |
47 | + | |
48 | + baseUrl: 'http://0.0.0.0:3000', | |
49 | + | |
50 | + rootElement: '[ng-app]', | |
51 | + | |
52 | + // The timeout in milliseconds for each script run on the browser. This should | |
53 | + // be longer than the maximum time your application needs to stabilize between | |
54 | + // tasks. | |
55 | + allScriptsTimeout: 15000, | |
56 | + | |
57 | + // How long to wait for a page to load. | |
58 | + getPageTimeout: 12000, | |
59 | + | |
60 | + // Spec patterns are relative to the current working directly when | |
61 | + // protractor is called. | |
62 | + specs: [paths.e2e + '/**/*.js'], | |
63 | + | |
64 | + // Options to be passed to Jasmine-node. | |
65 | + 'framework': 'jasmine2', | |
66 | + jasmineNodeOpts: { | |
67 | + showColors: true, | |
68 | + defaultTimeoutInterval: 30000 | |
69 | + }, | |
70 | + | |
71 | + plugins: [{ | |
72 | + path: 'node_modules/gulp-protractor/node_modules/protractor/plugins/accessibility', | |
73 | + chromeA11YDevTools: { | |
74 | + treatWarningsAsFailures: true | |
75 | + } | |
76 | + }, { | |
77 | + path: 'node_modules/gulp-protractor/node_modules/protractor/plugins/ngHint' | |
78 | + }] | |
79 | + }; | |
80 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,48 @@ |
1 | +<div class="a11y-bar"> | |
2 | + <div class="container"> | |
3 | + <div class="row"> | |
4 | + <div class="col-sm-6"> | |
5 | + <ul class="skip-links list-inline list-unstyled"> | |
6 | + <li> | |
7 | + <a accesskey="1" href="#content" id="skip-to-content" ng-click="skipToContent($event)"> | |
8 | + Ir para o conteúdo | |
9 | + <span>1</span> | |
10 | + </a> | |
11 | + </li> | |
12 | + <li> | |
13 | + <a accesskey="2" href="#navigation" id="skip-to-navigation" ng-click="skipToNavigation($event)"> | |
14 | + Ir para o menu | |
15 | + <span>2</span> | |
16 | + </a> | |
17 | + </li> | |
18 | + <li> | |
19 | + <a accesskey="3" href="#search" id="skip-to-search" ng-click="skipToSearch($event)"> | |
20 | + Ir para a busca | |
21 | + <span>3</span> | |
22 | + </a> | |
23 | + </li> | |
24 | + <li> | |
25 | + <a accesskey="4" href="#footer" id="skip-to-footer" ng-click="skipToFooter($event)"> | |
26 | + Ir para o rodapé | |
27 | + <span>4</span> | |
28 | + </a> | |
29 | + </li> | |
30 | + </ul> | |
31 | + </div> | |
32 | + | |
33 | + <div class="col-sm-6"> | |
34 | + <ul class="action-links list-inline list-unstyled pull-right"> | |
35 | + <li> | |
36 | + <a id="siteaction-accessibility" href="#" title="Acessibilidade" accesskey="5" ng-click="actionAccessibility()">Acessibilidade</a> | |
37 | + </li> | |
38 | + <li> | |
39 | + <a id="siteaction-contrast" href="#" title="Alto Contraste" accesskey="6" ng-click="actionContrast()">Alto Contraste</a> | |
40 | + </li> | |
41 | + <li> | |
42 | + <a id="siteaction-sitemap" ui-sref="mapa-do-site" title="Mapa do Site" accesskey="7" ng-click="actionSitemap()">Mapa do Site</a> | |
43 | + </li> | |
44 | + </ul> | |
45 | + </div> | |
46 | + </div> | |
47 | + </div> | |
48 | +</div> | ... | ... |
... | ... | @@ -0,0 +1,19 @@ |
1 | +(function() { | |
2 | + 'use strict'; | |
3 | + | |
4 | + angular | |
5 | + .module('dialoga') | |
6 | + .directive('a11yBar', a11yBar); | |
7 | + | |
8 | + /** @ngInject */ | |
9 | + function a11yBar() { | |
10 | + var directive = { | |
11 | + restrict: 'E', | |
12 | + templateUrl: 'app/components/a11y-bar/a11y-bar.html' | |
13 | + }; | |
14 | + | |
15 | + return directive; | |
16 | + | |
17 | + } | |
18 | + | |
19 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,68 @@ |
1 | +(function() { | |
2 | + 'use strict'; | |
3 | + | |
4 | + angular | |
5 | + .module('dialoga') | |
6 | + .directive('articleBar', articleBar); | |
7 | + | |
8 | + /** @ngInject */ | |
9 | + function articleBar() { | |
10 | + var directive = { | |
11 | + restrict: 'E', | |
12 | + templateUrl: 'app/components/article-bar/article-bar.html', | |
13 | + scope: { | |
14 | + category: '=', | |
15 | + categories: '=' | |
16 | + }, | |
17 | + controller: ArticleBarController, | |
18 | + controllerAs: 'vm', | |
19 | + bindToController: true | |
20 | + }; | |
21 | + | |
22 | + return directive; | |
23 | + | |
24 | + /** @ngInject */ | |
25 | + function ArticleBarController($scope, $rootScope, $state, $log) { | |
26 | + $log.debug('ArticleBarController'); | |
27 | + | |
28 | + var vm = this; | |
29 | + | |
30 | + vm.$scope = $scope; | |
31 | + vm.$rootScope = $rootScope; | |
32 | + vm.$state = $state; | |
33 | + vm.theme = 'blue'; | |
34 | + | |
35 | + // if(!vm.category) { | |
36 | + // throw 'article bar without category'; | |
37 | + // } | |
38 | + | |
39 | + // if(!vm.categories) { | |
40 | + // throw 'article bar without categories list'; | |
41 | + // } | |
42 | + | |
43 | + vm.currentCategory = vm.category; | |
44 | + | |
45 | + vm.$scope.$watch('vm.currentCategory', function(newValue, oldValue){ | |
46 | + if(newValue !== oldValue){ | |
47 | + vm.$state.go('inicio', { | |
48 | + tema: newValue.slug | |
49 | + }, { | |
50 | + location: true | |
51 | + }); | |
52 | + } | |
53 | + }); | |
54 | + | |
55 | + vm.goBack = function (){ | |
56 | + var vm = this; | |
57 | + var prevState = vm.$rootScope.$previousState; | |
58 | + if(prevState && prevState.state.name){ | |
59 | + vm.$state.go(prevState.state.name, prevState.params); | |
60 | + } else { | |
61 | + vm.$state.go('inicio'); | |
62 | + } | |
63 | + }; | |
64 | + } | |
65 | + | |
66 | + } | |
67 | + | |
68 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,23 @@ |
1 | +<div class="article-bar" ng-class="vm.theme"> | |
2 | + <div class="navbar"> | |
3 | + <div class="navbar-header"> | |
4 | + <button class="article-bar--item btn btn-link" ng-click="vm.goBack()"> | |
5 | + <!-- <span class="glyphicon glyphicon-share-alt" aria-hidden="true"></span> --> | |
6 | + <span class="glyphicon glyphicon-arrow-left" aria-hidden="true"></span> | |
7 | + Voltar | |
8 | + </button> | |
9 | + </div> | |
10 | + <div class="navbar-left" ng-if="vm.category"> | |
11 | + <button class="article-bar--item article-bar--category-button btn btn-link"> | |
12 | + <span class="icon" ng-class="'icon-tema-' + vm.category.slug"></span> | |
13 | + <span class="category-name">{{::vm.category.name}}</span> | |
14 | + </button> | |
15 | + </div> | |
16 | + <div class="navbar-right" ng-if="vm.categories"> | |
17 | + <label for="selectCategory" class="control-label sr-only" title="Selecione uma opção para acessar os programas do tema">Temas:</label> | |
18 | + <select id="selectCategory" name="selectCategory" class="article-bar--item form-control" ng-model="vm.currentCategory" ng-options="category.name for category in vm.categories track by category.slug"> | |
19 | + </select> | |
20 | + </div> | |
21 | + </div> | |
22 | + </div> | |
23 | +</div> | ... | ... |
... | ... | @@ -0,0 +1,52 @@ |
1 | +.article-bar { | |
2 | + position: relative; | |
3 | + background-color: #0042b1; | |
4 | + | |
5 | + .btn { | |
6 | + color: #fff; | |
7 | + font-weight: bold; | |
8 | + } | |
9 | + | |
10 | + &--item { | |
11 | + margin: 8px 0; | |
12 | + | |
13 | + @media (max-width: $screen-xs) { | |
14 | + margin: 8px; | |
15 | + } | |
16 | + | |
17 | + } | |
18 | + | |
19 | + &--category-button { | |
20 | + position: relative; | |
21 | + width: 125px; | |
22 | + text-align: right; | |
23 | + margin-left: 10px; | |
24 | + font-size: 24px; | |
25 | + line-height: 20px; | |
26 | + font-family: 'Open Sans'; | |
27 | + | |
28 | + .icon { | |
29 | + display: inline-block; | |
30 | + margin: -40px -35px -40px -50px; | |
31 | + transform: scale(.37); | |
32 | + } | |
33 | + } | |
34 | + | |
35 | + .navbar { | |
36 | + margin-bottom: 0; | |
37 | + } | |
38 | + | |
39 | + .navbar-right { | |
40 | + margin-right: 15px; | |
41 | + } | |
42 | + | |
43 | + @each $category, $color in $categories { | |
44 | + &.#{$category} { | |
45 | + background-color: $color; | |
46 | + } | |
47 | + } | |
48 | + | |
49 | + .contraste & { | |
50 | + background-color: #262626; | |
51 | + } | |
52 | +} | ... | ... |
... | ... | @@ -0,0 +1,84 @@ |
1 | +(function() { | |
2 | + 'use strict'; | |
3 | + | |
4 | + angular | |
5 | + .module('dialoga') | |
6 | + .directive('articleBox', articleBox); | |
7 | + | |
8 | + /** @ngInject */ | |
9 | + function articleBox($rootScope) { | |
10 | + | |
11 | + /** @ngInject */ | |
12 | + function ArticleBoxController(ArticleService, $scope, $state, Slug, $log) { | |
13 | + $log.debug('ArticleBoxController'); | |
14 | + | |
15 | + var vm = this; | |
16 | + vm.ArticleService = ArticleService; | |
17 | + vm.$scope = $scope; | |
18 | + vm.$state = $state; | |
19 | + vm.Slug = Slug; | |
20 | + vm.$log = $log; | |
21 | + | |
22 | + vm.init(); | |
23 | + } | |
24 | + | |
25 | + ArticleBoxController.prototype.init = function () { | |
26 | + var vm = this; | |
27 | + | |
28 | + if(!vm.article.slug){ | |
29 | + vm.article.slug = vm.Slug.slugify(vm.article.title); | |
30 | + } | |
31 | + | |
32 | + if(!vm.category){ | |
33 | + vm.category = vm.article.categories[0]; | |
34 | + } | |
35 | + | |
36 | + if(!vm.banner){ | |
37 | + vm.banner = { | |
38 | + src: $rootScope.basePath + vm.article.image.url, | |
39 | + alt: 'Imagem de destaque do conteúdo' | |
40 | + }; | |
41 | + } | |
42 | + | |
43 | + // if(vm.article.color && !vm.article.bgColor){ | |
44 | + // // 15% more darker | |
45 | + // vm.article.colorDarker = window.ColorLuminance(vm.article.color, 0.15); | |
46 | + // } | |
47 | + }; | |
48 | + | |
49 | + ArticleBoxController.prototype.showContent = function () { | |
50 | + var vm = this; | |
51 | + | |
52 | + vm.$state.go('programa-conheca', { | |
53 | + slug: vm.article.slug | |
54 | + }, { | |
55 | + location: true | |
56 | + }); | |
57 | + }; | |
58 | + | |
59 | + ArticleBoxController.prototype.showPreview = function () { | |
60 | + var vm = this; | |
61 | + | |
62 | + vm.$state.go('programa', { | |
63 | + slug: vm.article.slug | |
64 | + }, { | |
65 | + location: true | |
66 | + }); | |
67 | + }; | |
68 | + | |
69 | + var directive = { | |
70 | + restrict: 'E', | |
71 | + templateUrl: 'app/components/article-box/article-box.html', | |
72 | + scope: { | |
73 | + article: '=' | |
74 | + }, | |
75 | + controller: ArticleBoxController, | |
76 | + controllerAs: 'vm', | |
77 | + bindToController: true | |
78 | + }; | |
79 | + | |
80 | + | |
81 | + return directive; | |
82 | + } | |
83 | + | |
84 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,18 @@ |
1 | +<article class="article-box" ng-click="vm.showPreview()" ng-class="vm.category.slug"> | |
2 | + <div> | |
3 | + <h2 class="article-box--category">{{vm.category.name}}</h2> | |
4 | + <div class="article-box--image-wrapper"> | |
5 | + <!-- <img class="article-box--image img-responsive" ng-src="{{vm.banner.src}}" alt="{{vm.banner.alt}}" /> --> | |
6 | + <div class="article-box--image" ng-style="{'background-image':'url( {{vm.banner.src}} )'}"></div> | |
7 | + </div> | |
8 | + <div class="article-box--title"> | |
9 | + <h1>{{::vm.article.title}}</h1> | |
10 | + </div> | |
11 | + <div class="article-box--abstract" ng-bind-html="vm.article.abstract"></div> | |
12 | + <div class="button--themed"> | |
13 | + <button class="btn btn-block"> | |
14 | + Participe | |
15 | + </button> | |
16 | + </div> | |
17 | + </div> | |
18 | +</article> | ... | ... |
... | ... | @@ -0,0 +1,146 @@ |
1 | +$article-box-space: 20px; | |
2 | + | |
3 | +.article-box { | |
4 | + cursor: pointer; | |
5 | + background-color: #fff; | |
6 | + margin-top: $article-box-space; | |
7 | + margin-bottom: $article-box-space; | |
8 | + border-radius: 3px; | |
9 | + overflow: hidden; | |
10 | + | |
11 | + .contraste & { | |
12 | + color: #fff; | |
13 | + background-color: #262626; | |
14 | + } | |
15 | + | |
16 | + &--category { | |
17 | + font-size: 14px; | |
18 | + font-weight: bold; | |
19 | + text-transform: uppercase; | |
20 | + line-height: 22px; | |
21 | + display: block; | |
22 | + height: 30px; | |
23 | + margin: 0; | |
24 | + padding: 5px $article-box-space; | |
25 | + color: #ffffff; | |
26 | + | |
27 | + @each $category, $color in $categories { | |
28 | + .#{$category} & { | |
29 | + background-color: $color; | |
30 | + } | |
31 | + } | |
32 | + | |
33 | + .contraste & { | |
34 | + background-color: #262626; | |
35 | + } | |
36 | + } | |
37 | + | |
38 | + &--title { | |
39 | + | |
40 | + padding: 0 $article-box-space; | |
41 | + | |
42 | + h1 { | |
43 | + font-size: 18px; | |
44 | + font-weight: bold; | |
45 | + margin: 0 0 $article-box-space 0; | |
46 | + display: table-cell; | |
47 | + vertical-align: middle; | |
48 | + | |
49 | + // Altura das linhas do abstract | |
50 | + $hLine: 20px; | |
51 | + // default | |
52 | + height: $hLine * 2; | |
53 | + | |
54 | + @media (max-width: $screen-xs) { | |
55 | + // height: $hLine * 3; | |
56 | + height: auto; | |
57 | + } | |
58 | + | |
59 | + @media (min-width: $screen-xs + 1) { | |
60 | + // height: $hLine * 2; | |
61 | + height: auto; | |
62 | + } | |
63 | + | |
64 | + @media (min-width: $screen-sm + 1) { | |
65 | + height: $hLine * 2; | |
66 | + } | |
67 | + | |
68 | + @media (min-width: $screen-md + 1) { | |
69 | + height: $hLine * 2; | |
70 | + } | |
71 | + } | |
72 | + } | |
73 | + | |
74 | + &--abstract { | |
75 | + padding: 0 $article-box-space; | |
76 | + display: table-cell; | |
77 | + vertical-align: middle; | |
78 | + | |
79 | + // Altura das linhas do abstract | |
80 | + $pLine: 20px; | |
81 | + // 1 linha: 19px -> 20 | |
82 | + // 2 linhas: 38px -> 40 | |
83 | + // 3 linhas: 57px -> 60 | |
84 | + // 4 linhas: 76px -> 80 | |
85 | + | |
86 | + height: $pLine * 2; // default | |
87 | + | |
88 | + @media (max-width: $screen-xs) { | |
89 | + // height: $pLine * 4; | |
90 | + height: auto; | |
91 | + } | |
92 | + | |
93 | + @media (min-width: $screen-xs + 1) { | |
94 | + // height: $pLine * 3; | |
95 | + height: auto; | |
96 | + } | |
97 | + | |
98 | + @media (min-width: $screen-sm + 1) { | |
99 | + height: $pLine * 4; | |
100 | + } | |
101 | + | |
102 | + @media (min-width: $screen-md + 1) { | |
103 | + height: $pLine * 3; | |
104 | + } | |
105 | + | |
106 | + p { margin: 0; } | |
107 | + } | |
108 | + | |
109 | + &--image-wrapper { | |
110 | + position: relative; | |
111 | + // width: 100%; | |
112 | + // width: 370px; | |
113 | + // height: 170px; | |
114 | + | |
115 | + overflow: hidden; | |
116 | + // text-align: center; | |
117 | + min-height: 170px; | |
118 | + } | |
119 | + | |
120 | + &--image { | |
121 | + min-height: 170px; | |
122 | + background-position: center; | |
123 | + background-size: cover; | |
124 | + background-repeat: no-repeat; | |
125 | + | |
126 | + -webkit-transition: all $time ease-in-out; | |
127 | + -moz-transition: all $time ease-in-out; | |
128 | + -o-transition: all $time ease-in-out; | |
129 | + transition: all $time ease-in-out; | |
130 | + } | |
131 | + | |
132 | + &:hover { | |
133 | + background-color: #d9d9d9; | |
134 | + | |
135 | + .article-box--image { | |
136 | + -webkit-transform: scale($scale); /* prefixo para browsers webkit */ | |
137 | + -moz-transform: scale($scale); /* prefixo para browsers gecko */ | |
138 | + -o-transform: scale($scale); /* prefixo para opera */ | |
139 | + transform: scale($scale); | |
140 | + } | |
141 | + | |
142 | + .contraste & { | |
143 | + background-color: #262626; | |
144 | + } | |
145 | + } | |
146 | +} | ... | ... |
src/app/components/article-content/article-content.directive.js
0 → 100644
src/app/components/article-grid/article-grid.directive.js
0 → 100644
... | ... | @@ -0,0 +1,322 @@ |
1 | +(function() { | |
2 | + 'use strict'; | |
3 | + | |
4 | + angular | |
5 | + .module('dialoga') | |
6 | + .directive('articleGrid', articleGrid); | |
7 | + | |
8 | + /** @ngInject */ | |
9 | + function articleGrid() { | |
10 | + | |
11 | + /** @ngInject */ | |
12 | + function ArticleGridController($scope, $rootScope, $element, ArticleService, $location, $filter, $log) { | |
13 | + $log.debug('ArticleGridController'); | |
14 | + | |
15 | + // alias | |
16 | + var vm = this; | |
17 | + | |
18 | + // dependencies | |
19 | + vm.$scope = $scope; | |
20 | + vm.$rootScope = $rootScope; | |
21 | + vm.$element = $element; | |
22 | + vm.ArticleService = ArticleService; | |
23 | + vm.$location = $location; | |
24 | + vm.$filter = $filter; | |
25 | + vm.$log = $log; | |
26 | + vm.defaultLimit = 6; | |
27 | + | |
28 | + // initialization | |
29 | + vm.init(); | |
30 | + } | |
31 | + | |
32 | + ArticleGridController.prototype.init = function() { | |
33 | + var vm = this; | |
34 | + | |
35 | + vm.ArticleService.getPrograms(function(programs){ | |
36 | + vm.articles = programs; | |
37 | + }); | |
38 | + | |
39 | + vm.ArticleService.getCategories(function(categories){ | |
40 | + vm.categories = categories; | |
41 | + }); | |
42 | + | |
43 | + vm.orderCriteries = [ | |
44 | + { label: 'Título', name: 'titulo' }, | |
45 | + { label: 'Tema', name: 'tema' }, | |
46 | + { label: 'Aleatório', name: 'aleatorio' } | |
47 | + ]; | |
48 | + | |
49 | + vm.filtredArticleList = vm.getFiltredArticles(); | |
50 | + vm.search = vm.$location.search(); | |
51 | + | |
52 | + // Add initial values for the filter | |
53 | + vm.query = (vm.search && vm.search.filtro) ? vm.search.filtro : null; | |
54 | + vm.limitTo = (vm.search && vm.search.limite) ? parseInt(vm.search.limite, 10) : vm.defaultLimit; | |
55 | + vm.orderCriteria = (vm.search && vm.search.ordem) ? { name: vm.search.ordem } : null; | |
56 | + vm.reverse = (vm.search && vm.search.reverso) ? true : false; | |
57 | + | |
58 | + // vm.selectedCategory = (vm.search && vm.search.tema) ? vm.getCategoryBySlug(vm.search.tema) : null; | |
59 | + if (vm.search && vm.search.tema) { | |
60 | + var slug = vm.search.tema; | |
61 | + vm.ArticleService.getCategoryBySlug(slug, function(category){ | |
62 | + vm.selectedCategory = category; | |
63 | + }, function(error){ | |
64 | + vm.$log.error('Error when try to "getCategoryBySlug"', error); | |
65 | + }); | |
66 | + } | |
67 | + | |
68 | + if (!angular.equals({}, vm.search)) { | |
69 | + var $el = vm.$element; | |
70 | + angular.element('body').animate({scrollTop: $el.offset().top}, 'slow'); | |
71 | + } | |
72 | + | |
73 | + // update window location params | |
74 | + vm.$scope.$on('change-selectedCategory', function(event, selectedCategory){ | |
75 | + vm.selectedCategory = selectedCategory; | |
76 | + }); | |
77 | + | |
78 | + vm.$scope.$watch('vm.query', function(newValue/*, oldValue*/) { | |
79 | + vm.search.filtro = newValue ? newValue : null; | |
80 | + vm.$location.search('filtro', vm.search.filtro); | |
81 | + if(vm.search.filtro){ | |
82 | + vm.limitTo = vm.articles.length; | |
83 | + }else{ | |
84 | + vm.limitTo = vm.defaultLimit; | |
85 | + } | |
86 | + vm.filtredArticleList = vm.getFiltredArticles(); | |
87 | + }); | |
88 | + | |
89 | + vm.$scope.$watch('vm.limitTo', function(newValue/*, oldValue*/) { | |
90 | + vm.search.limite = (newValue && newValue !== vm.defaultLimit) ? newValue : null; | |
91 | + vm.$location.search('limite', vm.search.limite); | |
92 | + vm.filtredArticleList = vm.getFiltredArticles(); | |
93 | + }); | |
94 | + | |
95 | + vm.$scope.$watch('vm.selectedCategory', function(newValue/*, oldValue*/) { | |
96 | + vm.search.tema = newValue ? newValue.slug : null; | |
97 | + vm.$location.search('tema', vm.search.tema); | |
98 | + if(vm.search.tema){ | |
99 | + vm.limitTo = vm.articles.length; | |
100 | + }else{ | |
101 | + vm.limitTo = vm.defaultLimit; | |
102 | + } | |
103 | + vm.filtredArticleList = vm.getFiltredArticles(); | |
104 | + }); | |
105 | + | |
106 | + vm.$scope.$watch('vm.orderCriteria', function(newValue/*, oldValue*/) { | |
107 | + vm.search.ordem = (newValue && newValue.name) ? newValue.name : null; | |
108 | + vm.$location.search('ordem', vm.search.ordem); | |
109 | + vm.filtredArticleList = vm.getFiltredArticles(); | |
110 | + }); | |
111 | + | |
112 | + vm.$scope.$watch('vm.reverse', function(newValue/*, oldValue*/) { | |
113 | + vm.search.reverso = newValue ? newValue : null; | |
114 | + vm.$location.search('reverso', vm.search.reverso); | |
115 | + vm.filtredArticleList = vm.getFiltredArticles(); | |
116 | + }); | |
117 | + | |
118 | + }; | |
119 | + | |
120 | + ArticleGridController.prototype.resetFilterValues = function() { | |
121 | + var vm = this; | |
122 | + | |
123 | + vm.query = null; | |
124 | + vm.limitTo = vm.defaultLimit; | |
125 | + vm.selectedCategory = null; | |
126 | + vm.orderCriteria = null; | |
127 | + }; | |
128 | + | |
129 | + ArticleGridController.prototype.getIconClasses = function(category) { | |
130 | + var vm = this; | |
131 | + | |
132 | + vm.$log.debug('[TODO] getIconClasses of category:', category); | |
133 | + return 'glyphicon glyphicon-exclamation-sign'; | |
134 | + }; | |
135 | + | |
136 | + ArticleGridController.prototype.getCategoryBySlug = function(categorySlug) { | |
137 | + var vm = this; | |
138 | + var result = null; | |
139 | + | |
140 | + angular.forEach(vm.categories, function(value/*, key*/) { | |
141 | + if (value.slug === categorySlug) { | |
142 | + result = value; | |
143 | + } | |
144 | + }); | |
145 | + | |
146 | + return result; | |
147 | + }; | |
148 | + | |
149 | + ArticleGridController.prototype.showAll = function($event) { | |
150 | + var vm = this; | |
151 | + | |
152 | + $event.stopPropagation(); | |
153 | + | |
154 | + vm.resetFilterValues(); | |
155 | + vm.limitTo = vm.articles.length; | |
156 | + }; | |
157 | + | |
158 | + ArticleGridController.prototype.getFiltredArticles = function() { | |
159 | + var vm = this; | |
160 | + | |
161 | + if(!vm.articles){ | |
162 | + vm.$log.warn('No articles loaded yet. Abort.'); | |
163 | + return null; | |
164 | + } | |
165 | + | |
166 | + var input = vm.articles; | |
167 | + var output = input; | |
168 | + var query = vm.query; | |
169 | + var selectedCategory = vm.selectedCategory; | |
170 | + var orderCriteria = vm.orderCriteria ? vm.orderCriteria : { name : 'aleatorio'}; | |
171 | + var filter = vm.$filter('filter'); | |
172 | + var orderBy = vm.$filter('orderBy'); | |
173 | + var limitTo = vm.$filter('limitTo'); | |
174 | + var limit = vm.limitTo ? vm.limitTo : 4; | |
175 | + | |
176 | + if (selectedCategory) { | |
177 | + output = _filterByCategory(output, selectedCategory); | |
178 | + } | |
179 | + | |
180 | + if (query) { | |
181 | + output = filter(output, query, false); | |
182 | + } | |
183 | + | |
184 | + switch (orderCriteria.name) { | |
185 | + case 'titulo': | |
186 | + output = orderBy(output, 'title', vm.reverse); | |
187 | + break; | |
188 | + case 'tema': | |
189 | + output = orderBy(output, 'categories[0].name', vm.reverse); | |
190 | + break; | |
191 | + case 'more_participants': | |
192 | + vm.$log.info('Criteria not handled yet: ', orderCriteria); | |
193 | + break; | |
194 | + case 'aleatorio': | |
195 | + // shuffling | |
196 | + // if (!vm._isShuffled){ | |
197 | + output = vm.filterShuffle(output); | |
198 | + // vm._isShuffled = true; | |
199 | + // } | |
200 | + | |
201 | + if (vm.reverse) { | |
202 | + output = output.slice().reverse(); | |
203 | + } | |
204 | + | |
205 | + break; | |
206 | + default: | |
207 | + vm.$log.warn('Criteria not matched: ', orderCriteria); | |
208 | + break; | |
209 | + } | |
210 | + | |
211 | + output = limitTo(output, limit); | |
212 | + | |
213 | + return output; | |
214 | + }; | |
215 | + | |
216 | + ArticleGridController.prototype.filterShuffle = function(input) { | |
217 | + var result = []; | |
218 | + var resultByCategory = {}; | |
219 | + | |
220 | + // divide by categories | |
221 | + for (var i = 0; i < input.length; i++) { | |
222 | + var program = input[i]; | |
223 | + var categorySlug = program.categories[0].slug; | |
224 | + | |
225 | + if (!resultByCategory[categorySlug]) { | |
226 | + resultByCategory[categorySlug] = []; | |
227 | + } | |
228 | + | |
229 | + resultByCategory[categorySlug].push(program); | |
230 | + } | |
231 | + | |
232 | + // shuffle each array | |
233 | + var prop = null; | |
234 | + var categoryWithPrograms = null; | |
235 | + for (prop in resultByCategory) { | |
236 | + if (resultByCategory.hasOwnProperty(prop)) { | |
237 | + categoryWithPrograms = resultByCategory[prop]; | |
238 | + resultByCategory[prop] = shuffle(categoryWithPrograms); | |
239 | + } | |
240 | + } | |
241 | + | |
242 | + // Concat all into result array | |
243 | + // > while has program at Lists on resultByCategory | |
244 | + var hasProgram = true; | |
245 | + while (hasProgram) { | |
246 | + | |
247 | + var foundProgram = false; | |
248 | + // each categoryList with array of program | |
249 | + prop = null; | |
250 | + categoryWithPrograms = null; | |
251 | + for (prop in resultByCategory) { | |
252 | + | |
253 | + if (resultByCategory.hasOwnProperty(prop)) { | |
254 | + categoryWithPrograms = resultByCategory[prop]; | |
255 | + | |
256 | + if (categoryWithPrograms.length > 0) { | |
257 | + var pivotProgram = categoryWithPrograms.pop(); | |
258 | + result.push(pivotProgram); | |
259 | + foundProgram = true; | |
260 | + } | |
261 | + } | |
262 | + } | |
263 | + | |
264 | + if (!foundProgram) { | |
265 | + hasProgram = false; | |
266 | + } | |
267 | + } | |
268 | + | |
269 | + return result; | |
270 | + }; | |
271 | + | |
272 | + var directive = { | |
273 | + restrict: 'E', | |
274 | + templateUrl: 'app/components/article-grid/article-grid.html', | |
275 | + controller: ArticleGridController, | |
276 | + controllerAs: 'vm', | |
277 | + bindToController: true | |
278 | + }; | |
279 | + | |
280 | + return directive; | |
281 | + } | |
282 | + | |
283 | + function _filterByCategory (input, category) { | |
284 | + input = input || []; | |
285 | + | |
286 | + if (!category) { | |
287 | + // no filter | |
288 | + return input; | |
289 | + } | |
290 | + | |
291 | + var out = []; | |
292 | + for (var i = 0; i < input.length; i++) { | |
293 | + var program = input[i]; | |
294 | + if (program.categories[0].slug === category.slug) { | |
295 | + out.push(program); | |
296 | + } | |
297 | + } | |
298 | + | |
299 | + return out; | |
300 | + } | |
301 | + | |
302 | + // -> Fisher–Yates shuffle algorithm | |
303 | + function shuffle (array) { | |
304 | + var currentIndex = array.length, temporaryValue, randomIndex ; | |
305 | + | |
306 | + // While there remain elements to shuffle... | |
307 | + while (0 !== currentIndex) { | |
308 | + | |
309 | + // Pick a remaining element... | |
310 | + randomIndex = Math.floor(Math.random() * currentIndex); | |
311 | + currentIndex -= 1; | |
312 | + | |
313 | + // And swap it with the current element. | |
314 | + temporaryValue = array[currentIndex]; | |
315 | + array[currentIndex] = array[randomIndex]; | |
316 | + array[randomIndex] = temporaryValue; | |
317 | + } | |
318 | + | |
319 | + return array; | |
320 | + } | |
321 | + | |
322 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,50 @@ |
1 | +<article class="article-grid"> | |
2 | + <header class="header"> | |
3 | + <h2>Conheça os programas <span class="small">({{vm.filtredArticleList.length}}/{{vm.articles.length}})</span></h2> | |
4 | + <button type="button" class="btn btn-link" ng-click="vm.showAll($event)"> | |
5 | + <span class="glyphicon glyphicon-chevron-right"></span> Ver todos os {{vm.articles.length}} programas | |
6 | + </button> | |
7 | + </header> | |
8 | + <div> | |
9 | + <div class="col-sm-12"> | |
10 | + <aside class="form-inline"> | |
11 | + <div class="row"> | |
12 | + <div class="col-xs-6 col-sm-7 col-md-9"> | |
13 | + <label for="articleQueryFilter" class="control-label sr-only">Filtrar programas:</label> | |
14 | + <input id="articleQueryFilter" type="search" class="form-control" ng-model="vm.query" placeholder="Filtrar programas" aria-label="Filtrar programas" > | |
15 | + </div> | |
16 | + | |
17 | + <!-- <label for="selectCategoryFilter" class="control-label sr-only">Filtrar por tema:</label> | |
18 | + <select id="selectCategoryFilter" name="selectCategoryFilter" class="form-control" ng-model="vm.categoryFilter" ng-options="category.name for category in vm.categories track by category.slug"> | |
19 | + <option value="">-- Filtrar por tema --</option> | |
20 | + </select> --> | |
21 | + | |
22 | + <div class="col-xs-6 col-sm-5 col-md-3"> | |
23 | + <label for="articleOrderByFilter" class="control-label sr-only">Ordernar por:</label> | |
24 | + <select id="articleOrderByFilter" name="articleOrderByFilter" class="form-control pull-right" ng-model="vm.orderCriteria" ng-options="orderCriteria.label for orderCriteria in vm.orderCriteries"> | |
25 | + <option value="">-- Ordernar por: --</option> | |
26 | + </select> | |
27 | + </div> | |
28 | + <!-- <div class="checkbox"> | |
29 | + <label> | |
30 | + <input type="checkbox" ng-model="vm.reverse"> | |
31 | + Reverso | |
32 | + </label> | |
33 | + </div> --> | |
34 | + | |
35 | + <!-- <input id="articleLimitFilter" type="number" class="form-control input-sm" size="4" step="2" ng-model="vm.limitTo" aria-label="Limitar" > | |
36 | + <label for="articleLimitFilter" class="control-label">Limite</label> --> | |
37 | + | |
38 | + </div> | |
39 | + </aside> | |
40 | + </div> | |
41 | + | |
42 | + <div ng-repeat="article in vm.filtredArticleList as results"> | |
43 | + <article-box article="article" class="col-xs-12 col-sm-6"></article-box> | |
44 | + <div ng-if="$odd" class="clearfix"></div> | |
45 | + </div> | |
46 | + <div class="animate-repeat" ng-if="results.length == 0"> | |
47 | + Nenhum programa encontrado. | |
48 | + </div> | |
49 | + </div> | |
50 | +</article> | ... | ... |
... | ... | @@ -0,0 +1,20 @@ |
1 | +.article-grid { | |
2 | + .header { | |
3 | + position: relative; | |
4 | + height: 40px; | |
5 | + margin-bottom: 10px; | |
6 | + | |
7 | + button { | |
8 | + position: absolute; | |
9 | + right: 0; | |
10 | + top: 2px; | |
11 | + } | |
12 | + } | |
13 | + | |
14 | + .form-inline { | |
15 | + input, | |
16 | + select { | |
17 | + width: 100%; | |
18 | + } | |
19 | + } | |
20 | +} | ... | ... |
src/app/components/article-preview/article-preview.directive.js
0 → 100644
... | ... | @@ -0,0 +1,74 @@ |
1 | +(function() { | |
2 | + 'use strict'; | |
3 | + | |
4 | + angular | |
5 | + .module('dialoga') | |
6 | + .directive('articlePreview', articlePreview); | |
7 | + | |
8 | + /** @ngInject */ | |
9 | + function articlePreview($rootScope) { | |
10 | + | |
11 | + /** @ngInject */ | |
12 | + function ArticlePreviewController(ArticleService, $scope, $state, Slug, $log) { | |
13 | + $log.debug('ArticlePreviewController'); | |
14 | + | |
15 | + var vm = this; | |
16 | + vm.ArticleService = ArticleService; | |
17 | + vm.$scope = $scope; | |
18 | + vm.$state = $state; | |
19 | + vm.Slug = Slug; | |
20 | + vm.$log = $log; | |
21 | + | |
22 | + vm.init(); | |
23 | + } | |
24 | + | |
25 | + ArticlePreviewController.prototype.init = function () { | |
26 | + var vm = this; | |
27 | + | |
28 | + if(!vm.article.slug){ | |
29 | + vm.article.slug = vm.Slug.slugify(vm.article.title); | |
30 | + } | |
31 | + | |
32 | + if(!vm.category){ | |
33 | + vm.category = vm.article.categories[0]; | |
34 | + } | |
35 | + | |
36 | + if(!vm.banner){ | |
37 | + vm.banner = { | |
38 | + src: $rootScope.basePath + vm.article.image.url, | |
39 | + alt: 'Imagem de destaque do programa' | |
40 | + }; | |
41 | + } | |
42 | + | |
43 | + // if(vm.article.color && !vm.article.bgColor){ | |
44 | + // // 15% more darker | |
45 | + // vm.article.colorDarker = window.ColorLuminance(vm.article.color, 0.15); | |
46 | + // } | |
47 | + }; | |
48 | + | |
49 | + ArticlePreviewController.prototype.showContent = function () { | |
50 | + var vm = this; | |
51 | + | |
52 | + vm.$state.go('conheca-o-programa', { | |
53 | + slug: vm.article.slug | |
54 | + }, { | |
55 | + location: true | |
56 | + }); | |
57 | + }; | |
58 | + | |
59 | + var directive = { | |
60 | + restrict: 'E', | |
61 | + templateUrl: 'app/components/article-preview/article-preview.html', | |
62 | + scope: { | |
63 | + article: '=' | |
64 | + }, | |
65 | + controller: ArticlePreviewController, | |
66 | + controllerAs: 'vm', | |
67 | + bindToController: true | |
68 | + }; | |
69 | + | |
70 | + | |
71 | + return directive; | |
72 | + } | |
73 | + | |
74 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,101 @@ |
1 | +<article class="article-preview" ng-class="vm.category.slug"> | |
2 | + <header class="article-banner"> | |
3 | + <img class="article-banner--image" ng-src="{{vm.banner.src}}" alt="{{vm.banner.alt}}"> | |
4 | + <div class="article-banner--strip"> | |
5 | + <h1 class="article-banner--title">{{::vm.article.title}}</h1> | |
6 | + <p class="article-banner--abstract" ng-bind-html="vm.article.abstract"></p> | |
7 | + </div> | |
8 | + </header> | |
9 | + | |
10 | + <section class="call-to-action--section"> | |
11 | + <div class="row show-content-row"> | |
12 | + <div class="col-xs-10 col-xs-offset-1 col-md-8 col-md-offset-2 col-lg-6 col-lg-offset-3"> | |
13 | + <div class="button--themed"> | |
14 | + <button class="btn btn-block" ng-click="vm.showContent()">Conheça o programa</button> | |
15 | + </div> | |
16 | + </div> | |
17 | + </div> | |
18 | + <div class="row proposal-row"> | |
19 | + <div class="row-height"> | |
20 | + <div class="col-md-6 col-height"> | |
21 | + <div class="inside-full-height"> | |
22 | + <div class="proposal-box make-proposal"> | |
23 | + <h2 class="proposal-box--title">Faça uma proposta</h2> | |
24 | + <p class="proposal-box--text">Qual a sua sugestão para melhorar este programa?</p> | |
25 | + <div class="row"> | |
26 | + <div class="col-xs-8 col-xs-offset-2"> | |
27 | + <div class="button--themed"> | |
28 | + <button class="btn btn-block" ng-click="vm.goSendProposal()"> | |
29 | + Envie sua proposta | |
30 | + </button> | |
31 | + </div> | |
32 | + </div> | |
33 | + </div> | |
34 | + </div> | |
35 | + </div> | |
36 | + </div> | |
37 | + <div class="col-md-6 col-height"> | |
38 | + <div class="inside-full-height"> | |
39 | + <div class="proposal-box support-proposal"> | |
40 | + <h2 class="proposal-box--title">Apoie outras propostas</h2> | |
41 | + <p class="proposal-box--text"> | |
42 | + Lorem qual a sua sugestão para melhorar este programa | |
43 | + Lorem qual a sua sugestão para melhorar este programa | |
44 | + Lorem qual a sua sugestão para melhorar este programa | |
45 | + Lorem qual a sua sugestão para melhorar este programa | |
46 | + Lorem qual a sua sugestão para melhorar este programa | |
47 | + Lorem qual a sua sugestão para melhorar este programa? | |
48 | + </p> | |
49 | + <div class="col-lg-12"> | |
50 | + <div class="col-xs-8 col-xs-offset-2 col-sm-10 col-sm-offset-1 col-md-8 col-md-offset-2"> | |
51 | + <div class="button--themed vote-buttons"> | |
52 | + <button class="btn btn-circle vote-buttons-up" ng-click="vm.vote(1)"> | |
53 | + <span class="sr-only">Eu <b>apoio</b> esta proposta.</span> | |
54 | + <span class="glyphicon glyphicon-ok" aria-hidden="true"></span> | |
55 | + </button> | |
56 | + | |
57 | + <button class="btn btn-circle vote-buttons-down" ng-click="vm.vote(-1)"> | |
58 | + <span class="sr-only">Eu <b>não apoio</b> esta proposta.</span> | |
59 | + <span class="glyphicon glyphicon-remove" aria-hidden="true"></span> | |
60 | + </button> | |
61 | + | |
62 | + <button class="btn btn-block vote-buttons-skip" ng-click="vm.vote(0)"> | |
63 | + <span class="sr-only">Pular esta proposta.</span> | |
64 | + <span class="icon" aria-hidden="true"></span> | |
65 | + Pular | |
66 | + </button> | |
67 | + </div> | |
68 | + </div> | |
69 | + </div> | |
70 | + <div class="col-lg-12"> | |
71 | + <div class="col-xs-8 col-xs-offset-2 col-sm-10 col-sm-offset-1 col-md-8 col-md-offset-2"> | |
72 | + <div class="text-center"> | |
73 | + <button class="btn btn-link" ng-click="vm.showResults()">Resultados</button> | |
74 | + </div> | |
75 | + </div> | |
76 | + </div> | |
77 | + <div class="col-md-12"> | |
78 | + <div class="col-xs-12"> | |
79 | + <div class="text-center"> | |
80 | + <span>Compartilhe esta proposta</span> | |
81 | + <social-share></social-share> | |
82 | + </div> | |
83 | + </div> | |
84 | + </div> | |
85 | + <div class="clearfix"></div> | |
86 | + </div> | |
87 | + </div> | |
88 | + </div> | |
89 | + </div> | |
90 | + </div> | |
91 | + <div class="talk-proposal row proposal-row"> | |
92 | + <div class="row-height"> | |
93 | + <div class="col-md-12 col-height"> | |
94 | + <div class=""> | |
95 | + <h2>Bate-papo virtual com ministr@s</h2> | |
96 | + </div> | |
97 | + </div> | |
98 | + </div> | |
99 | + </div> | |
100 | + </section> | |
101 | +</article> | ... | ... |
... | ... | @@ -0,0 +1,111 @@ |
1 | +.article-preview { | |
2 | + .article-banner { | |
3 | + position: relative; | |
4 | + } | |
5 | + | |
6 | + .article-banner--image { | |
7 | + width: 100%; | |
8 | + } | |
9 | + | |
10 | + .article-banner--strip { | |
11 | + color: #fff; | |
12 | + position: absolute; | |
13 | + bottom: 15%; | |
14 | + right: 0; | |
15 | + width: 50%; | |
16 | + text-align: center; | |
17 | + | |
18 | + @each $category, $color in $categories { | |
19 | + .#{$category} & { | |
20 | + background-color: $color; | |
21 | + } | |
22 | + } | |
23 | + | |
24 | + @media (max-width: $screen-sm){ | |
25 | + position: relative; | |
26 | + width: 100%; | |
27 | + } | |
28 | + } | |
29 | + | |
30 | + .article-banner--title { | |
31 | + font-size: 32px; | |
32 | + text-transform: uppercase; | |
33 | + margin-top: 0; | |
34 | + padding-top: 20px; | |
35 | + } | |
36 | + .article-banner--title, | |
37 | + .article-banner--abstract { | |
38 | + font-weight: bold; | |
39 | + } | |
40 | + .article-banner--abstract { | |
41 | + padding-bottom: 10px; | |
42 | + } | |
43 | + | |
44 | + .show-content-row { | |
45 | + .button--themed { | |
46 | + .btn { | |
47 | + font-size: 38px; | |
48 | + | |
49 | + @media (max-width: $screen-sm){ | |
50 | + font-size: 20px; | |
51 | + } | |
52 | + } | |
53 | + } | |
54 | + } | |
55 | + | |
56 | + .talk-proposal { | |
57 | + margin-top: -20px; | |
58 | + } | |
59 | + | |
60 | + .proposal-box { | |
61 | + | |
62 | + // padding: 10px 20px; | |
63 | + | |
64 | + .proposal-box--title { | |
65 | + font-size: 38px; | |
66 | + font-weight: 400; | |
67 | + text-align: center; | |
68 | + | |
69 | + margin-bottom: 20px; | |
70 | + } | |
71 | + | |
72 | + .proposal-box--text { | |
73 | + font-size: 24px; | |
74 | + font-weight: 700; | |
75 | + line-height: 1.2; | |
76 | + margin-bottom: 20px; | |
77 | + } | |
78 | + | |
79 | + @each $category, $color in $categories { | |
80 | + .#{$category} & { | |
81 | + border-color: $color; | |
82 | + | |
83 | + .proposal-box--title { | |
84 | + color: $color; | |
85 | + } | |
86 | + } | |
87 | + } | |
88 | + } | |
89 | + | |
90 | + .row-height { | |
91 | + border-spacing: 20px; | |
92 | + } | |
93 | + | |
94 | + .col-height { | |
95 | + | |
96 | + border: 1px solid #000; | |
97 | + border-radius: 3px; | |
98 | + | |
99 | + @each $category, $color in $categories { | |
100 | + .#{$category} & { | |
101 | + border-color: $color; | |
102 | + } | |
103 | + } | |
104 | + | |
105 | + @media (max-width: $screen-sm){ | |
106 | + display: block; | |
107 | + border: none; | |
108 | + } | |
109 | + | |
110 | + } | |
111 | +} | ... | ... |
src/app/components/auth/auth.service.js
... | ... | @@ -8,7 +8,7 @@ |
8 | 8 | .factory('AuthInterceptor', AuthInterceptor); |
9 | 9 | |
10 | 10 | /** @ngInject */ |
11 | - function AuthService($http, $rootScope, Session, AUTH_EVENTS, api, $log) { | |
11 | + function AuthService($http, $rootScope, Session, AUTH_EVENTS, API, $log) { | |
12 | 12 | |
13 | 13 | var service = { |
14 | 14 | login: login, |
... | ... | @@ -21,7 +21,7 @@ |
21 | 21 | return service; |
22 | 22 | |
23 | 23 | function login (credentials) { |
24 | - var url = api.host + '/api/v1/login'; | |
24 | + var url = API.host + '/api/v1/login'; | |
25 | 25 | var encodedData = 'login=' + credentials.username + '&password=' + credentials.password; |
26 | 26 | |
27 | 27 | return $http | ... | ... |
src/app/components/category-list/category-list.directive.js
0 → 100644
... | ... | @@ -0,0 +1,77 @@ |
1 | +(function() { | |
2 | + 'use strict'; | |
3 | + | |
4 | + angular | |
5 | + .module('dialoga') | |
6 | + .directive('categoryList', categoryList); | |
7 | + | |
8 | + /** @ngInject */ | |
9 | + function categoryList() { | |
10 | + | |
11 | + /** @ngInject */ | |
12 | + function CategoryListController($rootScope, ArticleService, $location, $log) { | |
13 | + $log.debug('CategoryListController'); | |
14 | + | |
15 | + // alias | |
16 | + var vm = this; | |
17 | + | |
18 | + // dependencies | |
19 | + vm.$rootScope = $rootScope; | |
20 | + vm.ArticleService = ArticleService; | |
21 | + vm.$location = $location; | |
22 | + vm.$log = $log; | |
23 | + vm.defaultLimit = 6; | |
24 | + | |
25 | + // initialization | |
26 | + vm.init(); | |
27 | + } | |
28 | + | |
29 | + CategoryListController.prototype.init = function() { | |
30 | + var vm = this; | |
31 | + | |
32 | + vm.selectedCategory = null; | |
33 | + vm.ArticleService.getCategories(function(categories){ | |
34 | + vm.categories = categories; | |
35 | + | |
36 | + }); | |
37 | + | |
38 | + vm.search = vm.$location.search(); | |
39 | + if (vm.search && vm.search.tema) { | |
40 | + var slug = vm.search.tema; | |
41 | + vm.ArticleService.getCategoryBySlug(slug, function(category){ | |
42 | + vm.selectedCategory = category; | |
43 | + }, function(error){ | |
44 | + vm.$log.error('Error when try to "getCategoryBySlug"', error); | |
45 | + }); | |
46 | + } | |
47 | + }; | |
48 | + | |
49 | + CategoryListController.prototype.selectCategory = function(category, $event) { | |
50 | + var vm = this; | |
51 | + | |
52 | + // prevent glitch | |
53 | + $event.stopPropagation(); | |
54 | + | |
55 | + if (category !== vm.selectedCategory) { | |
56 | + // selected new filter | |
57 | + vm.selectedCategory = category; | |
58 | + } else { | |
59 | + vm.selectedCategory = null; | |
60 | + } | |
61 | + | |
62 | + // send event to all controllers | |
63 | + vm.$rootScope.$broadcast('change-selectedCategory', vm.selectedCategory); | |
64 | + }; | |
65 | + | |
66 | + var directive = { | |
67 | + restrict: 'E', | |
68 | + templateUrl: 'app/components/category-list/category-list.html', | |
69 | + controller: CategoryListController, | |
70 | + controllerAs: 'categoryListCtrl', | |
71 | + bindToController: true | |
72 | + }; | |
73 | + | |
74 | + return directive; | |
75 | + } | |
76 | + | |
77 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,17 @@ |
1 | +<div class="category-list"> | |
2 | + <nav class="navigation"> | |
3 | + <h3 class="category-list--title"><b>Programas</b> por Tema</h3> | |
4 | + <div class="list-group category-list" ng-class="categoryListCtrl.selectedCategory.slug"> | |
5 | + <button type="button" class="list-group-item category-list--item" | |
6 | + ng-repeat="category in categoryListCtrl.categories" | |
7 | + ng-class="{active: categoryListCtrl.selectedCategory.slug === category.slug}" | |
8 | + ng-click="categoryListCtrl.selectCategory(category, $event)"> | |
9 | + | |
10 | + <span class="category-list--icon-circle" aria-hidden="true" ng-class="category.slug"></span> | |
11 | + <span class="category-list--icon icon" aria-hidden="true" ng-class="'icon-tema-' + category.slug"></span> | |
12 | + <span class="category-list--label">{{::category.name}}</span> | |
13 | + <span class="category-list--icon--right glyphicon glyphicon-chevron-right"></span> | |
14 | + </button> | |
15 | + </div> | |
16 | + </nav> | |
17 | +</div> | ... | ... |
... | ... | @@ -0,0 +1,111 @@ |
1 | +.category-list { | |
2 | + .category-list--title { | |
3 | + color: #ffffff; | |
4 | + font-size: 16px; | |
5 | + margin: 0; | |
6 | + padding: 20px; | |
7 | + background-color: #484848; | |
8 | + border-top-left-radius: 5px; | |
9 | + border-top-right-radius: 5px; | |
10 | + overflow: hidden; | |
11 | + } | |
12 | + | |
13 | + | |
14 | + .category-list--group { | |
15 | + } | |
16 | + | |
17 | + .category-list--item { | |
18 | + position: relative; | |
19 | + text-transform: uppercase; | |
20 | + font-weight: bold; | |
21 | + padding: 0; | |
22 | + height: 68px; | |
23 | + overflow: hidden; | |
24 | + } | |
25 | + | |
26 | + .category-list--label { | |
27 | + margin-left: 70px; | |
28 | + margin-right: 30px; | |
29 | + display: inline-block; | |
30 | + z-index: 99999; | |
31 | + } | |
32 | + | |
33 | + &--icon-circle { | |
34 | + width: 48px; | |
35 | + height: 48px; | |
36 | + position: absolute; | |
37 | + top: 10px; | |
38 | + left: 10px; | |
39 | + // border: 1px solid #fff; | |
40 | + border-radius: 48px; | |
41 | + | |
42 | + -webkit-transition: -webkit-transform 0.2s ease-in-out; | |
43 | + -moz-transition: -moz-transform 0.2s ease-in-out; | |
44 | + -o-transition: -o-transform 0.2s ease-in-out; | |
45 | + transition: transform 0.2s ease-in-out; | |
46 | + | |
47 | + // -webkit-transition: all 0.2s ease-in-out; | |
48 | + // -moz-transition: all 0.2s ease-in-out; | |
49 | + // -o-transition: all 0.2s ease-in-out; | |
50 | + // transition: all 0.2s ease-in-out; | |
51 | + | |
52 | + z-index: 0; | |
53 | + | |
54 | + .active & { | |
55 | + z-index: -1; | |
56 | + | |
57 | + @media (max-width: $screen-xs) { | |
58 | + transform: scale(20); | |
59 | + } | |
60 | + | |
61 | + @media (min-width: $screen-xs + 1) { | |
62 | + transform: scale(40); | |
63 | + } | |
64 | + | |
65 | + @media (min-width: $screen-sm + 1) { | |
66 | + transform: scale(20); | |
67 | + } | |
68 | + | |
69 | + // @media (min-width: $screen-md + 1) { | |
70 | + // transform: scale(20); | |
71 | + // } | |
72 | + } | |
73 | + | |
74 | + @each $category, $color in $categories { | |
75 | + &.#{$category} { | |
76 | + background-color: $color; | |
77 | + } | |
78 | + } | |
79 | + } | |
80 | + | |
81 | + .category-list--icon { | |
82 | + position: absolute; | |
83 | + top: -16px; | |
84 | + left: -14px; | |
85 | + transform: scale(0.35); | |
86 | + } | |
87 | + | |
88 | + .category-list--icon--right { | |
89 | + position: absolute; | |
90 | + right: 9px; | |
91 | + top: 50%; | |
92 | + margin-top: -9px; | |
93 | + transform: scale(1.4); | |
94 | + } | |
95 | + | |
96 | + .list-group-item.active, | |
97 | + .list-group-item.active:hover, | |
98 | + .list-group-item.active:focus { | |
99 | + background-color: #f5f5f5; | |
100 | + } | |
101 | + | |
102 | + // @each $category, $color in $categories { | |
103 | + // &.#{$category} { | |
104 | + // .list-group-item.active, | |
105 | + // .list-group-item.active:hover, | |
106 | + // .list-group-item.active:focus { | |
107 | + // background-color: $color; | |
108 | + // } | |
109 | + // } | |
110 | + // } | |
111 | +} | ... | ... |
... | ... | @@ -0,0 +1,53 @@ |
1 | +(function() { | |
2 | + 'use strict'; | |
3 | + | |
4 | + angular | |
5 | + .module('dialoga') | |
6 | + .directive('eventList', eventList); | |
7 | + | |
8 | + /** @ngInject */ | |
9 | + function eventList() { | |
10 | + /** @ngInject */ | |
11 | + function EventListController($scope, $rootScope, $state, $log) { | |
12 | + $log.debug('EventListController'); | |
13 | + | |
14 | + var vm = this; | |
15 | + | |
16 | + vm.$scope = $scope; | |
17 | + vm.$rootScope = $rootScope; | |
18 | + vm.$state = $state; | |
19 | + vm.$log = $log; | |
20 | + | |
21 | + vm.init(); | |
22 | + } | |
23 | + | |
24 | + EventListController.prototype.init = function () { | |
25 | + var vm = this; | |
26 | + | |
27 | + vm.eventList = []; | |
28 | + vm.isListVisible = false; | |
29 | + }; | |
30 | + | |
31 | + EventListController.prototype.toggleView = function () { | |
32 | + var vm = this; | |
33 | + vm.isListVisible = !vm.isListVisible; | |
34 | + }; | |
35 | + | |
36 | + EventListController.prototype.subscribe = function (data) { | |
37 | + var vm = this; | |
38 | + | |
39 | + vm.$log.debug('data', data); | |
40 | + }; | |
41 | + | |
42 | + var directive = { | |
43 | + restrict: 'E', | |
44 | + templateUrl: 'app/components/event-list/event-list.html', | |
45 | + controller: EventListController, | |
46 | + controllerAs: 'eventListCtrl', | |
47 | + bindToController: true | |
48 | + }; | |
49 | + | |
50 | + return directive; | |
51 | + | |
52 | + } | |
53 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,109 @@ |
1 | +<div class="event-list"> | |
2 | + <div class="event-tab--trigger" ng-show="!eventListCtrl.isListVisible" ng-click="eventListCtrl.toggleView()"> | |
3 | + <div class="event-tab--header"> | |
4 | + <div class="event-tab--icon"> | |
5 | + <span class="glyphicon glyphicon-calendar" aria-hidden="true"></span> | |
6 | + </div> | |
7 | + <div class="event-tab--title">Bate-Papo com ministr@s</div> | |
8 | + </div> | |
9 | + <button class="btn btn-link event-tab--button"> | |
10 | + <span class="event-tab--total-scheduled">18</span> | |
11 | + <span>bate-papos agendados</span> | |
12 | + <span class="glyphicon glyphicon-triangle-bottom" aria-hidden="true"></span> | |
13 | + </button> | |
14 | + </div> | |
15 | + | |
16 | + <div class="event-list--panel ng-hide" ng-show="eventListCtrl.isListVisible"> | |
17 | + <div class="event-list--header"> | |
18 | + <div class="event-list--icon"> | |
19 | + <div class="glyphicon glyphicon-calendar" aria-hidden="true"></div> | |
20 | + </div> | |
21 | + <h2 class="event-list--title">Bate-papo com ministr@s</h2> | |
22 | + <div class="event-list--minimize"> | |
23 | + <button type="button" class="btn btn-link" ng-click="eventListCtrl.toggleView()"> | |
24 | + <span>Minimizar</span> | |
25 | + <span class="glyphicon glyphicon-triangle-top" aria-hidden="true"></span> | |
26 | + </button> | |
27 | + </div> | |
28 | + </div> | |
29 | + <div class="event-list--table-wrapper"> | |
30 | + <div class="table-responsive"> | |
31 | + <table class="table event-list--table"> | |
32 | + <!-- <thead></thead> --> | |
33 | + <tbody> | |
34 | + <tr> | |
35 | + <td> | |
36 | + <span class="date">dd/mm/aaaa</span> | |
37 | + <span class="separator">-</span> | |
38 | + <span class="time">HH:mm</span> | |
39 | + <span class="separator">-</span> | |
40 | + <span class="description">Mais médicos, Segurança Nacional, SAMU</span> | |
41 | + <button type="button" class="btn" ng-click="eventListCtrl.subscribe('EVENT_ID')"> | |
42 | + Inscreva-se | |
43 | + <span class="sr-only">no bate-papo com (ministro) no dia (date) as (hh:mm) horas</span> | |
44 | + </button> | |
45 | + <span class="subscribers">123 inscritos</span> | |
46 | + </td> | |
47 | + </tr> | |
48 | + <tr> | |
49 | + <td> | |
50 | + <span class="date">dd/mm/aaaa</span> | |
51 | + <span class="separator">-</span> | |
52 | + <span class="time">HH:mm</span> | |
53 | + <span class="separator">-</span> | |
54 | + <span class="description">Mais médicos, Segurança Nacional, SAMU</span> | |
55 | + <button type="button" class="btn">Inscreva-se</button> | |
56 | + <span class="subscribers">123 inscritos</span> | |
57 | + </td> | |
58 | + </tr> | |
59 | + <tr> | |
60 | + <td> | |
61 | + <span class="date">dd/mm/aaaa</span> | |
62 | + <span class="separator">-</span> | |
63 | + <span class="time">HH:mm</span> | |
64 | + <span class="separator">-</span> | |
65 | + <span class="description">Mais médicos, Segurança Nacional, SAMU</span> | |
66 | + <button type="button" class="btn">Inscreva-se</button> | |
67 | + <span class="subscribers">123 inscritos</span> | |
68 | + </td> | |
69 | + </tr> | |
70 | + <tr> | |
71 | + <td> | |
72 | + <span class="date">dd/mm/aaaa</span> | |
73 | + <span class="separator">-</span> | |
74 | + <span class="time">HH:mm</span> | |
75 | + <span class="separator">-</span> | |
76 | + <span class="description">Mais médicos, Segurança Nacional, SAMU</span> | |
77 | + <button type="button" class="btn">Inscreva-se</button> | |
78 | + <span class="subscribers">123 inscritos</span> | |
79 | + </td> | |
80 | + </tr> | |
81 | + <tr> | |
82 | + <td> | |
83 | + <span class="date">dd/mm/aaaa</span> | |
84 | + <span class="separator">-</span> | |
85 | + <span class="time">HH:mm</span> | |
86 | + <span class="separator">-</span> | |
87 | + <span class="description">Mais médicos, Segurança Nacional, SAMU</span> | |
88 | + <button type="button" class="btn">Inscreva-se</button> | |
89 | + <span class="subscribers">123 inscritos</span> | |
90 | + </td> | |
91 | + </tr> | |
92 | + <tr> | |
93 | + <td> | |
94 | + <span class="date">dd/mm/aaaa</span> | |
95 | + <span class="separator">-</span> | |
96 | + <span class="time">HH:mm</span> | |
97 | + <span class="separator">-</span> | |
98 | + <span class="description">Mais médicos, Segurança Nacional, SAMU</span> | |
99 | + <button type="button" class="btn">Inscreva-se</button> | |
100 | + <span class="subscribers">123 inscritos</span> | |
101 | + </td> | |
102 | + </tr> | |
103 | + </tbody> | |
104 | + <!-- <tfooter></tfooter> --> | |
105 | + </table> | |
106 | + </div> | |
107 | + </div> | |
108 | + </div> | |
109 | +</div> | ... | ... |
... | ... | @@ -0,0 +1,82 @@ |
1 | +.event-list { | |
2 | + position: relative; | |
3 | + background-color: #eeeeee; | |
4 | + | |
5 | + .event-list--panel { | |
6 | + height: 310px; | |
7 | + border: 1px solid #333333; | |
8 | + padding: 20px; | |
9 | + margin: 20px 0; | |
10 | + line-height: 20px; | |
11 | + transition: .3s linear all; | |
12 | + | |
13 | + &.ng-hide { | |
14 | + height: 0px; | |
15 | + line-height: 0px; | |
16 | + } | |
17 | + | |
18 | + .event-list--header { | |
19 | + border-bottom: 1px solid #333333; | |
20 | + } | |
21 | + | |
22 | + .event-list--icon { | |
23 | + font-size: 25px; | |
24 | + display: inline-block; | |
25 | + } | |
26 | + | |
27 | + .event-list--title { | |
28 | + margin: 0 10px; | |
29 | + display: inline-block; | |
30 | + } | |
31 | + | |
32 | + .event-list--minimize { | |
33 | + display: inline-block; | |
34 | + float: right; | |
35 | + width: 100px; | |
36 | + } | |
37 | + } | |
38 | + | |
39 | + .event-tab--trigger { | |
40 | + $event-tab-height: 130px; | |
41 | + width: 150px; | |
42 | + height: $event-tab-height; | |
43 | + position: absolute; | |
44 | + right: 0; | |
45 | + top: $event-tab-height * (-1); | |
46 | + padding: 5px; | |
47 | + background-color: #eeeeee; | |
48 | + border: 1px solid #333333; | |
49 | + text-align: center; | |
50 | + line-height: 20px; | |
51 | + cursor: pointer; | |
52 | + transition: .3s linear all; | |
53 | + overflow: hidden; | |
54 | + z-index: 100; | |
55 | + | |
56 | + &.ng-hide { | |
57 | + height: 0px; | |
58 | + line-height: 0px; | |
59 | + top: -1px; | |
60 | + } | |
61 | + } | |
62 | + | |
63 | + .table-responsive { | |
64 | + height: 250px; | |
65 | + overflow-y: scroll; | |
66 | + } | |
67 | + | |
68 | + .event-tab--icon { | |
69 | + font-size: 25px; | |
70 | + } | |
71 | + .event-tab--title { | |
72 | + font-weight: bold; | |
73 | + } | |
74 | + | |
75 | + .event-tab--button { | |
76 | + font-size: 12px; | |
77 | + margin: 10px 0 0 0; | |
78 | + padding: 0; | |
79 | + width: 100%; | |
80 | + white-space: normal; | |
81 | + } | |
82 | +} | ... | ... |
src/app/components/navbar/navbar.directive.js
... | ... | @@ -11,7 +11,7 @@ |
11 | 11 | restrict: 'E', |
12 | 12 | templateUrl: 'app/components/navbar/navbar.html', |
13 | 13 | scope: { |
14 | - creationDate: '=' | |
14 | + creationDate: '=' | |
15 | 15 | }, |
16 | 16 | controller: NavbarController, |
17 | 17 | controllerAs: 'vm', |
... | ... | @@ -23,11 +23,15 @@ |
23 | 23 | /** @ngInject */ |
24 | 24 | function NavbarController($log) { |
25 | 25 | $log.debug('NavbarController'); |
26 | - // var vm = this; | |
27 | 26 | |
28 | - // "vm.creation" is avaible by directive option "bindToController: true" | |
29 | - // vm.relativeDate = moment(vm.creationDate).fromNow(); | |
27 | + var vm = this; | |
28 | + | |
29 | + vm.scrollTo = function(hash) { | |
30 | + var $el = angular.element('#' + hash); | |
31 | + angular.element('body').animate({scrollTop: $el.offset().top}, 'slow'); | |
32 | + }; | |
30 | 33 | } |
34 | + | |
31 | 35 | } |
32 | 36 | |
33 | 37 | })(); | ... | ... |
src/app/components/navbar/navbar.html
1 | -<nav class="navbar navbar-static-top"> | |
1 | +<nav id="navigation" class="header-navbar navbar navbar-static-top" role="navigation"> | |
2 | 2 | <div class="container-fluid"> |
3 | 3 | <div class="navbar-header"> |
4 | 4 | <button type="button" class="navbar-toggle collapsed" data-toggle="collapse" data-target="#navbar-collapse" aria-expanded="false"> |
5 | 5 | <span class="sr-only">Alternar menu de navegação</span> |
6 | - <span class="icon-bar"></span> | |
7 | - <span class="icon-bar"></span> | |
8 | - <span class="icon-bar"></span> | |
6 | + <span class="icon-bar" aria-hidden="true"></span> | |
7 | + <span class="icon-bar" aria-hidden="true"></span> | |
8 | + <span class="icon-bar" aria-hidden="true"></span> | |
9 | 9 | </button> |
10 | 10 | <a class="navbar-brand" ui-sref="inicio"> |
11 | 11 | <img src="/assets/images/logo.png" alt="Dialoga Brasil | O país fica melhor quando você participa" /> |
... | ... | @@ -16,7 +16,7 @@ |
16 | 16 | <div id="navbar-collapse" class="collapse navbar-collapse"> |
17 | 17 | <ul class="nav navbar-nav"> |
18 | 18 | <li><a ui-sref="sobre">Sobre</a></li> |
19 | - <li><a ui-sref="programas">Programas</a></li> | |
19 | + <li><a ui-sref="inicio({'#':'lista-de-programas'})" ng-click="vm.scrollTo('lista-de-programas')">Programas</a></li> | |
20 | 20 | <!-- <li><a ui-sref="ranking">Ranking</a></li> --> |
21 | 21 | <!-- <li><a ui-sref="duvidas">Dúvidas</a></li> --> |
22 | 22 | <!-- <li><a ui-sref="respostas">Respostas</a></li> --> | ... | ... |
src/app/components/navbar/navbar.scss
1 | -.navbar-brand { | |
2 | - height: auto; | |
3 | -} | |
1 | +.header-navbar { | |
4 | 2 | |
5 | -.navbar-nav > li > a { | |
6 | - padding-top: 30px; | |
7 | - padding-bottom: 30px; | |
8 | -} | |
3 | + .navbar-brand { | |
4 | + height: auto; | |
5 | + } | |
6 | + | |
7 | + .navbar-nav a { | |
8 | + padding-top: 30px; | |
9 | + padding-bottom: 30px; | |
10 | + text-transform: uppercase; | |
11 | + color: #03316f; | |
12 | + | |
13 | + -webkit-transition: all 0.2s ease-in-out; | |
14 | + -moz-transition: all 0.2s ease-in-out; | |
15 | + -o-transition: all 0.2s ease-in-out; | |
16 | + transition: all 0.2s ease-in-out; | |
17 | + | |
18 | + .contraste & { | |
19 | + color: #fff; | |
20 | + } | |
21 | + } | |
9 | 22 | |
10 | -.navbar-toggle .icon-bar { | |
11 | - background-color: #333; | |
23 | + .navbar-toggle .icon-bar { | |
24 | + background-color: #333; | |
25 | + } | |
12 | 26 | } | ... | ... |
src/app/components/programa/programa.directive.js
... | ... | @@ -1,73 +0,0 @@ |
1 | -(function() { | |
2 | - 'use strict'; | |
3 | - | |
4 | - angular | |
5 | - .module('dialoga') | |
6 | - .directive('programaBox', programaBox); | |
7 | - | |
8 | - /** @ngInject */ | |
9 | - function programaBox(api) { | |
10 | - | |
11 | - /** @ngInject */ | |
12 | - function ProgramaController($log) { | |
13 | - $log.debug('ProgramaController'); | |
14 | - | |
15 | - var vm = this; | |
16 | - vm.$log = $log; | |
17 | - | |
18 | - vm.init(); | |
19 | - } | |
20 | - | |
21 | - ProgramaController.prototype.init = function () { | |
22 | - | |
23 | - }; | |
24 | - | |
25 | - ProgramaController.prototype.getCategory = function () { | |
26 | - var vm = this; | |
27 | - | |
28 | - return vm.program.categories[0]; | |
29 | - }; | |
30 | - | |
31 | - ProgramaController.prototype.getCategoryName = function () { | |
32 | - return this.getCategory().name; | |
33 | - }; | |
34 | - | |
35 | - ProgramaController.prototype.getCategorySlug = function () { | |
36 | - return this.getCategory().slug; | |
37 | - }; | |
38 | - | |
39 | - ProgramaController.prototype.getImageUrl = function () { | |
40 | - var vm = this; | |
41 | - | |
42 | - return api.host + vm.program.image.url; | |
43 | - }; | |
44 | - | |
45 | - ProgramaController.prototype.getImageAlt = function () { | |
46 | - var vm = this; | |
47 | - | |
48 | - vm.$log.warn('image is not accessible.'); | |
49 | - return 'TODO: create image alt on server-side.'; | |
50 | - }; | |
51 | - | |
52 | - ProgramaController.prototype.showContent = function () { | |
53 | - var vm = this; | |
54 | - | |
55 | - vm.$log.debug('TODO: showContent()', vm.program); | |
56 | - }; | |
57 | - | |
58 | - var directive = { | |
59 | - restrict: 'E', | |
60 | - templateUrl: 'app/components/programa/programa.html', | |
61 | - scope: { | |
62 | - program: '=' | |
63 | - }, | |
64 | - controller: ProgramaController, | |
65 | - controllerAs: 'vm', | |
66 | - bindToController: true | |
67 | - }; | |
68 | - | |
69 | - | |
70 | - return directive; | |
71 | - } | |
72 | - | |
73 | -})(); |
src/app/components/programa/programa.html
... | ... | @@ -1,8 +0,0 @@ |
1 | -<article class="program-box {{::vm.getCategorySlug()}}" ng-if="vm.program" ng-click="vm.showContent()"> | |
2 | - <h2 class="category-name">{{::vm.getCategoryName()}}</h2> | |
3 | - <div class="image-wrapper"> | |
4 | - <img class="img-responsive" ng-src="{{::vm.getImageUrl()}}" alt="{{::vm.getImageAlt()}}" /> | |
5 | - </div> | |
6 | - <h1 class="program-title">{{::vm.program.title}}</h1> | |
7 | - <div class="program-abstract" ng-bind-html="vm.program.abstract"></div> | |
8 | -</article> |
src/app/components/programa/programa.scss
... | ... | @@ -1,39 +0,0 @@ |
1 | -// Variables | |
2 | -$scale: 1.1; | |
3 | -$time: .3s; | |
4 | - | |
5 | -// sandbox | |
6 | -.program-box { | |
7 | - cursor: pointer; | |
8 | - .category-name { | |
9 | - font-size: 14px; | |
10 | - font-weight: bold; | |
11 | - line-height: 30px; | |
12 | - display: block; | |
13 | - height: 30px; | |
14 | - margin-bottom: 0; | |
15 | - color: #ffffff; | |
16 | - background-color: #000000; | |
17 | - } | |
18 | - .image-wrapper { | |
19 | - position: relative; | |
20 | - // width: 100%; | |
21 | - // width: 370px; | |
22 | - // height: 170px; | |
23 | - | |
24 | - overflow: hidden; | |
25 | - text-align: center; | |
26 | - } | |
27 | - .img-responsive { | |
28 | - -webkit-transition: all $time ease-in-out; | |
29 | - -moz-transition: all $time ease-in-out; | |
30 | - -o-transition: all $time ease-in-out; | |
31 | - transition: all $time ease-in-out; | |
32 | - } | |
33 | - &:hover .img-responsive { | |
34 | - -webkit-transform: scale($scale); /* prefixo para browsers webkit */ | |
35 | - -moz-transform: scale($scale); /* prefixo para browsers gecko */ | |
36 | - -o-transform: scale($scale); /* prefixo para opera */ | |
37 | - transform: scale($scale); | |
38 | - } | |
39 | -} |
src/app/components/programas/programas.directive.js
... | ... | @@ -3,15 +3,13 @@ |
3 | 3 | |
4 | 4 | angular |
5 | 5 | .module('dialoga') |
6 | - .filter('filterByCategory', filterByCategory) | |
7 | - .filter('filterByCriteria', filterByCriteria) | |
8 | 6 | .directive('programaList', programaList); |
9 | 7 | |
10 | 8 | /** @ngInject */ |
11 | 9 | function programaList() { |
12 | 10 | |
13 | 11 | /** @ngInject */ |
14 | - function ProgramaListController($scope, $location, $log) { | |
12 | + function ProgramaListController($scope, $element, $location, $filter, $log) { | |
15 | 13 | $log.debug('ProgramaListController'); |
16 | 14 | |
17 | 15 | // alias |
... | ... | @@ -19,115 +17,248 @@ |
19 | 17 | |
20 | 18 | // dependencies |
21 | 19 | vm.$scope = $scope; |
20 | + vm.$element = $element; | |
22 | 21 | vm.$location = $location; |
22 | + vm.$filter = $filter; | |
23 | 23 | vm.$log = $log; |
24 | + vm.defaultLimit = 6; | |
24 | 25 | |
25 | 26 | // initialization |
26 | 27 | vm.init(); |
27 | 28 | } |
28 | 29 | |
29 | - ProgramaListController.prototype.init = function () { | |
30 | + ProgramaListController.prototype.init = function() { | |
30 | 31 | var vm = this; |
31 | 32 | |
32 | - if(!vm.article){ | |
33 | + if (!vm.article) { | |
33 | 34 | vm.$log.warn('no article to display. Tip: use a ng-if before use this directive'); |
34 | 35 | return; |
35 | 36 | } |
36 | 37 | |
37 | 38 | vm.categories = vm.article.categories; |
38 | 39 | vm.programs = vm.article.children; |
39 | - vm.filtredProgramList = []; | |
40 | 40 | vm.orderCriteries = [ |
41 | - { label: 'Título', name: 'title' }, | |
42 | - { label: 'Tema', name: 'category' } | |
43 | - // , { label: 'Mais participações', name: 'more_participants' } | |
41 | + { label: 'Título', name: 'titulo' }, | |
42 | + { label: 'Tema', name: 'tema' }, | |
43 | + { label: 'Aleatório', name: 'aleatorio' } | |
44 | 44 | ]; |
45 | 45 | |
46 | + vm.filtredProgramList = vm.getFiltredPrograms(); | |
46 | 47 | vm.search = vm.$location.search(); |
47 | 48 | |
48 | 49 | // Add initial values for the filter |
49 | 50 | vm.query = (vm.search && vm.search.filtro) ? vm.search.filtro : null; |
50 | - vm.limitTo = (vm.search && vm.search.limite) ? parseInt(vm.search.limite, 10) : 4; | |
51 | - vm.categoryFilter = (vm.search && vm.search.tema) ? vm.filterByCategorySlug(vm.search.tema) : null; | |
51 | + vm.limitTo = (vm.search && vm.search.limite) ? parseInt(vm.search.limite, 10) : vm.defaultLimit; | |
52 | + vm.categoryFilter = (vm.search && vm.search.tema) ? vm.getCategoryBySlug(vm.search.tema) : null; | |
53 | + vm.orderCriteria = (vm.search && vm.search.ordem) ? { name: vm.search.ordem } : null; | |
54 | + vm.reverse = (vm.search && vm.search.reverso) ? true : false; | |
55 | + | |
56 | + if (!angular.equals({}, vm.search)) { | |
57 | + var $el = vm.$element; | |
58 | + angular.element('body').animate({scrollTop: $el.offset().top}, 'slow'); | |
59 | + } | |
52 | 60 | |
53 | 61 | // update window location params |
54 | - vm.$scope.$watch('vm.query', function(newValue, oldValue){ | |
55 | - vm.search.filtro = newValue; | |
56 | - vm.$location.search(vm.search); | |
62 | + vm.$scope.$watch('vm.query', function(newValue/*, oldValue*/) { | |
63 | + vm.search.filtro = newValue ? newValue : null; | |
64 | + vm.$location.search('filtro', vm.search.filtro); | |
65 | + if(vm.search.filtro){ | |
66 | + vm.limitTo = vm.programs.length; | |
67 | + }else{ | |
68 | + vm.limitTo = vm.defaultLimit; | |
69 | + } | |
70 | + vm.filtredProgramList = vm.getFiltredPrograms(); | |
57 | 71 | }); |
58 | 72 | |
59 | - vm.$scope.$watch('vm.limitTo', function(newValue, oldValue){ | |
60 | - vm.search.limite = newValue; | |
61 | - vm.$location.search(vm.search); | |
73 | + vm.$scope.$watch('vm.limitTo', function(newValue/*, oldValue*/) { | |
74 | + vm.search.limite = (newValue && newValue !== vm.defaultLimit) ? newValue : null; | |
75 | + vm.$location.search('limite', vm.search.limite); | |
76 | + vm.filtredProgramList = vm.getFiltredPrograms(); | |
77 | + }); | |
78 | + | |
79 | + vm.$scope.$watch('vm.categoryFilter', function(newValue/*, oldValue*/) { | |
80 | + vm.search.tema = newValue ? newValue.slug : null; | |
81 | + vm.$location.search('tema', vm.search.tema); | |
82 | + if(vm.search.tema){ | |
83 | + vm.limitTo = vm.programs.length; | |
84 | + } | |
85 | + vm.filtredProgramList = vm.getFiltredPrograms(); | |
62 | 86 | }); |
63 | 87 | |
64 | - vm.$scope.$watch('vm.categoryFilter', function(newValue, oldValue){ | |
65 | - vm.search.tema = newValue ? newValue.slug : ''; | |
66 | - vm.$location.search(vm.search); | |
88 | + vm.$scope.$watch('vm.orderCriteria', function(newValue/*, oldValue*/) { | |
89 | + vm.search.ordem = (newValue && newValue.name) ? newValue.name : null; | |
90 | + vm.$location.search('ordem', vm.search.ordem); | |
91 | + vm.filtredProgramList = vm.getFiltredPrograms(); | |
92 | + }); | |
93 | + | |
94 | + vm.$scope.$watch('vm.reverse', function(newValue/*, oldValue*/) { | |
95 | + vm.search.reverso = newValue ? newValue : null; | |
96 | + vm.$location.search('reverso', vm.search.reverso); | |
97 | + vm.filtredProgramList = vm.getFiltredPrograms(); | |
67 | 98 | }); |
68 | 99 | |
69 | 100 | }; |
70 | 101 | |
71 | - ProgramaListController.prototype.resetFilterValues = function () { | |
102 | + ProgramaListController.prototype.resetFilterValues = function() { | |
72 | 103 | var vm = this; |
73 | 104 | |
74 | 105 | vm.query = null; |
75 | - vm.limitTo = 4; | |
106 | + vm.limitTo = vm.defaultLimit; | |
76 | 107 | vm.categoryFilter = null; |
108 | + vm.orderCriteria = null; | |
77 | 109 | }; |
78 | 110 | |
79 | - ProgramaListController.prototype.getIconClasses = function (category) { | |
111 | + ProgramaListController.prototype.getIconClasses = function(category) { | |
80 | 112 | var vm = this; |
81 | 113 | |
82 | 114 | vm.$log.debug('[TODO] getIconClasses of category:', category); |
83 | 115 | return 'glyphicon glyphicon-exclamation-sign'; |
84 | 116 | }; |
85 | 117 | |
86 | - ProgramaListController.prototype.filterByCategorySlug = function (categorySlug) { | |
118 | + ProgramaListController.prototype.getCategoryBySlug = function(categorySlug) { | |
87 | 119 | var vm = this; |
88 | 120 | var result = null; |
89 | 121 | |
90 | - angular.forEach(vm.categories, function (value, key){ | |
91 | - if(value.slug === categorySlug){ | |
122 | + angular.forEach(vm.categories, function(value/*, key*/) { | |
123 | + if (value.slug === categorySlug) { | |
92 | 124 | result = value; |
93 | 125 | } |
94 | - }) | |
126 | + }); | |
127 | + | |
95 | 128 | return result; |
96 | - } | |
129 | + }; | |
97 | 130 | |
98 | - ProgramaListController.prototype.filterByCategory = function (category, $event) { | |
131 | + ProgramaListController.prototype.filterByCategory = function(category, $event) { | |
99 | 132 | var vm = this; |
100 | 133 | |
101 | 134 | $event.stopPropagation(); |
102 | 135 | |
103 | - if(category !== vm.categoryFilter){ | |
136 | + if (category !== vm.categoryFilter) { | |
104 | 137 | |
105 | 138 | // selected new filter |
106 | 139 | vm.categoryFilter = category; |
107 | - }else{ | |
108 | - // already selected. Unselect. | |
109 | - vm.showAll(); | |
140 | + } else { | |
141 | + vm.categoryFilter = null; | |
110 | 142 | } |
111 | 143 | }; |
112 | 144 | |
113 | - ProgramaListController.prototype.showAll = function ($event) { | |
145 | + ProgramaListController.prototype.showAll = function($event) { | |
114 | 146 | var vm = this; |
115 | 147 | |
116 | 148 | $event.stopPropagation(); |
117 | 149 | |
118 | 150 | vm.resetFilterValues(); |
151 | + vm.limitTo = vm.programs.length; | |
152 | + }; | |
153 | + | |
154 | + ProgramaListController.prototype.getFiltredPrograms = function() { | |
155 | + var vm = this; | |
156 | + | |
157 | + var input = vm.programs; | |
158 | + var output = input; | |
159 | + var query = vm.query; | |
160 | + var categoryFilter = vm.categoryFilter; | |
161 | + var orderCriteria = vm.orderCriteria ? vm.orderCriteria : { name : 'aleatorio'}; | |
162 | + var filter = vm.$filter('filter'); | |
163 | + var orderBy = vm.$filter('orderBy'); | |
164 | + var limitTo = vm.$filter('limitTo'); | |
165 | + var limit = vm.limitTo ? vm.limitTo : 4; | |
166 | + | |
167 | + if (categoryFilter) { | |
168 | + output = _filterByCategory(output, categoryFilter); | |
169 | + } | |
170 | + | |
171 | + if (query) { | |
172 | + output = filter(output, query, false); | |
173 | + } | |
174 | + | |
175 | + switch (orderCriteria.name) { | |
176 | + case 'titulo': | |
177 | + output = orderBy(output, 'title', vm.reverse); | |
178 | + break; | |
179 | + case 'tema': | |
180 | + output = orderBy(output, 'categories[0].name', vm.reverse); | |
181 | + break; | |
182 | + case 'more_participants': | |
183 | + vm.$log.info('Criteria not handled yet: ', orderCriteria); | |
184 | + break; | |
185 | + case 'aleatorio': | |
186 | + // shuffling | |
187 | + // if (!vm._isShuffled){ | |
188 | + output = vm.filterShuffle(output); | |
189 | + // vm._isShuffled = true; | |
190 | + // } | |
191 | + | |
192 | + if (vm.reverse) { | |
193 | + output = output.slice().reverse(); | |
194 | + } | |
195 | + | |
196 | + break; | |
197 | + default: | |
198 | + vm.$log.warn('Criteria not matched: ', orderCriteria); | |
199 | + break; | |
200 | + } | |
201 | + | |
202 | + output = limitTo(output, limit); | |
203 | + | |
204 | + return output; | |
119 | 205 | }; |
120 | 206 | |
121 | - // function ProgramaListLinker (scope, element, attrs) { | |
207 | + ProgramaListController.prototype.filterShuffle = function(input) { | |
208 | + var result = []; | |
209 | + var resultByCategory = {}; | |
122 | 210 | |
123 | - // scope.$watch('article', function(newValue, oldValue){ | |
124 | - // if(!newValue){ | |
125 | - // return; | |
126 | - // } | |
127 | - // scope.vm.categories = scope.vm.article.categories; | |
128 | - // scope.vm.programs = scope.vm.article.children; | |
129 | - // }); | |
130 | - // } | |
211 | + // divide by categories | |
212 | + for (var i = 0; i < input.length; i++) { | |
213 | + var program = input[i]; | |
214 | + var categorySlug = program.categories[0].slug; | |
215 | + | |
216 | + if (!resultByCategory[categorySlug]) { | |
217 | + resultByCategory[categorySlug] = []; | |
218 | + } | |
219 | + | |
220 | + resultByCategory[categorySlug].push(program); | |
221 | + } | |
222 | + | |
223 | + // shuffle each array | |
224 | + var prop = null; | |
225 | + var categoryWithPrograms = null; | |
226 | + for (prop in resultByCategory) { | |
227 | + if (resultByCategory.hasOwnProperty(prop)) { | |
228 | + categoryWithPrograms = resultByCategory[prop]; | |
229 | + resultByCategory[prop] = shuffle(categoryWithPrograms); | |
230 | + } | |
231 | + } | |
232 | + | |
233 | + // Concat all into result array | |
234 | + // > while has program at Lists on resultByCategory | |
235 | + var hasProgram = true; | |
236 | + while (hasProgram) { | |
237 | + | |
238 | + var foundProgram = false; | |
239 | + // each categoryList with array of program | |
240 | + prop = null; | |
241 | + categoryWithPrograms = null; | |
242 | + for (prop in resultByCategory) { | |
243 | + | |
244 | + if (resultByCategory.hasOwnProperty(prop)) { | |
245 | + categoryWithPrograms = resultByCategory[prop]; | |
246 | + | |
247 | + if (categoryWithPrograms.length > 0) { | |
248 | + var pivotProgram = categoryWithPrograms.pop(); | |
249 | + result.push(pivotProgram); | |
250 | + foundProgram = true; | |
251 | + } | |
252 | + } | |
253 | + } | |
254 | + | |
255 | + if (!foundProgram) { | |
256 | + hasProgram = false; | |
257 | + } | |
258 | + } | |
259 | + | |
260 | + return result; | |
261 | + }; | |
131 | 262 | |
132 | 263 | var directive = { |
133 | 264 | restrict: 'E', |
... | ... | @@ -137,76 +268,49 @@ |
137 | 268 | }, |
138 | 269 | controller: ProgramaListController, |
139 | 270 | controllerAs: 'vm', |
140 | - bindToController: true, | |
141 | - // link: ProgramaListLinker | |
271 | + bindToController: true | |
142 | 272 | }; |
143 | 273 | |
144 | - | |
145 | 274 | return directive; |
146 | 275 | } |
147 | 276 | |
148 | - function filterByCategory(){ | |
149 | - return function (input, category){ | |
150 | - input = input || []; | |
277 | + function _filterByCategory (input, category) { | |
278 | + input = input || []; | |
151 | 279 | |
152 | - if(!category){ | |
153 | - // no filter | |
154 | - return input; | |
155 | - } | |
280 | + if (!category) { | |
281 | + // no filter | |
282 | + return input; | |
283 | + } | |
156 | 284 | |
157 | - var out = []; | |
158 | - for (var i = 0; i < input.length; i++) { | |
159 | - var program = input[i]; | |
160 | - if(program.categories[0].slug === category.slug){ | |
161 | - out.push(program); | |
162 | - } | |
285 | + var out = []; | |
286 | + for (var i = 0; i < input.length; i++) { | |
287 | + var program = input[i]; | |
288 | + if (program.categories[0].slug === category.slug) { | |
289 | + out.push(program); | |
163 | 290 | } |
291 | + } | |
164 | 292 | |
165 | - return out; | |
166 | - }; | |
293 | + return out; | |
167 | 294 | } |
168 | 295 | |
169 | - /** @ngInject */ | |
170 | - function filterByCriteria($filter, $log){ | |
171 | - var orderBy = $filter('orderBy'); | |
172 | - | |
173 | - return function (input, criteria, reverse){ | |
174 | - input = input || []; | |
175 | - criteria = criteria || {}; | |
176 | - reverse = reverse || false; | |
296 | + // -> Fisher–Yates shuffle algorithm | |
297 | + function shuffle (array) { | |
298 | + var currentIndex = array.length, temporaryValue, randomIndex ; | |
177 | 299 | |
178 | - var out = []; | |
179 | - // for (var i = 0; i < input.length; i++) { | |
180 | - // var program = input[i]; | |
300 | + // While there remain elements to shuffle... | |
301 | + while (0 !== currentIndex) { | |
181 | 302 | |
182 | - // // todo ordering | |
183 | - // out.push(program); | |
184 | - // } | |
185 | - | |
186 | - switch(criteria.name){ | |
187 | - case 'title': | |
188 | - out = orderBy(input, 'title', reverse); | |
189 | - break; | |
190 | - case 'category': | |
191 | - out = orderBy(input, 'categories[0].name', reverse); | |
192 | - break; | |
193 | - case 'more_participants': | |
194 | - // break; | |
195 | - default: | |
196 | - $log.info('Criteria not handled yet: ', criteria); | |
197 | - | |
198 | - if(reverse){ | |
199 | - out = input.slice().reverse(); | |
200 | - }else{ | |
201 | - out = input; | |
202 | - } | |
203 | - break; | |
204 | - } | |
303 | + // Pick a remaining element... | |
304 | + randomIndex = Math.floor(Math.random() * currentIndex); | |
305 | + currentIndex -= 1; | |
205 | 306 | |
307 | + // And swap it with the current element. | |
308 | + temporaryValue = array[currentIndex]; | |
309 | + array[currentIndex] = array[randomIndex]; | |
310 | + array[randomIndex] = temporaryValue; | |
311 | + } | |
206 | 312 | |
207 | - return out; | |
208 | - }; | |
313 | + return array; | |
209 | 314 | } |
210 | 315 | |
211 | - | |
212 | 316 | })(); | ... | ... |
src/app/components/programas/programas.directive.spec.js
0 → 100644
... | ... | @@ -0,0 +1,32 @@ |
1 | +(function() { | |
2 | + 'use strict'; | |
3 | + | |
4 | + describe('program directive', function() { | |
5 | + var compile, scope, directiveElem; | |
6 | + | |
7 | + beforeEach(function(){ | |
8 | + module('dialoga'); | |
9 | + | |
10 | + inject(function($compile, $rootScope){ | |
11 | + compile = $compile; | |
12 | + scope = $rootScope.$new(); | |
13 | + // mock article | |
14 | + scope.article = {}; | |
15 | + }); | |
16 | + | |
17 | + directiveElem = getCompiledElement(); | |
18 | + }); | |
19 | + | |
20 | + function getCompiledElement(){ | |
21 | + var element = compile(angular.element('<programa-list></programa-list>'))(scope); | |
22 | + var compiledElement = compile(element)(scope); | |
23 | + scope.$digest(); | |
24 | + return compiledElement; | |
25 | + } | |
26 | + | |
27 | + it('ensure exist only one id "lista-de-programas"', function() {}); | |
28 | + | |
29 | + it('should show default programs, one each category', function() {}); | |
30 | + | |
31 | + }); | |
32 | +})(); | ... | ... |
src/app/components/programas/programas.html
... | ... | @@ -1,68 +0,0 @@ |
1 | -<div class="row"> | |
2 | - <div class="col-sm-3"> | |
3 | - <div class="category-list"> | |
4 | - <nav class="navigation"> | |
5 | - <h3 class="title"><b>Programas</b> por Tema</h3> | |
6 | - <div class="list-group category-list"> | |
7 | - <button type="button" class="list-group-item category-item" | |
8 | - ng-repeat="category in vm.categories" | |
9 | - ng-class="{active: vm.categoryFilter.slug === category.slug}" | |
10 | - ng-click="vm.filterByCategory(category, $event)"> | |
11 | - | |
12 | - <span ng-class="[category.iconClass]"></span> | |
13 | - <span>{{::category.name}}</span> | |
14 | - <span class="glyphicon glyphicon-chevron-right pull-right"></span> | |
15 | - | |
16 | - </button> | |
17 | - </div> | |
18 | - </nav> | |
19 | - </div> | |
20 | - </div> | |
21 | - | |
22 | - <div class="col-sm-9"> | |
23 | - <article class="program-list"> | |
24 | - <header class="header"> | |
25 | - <h2>Programas</h2> | |
26 | - <button type="button" class="btn btn-link" ng-click="vm.showAll($event)"> | |
27 | - <span class="glyphicon glyphicon-chevron-right"></span> Ver todos os programas | |
28 | - </button> | |
29 | - </header> | |
30 | - <div> | |
31 | - <div class="col-sm-12"> | |
32 | - <aside class="form-inline"> | |
33 | - <div class="form-group"> | |
34 | - <label for="programListFilter" class="control-label sr-only">Filtrar programas:</label> | |
35 | - <input id="programListFilter" type="search" class="form-control" ng-model="vm.query" placeholder="Filtrar programas" aria-label="Filtrar programas" > | |
36 | - | |
37 | - <select class="form-control" ng-model="vm.categoryFilter" ng-options="category.name for category in vm.categories track by category.slug"> | |
38 | - <option value="">-- Filtrar por tema --</option> | |
39 | - </select> | |
40 | - | |
41 | - <select class="form-control" ng-model="vm.orderCriteria" ng-options="orderCriteria.label for orderCriteria in vm.orderCriteries"> | |
42 | - <option value="">-- Ordernar por: --</option> | |
43 | - </select> | |
44 | - | |
45 | - <div class="checkbox"> | |
46 | - <label> | |
47 | - <input type="checkbox" ng-model="orderReverse"> | |
48 | - Reverso | |
49 | - </label> | |
50 | - </div> | |
51 | - | |
52 | - <input id="programListLimit" type="number" class="form-control input-sm" size="4" step="2" ng-model="vm.limitTo" aria-label="Limitar" > | |
53 | - <label for="programListLimit" class="control-label">Limite</label> | |
54 | - | |
55 | - </div> | |
56 | - </aside> | |
57 | - </div> | |
58 | - <div ng-repeat="program in vm.programs | filterByCategory:vm.categoryFilter | filterByCriteria:vm.orderCriteria:orderReverse | filter:vm.query | limitTo:vm.limitTo as results"> | |
59 | - <programa-box program="program" class="col-sm-12 col-md-6"></programa-box> | |
60 | - <div ng-if="$odd" class="clearfix"></div> | |
61 | - </div> | |
62 | - <div class="animate-repeat" ng-if="results.length == 0"> | |
63 | - Nenhum programa encontrado. | |
64 | - </div> | |
65 | - </div> | |
66 | - </article> | |
67 | - </div> | |
68 | -</div> |
src/app/components/programas/programas.scss
... | ... | @@ -0,0 +1,30 @@ |
1 | +(function() { | |
2 | + 'use strict'; | |
3 | + | |
4 | + angular | |
5 | + .module('dialoga') | |
6 | + .directive('socialShare', socialShare); | |
7 | + | |
8 | + /** @ngInject */ | |
9 | + function socialShare() { | |
10 | + var directive = { | |
11 | + restrict: 'E', | |
12 | + templateUrl: 'app/components/socialShare/socialShare.html', | |
13 | + scope: { | |
14 | + }, | |
15 | + controller: SocialShareController, | |
16 | + controllerAs: 'vm', | |
17 | + bindToController: true | |
18 | + }; | |
19 | + | |
20 | + return directive; | |
21 | + | |
22 | + /** @ngInject */ | |
23 | + function SocialShareController($log) { | |
24 | + $log.debug('SocialShareController'); | |
25 | + | |
26 | + var vm = this; | |
27 | + } | |
28 | + } | |
29 | + | |
30 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,35 @@ |
1 | +<div class="social-share"> | |
2 | + <ul> | |
3 | + <li> | |
4 | + <a social-facebook custom-url="http://dialoga.gov.br"> | |
5 | + <span class="icon icon-social-facebook"></span> | |
6 | + <span class="sr-only">Compartilhar no Facebook</span> | |
7 | + </a> | |
8 | + </li> | |
9 | + <li> | |
10 | + <a social-twitter custom-url="http://dialoga.gov.br" status="This status is #{{ ctrl.coolWord }}"> | |
11 | + <span class="icon icon-social-twitter"></span> | |
12 | + <span class="sr-only">Compartilhar no Twitter</span> | |
13 | + </a> | |
14 | + </li> | |
15 | + <li> | |
16 | + <a social-gplus custom-url="http://dialoga.gov.br"> | |
17 | + <span class="icon icon-social-google-plus"></span> | |
18 | + <span class="sr-only">Compartilhar no Google Plus</span> | |
19 | + </a> | |
20 | + </li> | |
21 | + <li> | |
22 | + <a href="whatsapp://send?text=Apoio ao audiovisual brasileiro: ampliação da produção, da difusão e do acesso http%3A%2F%2Fdialoga.gov.br%2F%23%2Fprogramas%2F121492%2Fsobre-o-programa" target="_blank"> | |
23 | + <span class="icon icon-social-whatsapp"></span> | |
24 | + <span class="sr-only">Compartilhar no WhatsApp</span> | |
25 | + </a> | |
26 | + </li> | |
27 | + </ul> | |
28 | +</div> | |
29 | + | |
30 | +<!-- <ul> | |
31 | + <li><a href="http://dialoga.gov.br/#/programas/121492/sobre-o-programa" class="fb-share icon icon-facebook" data-caption="Brasil de Todas as Telas" data-description="Apoio ao audiovisual brasileiro: ampliação da produção, da difusão e do acesso"><span class="fa fa-facebook"></span><span class="sr-only">Compartilhar no Facebook</span></a></li> | |
32 | + <li><a href="https://twitter.com/intent/tweet?url=http%3A%2F%2Fdialoga.gov.br%2F%23%2Fprogramas%2F121492%2Fsobre-o-programa&text=Apoio ao audiovisual brasileiro: ampliação da produção, da difusão e do acesso" target="_blank" class="tw-share icon icon-twitter popup"><span class="fa fa-twitter"></span><span class="sr-only">Compartilhar no Twitter</span></a></li> | |
33 | + <li><a href="https://plus.google.com/share?url=http%3A%2F%2Fdialoga.gov.br%2F%23%2Fprogramas%2F121492%2Fsobre-o-programa" target="_blank" class="gp-share icon icon-gplus popup"><span class="fa fa-google-plus"></span><span class="sr-only">Compartilhar no Google Plus</span></a></li> | |
34 | + <li><a href="whatsapp://send?text=Apoio ao audiovisual brasileiro: ampliação da produção, da difusão e do acesso http%3A%2F%2Fdialoga.gov.br%2F%23%2Fprogramas%2F121492%2Fsobre-o-programa" target="_blank" class="ws-share icon icon-whatsapp"><span class="fa fa-whatsapp"></span><span class="sr-only">Compartilhar no WhatsApp</span></a></li> | |
35 | +</ul> --> | ... | ... |
... | ... | @@ -0,0 +1,28 @@ |
1 | +.social-share { | |
2 | + ul { | |
3 | + display: inline-block; | |
4 | + vertical-align: middle; | |
5 | + list-style: none; | |
6 | + padding-left: 0; | |
7 | + } | |
8 | + | |
9 | + li{ | |
10 | + display: inline-block; | |
11 | + padding: 0 2px !important; | |
12 | + vertical-align: top; | |
13 | + } | |
14 | + | |
15 | + .social-share--description { | |
16 | + display: inline-block; | |
17 | + color: #000; | |
18 | + font-size: 12px; | |
19 | + font-weight: 300; | |
20 | + padding-right: 10px; | |
21 | + text-align: right; | |
22 | + vertical-align: middle; | |
23 | + } | |
24 | + | |
25 | + .icon { | |
26 | + display: block; | |
27 | + } | |
28 | +} | ... | ... |
src/app/index.config.js
... | ... | @@ -4,6 +4,7 @@ |
4 | 4 | angular |
5 | 5 | .module('dialoga') |
6 | 6 | .config(configAuthInterceptor) |
7 | + .config(configLocationProvider) | |
7 | 8 | .config(config); |
8 | 9 | |
9 | 10 | /** @ngInject */ |
... | ... | @@ -27,7 +28,13 @@ |
27 | 28 | return $injector.get('AuthInterceptor'); |
28 | 29 | } |
29 | 30 | ]); |
31 | + } | |
30 | 32 | |
33 | + /** @ngInject */ | |
34 | + function configLocationProvider ($locationProvider, Modernizr) { | |
35 | + if (Modernizr.history) { | |
36 | + $locationProvider.html5Mode(true); | |
37 | + } | |
31 | 38 | } |
32 | 39 | |
33 | 40 | /** @ngInject */ | ... | ... |
src/app/index.constants.js
... | ... | @@ -4,12 +4,15 @@ |
4 | 4 | |
5 | 5 | angular |
6 | 6 | .module('dialoga') |
7 | - .constant('api', { | |
7 | + .constant('API', { | |
8 | 8 | token: null, |
9 | - host: 'http://hom.login.dialoga.gov.br', | |
10 | - // host: 'http://www.participa.br', | |
9 | + hostDev: '', | |
10 | + hostHom: 'http://hom.dialoga.gov.br', | |
11 | + hostProd: 'http://login.dialoga.gov.br', | |
11 | 12 | articleId: { |
12 | - home: 103358 | |
13 | + home: '103358', | |
14 | + about: '108073', | |
15 | + terms: '107880' | |
13 | 16 | } |
14 | 17 | }) |
15 | 18 | .constant('AUTH_EVENTS', { | ... | ... |
src/app/index.module.js
src/app/index.route.js
... | ... | @@ -9,76 +9,89 @@ |
9 | 9 | function routeConfig($stateProvider, $urlRouterProvider) { |
10 | 10 | $stateProvider |
11 | 11 | .state('inicio', { |
12 | - url: '/', | |
12 | + url: '/?limite&tema', | |
13 | + reloadOnSearch: false, | |
13 | 14 | views: { |
14 | - 'header': { templateUrl: 'app/partials/header/header.html' }, | |
15 | + 'header': { templateUrl: 'app/pages/header/header.html' }, | |
15 | 16 | 'main': { |
16 | - templateUrl: 'app/partials/inicio/inicio.html', | |
17 | - controller: 'InicioController', | |
18 | - controllerAs: 'inicio' | |
17 | + templateUrl: 'app/pages/inicio/inicio.html', | |
18 | + controller: 'InicioPageController', | |
19 | + controllerAs: 'pageInicio' | |
19 | 20 | }, |
20 | - 'footer': { templateUrl: 'app/partials/footer/footer.html' } | |
21 | + 'footer': { templateUrl: 'app/pages/footer/footer.html' } | |
21 | 22 | } |
22 | 23 | }) |
23 | 24 | .state('entrar', { |
24 | 25 | url: '/entrar', |
25 | 26 | views: { |
26 | - 'header': { templateUrl: 'app/partials/header/header.html' }, | |
27 | + 'header': { templateUrl: 'app/pages/header/header.html' }, | |
27 | 28 | 'main': { |
28 | - templateUrl: 'app/partials/auth/signin.html', | |
29 | - controller: 'AuthController', | |
30 | - controllerAs: 'signin' | |
29 | + templateUrl: 'app/pages/auth/signin.html', | |
30 | + controller: 'AuthPageController', | |
31 | + controllerAs: 'pageSignin' | |
31 | 32 | }, |
32 | - 'footer': { templateUrl: 'app/partials/footer/footer.html' } | |
33 | + 'footer': { templateUrl: 'app/pages/footer/footer.html' } | |
33 | 34 | } |
34 | 35 | }) |
35 | 36 | .state('cadastrar', { |
36 | 37 | url: '/cadastrar', |
37 | 38 | views: { |
38 | - 'header': { templateUrl: 'app/partials/header/header.html' }, | |
39 | + 'header': { templateUrl: 'app/pages/header/header.html' }, | |
39 | 40 | 'main': { |
40 | - templateUrl: 'app/partials/auth/signup.html', | |
41 | - controller: 'AuthController', | |
42 | - controllerAs: 'signup' | |
41 | + templateUrl: 'app/pages/auth/signup.html', | |
42 | + controller: 'AuthPageController', | |
43 | + controllerAs: 'pageSignup' | |
43 | 44 | }, |
44 | - 'footer': { templateUrl: 'app/partials/footer/footer.html' } | |
45 | + 'footer': { templateUrl: 'app/pages/footer/footer.html' } | |
45 | 46 | } |
46 | 47 | }) |
47 | - .state('programas', { | |
48 | - url: '/programas', | |
48 | + .state('programa', { | |
49 | + url: '/programa/:slug', | |
49 | 50 | views: { |
50 | - 'header': { templateUrl: 'app/partials/header/header.html' }, | |
51 | + 'header': { templateUrl: 'app/pages/header/header.html' }, | |
51 | 52 | 'main': { |
52 | - templateUrl: 'app/partials/programas/programas.html', | |
53 | - controller: 'ProgramasController', | |
54 | - controllerAs: 'programas' | |
53 | + templateUrl: 'app/pages/programas/programa.html', | |
54 | + controller: 'ProgramaPageController', | |
55 | + controllerAs: 'pagePrograma' | |
55 | 56 | }, |
56 | - 'footer': { templateUrl: 'app/partials/footer/footer.html' } | |
57 | + 'footer': { templateUrl: 'app/pages/footer/footer.html' } | |
58 | + } | |
59 | + }) | |
60 | + .state('conheca-o-programa', { | |
61 | + url: '/programa/:slug/conheca-o-programa', | |
62 | + views: { | |
63 | + 'header': { templateUrl: 'app/pages/header/header.html' }, | |
64 | + 'main': { | |
65 | + templateUrl: 'app/pages/programas/conheca-o-programa.html', | |
66 | + controller: 'ProgramaContentPageController', | |
67 | + controllerAs: 'pageProgramaContent' | |
68 | + }, | |
69 | + 'footer': { templateUrl: 'app/pages/footer/footer.html' } | |
57 | 70 | } |
58 | 71 | }) |
59 | 72 | .state('sobre', { |
60 | 73 | url: '/sobre', |
61 | 74 | views: { |
62 | - 'header': { templateUrl: 'app/partials/header/header.html' }, | |
75 | + 'header': { templateUrl: 'app/pages/header/header.html' }, | |
63 | 76 | 'main': { |
64 | - templateUrl: 'app/partials/article/article.html', | |
65 | - controller: 'ArticleController', | |
66 | - controllerAs: 'article' | |
77 | + templateUrl: 'app/pages/article/article.html', | |
78 | + controller: 'ArticlePageController', | |
79 | + controllerAs: 'pageArticle' | |
67 | 80 | }, |
68 | - 'footer': { templateUrl: 'app/partials/footer/footer.html' } | |
81 | + 'footer': { templateUrl: 'app/pages/footer/footer.html' } | |
69 | 82 | } |
70 | 83 | }) |
71 | 84 | .state('termos-de-uso', { |
72 | 85 | url: '/termos-de-uso', |
73 | - controller: 'ArticleController', | |
86 | + controller: 'ArticlePageController', | |
74 | 87 | views: { |
75 | - 'header': { templateUrl: 'app/partials/header/header.html' }, | |
88 | + 'header': { templateUrl: 'app/pages/header/header.html' }, | |
76 | 89 | 'main': { |
77 | - templateUrl: 'app/partials/article/article.html', | |
78 | - controller: 'ArticleController', | |
79 | - controllerAs: 'article' | |
90 | + templateUrl: 'app/pages/article/article.html', | |
91 | + controller: 'ArticlePageController', | |
92 | + controllerAs: 'pageArticle' | |
80 | 93 | }, |
81 | - 'footer': { templateUrl: 'app/partials/footer/footer.html' } | |
94 | + 'footer': { templateUrl: 'app/pages/footer/footer.html' } | |
82 | 95 | } |
83 | 96 | }) |
84 | 97 | ; | ... | ... |
src/app/index.run.js
... | ... | @@ -6,15 +6,19 @@ |
6 | 6 | .module('dialoga') |
7 | 7 | .run(runAuth) |
8 | 8 | .run(runAccessibility) |
9 | + .run(runHistory) | |
10 | + .run(runPath) | |
11 | + .run(runColorUtils) | |
9 | 12 | .run(runBlock); |
10 | 13 | |
11 | 14 | /** @ngInject */ |
12 | - function runAuth($rootScope, $cookies, USER_ROLES, AUTH_EVENTS, AuthService, $log){ | |
15 | + function runAuth($rootScope, $cookies, USER_ROLES, AUTH_EVENTS, AuthService, $log) { | |
13 | 16 | |
14 | 17 | // Listner url/state changes, and check permission |
15 | - $rootScope.$on('$stateChangeStart', function (event, next) { | |
16 | - if(!next.data || !next.data.authorizedRoles){ | |
17 | - $log.debug('public url/state'); | |
18 | + $rootScope.$on('$stateChangeStart', function(event, next) { | |
19 | + | |
20 | + if (!next.data || !next.data.authorizedRoles) { | |
21 | + $log.debug('[RUN] Auth: public url/state'); | |
18 | 22 | return; |
19 | 23 | } |
20 | 24 | |
... | ... | @@ -33,48 +37,111 @@ |
33 | 37 | } |
34 | 38 | }); |
35 | 39 | |
36 | - $log.debug('runAuth end.'); | |
40 | + $log.debug('[RUN] Auth end.'); | |
37 | 41 | } |
38 | 42 | |
39 | 43 | /** @ngInject */ |
40 | 44 | function runAccessibility($rootScope, $timeout, $cookies, $log) { |
41 | 45 | |
42 | - var contrast = $cookies.get('dialoga_contraste') === "true"; | |
46 | + var contrast = $cookies.get('dialoga_contraste') === 'true'; | |
43 | 47 | adjustContrast(contrast); |
44 | 48 | |
45 | - function adjustContrast(state){ | |
49 | + function adjustContrast(state) { | |
46 | 50 | var bodyEl = angular.element(document).find('body'); |
47 | 51 | angular.element(bodyEl).toggleClass('contraste', !!state); |
48 | 52 | } |
49 | 53 | |
50 | - $rootScope.toggleContrast = function () { | |
54 | + $rootScope.skipToContent = function() { | |
55 | + angular.element('#content').attr('tabIndex', -1).focus(); | |
56 | + }; | |
57 | + | |
58 | + $rootScope.skipToNavigation = function() { | |
59 | + angular.element('#navigation').attr('tabIndex', -1).focus(); | |
60 | + }; | |
61 | + | |
62 | + $rootScope.skipToSearch = function() { | |
63 | + // angular.element('#search').attr('tabIndex', -1).focus(); | |
64 | + angular.element('#articleQueryFilter').attr('tabIndex', -1).focus(); | |
65 | + }; | |
66 | + | |
67 | + $rootScope.skipToFooter = function() { | |
68 | + angular.element('#footer').attr('tabIndex', -1).focus(); | |
69 | + }; | |
70 | + | |
71 | + $rootScope.actionContrast = function() { | |
72 | + // toggle contrast | |
51 | 73 | contrast = !contrast; |
52 | 74 | $cookies.put('dialoga_contraste', contrast); |
53 | 75 | adjustContrast(contrast); |
54 | 76 | }; |
55 | 77 | |
56 | - $rootScope.focusMainContent = function ($event) { | |
78 | + $rootScope.focusMainContent = function($event) { | |
57 | 79 | |
58 | 80 | // prevent skip link from redirecting |
59 | 81 | if ($event) { $event.preventDefault(); } |
60 | 82 | |
61 | 83 | var mainContentArea = document.querySelector('[role="main"]'); |
62 | 84 | |
63 | - if ( mainContentArea ) { | |
64 | - $timeout(function(){ | |
65 | - mainContentArea.focus(); | |
66 | - },90); | |
67 | - }else{ | |
85 | + if (mainContentArea) { | |
86 | + $timeout(function() { | |
87 | + var $el = angular.element(mainContentArea); | |
88 | + | |
89 | + angular.element('body').animate({scrollTop: $el.offset().top}, 'slow'); | |
90 | + }, 90); | |
91 | + } else { | |
68 | 92 | $log.warn('role="main" not found.'); |
69 | 93 | } |
70 | 94 | }; |
71 | 95 | |
72 | - $log.debug('runAccessibility end.'); | |
96 | + $log.debug('[RUN] Accessibility end.'); | |
97 | + } | |
98 | + | |
99 | + /** @ngInject */ | |
100 | + function runHistory($rootScope) { | |
101 | + $rootScope.$on('$stateChangeSuccess', function(event, toState, toStateParams, fromState, fromStateParams) { | |
102 | + $rootScope.$previousState = { state: fromState, params: fromStateParams}; | |
103 | + }); | |
104 | + } | |
105 | + | |
106 | + /** @ngInject */ | |
107 | + function runPath($rootScope, API, $window, $log) { | |
108 | + var isProd = (/^http:\/\/dialoga\.gov\.br\//.test($window.location.href)); | |
109 | + var isHom = (/^http:\/\/hom.dialoga\.gov\.br\//.test($window.location.href)); | |
110 | + $rootScope.basePath = isProd ? API.hostProd : (isHom ? API.hostHom : API.hostDev); | |
111 | + | |
112 | + $log.debug('[RUN] Path end.'); | |
113 | + } | |
114 | + | |
115 | + /** @ngInject */ | |
116 | + function runColorUtils($window) { | |
117 | + | |
118 | + $window.ColorLuminance = function(hex, lum) { | |
119 | + | |
120 | + // validate hex string | |
121 | + hex = String(hex).replace(/[^0-9a-f]/gi, ''); | |
122 | + if (hex.length < 6) { | |
123 | + hex = hex[0] + hex[0] + hex[1] + hex[1] + hex[2] + hex[2]; | |
124 | + } | |
125 | + lum = lum || 0; | |
126 | + | |
127 | + // convert to decimal and change luminosity | |
128 | + var rgb = '#'; | |
129 | + var c; | |
130 | + var i; | |
131 | + | |
132 | + for (i = 0; i < 3; i++) { | |
133 | + c = parseInt(hex.substr(i * 2, 2), 16); | |
134 | + c = Math.round(Math.min(Math.max(0, c + (c * lum)), 255)).toString(16); | |
135 | + rgb += ('00' + c).substr(c.length); | |
136 | + } | |
137 | + | |
138 | + return rgb; | |
139 | + }; | |
73 | 140 | } |
74 | 141 | |
75 | 142 | /** @ngInject */ |
76 | 143 | function runBlock($log) { |
77 | - $log.debug('runBlock end.'); | |
144 | + $log.debug('[RUN] Block end.'); | |
78 | 145 | } |
79 | 146 | |
80 | 147 | })(); | ... | ... |
src/app/index.scss
... | ... | @@ -5,6 +5,7 @@ |
5 | 5 | // $navbar-inverse-link-color: #5AADBB; |
6 | 6 | $icon-font-path: "../../bower_components/bootstrap-sass-official/assets/fonts/bootstrap/"; |
7 | 7 | |
8 | + | |
8 | 9 | /** |
9 | 10 | * Do not remove this comments bellow. It's the markers used by wiredep to inject |
10 | 11 | * sass dependencies when defined in the bower.json of your dependencies |
... | ... | @@ -20,53 +21,115 @@ $gray: #f1f1f1; |
20 | 21 | |
21 | 22 | // ------------- |
22 | 23 | |
24 | +// 1.4 - dicionarios | |
25 | +$categories: (saude: #3449b7, seguranca-publica: #e34748, educacao: #f39720, reducao-da-pobreza: #3ebb8f, cultura: #a63738); | |
26 | +$categories-descriptions: (saude: "Saúde é direito de todos e dever do Estado. O Sistema Único de Saúde (SUS) é universal, integral e de responsabilidade do Governo Federal, estados e municípios. Atende a todos os brasileiros.", seguranca-publica: "A segurança pública é um direito fundamental dos cidadãos. A proteção da vida, a disseminação da cultura da paz e a integração dos órgãos e instituições municipais, estaduais e federais são os maiores compromissos dessa política pública.", educacao: "Uma pátria educadora se faz com oportunidades para todos. Nos últimos anos, o Brasil criou esse caminho de oportunidades. Ampliamos o acesso à educação em todos os níveis de ensino – da creche à pós-graduação – e para todos os brasileiros, independentemente de sua classe social. E ainda há muito a fazer. O Plano Nacional de Educação (PNE) estabelece novas metas para que o governo federal trabalhe em parceria com a sociedade, com os estados e os municípios na construção de um futuro melhor. Queremos agora um salto na qualidade do ensino.", reducao-da-pobreza: "Com o esforço do Brasil para reduzir a pobreza e a desigualdade, 36 milhões de pessoas superaram a miséria na última década e o país saiu do Mapa da Fome das Nações Unidas.", cultura: "O que nos singulariza no conjunto das nações é, em última instância, nossa cultura. É por ela que nos identificamos como brasileiros de norte a sul deste país. Uma grande nação precisa ter um desenvolvimento cultural à altura de sua grandeza, contemplando as dimensões simbólica, econômica e cidadã da cultura, que são parte central do projeto de um país democrático e plural. A pluralidade é nossa singularidade."); | |
23 | 27 | |
24 | -// ------------- | |
25 | -// Paleta de Cores | |
26 | -// ------------- | |
27 | -$cinza1: #f1f1f1; | |
28 | -$cinza2: #eaeaea; | |
29 | -$cinza3: #dadada; | |
30 | -$cinza4: #989898; | |
31 | -$cinza5: #606060; | |
32 | -$cinza6: #484848; | |
28 | +// Programs | |
29 | +$scale: 1.1; | |
30 | +$time: .2s; | |
31 | +$darken: 15%; | |
33 | 32 | |
34 | 33 | |
35 | 34 | // ------------- |
36 | -// Tipografia | |
37 | -// ------------- | |
38 | -// $open-sans-regular: | |
39 | -// $open-sans-bold: | |
40 | -$titulo1-size: 32pt; | |
41 | -$titulo1-line-height: 36pt; | |
42 | - | |
43 | -$titulo2-size: 26pt; | |
44 | -$titulo2-line-height: 30pt; | |
45 | 35 | |
46 | -$titulo3-size: 22pt; | |
47 | -$titulo3-line-height: 26pt; | |
48 | - | |
49 | -$titulo4-size: 18pt; | |
50 | -$titulo4-line-height: 22pt; | |
51 | - | |
52 | -$titulo5-size: 14pt; | |
53 | -$titulo5-line-height: 18pt; | |
54 | - | |
55 | -$paragraph-size: 12pt; | |
56 | -$paragraph-line-height: 16pt; | |
57 | - | |
58 | -// ------------- | |
59 | -.skip-links a:focus { | |
60 | - background-color: #fff !important; | |
61 | - opacity: 1; | |
62 | - z-index: 2; | |
36 | +body { | |
37 | + font-family: "Open Sans", sans-serif; | |
38 | + &.contraste { | |
39 | + color: #fff; | |
40 | + background-color: #000; | |
41 | + | |
42 | + a, | |
43 | + .btn { | |
44 | + color: #fff; | |
45 | + background-color: #000; | |
46 | + } | |
47 | + } | |
63 | 48 | } |
64 | 49 | |
65 | -.browsehappy { | |
66 | - margin: 0.2em 0; | |
67 | - background: #ccc; | |
68 | - color: #000; | |
69 | - padding: 0.2em 0; | |
50 | +// Commons | |
51 | +.button--themed { | |
52 | + padding: 20px; | |
53 | + .btn { | |
54 | + color: #fff; | |
55 | + font-weight: bold; | |
56 | + padding: 15px 0; | |
57 | + border-left: 0; | |
58 | + border-right: 0; | |
59 | + border-top: 0; | |
60 | + border-radius: 6px; | |
61 | + | |
62 | + -webkit-transition: all $time ease-in-out; | |
63 | + -moz-transition: all $time ease-in-out; | |
64 | + -o-transition: all $time ease-in-out; | |
65 | + transition: all $time ease-in-out; | |
66 | + | |
67 | + @each $category, $color in $categories { | |
68 | + .#{$category} & { | |
69 | + background-color: $color; | |
70 | + border-bottom: 3px solid darken($color, $darken); | |
71 | + } | |
72 | + } | |
73 | + | |
74 | + &:hover, | |
75 | + &:focus { | |
76 | + @each $category, $color in $categories { | |
77 | + .#{$category} & { | |
78 | + background-color: darken($color, $darken); | |
79 | + } | |
80 | + } | |
81 | + } | |
82 | + | |
83 | + .contraste & { | |
84 | + color: #262626; | |
85 | + background-color: #fff; | |
86 | + } | |
87 | + } | |
88 | + | |
89 | + .btn-circle { | |
90 | + width: 64px; | |
91 | + height: 64px; | |
92 | + border-radius: 100%; | |
93 | + } | |
94 | + | |
95 | + // &.vote-buttons { | |
96 | + // padding-bottom: 40px; | |
97 | + // } | |
98 | + | |
99 | + .btn.vote-buttons-up { | |
100 | + float: right; | |
101 | + margin-right: 10px; | |
102 | + background-color: #32dbb5; | |
103 | + border-bottom: 3px solid #1da485; | |
104 | + | |
105 | + &:hover, | |
106 | + &:focus { | |
107 | + background-color: #1da485; | |
108 | + } | |
109 | + } | |
110 | + | |
111 | + .btn.vote-buttons-down { | |
112 | + float: left; | |
113 | + margin-left: 10px; | |
114 | + background-color: #db4127; | |
115 | + border-bottom: 3px solid #9c2d1a; | |
116 | + | |
117 | + &:hover, | |
118 | + &:focus { | |
119 | + background-color: #9c2d1a; | |
120 | + } | |
121 | + | |
122 | + | |
123 | + // @media (max-width: $screen-sm) { | |
124 | + // margin-left: | |
125 | + // } | |
126 | + } | |
127 | + | |
128 | + .vote-buttons-up, | |
129 | + .vote-buttons-down { | |
130 | + font-size: 30px; | |
131 | + margin-bottom: 20px; | |
132 | + } | |
70 | 133 | } |
71 | 134 | |
72 | 135 | // Hack to fix "Barra do Brasil" | ... | ... |
... | ... | @@ -0,0 +1,54 @@ |
1 | +.row-height { | |
2 | + display: table; | |
3 | + table-layout: fixed; | |
4 | + height: 100%; | |
5 | + width: 100%; | |
6 | + | |
7 | + @media (max-width: $screen-sm) { | |
8 | + display: block; | |
9 | + } | |
10 | + | |
11 | + // @media (min-width: $screen-sm + 1) { | |
12 | + // height: $hLine * 2; | |
13 | + // } | |
14 | + | |
15 | + // @media (min-width: $screen-md + 1) { | |
16 | + // height: $hLine * 2; | |
17 | + // } | |
18 | +} | |
19 | + | |
20 | +.col-height { | |
21 | + display: table-cell; | |
22 | + float: none; | |
23 | + height: 100%; | |
24 | + vertical-align: top; | |
25 | +} | |
26 | + | |
27 | +.col-height--align-bottom { | |
28 | + vertical-align: bottom; | |
29 | +} | |
30 | + | |
31 | +.inside { | |
32 | + margin-top: 20px; | |
33 | + margin-bottom: 20px; | |
34 | +} | |
35 | + | |
36 | +.inside-full-height { | |
37 | + height: 100%; | |
38 | + margin-top: 0; | |
39 | + margin-bottom: 0; | |
40 | + | |
41 | + | |
42 | + @media (max-width: $screen-sm) { | |
43 | + border: 1px solid; | |
44 | + border-radius: 3px; | |
45 | + padding: 20px; | |
46 | + margin: 10px 0; | |
47 | + | |
48 | + @each $category, $color in $categories { | |
49 | + .#{$category} & { | |
50 | + border-color: $color; | |
51 | + } | |
52 | + } | |
53 | + } | |
54 | +} | ... | ... |
... | ... | @@ -0,0 +1,50 @@ |
1 | +(function() { | |
2 | + 'use strict'; | |
3 | + | |
4 | + angular | |
5 | + .module('dialoga') | |
6 | + .controller('ArticlePageController', ArticlePageController); | |
7 | + | |
8 | + /** @ngInject */ | |
9 | + function ArticlePageController(ArticleService, $state, $sce, $log) { | |
10 | + $log.debug('ArticlePageController'); | |
11 | + | |
12 | + var vm = this; | |
13 | + vm.ArticleService = ArticleService; | |
14 | + vm.$state = $state; | |
15 | + vm.$sce = $sce; | |
16 | + vm.$log = $log; | |
17 | + | |
18 | + vm.init(); | |
19 | + } | |
20 | + | |
21 | + ArticlePageController.prototype.init = function() { | |
22 | + var vm = this; | |
23 | + | |
24 | + vm.page = vm.$state.current.name; | |
25 | + vm.article = null; | |
26 | + vm.loading = true; | |
27 | + switch (vm.page){ | |
28 | + case 'sobre': | |
29 | + vm.ArticleService.getAbout(handleSuccess, handleError); | |
30 | + break; | |
31 | + case 'termos-de-uso': | |
32 | + vm.ArticleService.getTerms(handleSuccess, handleError); | |
33 | + break; | |
34 | + default: | |
35 | + vm.$log.warn('Page not handled:', vm.page); | |
36 | + break; | |
37 | + } | |
38 | + | |
39 | + function handleSuccess (data) { | |
40 | + vm.loading = false; | |
41 | + vm.article = data.article; | |
42 | + // vm.article.body = vm.$sce.trustAsHtml(vm.article.body); | |
43 | + } | |
44 | + | |
45 | + function handleError (error) { | |
46 | + vm.loading = false; | |
47 | + vm.error = error; | |
48 | + } | |
49 | + }; | |
50 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,15 @@ |
1 | +(function() { | |
2 | + 'use strict'; | |
3 | + | |
4 | + describe('controllers', function(){ | |
5 | + | |
6 | + beforeEach(module('dialoga')); | |
7 | + | |
8 | + it('should define more than 5 awesome things', inject(function($controller) { | |
9 | + var vm = $controller('ArticlePageController'); | |
10 | + | |
11 | + vm.init(); | |
12 | + expect(vm.page).toBeDefined(); | |
13 | + })); | |
14 | + }); | |
15 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,25 @@ |
1 | +<div class="container" role="main"> | |
2 | + | |
3 | + <article-bar></article-bar> | |
4 | + | |
5 | + <div ng-if="pageArticle.loading"> | |
6 | + <div class="alert alert-info"> | |
7 | + Carregando conteúdo... | |
8 | + </div> | |
9 | + </div> | |
10 | + | |
11 | + <div ng-if="pageArticle.error"> | |
12 | + <div class="alert alert-info"> | |
13 | + Erro ao carregar conteúdo. | |
14 | + </div> | |
15 | + </div> | |
16 | + | |
17 | + <div ng-if="pageArticle.article"> | |
18 | + <article> | |
19 | + <header> | |
20 | + <h1>{{::pageArticle.article.title}}</h1> | |
21 | + </header> | |
22 | + <section ng-bind-html="pageArticle.article.body"></section> | |
23 | + </article> | |
24 | + </div> | |
25 | +</div> | ... | ... |
... | ... | @@ -0,0 +1,173 @@ |
1 | +(function() { | |
2 | + 'use strict'; | |
3 | + | |
4 | + angular | |
5 | + .module('dialoga') | |
6 | + .factory('ArticleService', ArticleService); | |
7 | + | |
8 | + /** @ngInject */ | |
9 | + function ArticleService($http, $q, $rootScope, API, UtilService, Slug, $log) { | |
10 | + $log.debug('ArticleService'); | |
11 | + | |
12 | + var idArticleHome = API.articleId.home; | |
13 | + var idArticleAbout = API.articleId.about; | |
14 | + var idArticleTerms = API.articleId.terms; | |
15 | + | |
16 | + var _savedAbstract = null; | |
17 | + | |
18 | + var service = { | |
19 | + apiArticles: $rootScope.basePath + '/api/v1/articles/', | |
20 | + getHome: getHome, | |
21 | + getAbout: getAbout, | |
22 | + getTerms: getTerms, | |
23 | + getArticleById: getArticleById, | |
24 | + getArticleBySlug: getArticleBySlug, | |
25 | + getCategories: getCategories, | |
26 | + getCategoryBySlug: getCategoryBySlug, | |
27 | + getPrograms: getPrograms, | |
28 | + getContentById: getContentById, | |
29 | + setHomeAbstract: setHomeAbstract, | |
30 | + getHomeAbstract: getHomeAbstract | |
31 | + }; | |
32 | + | |
33 | + var CACHE = {}; // cache by article id | |
34 | + | |
35 | + return service; | |
36 | + | |
37 | + function loadArticleById (articleId, params, cbSuccess, cbError) { | |
38 | + | |
39 | + var url = service.apiArticles + articleId; | |
40 | + var paramsExtended = angular.extend({}, params); | |
41 | + | |
42 | + UtilService.get(url, {params: paramsExtended}).then(function(data){ | |
43 | + CACHE[articleId] = data; | |
44 | + cbSuccess(data); | |
45 | + }, function(error){ | |
46 | + cbError(error); | |
47 | + }); | |
48 | + } | |
49 | + | |
50 | + function getArticleById (articleId, params, cbSuccess, cbError) { | |
51 | + var cachedArticle = CACHE[articleId]; | |
52 | + | |
53 | + if(cachedArticle){ | |
54 | + cbSuccess(cachedArticle); | |
55 | + }else{ | |
56 | + loadArticleById(articleId, params, cbSuccess, cbError); | |
57 | + } | |
58 | + } | |
59 | + | |
60 | + function getArticleBySlug (slug, cbSuccess, cbError) { | |
61 | + var vm = this; | |
62 | + | |
63 | + /** | |
64 | + * XXX: get from home article util we have a endpoint to do-it. | |
65 | + */ | |
66 | + vm.getHome(function (data) { | |
67 | + var mainArticle = data.article; | |
68 | + var programList = mainArticle.children; | |
69 | + var categories = mainArticle.categories; | |
70 | + | |
71 | + $rootScope._CATEGORIES = $rootScope._CATEGORIES ? $rootScope._CATEGORIES : categories; | |
72 | + | |
73 | + var result = null; | |
74 | + for (var i = programList.length - 1; i >= 0; i--) { | |
75 | + var program = programList[i]; | |
76 | + | |
77 | + if(!program.slug){ | |
78 | + program.slug = Slug.slugify(program.title); | |
79 | + } | |
80 | + | |
81 | + if(program.slug === slug){ | |
82 | + result = program; | |
83 | + break; | |
84 | + } | |
85 | + } | |
86 | + | |
87 | + if(result){ | |
88 | + cbSuccess(result); | |
89 | + }else{ | |
90 | + cbError('None program with slug "' + slug + '"" was found.'); | |
91 | + } | |
92 | + }, cbError); | |
93 | + } | |
94 | + | |
95 | + function getCategories (cbSuccess, cbError) { | |
96 | + return getHome(function(data){ | |
97 | + cbSuccess(data.article.categories); | |
98 | + }, cbError); | |
99 | + } | |
100 | + | |
101 | + function getCategoryBySlug (slug, cbSuccess, cbError) { | |
102 | + return getHome(function (data){ | |
103 | + var result = null; | |
104 | + | |
105 | + for (var i = data.article.categories.length - 1; i >= 0; i--) { | |
106 | + var category = data.article.categories[i]; | |
107 | + if (category.slug === slug) { | |
108 | + result = category; | |
109 | + break; | |
110 | + } | |
111 | + } | |
112 | + | |
113 | + cbSuccess(result); | |
114 | + }, cbError); | |
115 | + } | |
116 | + | |
117 | + function getPrograms (cbSuccess, cbError) { | |
118 | + return getHome(function(data){ | |
119 | + cbSuccess(data.article.children); | |
120 | + }, cbError); | |
121 | + } | |
122 | + | |
123 | + function getContentById (contentId, cbSuccess, cbError) { | |
124 | + return getArticleById(contentId, { | |
125 | + fields: 'id,body&content_type=ProposalsDiscussionPlugin::Topic' | |
126 | + }, cbSuccess, cbError); | |
127 | + } | |
128 | + | |
129 | + function getHome (cbSuccess, cbError) { | |
130 | + return getArticleById(idArticleHome, { | |
131 | + fields: 'id,children,categories,abstract,title,image,url,setting,position', | |
132 | + private_token: 'null' | |
133 | + }, _handleCategory(cbSuccess), cbError); | |
134 | + } | |
135 | + | |
136 | + function getAbout (cbSuccess, cbError) { | |
137 | + return getArticleById(idArticleAbout, {}, cbSuccess, cbError); | |
138 | + } | |
139 | + | |
140 | + function getTerms (cbSuccess, cbError) { | |
141 | + return getArticleById(idArticleTerms, {}, cbSuccess, cbError); | |
142 | + } | |
143 | + | |
144 | + function _handleCategory (cbSuccess) { | |
145 | + // var darkFactor = 0.15; | |
146 | + | |
147 | + return function (data) { | |
148 | + if(data.article.categories){ | |
149 | + // var categories = data.article.categories; | |
150 | + | |
151 | + // Handle Category Data | |
152 | + | |
153 | + // Handle Category Colors | |
154 | + // for (var i = categories.length - 1; i >= 0; i--) { | |
155 | + // var category = categories[i]; | |
156 | + // if(category.color && !category.bgColor){ | |
157 | + // category.colorDarker = $window.ColorLuminance(category.color, 0.15); | |
158 | + // } | |
159 | + // }; | |
160 | + } | |
161 | + cbSuccess(data); | |
162 | + }; | |
163 | + } | |
164 | + | |
165 | + function setHomeAbstract (newAbstract) { | |
166 | + _savedAbstract = newAbstract; | |
167 | + } | |
168 | + | |
169 | + function getHomeAbstract () { | |
170 | + return _savedAbstract; | |
171 | + } | |
172 | + } | |
173 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,67 @@ |
1 | +(function() { | |
2 | + 'use strict'; | |
3 | + | |
4 | + describe('article services', function() { | |
5 | + var ArticleService, httpBackend; | |
6 | + | |
7 | + beforeEach(module('dialoga')); | |
8 | + | |
9 | + beforeEach(inject(function(_ArticleService_, $httpBackend) { | |
10 | + ArticleService = _ArticleService_; | |
11 | + httpBackend = $httpBackend; | |
12 | + })); | |
13 | + | |
14 | + it('should return the main article', function() { | |
15 | + var url = 'http://login.dialoga.gov.br/api/v1/articles/103358?fields=id,children,categories,abstract,title,image,url,setting,position&private_token=null'; | |
16 | + httpBackend.whenGET(url).respond({ | |
17 | + 'article':{'id':103358,'abstract':'\u003Cp style=\"text-align: center;\"\u003E\u003Ciframe src=\"https://www.youtube.com/embed/kpAdrO-emV0?rel=0\u0026amp;showinfo=0\u0026amp;iv_load_policy=3\u0026amp;controls=1\" style=\"max-width: 1000px; left: 5%;\" width=\"275\" height=\"200\"\u003E\u003C/iframe\u003E\u003C/p\u003E','title':'Dialoga Brasil','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null},{'name':'Seguran\u00e7a P\u00fablica','id':182,'slug':'seguranca-publica','image':null},{'name':'Educa\u00e7\u00e3o','id':181,'slug':'educacao','image':null},{'name':'Redu\u00e7\u00e3o da Pobreza','id':183,'slug':'reducao-da-pobreza','image':null}],'image':null,'setting':{'custom_body_label':'Corpo','phase':'proposals','allow_topics':true,'moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Leandro Nunes dos Santos','moderate_proposals':true,'allow_members_to_edit':false},'position':null,'children':[{'id':103644,'abstract':'\u003Cp\u003EUm caminho de oportunidades com o Enem: Sisu, Prouni, Fies, Ci\u00eancia sem Fronteiras\u003C/p\u003E','title':'Ensino Superior','categories':[{'name':'Educa\u00e7\u00e3o','id':181,'slug':'educacao','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0128/enem.jpg'},'setting':{'color':'#cfe2f3','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':9},{'id':103673,'abstract':'\u003Cp\u003EA melhor escolha \u00e9 se informar.\u003C/p\u003E','title':'Incentivo ao Parto Normal','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0092/parto-normal.jpg'},'setting':{'color':'#ff0000','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':6},{'id':103397,'abstract':'\u003Cp\u003ERenda, inclus\u00e3o produtiva e acesso a servi\u00e7os.\u003C/p\u003E','title':'Brasil Sem Mis\u00e9ria','categories':[{'name':'Redu\u00e7\u00e3o da Pobreza','id':183,'slug':'reducao-da-pobreza','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0116/bsm_redim.jpg'},'setting':{'color':'','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':18},{'id':103379,'abstract':'\u003Cp\u003EResgate e atendimento 24 horas, sete dias da semana.\u003C/p\u003E','title':'SAMU 192 e UPAs','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0060/SAMU.jpg'},'setting':{'color':'#45818e','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':4},{'id':103521,'abstract':'\u003Cp\u003EMais atendimento nos munic\u00edpios, mais sa\u00fade para quem mais precisa.\u003C/p\u003E','title':'Mais M\u00e9dicos','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0025/Mais_M_dicos.jpg'},'setting':{'color':'#ffe599','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':1},{'id':103390,'abstract':'\u003Cp\u003EPreven\u00e7\u00e3o, tratamento e enfrentamento ao tr\u00e1fico.\u003C/p\u003E','title':'Crack, \u00e9 poss\u00edvel vencer!','categories':[{'name':'Seguran\u00e7a P\u00fablica','id':182,'slug':'seguranca-publica','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0104/crack.jpg'},'setting':{'color':'#00ff00','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':14},{'id':103592,'abstract':'\u003Cp\u003EGarantir acesso \u00e0 prote\u00e7\u00e3o social.\u003C/p\u003E','title':'Assist\u00eancia Social','categories':[{'name':'Redu\u00e7\u00e3o da Pobreza','id':183,'slug':'reducao-da-pobreza','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0122/assistencia_social.jpg'},'setting':{'color':'#a61c00','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':19},{'id':103426,'abstract':'\u003Cp\u003EDa sa\u00fade se cuida todos os dias.\u003C/p\u003E','title':'Vida saud\u00e1vel','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0046/vida_saudavel.jpg'},'setting':{'color':'#d9d2e9','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':7},{'id':103695,'abstract':'\u003Cp\u003ENovo modelo de atua\u00e7\u00e3o em Seguran\u00e7a P\u00fablica.\u003C/p\u003E','title':'Seguran\u00e7a P\u00fablica Integrada','categories':[{'name':'Seguran\u00e7a P\u00fablica','id':182,'slug':'seguranca-publica','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0152/policiaintegrada.jpg'},'setting':{'color':'#ff00ff','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':13},{'id':103663,'abstract':'\u003Cp\u003EMais educa\u00e7\u00e3o profissional e tecnol\u00f3gica, mais desenvolvimento\u003C/p\u003E','title':'Ensino T\u00e9cnico','categories':[{'name':'Educa\u00e7\u00e3o','id':181,'slug':'educacao','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0134/Ensino_tecnico.jpg'},'setting':{'color':'#d0e0e3','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':10},{'id':103472,'abstract':'\u003Cp\u003EPol\u00edcia Federal, Pol\u00edcia Rodovi\u00e1ria Federal e For\u00e7a Nacional de Seguran\u00e7a P\u00fablica.\u003C/p\u003E','title':'For\u00e7as Federais de Seguran\u00e7a','categories':[{'name':'Seguran\u00e7a P\u00fablica','id':182,'slug':'seguranca-publica','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0031/federais2.png'},'setting':{'color':'','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':16},{'id':103612,'abstract':'\u003Cp\u003EGarantir \u00e1gua para beber e produzir.\u003C/p\u003E','title':'Cisternas','categories':[{'name':'Redu\u00e7\u00e3o da Pobreza','id':183,'slug':'reducao-da-pobreza','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0039/cisterna_redim.jpg'},'setting':{'color':'#0000ff','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':20},{'id':103442,'abstract':'\u003Cp\u003EComplemento \u00e0 renda e acompanhamento em educa\u00e7\u00e3o e sa\u00fade.\u003C/p\u003E','title':'Bolsa Fam\u00edlia','categories':[{'name':'Redu\u00e7\u00e3o da Pobreza','id':183,'slug':'reducao-da-pobreza','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0013/bolsa_familia_redim.jpg'},'setting':{'color':'#ff9900','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':17},{'id':103507,'abstract':'\u003Cp\u003ETecnologia a servi\u00e7o da seguran\u00e7a do cidad\u00e3o.\u003C/p\u003E','title':'Sinesp','categories':[{'name':'Seguran\u00e7a P\u00fablica','id':182,'slug':'seguranca-publica','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0098/sinesp.png'},'setting':{'color':'#00ff00','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':12},{'id':103683,'abstract':'\u003Cp\u003ESa\u00fade n\u00e3o tem pre\u00e7o.\u003C/p\u003E','title':'Aqui tem Farm\u00e1cia Popular','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0019/saude_nao_tem_preco.jpg'},'setting':{'color':'#e69138','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':5},{'id':103457,'abstract':'\u003Cp\u003EA\u00e7\u00e3o conjunta e coopera\u00e7\u00e3o transfronteiri\u00e7a.\u003C/p\u003E','title':'Prote\u00e7\u00e3o das Fronteiras','categories':[{'name':'Seguran\u00e7a P\u00fablica','id':182,'slug':'seguranca-publica','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0110/fronteira_redim.jpg'},'setting':{'color':'#a64d79','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':15},{'id':103494,'abstract':'\u003Cp\u003EDa Educa\u00e7\u00e3o Infantil ao Ensino M\u00e9dio.\u003C/p\u003E','title':'Educa\u00e7\u00e3o B\u00e1sica','categories':[{'name':'Educa\u00e7\u00e3o','id':181,'slug':'educacao','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0076/Educa__o_B_sica.jpg'},'setting':{'color':'#fce5cd','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':8},{'id':103359,'abstract':'\u003Cp\u003EAcesso a exames e consultas com especialistas.\u003C/p\u003E','title':'Mais Especialidades','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0083/mais_especialidades1.png'},'setting':{'color':'#ea9999','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':2},{'id':103485,'abstract':'\u003Cp\u003ECaminho para uma educa\u00e7\u00e3o de qualidade.\u003C/p\u003E','title':'Valoriza\u00e7\u00e3o dos Professores','categories':[{'name':'Educa\u00e7\u00e3o','id':181,'slug':'educacao','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0140/valorizacao_professor.jpg'},'setting':{'color':'#ffff00','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':11},{'id':103416,'abstract':'\u003Cp\u003EEstrutura adequada para atender melhor a popula\u00e7\u00e3o na aten\u00e7\u00e3o b\u00e1sica.\u003C/p\u003E','title':'Melhorar os Postos de Sa\u00fade','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0053/requalif_redim.jpg'},'setting':{'color':'#cc4125','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':3}]}}); | |
18 | + | |
19 | + ArticleService.getHome(function(result){ | |
20 | + expect(result.article).toBeDefined(); | |
21 | + expect(result.article.title).toEqual('Dialoga Brasil'); | |
22 | + expect(result.article.categories).toBeDefined(); | |
23 | + }); | |
24 | + | |
25 | + httpBackend.flush(); | |
26 | + }); | |
27 | + | |
28 | + // it('should return a list of articles', function() { | |
29 | + | |
30 | + // httpBackend.whenGET('http://login.dialoga.gov.br/api/v1/articles').respond({ | |
31 | + // "articles": [ | |
32 | + // { | |
33 | + // abstract: "Que exista educação continuada permanente dos profissionais!!", | |
34 | + // author: null, | |
35 | + // body: "", | |
36 | + // categories: [], | |
37 | + // children: [], | |
38 | + // created_at: "2015/08/04 16:36:13", | |
39 | + // end_date: null, | |
40 | + // hits: 0, | |
41 | + // id: 120568, | |
42 | + // image: null, | |
43 | + // parent: {id: 103379,…}, | |
44 | + // position: null, | |
45 | + // profile: {identifier: "dialoga", name: "dialoga", id: 19195, created_at: "2015/04/15 09:38:36", image: null}, | |
46 | + // setting: {comment_paragraph_plugin_activate: false, author_name: "estacio"}, | |
47 | + // start_date: null, | |
48 | + // tag_list: [], | |
49 | + // title: "article_f4f4601c-0f36-e90e-d01a-9871f0bd126b", | |
50 | + // votes_against: 0, | |
51 | + // votes_for: 0, | |
52 | + // } | |
53 | + // ] | |
54 | + // }); | |
55 | + | |
56 | + // ArticleService.getList().then(function(result) { | |
57 | + // console.log('result', result); | |
58 | + | |
59 | + // expect(result.data.article).toBeDefined(); | |
60 | + // expect(result.data.article.title).toEqual('Dialoga Brasil'); | |
61 | + | |
62 | + // }); | |
63 | + | |
64 | + // httpBackend.flush(); | |
65 | + // }); | |
66 | + }); | |
67 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,44 @@ |
1 | +(function () { | |
2 | + 'use strict'; | |
3 | + | |
4 | + angular | |
5 | + .module('dialoga') | |
6 | + .controller('AuthPageController', AuthPageController); | |
7 | + | |
8 | + /** @ngInject */ | |
9 | + function AuthPageController($rootScope, AUTH_EVENTS, AuthService, Session, $log) { | |
10 | + $log.debug('AuthPageController'); | |
11 | + | |
12 | + var vm = this; | |
13 | + | |
14 | + vm.$rootScope = $rootScope; | |
15 | + vm.AUTH_EVENTS = AUTH_EVENTS; | |
16 | + vm.AuthService = AuthService; | |
17 | + vm.Session = Session; | |
18 | + vm.$log = $log; | |
19 | + | |
20 | + vm.init(); | |
21 | + } | |
22 | + | |
23 | + AuthPageController.prototype.init = function() { | |
24 | + var vm = this; | |
25 | + | |
26 | + // init variables | |
27 | + vm.credentials = {}; | |
28 | + | |
29 | + // attach events | |
30 | + | |
31 | + // ... | |
32 | + }; | |
33 | + | |
34 | + AuthPageController.prototype.login = function(credentials) { | |
35 | + var vm = this; | |
36 | + | |
37 | + vm.AuthService.login(credentials).then(function(/*user*/) { | |
38 | + // handle view | |
39 | + }, function() { | |
40 | + // handle view | |
41 | + }); | |
42 | + }; | |
43 | + | |
44 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,63 @@ |
1 | +.auth-content{ | |
2 | + | |
3 | + .btn-social { | |
4 | + color: #fff; | |
5 | + font-weight: bold; | |
6 | + | |
7 | + &:hover, | |
8 | + &:focus {color: #fff;} | |
9 | + | |
10 | + &.btn-facebook { | |
11 | + background-color: #33477a; | |
12 | + &:hover, | |
13 | + &:focus {background-color: #304373; } | |
14 | + &:active {background-color: #33477a; } | |
15 | + } | |
16 | + &.btn-google-plus { | |
17 | + background-color: #b92d25; | |
18 | + &:hover, | |
19 | + &:focus {background-color: #b12b23; } | |
20 | + &:active {background-color: #b92d25; } | |
21 | + } | |
22 | + } | |
23 | + | |
24 | + .btn { | |
25 | + .contraste & { | |
26 | + color: #fff; | |
27 | + } | |
28 | + } | |
29 | + .btn-primary { | |
30 | + .contraste & { | |
31 | + background-color: #262626; | |
32 | + border-color: #666; | |
33 | + } | |
34 | + } | |
35 | + | |
36 | + .glyphicon { | |
37 | + &.icon-white { | |
38 | + fill: white; | |
39 | + } | |
40 | + } | |
41 | + | |
42 | + .separator-or { | |
43 | + border-top: 2px solid #d8d8d8; | |
44 | + text-align: center; | |
45 | + font-weight: bold; | |
46 | + | |
47 | + &:after { | |
48 | + content: "ou"; | |
49 | + position: absolute; | |
50 | + top: 4px; | |
51 | + left: 50%; | |
52 | + margin-left: -26px; | |
53 | + font-size: 30px; | |
54 | + line-height: 30px; | |
55 | + padding: 0 0.25em; | |
56 | + background: $gray; | |
57 | + | |
58 | + .contraste & { | |
59 | + background: #000; | |
60 | + } | |
61 | + } | |
62 | + } | |
63 | +} | ... | ... |
... | ... | @@ -0,0 +1,38 @@ |
1 | +<section role="main" class="section-gray auth-content"> | |
2 | + <div class="container"> | |
3 | + <div class="row"> | |
4 | + <div class="col-sm-8 col-sm-offset-2"> | |
5 | + <h2>Identifique-se</h2> | |
6 | + <form name="loginForm" ng-submit="pageSignin.login(pageSignin.credentials)"> | |
7 | + <div class="form-group"> | |
8 | + <label for="inputUsername" class="sr-only">E-mail:</label> | |
9 | + <div class="input-group"> | |
10 | + <div class="input-group-addon"><span class="glyphicon glyphicon-user"></span></div> | |
11 | + <input type="text" id="inputUsername" class="form-control" placeholder="E-mail" required="" autofocus="" ng-model="pageSignin.credentials.username"> | |
12 | + </div> | |
13 | + </div> | |
14 | + <div class="form-group"> | |
15 | + <label for="inputPassword" class="sr-only">Senha:</label> | |
16 | + <div class="input-group"> | |
17 | + <div class="input-group-addon"><span class="glyphicon glyphicon-lock"></span></div> | |
18 | + <input type="password" id="inputPassword" class="form-control" placeholder="Senha" required="" ng-model="pageSignin.credentials.password"> | |
19 | + </div> | |
20 | + </div> | |
21 | + <div class="form-group"> | |
22 | + <button class="btn btn-lg btn-primary btn-block" type="submit">Entrar</button> | |
23 | + </div> | |
24 | + </form> | |
25 | + </div> | |
26 | + </div> | |
27 | + <div class="row"> | |
28 | + <div class="col-sm-8 col-sm-offset-2"> | |
29 | + <hr class="separator-or"></hr> | |
30 | + </div> | |
31 | + </div> | |
32 | + <div class="row"> | |
33 | + <div class="col-sm-8 col-sm-offset-2"> | |
34 | + <button class="btn btn-lg btn-link btn-block" type="button" ui-sref="cadastrar">Cadastre-se</button> | |
35 | + </div> | |
36 | + </div> | |
37 | + </div> | |
38 | +</section> | ... | ... |
... | ... | @@ -0,0 +1,58 @@ |
1 | +<!-- Facebook --> | |
2 | +<!-- <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 33 33" width="25" height="25"><path d="M18 32L12 32 12 16l-4 0 0-5.5 4 0 0-3.2C12 2.7 13.2 0 18.5 0l4.4 0 0 5.5 -2.8 0c-2.1 0-2.2 0.8-2.2 2.2l0 2.8 5 0 -0.6 5.5L18 16 18 32z"/></svg> --> | |
3 | +<!-- Twitter --> | |
4 | +<!-- <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 33 33" width="25" height="25"><path d="M32 6.1c-1.2 0.5-2.4 0.9-3.8 1 1.4-0.8 2.4-2.1 2.9-3.6 -1.3 0.8-2.7 1.3-4.2 1.6 -1.2-1.3-2.9-2.1-4.8-2.1 -3.6 0-6.6 2.9-6.6 6.6 0 0.5 0.1 1 0.2 1.5 -5.5-0.3-10.3-2.9-13.5-6.9 -0.6 1-0.9 2.1-0.9 3.3 0 2.3 1.2 4.3 2.9 5.5 -1.1 0-2.1-0.3-3-0.8 0 0 0 0.1 0 0.1 0 3.2 2.3 5.8 5.3 6.4 -0.6 0.2-1.1 0.2-1.7 0.2 -0.4 0-0.8 0-1.2-0.1 0.8 2.6 3.3 4.5 6.1 4.6 -2.2 1.8-5.1 2.8-8.2 2.8 -0.5 0-1.1 0-1.6-0.1 2.9 1.9 6.4 3 10.1 3 12.1 0 18.7-10 18.7-18.7 0-0.3 0-0.6 0-0.8C30 8.5 31.1 7.4 32 6.1z"/></svg> --> | |
5 | +<!-- Google Plus --> | |
6 | +<!-- <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 33 33" width="25" height="25"><path d="M17.5 2c0 0-6.3 0-8.4 0C5.3 2 1.8 4.8 1.8 8.1c0 3.4 2.6 6.1 6.4 6.1 0.3 0 0.5 0 0.8 0 -0.2 0.5-0.4 1-0.4 1.6 0 0.9 0.5 1.7 1.1 2.3 -0.5 0-0.9 0-1.5 0C3.6 18.1 0 21.1 0 24.1c0 3 3.9 4.9 8.6 4.9 5.3 0 8.2-3 8.2-6 0-2.4-0.7-3.9-2.9-5.4 -0.8-0.5-2.2-1.8-2.2-2.6 0-0.9 0.3-1.3 1.6-2.4 1.4-1.1 2.4-2.6 2.4-4.4 0-2.1-0.9-4.2-2.7-4.8l2.7 0L17.5 2zM14.5 22.5c0.1 0.3 0.1 0.6 0.1 0.9 0 2.4-1.6 4.4-6.1 4.4 -3.2 0-5.5-2-5.5-4.5 0-2.4 2.9-4.4 6.1-4.4 0.8 0 1.4 0.1 2.1 0.3C12.9 20.4 14.2 21.1 14.5 22.5zM9.4 13.4c-2.2-0.1-4.2-2.4-4.6-5.2 -0.4-2.8 1.1-5 3.2-4.9 2.2 0.1 4.2 2.3 4.6 5.2C13 11.2 11.6 13.4 9.4 13.4zM26 8L26 2 24 2 24 8 18 8 18 10 24 10 24 16 26 16 26 10 32 10 32 8z"/></svg> --> | |
7 | + | |
8 | +<section> | |
9 | + <div class="container"> | |
10 | + <div class="row"> | |
11 | + <div class="col-sm-12"> | |
12 | + <h1>Cadastro</h1> | |
13 | + <p>Cadastre-se para fazer parte do Dialoga Brasil, interagir com as propostas e enviar as suas!</p> | |
14 | + </div> | |
15 | + </div> | |
16 | + </div> | |
17 | +</section> | |
18 | +<section role="main" class="section-gray auth-content"> | |
19 | + <div class="container"> | |
20 | + <div class="row"> | |
21 | + <div class="col-sm-8 col-sm-offset-2"> | |
22 | + <h2>Conecte-se por redes sociais</h2> | |
23 | + <div class="col-sm-6"> | |
24 | + <button type="button" class="btn btn-lg btn-block btn-social btn-facebook"> | |
25 | + <span class="glyphicon icon-facebook icon-white" aria-hidden="true"> | |
26 | + <!-- Facebook --> | |
27 | + <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 33 33" width="25" height="25"><path d="M18 32L12 32 12 16l-4 0 0-5.5 4 0 0-3.2C12 2.7 13.2 0 18.5 0l4.4 0 0 5.5 -2.8 0c-2.1 0-2.2 0.8-2.2 2.2l0 2.8 5 0 -0.6 5.5L18 16 18 32z"/></svg> | |
28 | + </span> | |
29 | + <span class="text"> | |
30 | + Conectar pelo Facebook | |
31 | + </span> | |
32 | + </button> | |
33 | + </div> | |
34 | + <div class="col-sm-6"> | |
35 | + <button type="button" class="btn btn-lg btn-block btn-social btn-google-plus"> | |
36 | + <span class="glyphicon icon-google-plus icon-white" aria-hidden="true"> | |
37 | + <!-- Google Plus --> | |
38 | + <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 33 33" width="25" height="25"><path d="M17.5 2c0 0-6.3 0-8.4 0C5.3 2 1.8 4.8 1.8 8.1c0 3.4 2.6 6.1 6.4 6.1 0.3 0 0.5 0 0.8 0 -0.2 0.5-0.4 1-0.4 1.6 0 0.9 0.5 1.7 1.1 2.3 -0.5 0-0.9 0-1.5 0C3.6 18.1 0 21.1 0 24.1c0 3 3.9 4.9 8.6 4.9 5.3 0 8.2-3 8.2-6 0-2.4-0.7-3.9-2.9-5.4 -0.8-0.5-2.2-1.8-2.2-2.6 0-0.9 0.3-1.3 1.6-2.4 1.4-1.1 2.4-2.6 2.4-4.4 0-2.1-0.9-4.2-2.7-4.8l2.7 0L17.5 2zM14.5 22.5c0.1 0.3 0.1 0.6 0.1 0.9 0 2.4-1.6 4.4-6.1 4.4 -3.2 0-5.5-2-5.5-4.5 0-2.4 2.9-4.4 6.1-4.4 0.8 0 1.4 0.1 2.1 0.3C12.9 20.4 14.2 21.1 14.5 22.5zM9.4 13.4c-2.2-0.1-4.2-2.4-4.6-5.2 -0.4-2.8 1.1-5 3.2-4.9 2.2 0.1 4.2 2.3 4.6 5.2C13 11.2 11.6 13.4 9.4 13.4zM26 8L26 2 24 2 24 8 18 8 18 10 24 10 24 16 26 16 26 10 32 10 32 8z"/></svg> | |
39 | + </span> | |
40 | + <span class="text"> | |
41 | + Conectar pelo Google+ | |
42 | + </span> | |
43 | + </button> | |
44 | + </div> | |
45 | + </div> | |
46 | + </div> | |
47 | + <div class="row"> | |
48 | + <div class="col-sm-8 col-sm-offset-2"> | |
49 | + <hr class="separator-or"></hr> | |
50 | + </div> | |
51 | + </div> | |
52 | + <div class="row"> | |
53 | + <div class="col-sm-8 col-sm-offset-2"> | |
54 | + <h2>Faça o cadastro abaixo</h2> | |
55 | + </div> | |
56 | + </div> | |
57 | + </div> | |
58 | +</section> | ... | ... |
... | ... | @@ -0,0 +1,21 @@ |
1 | +$barra-theme: ("green": #00420c, "yellow": #2c66ce, "blue": #0042b1); | |
2 | + | |
3 | +#footer-brasil { | |
4 | + background: none repeat scroll 0% 0% map-get($barra-theme, "blue"); | |
5 | + padding: 1em 0px; | |
6 | + max-width: 100%; | |
7 | +} | |
8 | + | |
9 | +#footer { | |
10 | + padding: 20px 0; | |
11 | + a { | |
12 | + margin: 10px auto; | |
13 | + } | |
14 | + | |
15 | + .contraste & { | |
16 | + background-color: #000; | |
17 | + a { | |
18 | + color: #fff; | |
19 | + } | |
20 | + } | |
21 | +} | ... | ... |
... | ... | @@ -0,0 +1,26 @@ |
1 | +<header class="container"> | |
2 | + | |
3 | + <div class="row"> | |
4 | + <div class="col-sm-12"> | |
5 | + | |
6 | + <div class="accessibility-wrapper"> | |
7 | + | |
8 | + <button type="button" class="btn btn-link pull-right" ui-sref="entrar"> | |
9 | + <span class="icon icon-user" aria-hidden="true"></span> | |
10 | + Entrar | |
11 | + </button> | |
12 | + </div> | |
13 | + </div> | |
14 | + </div> | |
15 | + | |
16 | + <div class="row"> | |
17 | + <app-navbar></app-navbar> | |
18 | + </div> | |
19 | + | |
20 | + <!-- TODO: breadcrumb --> | |
21 | + <!-- <ol class="breadcrumb"> | |
22 | + <li><a href="#">Home</a></li> | |
23 | + <li><a href="#">Library</a></li> | |
24 | + <li class="active">Data</li> | |
25 | + </ol> --> | |
26 | +</header> | ... | ... |
... | ... | @@ -0,0 +1,16 @@ |
1 | +.accessibility-wrapper { | |
2 | + .icon-user { | |
3 | + display: inline-block; | |
4 | + vertical-align: middle; | |
5 | + width: 26px; | |
6 | + height: 26px; | |
7 | + border: 1px solid #ccc; | |
8 | + border-radius: 100%; | |
9 | + background-position: 1px 0px; | |
10 | + | |
11 | + .contraste & { | |
12 | + // XXX: chage for dinamic handler | |
13 | + background-position: -0px -24px; | |
14 | + } | |
15 | + } | |
16 | +} | ... | ... |
... | ... | @@ -0,0 +1,152 @@ |
1 | +/* globals document:true, window:true */ | |
2 | +(function() { | |
3 | + 'use strict'; | |
4 | + | |
5 | + angular | |
6 | + .module('dialoga') | |
7 | + .controller('InicioPageController', InicioPageController); | |
8 | + | |
9 | + /** @ngInject */ | |
10 | + function InicioPageController(ArticleService, $rootScope, $sce, $log) { | |
11 | + var vm = this; | |
12 | + | |
13 | + // aliases | |
14 | + vm.ArticleService = ArticleService; | |
15 | + vm.$sce = $sce; | |
16 | + vm.$log = $log; | |
17 | + | |
18 | + vm.init(); | |
19 | + vm.$log.debug('InicioPageController'); | |
20 | + } | |
21 | + | |
22 | + InicioPageController.prototype.init = function() { | |
23 | + var vm = this; | |
24 | + | |
25 | + vm.error = null; | |
26 | + vm.loading = true; | |
27 | + vm.loadHomeArticle(); | |
28 | + }; | |
29 | + | |
30 | + InicioPageController.prototype.loadHomeArticle = function() { | |
31 | + var vm = this; | |
32 | + | |
33 | + vm.content = vm.ArticleService.getHomeAbstract(); | |
34 | + vm.isCached = !!vm.content; | |
35 | + | |
36 | + if (vm.isCached) { | |
37 | + hideBackground(2000); | |
38 | + } | |
39 | + | |
40 | + vm.ArticleService.getHome(function(data) { | |
41 | + vm.loading = false; | |
42 | + vm.article = data.article; | |
43 | + }, function(error) { | |
44 | + vm.$log.error('Error on getHome article.', error); | |
45 | + vm.error = 'Erro ao carregar o conteúdo principal.'; | |
46 | + }); | |
47 | + }; | |
48 | + | |
49 | + InicioPageController.prototype.showVideo = function() { | |
50 | + var vm = this; | |
51 | + | |
52 | + // we need handle home content | |
53 | + if (vm.isCached) { | |
54 | + hideBackground(0); // force to hide | |
55 | + vm.$log.warn('The content already cached. Aborting.'); | |
56 | + return; | |
57 | + } | |
58 | + | |
59 | + vm.content = vm.handleHomeAbstract(vm.article.abstract); | |
60 | + vm.ArticleService.setHomeAbstract(vm.content); | |
61 | + | |
62 | + // inject dependencies | |
63 | + injectIframeApiJs(); | |
64 | + window.onYouTubeIframeAPIReady = window.onYouTubeIframeAPIReady || onYouTubeIframeAPIReady; | |
65 | + window.onYouTubePlayerReady = window.onYouTubePlayerReady || onYouTubePlayerReady; | |
66 | + }; | |
67 | + | |
68 | + InicioPageController.prototype.handleHomeAbstract = function(abstract) { | |
69 | + var vm = this; | |
70 | + | |
71 | + abstract = forceIframeParams(abstract); | |
72 | + abstract = removeStylefromIframe(abstract); | |
73 | + | |
74 | + return vm.$sce.trustAsHtml(abstract); | |
75 | + }; | |
76 | + | |
77 | + function injectIframeApiJs() { | |
78 | + var tag = document.createElement('script'); | |
79 | + tag.src = 'https://www.youtube.com/iframe_api'; | |
80 | + | |
81 | + var firstScriptTag = document.getElementsByTagName('script')[0]; | |
82 | + firstScriptTag.parentNode.insertBefore(tag, firstScriptTag); | |
83 | + } | |
84 | + | |
85 | + function onYouTubeIframeAPIReady() { | |
86 | + var ytIframe = angular.element.find('.js-iframe iframe'); | |
87 | + var YTPlayer = window.YT.Player; | |
88 | + new YTPlayer(ytIframe[0], { | |
89 | + events: { | |
90 | + 'onReady': onYouTubePlayerReady | |
91 | + } | |
92 | + }); | |
93 | + } | |
94 | + | |
95 | + function onYouTubePlayerReady (event) { | |
96 | + event.target.playVideo(); | |
97 | + hideBackground(1000); | |
98 | + } | |
99 | + | |
100 | + function hideBackground (ms) { | |
101 | + var $elBg = angular.element.find('.video-background'); | |
102 | + angular.element($elBg).fadeOut(ms || 100); | |
103 | + // angular.element($elBg).hide(); | |
104 | + } | |
105 | + | |
106 | + function forceIframeParams(abstract) { | |
107 | + var patternIframe = '<iframe src="'; | |
108 | + var indexOfIframe = abstract.indexOf(patternIframe); | |
109 | + | |
110 | + if (indexOfIframe === -1) { | |
111 | + return abstract; | |
112 | + } | |
113 | + | |
114 | + var startSrcUrl = indexOfIframe + patternIframe.length; | |
115 | + var endSrcUrl = abstract.indexOf('"', startSrcUrl); | |
116 | + var srcUrl = abstract.substring(startSrcUrl , endSrcUrl); | |
117 | + var resultUrl = srcUrl; | |
118 | + var c = (srcUrl.indexOf('?') !== -1) ? '&' : ''; // already have url params. So, append-it | |
119 | + | |
120 | + // enable js api | |
121 | + if (srcUrl.indexOf('enablejsapi=1') === -1) { | |
122 | + resultUrl += c + 'enablejsapi=1'; | |
123 | + c = '&'; // force to always use '&' after here | |
124 | + } | |
125 | + | |
126 | + // set opaque mode | |
127 | + if (srcUrl.indexOf('wmode=opaque') === -1) { | |
128 | + resultUrl += c + 'wmode=opaque'; | |
129 | + // c = '&'; // force to always use '&' after here | |
130 | + } | |
131 | + | |
132 | + abstract = abstract.replace(srcUrl, resultUrl); | |
133 | + | |
134 | + return abstract; | |
135 | + } | |
136 | + | |
137 | + function removeStylefromIframe (abstract) { | |
138 | + var patternIframe = 'style="'; | |
139 | + var indexOfIframe = abstract.indexOf('<iframe'); | |
140 | + var indexOfStyleOnIframe = abstract.indexOf('style="', indexOfIframe); | |
141 | + | |
142 | + if (indexOfStyleOnIframe === -1) { | |
143 | + return abstract; | |
144 | + } | |
145 | + | |
146 | + var startStyleContent = indexOfStyleOnIframe + patternIframe.length; | |
147 | + var endStyleContent = abstract.indexOf('"', startStyleContent); | |
148 | + var style = abstract.substring(startStyleContent , endStyleContent); | |
149 | + | |
150 | + return abstract.replace(style, ''); | |
151 | + } | |
152 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,15 @@ |
1 | +(function() { | |
2 | + 'use strict'; | |
3 | + | |
4 | + describe('controllers', function(){ | |
5 | + | |
6 | + beforeEach(module('dialoga')); | |
7 | + | |
8 | + // it('should define more than 5 awesome things', inject(function($controller) { | |
9 | + // var vm = $controller('InicioPageController'); | |
10 | + | |
11 | + // expect(angular.isArray(vm.awesomeThings)).toBeTruthy(); | |
12 | + // expect(vm.awesomeThings.length > 5).toBeTruthy(); | |
13 | + // })); | |
14 | + }); | |
15 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,50 @@ |
1 | +<section class="container" role="main"> | |
2 | + <div class="row"> | |
3 | + <div class="col-sm-10 col-sm-offset-1"> | |
4 | + <div class="video-wrapper"> | |
5 | + <div class="video-player js-youtube"> | |
6 | + <div class="embed-responsive embed-responsive-16by9"> | |
7 | + <div class="js-iframe" ng-show="pageInicio.content" ng-bind-html="pageInicio.content"></div> | |
8 | + <div class="video-background" ng-click="pageInicio.showVideo()"> | |
9 | + <div class="video-thumbnail" aria-hidden="true" style="background-image:url(/assets/images/youtube-background.png)"></div> | |
10 | + <button class="video-play-button" aria-live="assertive" aria-label="Assistir o vídeo tutorial Dialoga Brasil"> | |
11 | + <svg height="100%" version="1.1" viewBox="0 0 68 48" width="100%"><path class="ytp-play-button-bg" d="m .66,37.62 c 0,0 .66,4.70 2.70,6.77 2.58,2.71 5.98,2.63 7.49,2.91 5.43,.52 23.10,.68 23.12,.68 .00,-1.3e-5 14.29,-0.02 23.81,-0.71 1.32,-0.15 4.22,-0.17 6.81,-2.89 2.03,-2.07 2.70,-6.77 2.70,-6.77 0,0 .67,-5.52 .67,-11.04 l 0,-5.17 c 0,-5.52 -0.67,-11.04 -0.67,-11.04 0,0 -0.66,-4.70 -2.70,-6.77 C 62.03,.86 59.13,.84 57.80,.69 48.28,0 34.00,0 34.00,0 33.97,0 19.69,0 10.18,.69 8.85,.84 5.95,.86 3.36,3.58 1.32,5.65 .66,10.35 .66,10.35 c 0,0 -0.55,4.50 -0.66,9.45 l 0,8.36 c .10,4.94 .66,9.45 .66,9.45 z" fill="#1f1f1e" fill-opacity="0.9"></path><path d="m 26.96,13.67 18.37,9.62 -18.37,9.55 -0.00,-19.17 z" fill="#fff"></path><path d="M 45.02,23.46 45.32,23.28 26.96,13.67 43.32,24.34 45.02,23.46 z" fill="#ccc"></path></svg> | |
12 | + </button> | |
13 | + </div> | |
14 | + </div> | |
15 | + </div> | |
16 | + </div> | |
17 | + </div> | |
18 | + </div> | |
19 | + <!-- <div class="js-event-wrapper hide" ng-show="inicio.eventListIsVisible"> --> | |
20 | + <div class="js-event-wrapper"> | |
21 | + <event-list></event-list> | |
22 | + </div> | |
23 | +</section> | |
24 | + | |
25 | +<section class="info-section" ng-if="pageInicio.loading || pageInicio.error"> | |
26 | + <div class="container"> | |
27 | + <div class="col-md-12"> | |
28 | + <div ng-if="pageInicio.loading && !pageInicio.error"> | |
29 | + <div class="alert alert-info">Carregando conteúdo...</div> | |
30 | + </div> | |
31 | + | |
32 | + <div ng-if="pageInicio.error"> | |
33 | + <div class="alert alert-danger">{{pageInicio.error}}</div> | |
34 | + </div> | |
35 | + </div> | |
36 | + </div> | |
37 | +</section> | |
38 | + | |
39 | +<section class="section-gray section-space-up" ng-if="pageInicio.article"> | |
40 | + <div class="container"> | |
41 | + <div id="lista-de-programas" class="row"> | |
42 | + <div class="col-sm-4 col-md-3"> | |
43 | + <category-list></category-list> | |
44 | + </div> | |
45 | + <div class="col-sm-8 col-md-9"> | |
46 | + <article-grid></article-grid> | |
47 | + </div> | |
48 | + </div> | |
49 | + </div> | |
50 | +</section> | ... | ... |
... | ... | @@ -0,0 +1,89 @@ |
1 | +.section-gray { | |
2 | + background-color: $gray; | |
3 | + | |
4 | + .contraste & { | |
5 | + color: #fff; | |
6 | + background-color: #000; | |
7 | + } | |
8 | +} | |
9 | + | |
10 | +.section-space-up { | |
11 | + padding-top: 30px; | |
12 | +} | |
13 | + | |
14 | +.video-wrapper { | |
15 | + // margin-bottom: 30px; | |
16 | +} | |
17 | + | |
18 | +.video-player { | |
19 | + position: relative; | |
20 | + border: 1px solid #333; | |
21 | + | |
22 | + .video-background { | |
23 | + text-align: center; | |
24 | + cursor: pointer; | |
25 | + } | |
26 | + | |
27 | + .video-thumbnail { | |
28 | + position: absolute; | |
29 | + width: 100%; | |
30 | + height: 100%; | |
31 | + top: 0; | |
32 | + left: 0; | |
33 | + z-index: 10; | |
34 | + background-position: center; | |
35 | + background-repeat: no-repeat; | |
36 | + -moz-transition: opacity .5s cubic-bezier(0.0,0.0,0.2,1); | |
37 | + -webkit-transition: opacity .5s cubic-bezier(0.0,0.0,0.2,1); | |
38 | + transition: opacity .5s cubic-bezier(0.0,0.0,0.2,1); | |
39 | + background-size: cover; | |
40 | + -moz-background-size: cover; | |
41 | + -webkit-background-size: cover; | |
42 | + } | |
43 | + | |
44 | + .video-play-button { | |
45 | + border: none; | |
46 | + outline: 0; | |
47 | + color: inherit; | |
48 | + text-align: inherit; | |
49 | + font-size: 100%; | |
50 | + font-family: inherit; | |
51 | + cursor: pointer; | |
52 | + line-height: inherit; | |
53 | + background: transparent; | |
54 | + padding: 0; | |
55 | + | |
56 | + position: absolute; | |
57 | + top: 50%; | |
58 | + left: 50%; | |
59 | + width: 68px; | |
60 | + height: 48px; | |
61 | + margin-left: -34px; | |
62 | + margin-top: -24px; | |
63 | + z-index: 15; | |
64 | + | |
65 | + -moz-transition: opacity .25s cubic-bezier(0.0,0.0,0.2,1); | |
66 | + -webkit-transition: opacity .25s cubic-bezier(0.0,0.0,0.2,1); | |
67 | + transition: opacity .25s cubic-bezier(0.0,0.0,0.2,1); | |
68 | + } | |
69 | + | |
70 | + .ytp-play-button-bg { | |
71 | + -moz-transition: fill .1s cubic-bezier(0.4,0.0,1,1),opacity .1s cubic-bezier(0.4,0.0,1,1); | |
72 | + -webkit-transition: fill .1s cubic-bezier(0.4,0.0,1,1),opacity .1s cubic-bezier(0.4,0.0,1,1); | |
73 | + transition: fill .1s cubic-bezier(0.4,0.0,1,1),opacity .1s cubic-bezier(0.4,0.0,1,1); | |
74 | + fill: #1f1f1f; | |
75 | + opacity: .9; | |
76 | + } | |
77 | + | |
78 | + &:hover { | |
79 | + .ytp-play-button-bg { | |
80 | + fill: #cc181e; | |
81 | + opacity: 1; | |
82 | + } | |
83 | + } | |
84 | + | |
85 | + @media screen and (min-width: 992px) { | |
86 | + width: 80%; | |
87 | + margin: 0 auto; | |
88 | + } | |
89 | +} | ... | ... |
... | ... | @@ -0,0 +1,31 @@ |
1 | +<div class="container page--conheca-o-programa"> | |
2 | + <div ng-if="pageProgramaContent.article && pageProgramaContent.categories"> | |
3 | + <article-bar category="pageProgramaContent.article.categories[0]" categories="pageProgramaContent.categories"></article-bar> | |
4 | + </div> | |
5 | + | |
6 | + <div ng-if="!pageProgramaContent.article.body"> | |
7 | + <div ng-if="!pageProgramaContent.error" class="alert alert-info" role="alert">Carregando detalhes sobre o progama...</div> | |
8 | + <div ng-if="pageProgramaContent.error" class="alert alert-warning" role="alert">{{pageProgramaContent}}</div> | |
9 | + </div> | |
10 | + | |
11 | + <div ng-if="pageProgramaContent.article.body"> | |
12 | + <article class="program-content"> | |
13 | + <div> | |
14 | + <section ng-bind-html="pageProgramaContent.article.body"></section> | |
15 | + </div> | |
16 | + </article> | |
17 | + <aside class="program--aside"ng-class="pageProgramaContent.article.categories[0].slug"> | |
18 | + <div class="col-sm-6" > | |
19 | + <div class="button--themed"> | |
20 | + <button class="btn btn-block" ng-click="pageProgramaContent.goToPreview()"> | |
21 | + <span class="glyphicon glyphicon-arrow-left" aria-hidden="true"></span> | |
22 | + Participe | |
23 | + </button> | |
24 | + </div> | |
25 | + </div> | |
26 | + <div class="col-sm-6"> | |
27 | + <social-share></social-share> | |
28 | + </div> | |
29 | + </aside> | |
30 | + </div> | |
31 | +</div> | ... | ... |
... | ... | @@ -0,0 +1,81 @@ |
1 | +(function() { | |
2 | + 'use strict'; | |
3 | + | |
4 | + angular | |
5 | + .module('dialoga') | |
6 | + .controller('ProgramaContentPageController', ProgramaContentPageController); | |
7 | + | |
8 | + /** @ngInject */ | |
9 | + function ProgramaContentPageController(ArticleService, $state, $location, $scope, $rootScope, $log) { | |
10 | + $log.debug('ProgramaContentPageController'); | |
11 | + | |
12 | + var vm = this; | |
13 | + | |
14 | + vm.ArticleService = ArticleService; | |
15 | + vm.$state = $state; | |
16 | + vm.$location = $location; | |
17 | + vm.$scope = $scope; | |
18 | + vm.$rootScope = $rootScope; | |
19 | + vm.$log = $log; | |
20 | + | |
21 | + vm.init(); | |
22 | + } | |
23 | + | |
24 | + ProgramaContentPageController.prototype.init = function () { | |
25 | + var vm = this; | |
26 | + | |
27 | + var params = vm.$state.params; | |
28 | + var slug = params.slug; | |
29 | + | |
30 | + vm.article = null; | |
31 | + vm.categories = null; | |
32 | + vm.currentCategory = null; | |
33 | + vm.loading = true; | |
34 | + vm.error = false; | |
35 | + | |
36 | + vm.ArticleService.getCategories(function(categories){ | |
37 | + vm.categories = categories; | |
38 | + }, function (error) { | |
39 | + vm.error = error; | |
40 | + vm.$log.error(error); | |
41 | + }); | |
42 | + | |
43 | + vm.ArticleService.getArticleBySlug(slug, function(article){ | |
44 | + vm.article = article; | |
45 | + vm.currentCategory = vm.article.categories[0]; | |
46 | + | |
47 | + vm.loadContent(); | |
48 | + | |
49 | + }, function (error) { | |
50 | + vm.$log.error(error); | |
51 | + vm.$log.info('Rollback to home page.'); | |
52 | + vm.$state.go('inicio', {}, {location: true}); | |
53 | + }); | |
54 | + }; | |
55 | + | |
56 | + ProgramaContentPageController.prototype.loadContent = function () { | |
57 | + var vm = this; | |
58 | + | |
59 | + vm.loading = true; | |
60 | + if(!vm.article.body){ | |
61 | + vm.ArticleService.getContentById(vm.article.id, function (data) { | |
62 | + vm.article.body = data.article.body; | |
63 | + vm.loading = false; | |
64 | + }, function (error) { | |
65 | + vm.loading = false; | |
66 | + vm.error = error; | |
67 | + }); | |
68 | + } | |
69 | + vm.loading = false; | |
70 | + }; | |
71 | + | |
72 | + ProgramaContentPageController.prototype.goToPreview = function () { | |
73 | + var vm = this; | |
74 | + | |
75 | + vm.$state.go('programa', { | |
76 | + slug: vm.article.slug | |
77 | + }, { | |
78 | + location: true | |
79 | + }); | |
80 | + }; | |
81 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,68 @@ |
1 | +(function() { | |
2 | + 'use strict'; | |
3 | + | |
4 | + angular | |
5 | + .module('dialoga') | |
6 | + .controller('ProgramaPageController', ProgramaPageController); | |
7 | + | |
8 | + /** @ngInject */ | |
9 | + function ProgramaPageController(ArticleService, $state, $location, $scope, $rootScope, $log) { | |
10 | + $log.debug('ProgramaPageController'); | |
11 | + | |
12 | + var vm = this; | |
13 | + | |
14 | + vm.ArticleService = ArticleService; | |
15 | + vm.$state = $state; | |
16 | + vm.$location = $location; | |
17 | + vm.$scope = $scope; | |
18 | + vm.$rootScope = $rootScope; | |
19 | + vm.$log = $log; | |
20 | + | |
21 | + vm.init(); | |
22 | + } | |
23 | + | |
24 | + ProgramaPageController.prototype.init = function () { | |
25 | + var vm = this; | |
26 | + | |
27 | + var params = vm.$state.params; | |
28 | + var slug = params.slug; | |
29 | + | |
30 | + vm.article = null; | |
31 | + vm.categories = null; | |
32 | + vm.currentCategory = null; | |
33 | + vm.loading = true; | |
34 | + vm.error = false; | |
35 | + | |
36 | + vm.ArticleService.getCategories(function(categories){ | |
37 | + vm.categories = categories; | |
38 | + }, function (error) { | |
39 | + vm.error = error; | |
40 | + vm.$log.error(error); | |
41 | + }); | |
42 | + | |
43 | + vm.ArticleService.getArticleBySlug(slug, function(article){ | |
44 | + vm.article = article; | |
45 | + vm.currentCategory = vm.article.categories[0]; | |
46 | + | |
47 | + // load proposals | |
48 | + // vm.ArticleService.getRandomProposal(program.id, function(proposal){ | |
49 | + // vm.article.proposal = proposal; | |
50 | + // }, function (error){ | |
51 | + // vm.$log.error(error); | |
52 | + // }); | |
53 | + | |
54 | + // load events | |
55 | + // vm.ArticleService.getEvents(program.id, function(proposal){ | |
56 | + // vm.article.proposal = proposal; | |
57 | + // }, function (error){ | |
58 | + // vm.$log.error(error); | |
59 | + // }); | |
60 | + | |
61 | + }, function (error) { | |
62 | + vm.error = error; | |
63 | + vm.$log.error(error); | |
64 | + vm.$log.info('Rollback to home page.'); | |
65 | + vm.$state.go('inicio', {}, {location: true}); | |
66 | + }); | |
67 | + }; | |
68 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,52 @@ |
1 | +(function() { | |
2 | + 'use strict'; | |
3 | + | |
4 | + describe('Controller: ProgramaPageController', function(){ | |
5 | + var $rootScope, $scope, $location, $controller, httpBackend, programaPageController; | |
6 | + var ENDPOINT_ARTICLE_HOME = 'http://login.dialoga.gov.br/api/v1/articles/103358?fields=id,children,categories,abstract,title,image,url,setting,position&private_token=null'; | |
7 | + | |
8 | + beforeEach(module('dialoga')); | |
9 | + beforeEach( inject(function(_$rootScope_, _$controller_, _$location_, $httpBackend) { | |
10 | + $rootScope = _$rootScope_; | |
11 | + $controller = _$controller_; | |
12 | + $location = _$location_; | |
13 | + $scope = $rootScope.$new(); | |
14 | + httpBackend = $httpBackend; | |
15 | + | |
16 | + programaPageController = $controller('ProgramaPageController', { | |
17 | + '$rootScope': $rootScope, | |
18 | + '$scope': $scope | |
19 | + }); | |
20 | + | |
21 | + httpBackend.whenGET(ENDPOINT_ARTICLE_HOME).respond({ | |
22 | + 'article':{'id':103358,'abstract':'\u003Cp style=\"text-align: center;\"\u003E\u003Ciframe src=\"https://www.youtube.com/embed/kpAdrO-emV0?rel=0\u0026amp;showinfo=0\u0026amp;iv_load_policy=3\u0026amp;controls=1\" style=\"max-width: 1000px; left: 5%;\" width=\"275\" height=\"200\"\u003E\u003C/iframe\u003E\u003C/p\u003E','title':'Dialoga Brasil','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null},{'name':'Seguran\u00e7a P\u00fablica','id':182,'slug':'seguranca-publica','image':null},{'name':'Educa\u00e7\u00e3o','id':181,'slug':'educacao','image':null},{'name':'Redu\u00e7\u00e3o da Pobreza','id':183,'slug':'reducao-da-pobreza','image':null}],'image':null,'setting':{'custom_body_label':'Corpo','phase':'proposals','allow_topics':true,'moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Leandro Nunes dos Santos','moderate_proposals':true,'allow_members_to_edit':false},'position':null,'children':[{'id':103644,'abstract':'\u003Cp\u003EUm caminho de oportunidades com o Enem: Sisu, Prouni, Fies, Ci\u00eancia sem Fronteiras\u003C/p\u003E','title':'Ensino Superior','categories':[{'name':'Educa\u00e7\u00e3o','id':181,'slug':'educacao','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0128/enem.jpg'},'setting':{'color':'#cfe2f3','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':9},{'id':103673,'abstract':'\u003Cp\u003EA melhor escolha \u00e9 se informar.\u003C/p\u003E','title':'Incentivo ao Parto Normal','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0092/parto-normal.jpg'},'setting':{'color':'#ff0000','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':6},{'id':103397,'abstract':'\u003Cp\u003ERenda, inclus\u00e3o produtiva e acesso a servi\u00e7os.\u003C/p\u003E','title':'Brasil Sem Mis\u00e9ria','categories':[{'name':'Redu\u00e7\u00e3o da Pobreza','id':183,'slug':'reducao-da-pobreza','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0116/bsm_redim.jpg'},'setting':{'color':'','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':18},{'id':103379,'abstract':'\u003Cp\u003EResgate e atendimento 24 horas, sete dias da semana.\u003C/p\u003E','title':'SAMU 192 e UPAs','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0060/SAMU.jpg'},'setting':{'color':'#45818e','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':4},{'id':103521,'abstract':'\u003Cp\u003EMais atendimento nos munic\u00edpios, mais sa\u00fade para quem mais precisa.\u003C/p\u003E','title':'Mais M\u00e9dicos','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0025/Mais_M_dicos.jpg'},'setting':{'color':'#ffe599','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':1},{'id':103390,'abstract':'\u003Cp\u003EPreven\u00e7\u00e3o, tratamento e enfrentamento ao tr\u00e1fico.\u003C/p\u003E','title':'Crack, \u00e9 poss\u00edvel vencer!','categories':[{'name':'Seguran\u00e7a P\u00fablica','id':182,'slug':'seguranca-publica','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0104/crack.jpg'},'setting':{'color':'#00ff00','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':14},{'id':103592,'abstract':'\u003Cp\u003EGarantir acesso \u00e0 prote\u00e7\u00e3o social.\u003C/p\u003E','title':'Assist\u00eancia Social','categories':[{'name':'Redu\u00e7\u00e3o da Pobreza','id':183,'slug':'reducao-da-pobreza','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0122/assistencia_social.jpg'},'setting':{'color':'#a61c00','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':19},{'id':103426,'abstract':'\u003Cp\u003EDa sa\u00fade se cuida todos os dias.\u003C/p\u003E','title':'Vida saud\u00e1vel','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0046/vida_saudavel.jpg'},'setting':{'color':'#d9d2e9','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':7},{'id':103695,'abstract':'\u003Cp\u003ENovo modelo de atua\u00e7\u00e3o em Seguran\u00e7a P\u00fablica.\u003C/p\u003E','title':'Seguran\u00e7a P\u00fablica Integrada','categories':[{'name':'Seguran\u00e7a P\u00fablica','id':182,'slug':'seguranca-publica','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0152/policiaintegrada.jpg'},'setting':{'color':'#ff00ff','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':13},{'id':103663,'abstract':'\u003Cp\u003EMais educa\u00e7\u00e3o profissional e tecnol\u00f3gica, mais desenvolvimento\u003C/p\u003E','title':'Ensino T\u00e9cnico','categories':[{'name':'Educa\u00e7\u00e3o','id':181,'slug':'educacao','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0134/Ensino_tecnico.jpg'},'setting':{'color':'#d0e0e3','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':10},{'id':103472,'abstract':'\u003Cp\u003EPol\u00edcia Federal, Pol\u00edcia Rodovi\u00e1ria Federal e For\u00e7a Nacional de Seguran\u00e7a P\u00fablica.\u003C/p\u003E','title':'For\u00e7as Federais de Seguran\u00e7a','categories':[{'name':'Seguran\u00e7a P\u00fablica','id':182,'slug':'seguranca-publica','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0031/federais2.png'},'setting':{'color':'','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':16},{'id':103612,'abstract':'\u003Cp\u003EGarantir \u00e1gua para beber e produzir.\u003C/p\u003E','title':'Cisternas','categories':[{'name':'Redu\u00e7\u00e3o da Pobreza','id':183,'slug':'reducao-da-pobreza','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0039/cisterna_redim.jpg'},'setting':{'color':'#0000ff','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':20},{'id':103442,'abstract':'\u003Cp\u003EComplemento \u00e0 renda e acompanhamento em educa\u00e7\u00e3o e sa\u00fade.\u003C/p\u003E','title':'Bolsa Fam\u00edlia','categories':[{'name':'Redu\u00e7\u00e3o da Pobreza','id':183,'slug':'reducao-da-pobreza','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0013/bolsa_familia_redim.jpg'},'setting':{'color':'#ff9900','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':17},{'id':103507,'abstract':'\u003Cp\u003ETecnologia a servi\u00e7o da seguran\u00e7a do cidad\u00e3o.\u003C/p\u003E','title':'Sinesp','categories':[{'name':'Seguran\u00e7a P\u00fablica','id':182,'slug':'seguranca-publica','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0098/sinesp.png'},'setting':{'color':'#00ff00','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':12},{'id':103683,'abstract':'\u003Cp\u003ESa\u00fade n\u00e3o tem pre\u00e7o.\u003C/p\u003E','title':'Aqui tem Farm\u00e1cia Popular','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0019/saude_nao_tem_preco.jpg'},'setting':{'color':'#e69138','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':5},{'id':103457,'abstract':'\u003Cp\u003EA\u00e7\u00e3o conjunta e coopera\u00e7\u00e3o transfronteiri\u00e7a.\u003C/p\u003E','title':'Prote\u00e7\u00e3o das Fronteiras','categories':[{'name':'Seguran\u00e7a P\u00fablica','id':182,'slug':'seguranca-publica','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0110/fronteira_redim.jpg'},'setting':{'color':'#a64d79','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':15},{'id':103494,'abstract':'\u003Cp\u003EDa Educa\u00e7\u00e3o Infantil ao Ensino M\u00e9dio.\u003C/p\u003E','title':'Educa\u00e7\u00e3o B\u00e1sica','categories':[{'name':'Educa\u00e7\u00e3o','id':181,'slug':'educacao','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0076/Educa__o_B_sica.jpg'},'setting':{'color':'#fce5cd','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':8},{'id':103359,'abstract':'\u003Cp\u003EAcesso a exames e consultas com especialistas.\u003C/p\u003E','title':'Mais Especialidades','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0083/mais_especialidades1.png'},'setting':{'color':'#ea9999','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':2},{'id':103485,'abstract':'\u003Cp\u003ECaminho para uma educa\u00e7\u00e3o de qualidade.\u003C/p\u003E','title':'Valoriza\u00e7\u00e3o dos Professores','categories':[{'name':'Educa\u00e7\u00e3o','id':181,'slug':'educacao','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0140/valorizacao_professor.jpg'},'setting':{'color':'#ffff00','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':11},{'id':103416,'abstract':'\u003Cp\u003EEstrutura adequada para atender melhor a popula\u00e7\u00e3o na aten\u00e7\u00e3o b\u00e1sica.\u003C/p\u003E','title':'Melhorar os Postos de Sa\u00fade','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0053/requalif_redim.jpg'},'setting':{'color':'#cc4125','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':3}]} | |
23 | + }); | |
24 | + })); | |
25 | + | |
26 | + it('should have a ProgramaPageController controller', function () { | |
27 | + // console.log('programaPageController', programaPageController); | |
28 | + | |
29 | + // expect current path to equal '/programa/:slug' | |
30 | + $location.path('/programa/bolsa-familia'); | |
31 | + $rootScope.$apply(); | |
32 | + expect($location.path()).toBe('/programa/bolsa-familia'); | |
33 | + | |
34 | + // expect current scope has a friendly-url to a program | |
35 | + expect(programaPageController.$state).toBeDefined(); | |
36 | + expect(programaPageController.$state.params).toBeDefined(); | |
37 | + expect(programaPageController.$state.params.slug).toBe('bolsa-familia'); | |
38 | + | |
39 | + // what to check when user is not logged in here? | |
40 | + // what to check when user is logged in here? | |
41 | + }); | |
42 | + it('should be able to go back to "inicio"', function () {}); | |
43 | + it('ensure valid proposal to be sended', function () {}); | |
44 | + it('should be able to send a proposal', function () {}); | |
45 | + it('should be able to vote on proposal', function () {}); | |
46 | + it('should be able to vote on same proposal only once', function () {}); | |
47 | + it('should be able to view a unique proposal by URL', function () {}); | |
48 | + it('should be able to view a table with ranking of all proposals by category', function () {}); | |
49 | + it('should be able to share a proposal on social medias', function () {}); | |
50 | + | |
51 | + }); | |
52 | +})(); | ... | ... |
... | ... | @@ -0,0 +1,15 @@ |
1 | +<div class="container"> | |
2 | + | |
3 | + <div ng-if="pagePrograma.article && pagePrograma.categories"> | |
4 | + <article-bar category="pagePrograma.article.categories[0]" categories="pagePrograma.categories"></article-bar> | |
5 | + </div> | |
6 | + | |
7 | + <div ng-if="!pagePrograma.article"> | |
8 | + <div class="alert alert-info" role="alert">Carregando informações sobre o progama</div> | |
9 | + </div> | |
10 | + | |
11 | + <div ng-if="pagePrograma.article && pagePrograma.categories"> | |
12 | + <article-preview article="pagePrograma.article"></article-preview> | |
13 | + </div> | |
14 | +</div> | |
15 | + | ... | ... |
src/app/partials/article/article.controller.js
... | ... | @@ -1,28 +0,0 @@ |
1 | -(function() { | |
2 | - 'use strict'; | |
3 | - | |
4 | - angular | |
5 | - .module('dialoga') | |
6 | - .controller('ArticleController', ArticleController); | |
7 | - | |
8 | - /** @ngInject */ | |
9 | - function ArticleController($state, $log) { | |
10 | - $log.debug('ArticleController'); | |
11 | - | |
12 | - var vm = this; | |
13 | - | |
14 | - vm.page = $state.current.name; | |
15 | - | |
16 | - switch ( $state.current.name ) { | |
17 | - case 'sobre': | |
18 | - break; | |
19 | - case 'termos-de-uso': | |
20 | - break; | |
21 | - default: | |
22 | - $log.debug('$state.current.name', $state.current.name); | |
23 | - break; | |
24 | - } | |
25 | - | |
26 | - // page = $state.is('sobre'); | |
27 | - } | |
28 | -})(); |
src/app/partials/article/article.controller.spec.js
... | ... | @@ -1,15 +0,0 @@ |
1 | -(function() { | |
2 | - 'use strict'; | |
3 | - | |
4 | - describe('controllers', function(){ | |
5 | - | |
6 | - beforeEach(module('dialoga')); | |
7 | - | |
8 | - // it('should define more than 5 awesome things', inject(function($controller) { | |
9 | - // var vm = $controller('SobreController'); | |
10 | - | |
11 | - // // expect(angular.isArray(vm.awesomeThings)).toBeTruthy(); | |
12 | - // // expect(vm.awesomeThings.length > 5).toBeTruthy(); | |
13 | - // })); | |
14 | - }); | |
15 | -})(); |
src/app/partials/article/article.html
src/app/partials/article/article.service.js
... | ... | @@ -1,46 +0,0 @@ |
1 | -(function() { | |
2 | - 'use strict'; | |
3 | - | |
4 | - angular | |
5 | - .module('dialoga') | |
6 | - .factory('ArticleService', ArticleService); | |
7 | - | |
8 | - /** @ngInject */ | |
9 | - function ArticleService($http, $q, api, UtilService, $log) { | |
10 | - $log.debug('ArticleService'); | |
11 | - | |
12 | - var idArticleHome = '103358'; | |
13 | - var _savedAbstract = null; | |
14 | - | |
15 | - var service = { | |
16 | - apiArticles: api.host + '/api/v1/articles/', | |
17 | - getHome: getHome, | |
18 | - setHomeAbstract: setHomeAbstract, | |
19 | - getHomeAbstract: getHomeAbstract | |
20 | - }; | |
21 | - | |
22 | - return service; | |
23 | - | |
24 | - function getHome () { | |
25 | - return getArticleById(idArticleHome); | |
26 | - } | |
27 | - | |
28 | - function getArticleById (articleId) { | |
29 | - var url = service.apiArticles + articleId; | |
30 | - var params = { | |
31 | - fields: 'id,children,categories,abstract,title,image,url,setting,position', | |
32 | - private_token: 'null' | |
33 | - }; | |
34 | - | |
35 | - return UtilService.get(url, {params: params}); | |
36 | - } | |
37 | - | |
38 | - function setHomeAbstract (newAbstract) { | |
39 | - _savedAbstract = newAbstract; | |
40 | - } | |
41 | - | |
42 | - function getHomeAbstract () { | |
43 | - return _savedAbstract; | |
44 | - } | |
45 | - } | |
46 | -})(); |
src/app/partials/article/article.service.spec.js
... | ... | @@ -1,68 +0,0 @@ |
1 | -(function() { | |
2 | - 'use strict'; | |
3 | - | |
4 | - describe('article services', function() { | |
5 | - var ArticleService, httpBackend; | |
6 | - | |
7 | - beforeEach(module('dialoga')); | |
8 | - | |
9 | - beforeEach(inject(function(_ArticleService_, $httpBackend) { | |
10 | - ArticleService = _ArticleService_; | |
11 | - httpBackend = $httpBackend; | |
12 | - })); | |
13 | - | |
14 | - it('should return the main article', function() { | |
15 | - var url = 'http://login.dialoga.gov.br/api/v1/articles/103358?fields=id,children,categories,abstract,title,image,url,setting,position&private_token=null'; | |
16 | - httpBackend.whenGET(url).respond({ | |
17 | - 'article':{'id':103358,'abstract':'\u003Cp style=\"text-align: center;\"\u003E\u003Ciframe src=\"https://www.youtube.com/embed/kpAdrO-emV0?rel=0\u0026amp;showinfo=0\u0026amp;iv_load_policy=3\u0026amp;controls=1\" style=\"max-width: 1000px; left: 5%;\" width=\"275\" height=\"200\"\u003E\u003C/iframe\u003E\u003C/p\u003E','title':'Dialoga Brasil','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null},{'name':'Seguran\u00e7a P\u00fablica','id':182,'slug':'seguranca-publica','image':null},{'name':'Educa\u00e7\u00e3o','id':181,'slug':'educacao','image':null},{'name':'Redu\u00e7\u00e3o da Pobreza','id':183,'slug':'reducao-da-pobreza','image':null}],'image':null,'setting':{'custom_body_label':'Corpo','phase':'proposals','allow_topics':true,'moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Leandro Nunes dos Santos','moderate_proposals':true,'allow_members_to_edit':false},'position':null,'children':[{'id':103644,'abstract':'\u003Cp\u003EUm caminho de oportunidades com o Enem: Sisu, Prouni, Fies, Ci\u00eancia sem Fronteiras\u003C/p\u003E','title':'Ensino Superior','categories':[{'name':'Educa\u00e7\u00e3o','id':181,'slug':'educacao','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0128/enem.jpg'},'setting':{'color':'#cfe2f3','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':9},{'id':103673,'abstract':'\u003Cp\u003EA melhor escolha \u00e9 se informar.\u003C/p\u003E','title':'Incentivo ao Parto Normal','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0092/parto-normal.jpg'},'setting':{'color':'#ff0000','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':6},{'id':103397,'abstract':'\u003Cp\u003ERenda, inclus\u00e3o produtiva e acesso a servi\u00e7os.\u003C/p\u003E','title':'Brasil Sem Mis\u00e9ria','categories':[{'name':'Redu\u00e7\u00e3o da Pobreza','id':183,'slug':'reducao-da-pobreza','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0116/bsm_redim.jpg'},'setting':{'color':'','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':18},{'id':103379,'abstract':'\u003Cp\u003EResgate e atendimento 24 horas, sete dias da semana.\u003C/p\u003E','title':'SAMU 192 e UPAs','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0060/SAMU.jpg'},'setting':{'color':'#45818e','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':4},{'id':103521,'abstract':'\u003Cp\u003EMais atendimento nos munic\u00edpios, mais sa\u00fade para quem mais precisa.\u003C/p\u003E','title':'Mais M\u00e9dicos','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0025/Mais_M_dicos.jpg'},'setting':{'color':'#ffe599','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':1},{'id':103390,'abstract':'\u003Cp\u003EPreven\u00e7\u00e3o, tratamento e enfrentamento ao tr\u00e1fico.\u003C/p\u003E','title':'Crack, \u00e9 poss\u00edvel vencer!','categories':[{'name':'Seguran\u00e7a P\u00fablica','id':182,'slug':'seguranca-publica','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0104/crack.jpg'},'setting':{'color':'#00ff00','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':14},{'id':103592,'abstract':'\u003Cp\u003EGarantir acesso \u00e0 prote\u00e7\u00e3o social.\u003C/p\u003E','title':'Assist\u00eancia Social','categories':[{'name':'Redu\u00e7\u00e3o da Pobreza','id':183,'slug':'reducao-da-pobreza','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0122/assistencia_social.jpg'},'setting':{'color':'#a61c00','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':19},{'id':103426,'abstract':'\u003Cp\u003EDa sa\u00fade se cuida todos os dias.\u003C/p\u003E','title':'Vida saud\u00e1vel','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0046/vida_saudavel.jpg'},'setting':{'color':'#d9d2e9','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':7},{'id':103695,'abstract':'\u003Cp\u003ENovo modelo de atua\u00e7\u00e3o em Seguran\u00e7a P\u00fablica.\u003C/p\u003E','title':'Seguran\u00e7a P\u00fablica Integrada','categories':[{'name':'Seguran\u00e7a P\u00fablica','id':182,'slug':'seguranca-publica','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0152/policiaintegrada.jpg'},'setting':{'color':'#ff00ff','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':13},{'id':103663,'abstract':'\u003Cp\u003EMais educa\u00e7\u00e3o profissional e tecnol\u00f3gica, mais desenvolvimento\u003C/p\u003E','title':'Ensino T\u00e9cnico','categories':[{'name':'Educa\u00e7\u00e3o','id':181,'slug':'educacao','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0134/Ensino_tecnico.jpg'},'setting':{'color':'#d0e0e3','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':10},{'id':103472,'abstract':'\u003Cp\u003EPol\u00edcia Federal, Pol\u00edcia Rodovi\u00e1ria Federal e For\u00e7a Nacional de Seguran\u00e7a P\u00fablica.\u003C/p\u003E','title':'For\u00e7as Federais de Seguran\u00e7a','categories':[{'name':'Seguran\u00e7a P\u00fablica','id':182,'slug':'seguranca-publica','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0031/federais2.png'},'setting':{'color':'','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':16},{'id':103612,'abstract':'\u003Cp\u003EGarantir \u00e1gua para beber e produzir.\u003C/p\u003E','title':'Cisternas','categories':[{'name':'Redu\u00e7\u00e3o da Pobreza','id':183,'slug':'reducao-da-pobreza','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0039/cisterna_redim.jpg'},'setting':{'color':'#0000ff','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':20},{'id':103442,'abstract':'\u003Cp\u003EComplemento \u00e0 renda e acompanhamento em educa\u00e7\u00e3o e sa\u00fade.\u003C/p\u003E','title':'Bolsa Fam\u00edlia','categories':[{'name':'Redu\u00e7\u00e3o da Pobreza','id':183,'slug':'reducao-da-pobreza','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0013/bolsa_familia_redim.jpg'},'setting':{'color':'#ff9900','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':17},{'id':103507,'abstract':'\u003Cp\u003ETecnologia a servi\u00e7o da seguran\u00e7a do cidad\u00e3o.\u003C/p\u003E','title':'Sinesp','categories':[{'name':'Seguran\u00e7a P\u00fablica','id':182,'slug':'seguranca-publica','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0098/sinesp.png'},'setting':{'color':'#00ff00','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':12},{'id':103683,'abstract':'\u003Cp\u003ESa\u00fade n\u00e3o tem pre\u00e7o.\u003C/p\u003E','title':'Aqui tem Farm\u00e1cia Popular','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0019/saude_nao_tem_preco.jpg'},'setting':{'color':'#e69138','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':5},{'id':103457,'abstract':'\u003Cp\u003EA\u00e7\u00e3o conjunta e coopera\u00e7\u00e3o transfronteiri\u00e7a.\u003C/p\u003E','title':'Prote\u00e7\u00e3o das Fronteiras','categories':[{'name':'Seguran\u00e7a P\u00fablica','id':182,'slug':'seguranca-publica','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0110/fronteira_redim.jpg'},'setting':{'color':'#a64d79','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':15},{'id':103494,'abstract':'\u003Cp\u003EDa Educa\u00e7\u00e3o Infantil ao Ensino M\u00e9dio.\u003C/p\u003E','title':'Educa\u00e7\u00e3o B\u00e1sica','categories':[{'name':'Educa\u00e7\u00e3o','id':181,'slug':'educacao','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0076/Educa__o_B_sica.jpg'},'setting':{'color':'#fce5cd','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':8},{'id':103359,'abstract':'\u003Cp\u003EAcesso a exames e consultas com especialistas.\u003C/p\u003E','title':'Mais Especialidades','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0083/mais_especialidades1.png'},'setting':{'color':'#ea9999','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':2},{'id':103485,'abstract':'\u003Cp\u003ECaminho para uma educa\u00e7\u00e3o de qualidade.\u003C/p\u003E','title':'Valoriza\u00e7\u00e3o dos Professores','categories':[{'name':'Educa\u00e7\u00e3o','id':181,'slug':'educacao','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0140/valorizacao_professor.jpg'},'setting':{'color':'#ffff00','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':11},{'id':103416,'abstract':'\u003Cp\u003EEstrutura adequada para atender melhor a popula\u00e7\u00e3o na aten\u00e7\u00e3o b\u00e1sica.\u003C/p\u003E','title':'Melhorar os Postos de Sa\u00fade','categories':[{'name':'Sa\u00fade','id':180,'slug':'saude','image':null}],'image':{'url':'/image_uploads/dialoga/0000/0053/requalif_redim.jpg'},'setting':{'color':'#cc4125','moderate_comments':false,'comment_paragraph_plugin_activate':false,'author_name':'Ronald Emerson Scherolt da Costa','allow_members_to_edit':false},'position':3}]}}); | |
18 | - | |
19 | - ArticleService.getHome().then(function(result) { | |
20 | - | |
21 | - expect(result.article).toBeDefined(); | |
22 | - expect(result.article.title).toEqual('Dialoga Brasil'); | |
23 | - | |
24 | - }); | |
25 | - | |
26 | - httpBackend.flush(); | |
27 | - }); | |
28 | - | |
29 | - // it('should return a list of articles', function() { | |
30 | - | |
31 | - // httpBackend.whenGET('http://login.dialoga.gov.br/api/v1/articles').respond({ | |
32 | - // "articles": [ | |
33 | - // { | |
34 | - // abstract: "Que exista educação continuada permanente dos profissionais!!", | |
35 | - // author: null, | |
36 | - // body: "", | |
37 | - // categories: [], | |
38 | - // children: [], | |
39 | - // created_at: "2015/08/04 16:36:13", | |
40 | - // end_date: null, | |
41 | - // hits: 0, | |
42 | - // id: 120568, | |
43 | - // image: null, | |
44 | - // parent: {id: 103379,…}, | |
45 | - // position: null, | |
46 | - // profile: {identifier: "dialoga", name: "dialoga", id: 19195, created_at: "2015/04/15 09:38:36", image: null}, | |
47 | - // setting: {comment_paragraph_plugin_activate: false, author_name: "estacio"}, | |
48 | - // start_date: null, | |
49 | - // tag_list: [], | |
50 | - // title: "article_f4f4601c-0f36-e90e-d01a-9871f0bd126b", | |
51 | - // votes_against: 0, | |
52 | - // votes_for: 0, | |
53 | - // } | |
54 | - // ] | |
55 | - // }); | |
56 | - | |
57 | - // ArticleService.getList().then(function(result) { | |
58 | - // console.log('result', result); | |
59 | - | |
60 | - // expect(result.data.article).toBeDefined(); | |
61 | - // expect(result.data.article.title).toEqual('Dialoga Brasil'); | |
62 | - | |
63 | - // }); | |
64 | - | |
65 | - // httpBackend.flush(); | |
66 | - // }); | |
67 | - }); | |
68 | -})(); |
src/app/partials/auth/auth.controller.js
... | ... | @@ -1,44 +0,0 @@ |
1 | -(function() { | |
2 | - 'use strict'; | |
3 | - | |
4 | - angular | |
5 | - .module('dialoga') | |
6 | - .controller('AuthController', AuthController); | |
7 | - | |
8 | - /** @ngInject */ | |
9 | - function AuthController($rootScope, AUTH_EVENTS, AuthService, Session, $log) { | |
10 | - $log.debug('AuthController'); | |
11 | - | |
12 | - var vm = this; | |
13 | - | |
14 | - vm.$rootScope = $rootScope; | |
15 | - vm.AUTH_EVENTS = AUTH_EVENTS; | |
16 | - vm.AuthService = AuthService; | |
17 | - vm.Session = Session; | |
18 | - vm.$log = $log; | |
19 | - | |
20 | - vm.init(); | |
21 | - } | |
22 | - | |
23 | - AuthController.prototype.init = function() { | |
24 | - var vm = this; | |
25 | - | |
26 | - // init variables | |
27 | - vm.credentials = {}; | |
28 | - | |
29 | - // attach events | |
30 | - | |
31 | - // ... | |
32 | - }; | |
33 | - | |
34 | - AuthController.prototype.login = function(credentials) { | |
35 | - var vm = this; | |
36 | - | |
37 | - vm.AuthService.login(credentials).then(function(user) { | |
38 | - // handle view | |
39 | - }, function() { | |
40 | - // handle view | |
41 | - }); | |
42 | - }; | |
43 | - | |
44 | -})(); |
src/app/partials/auth/auth.scss
... | ... | @@ -1,44 +0,0 @@ |
1 | -.btn-social { | |
2 | - color: #fff; | |
3 | - font-weight: bold; | |
4 | - | |
5 | - &:hover, | |
6 | - &:focus {color: #fff;} | |
7 | - | |
8 | - &.btn-facebook { | |
9 | - background-color: #33477a; | |
10 | - &:hover, | |
11 | - &:focus {background-color: #304373; } | |
12 | - &:active {background-color: #33477a; } | |
13 | - } | |
14 | - &.btn-google-plus { | |
15 | - background-color: #b92d25; | |
16 | - &:hover, | |
17 | - &:focus {background-color: #b12b23; } | |
18 | - &:active {background-color: #b92d25; } | |
19 | - } | |
20 | -} | |
21 | - | |
22 | -.glyphicon { | |
23 | - &.icon-white { | |
24 | - fill: white; | |
25 | - } | |
26 | -} | |
27 | - | |
28 | -.separator-or { | |
29 | - border-top: 2px solid #d8d8d8; | |
30 | - text-align: center; | |
31 | - font-weight: bold; | |
32 | - | |
33 | - &:after { | |
34 | - content: "ou"; | |
35 | - position: absolute; | |
36 | - top: 4px; | |
37 | - left: 50%; | |
38 | - margin-left: -26px; | |
39 | - font-size: 30px; | |
40 | - line-height: 30px; | |
41 | - padding: 0 0.25em; | |
42 | - background: $gray; | |
43 | - } | |
44 | -} |
src/app/partials/auth/signin.html
... | ... | @@ -1,38 +0,0 @@ |
1 | -<section role="main" class="section-gray"> | |
2 | - <div class="container"> | |
3 | - <div class="row"> | |
4 | - <div class="col-sm-8 col-sm-offset-2"> | |
5 | - <h2>Identifique-se</h2> | |
6 | - <form name="loginForm" ng-submit="login.login(login.credentials)"> | |
7 | - <div class="form-group"> | |
8 | - <label for="inputUsername" class="sr-only">E-mail:</label> | |
9 | - <div class="input-group"> | |
10 | - <div class="input-group-addon"><span class="glyphicon glyphicon-user"></span></div> | |
11 | - <input type="text" id="inputUsername" class="form-control" placeholder="E-mail" required="" autofocus="" ng-model="login.credentials.username"> | |
12 | - </div> | |
13 | - </div> | |
14 | - <div class="form-group"> | |
15 | - <label for="inputPassword" class="sr-only">Senha:</label> | |
16 | - <div class="input-group"> | |
17 | - <div class="input-group-addon"><span class="glyphicon glyphicon-lock"></span></div> | |
18 | - <input type="password" id="inputPassword" class="form-control" placeholder="Senha" required="" ng-model="login.credentials.password"> | |
19 | - </div> | |
20 | - </div> | |
21 | - <div class="form-group"> | |
22 | - <button class="btn btn-lg btn-primary btn-block" type="submit">Entrar</button> | |
23 | - </div> | |
24 | - </form> | |
25 | - </div> | |
26 | - </div> | |
27 | - <div class="row"> | |
28 | - <div class="col-sm-8 col-sm-offset-2"> | |
29 | - <hr class="separator-or"></hr> | |
30 | - </div> | |
31 | - </div> | |
32 | - <div class="row"> | |
33 | - <div class="col-sm-8 col-sm-offset-2"> | |
34 | - <button class="btn btn-lg btn-link btn-block" type="button" ui-sref="cadastrar">Cadastre-se</button> | |
35 | - </div> | |
36 | - </div> | |
37 | - </div> | |
38 | -</section> |
src/app/partials/auth/signup.html
... | ... | @@ -1,54 +0,0 @@ |
1 | -<section> | |
2 | - <div class="container"> | |
3 | - <div class="row"> | |
4 | - <div class="col-sm-12"> | |
5 | - <h1>Cadastro</h1> | |
6 | - <p>Cadastre-se para fazer parte do Dialoga Brasil, interagir com as propostas e enviar as suas!</p> | |
7 | - </div> | |
8 | - </div> | |
9 | - </div> | |
10 | -</section> | |
11 | -<section role="main" class="section-gray"> | |
12 | - <div class="container"> | |
13 | - <div class="row"> | |
14 | - <div class="col-sm-8 col-sm-offset-2"> | |
15 | - <h2>Conecte-se por redes sociais</h2> | |
16 | - <div class="col-sm-6"> | |
17 | - <button type="button" class="btn btn-lg btn-block btn-social btn-facebook"> | |
18 | - <span class="glyphicon icon-facebook icon-white" aria-hidden="true"> | |
19 | - <!-- Facebook --> | |
20 | - <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 33 33" width="25" height="25"><path d="M18 32L12 32 12 16l-4 0 0-5.5 4 0 0-3.2C12 2.7 13.2 0 18.5 0l4.4 0 0 5.5 -2.8 0c-2.1 0-2.2 0.8-2.2 2.2l0 2.8 5 0 -0.6 5.5L18 16 18 32z"/></svg> | |
21 | - | |
22 | - <!-- Twitter --> | |
23 | - <!-- <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 33 33" width="25" height="25"><path d="M32 6.1c-1.2 0.5-2.4 0.9-3.8 1 1.4-0.8 2.4-2.1 2.9-3.6 -1.3 0.8-2.7 1.3-4.2 1.6 -1.2-1.3-2.9-2.1-4.8-2.1 -3.6 0-6.6 2.9-6.6 6.6 0 0.5 0.1 1 0.2 1.5 -5.5-0.3-10.3-2.9-13.5-6.9 -0.6 1-0.9 2.1-0.9 3.3 0 2.3 1.2 4.3 2.9 5.5 -1.1 0-2.1-0.3-3-0.8 0 0 0 0.1 0 0.1 0 3.2 2.3 5.8 5.3 6.4 -0.6 0.2-1.1 0.2-1.7 0.2 -0.4 0-0.8 0-1.2-0.1 0.8 2.6 3.3 4.5 6.1 4.6 -2.2 1.8-5.1 2.8-8.2 2.8 -0.5 0-1.1 0-1.6-0.1 2.9 1.9 6.4 3 10.1 3 12.1 0 18.7-10 18.7-18.7 0-0.3 0-0.6 0-0.8C30 8.5 31.1 7.4 32 6.1z"/></svg> --> | |
24 | - </span> | |
25 | - <span class="text"> | |
26 | - Conectar pelo Facebook | |
27 | - </span> | |
28 | - </button> | |
29 | - </div> | |
30 | - <div class="col-sm-6"> | |
31 | - <button type="button" class="btn btn-lg btn-block btn-social btn-google-plus"> | |
32 | - <span class="glyphicon icon-google-plus icon-white" aria-hidden="true"> | |
33 | - <!-- Google + --> | |
34 | - <svg xmlns="http://www.w3.org/2000/svg" viewBox="0 0 33 33" width="25" height="25"><path d="M17.5 2c0 0-6.3 0-8.4 0C5.3 2 1.8 4.8 1.8 8.1c0 3.4 2.6 6.1 6.4 6.1 0.3 0 0.5 0 0.8 0 -0.2 0.5-0.4 1-0.4 1.6 0 0.9 0.5 1.7 1.1 2.3 -0.5 0-0.9 0-1.5 0C3.6 18.1 0 21.1 0 24.1c0 3 3.9 4.9 8.6 4.9 5.3 0 8.2-3 8.2-6 0-2.4-0.7-3.9-2.9-5.4 -0.8-0.5-2.2-1.8-2.2-2.6 0-0.9 0.3-1.3 1.6-2.4 1.4-1.1 2.4-2.6 2.4-4.4 0-2.1-0.9-4.2-2.7-4.8l2.7 0L17.5 2zM14.5 22.5c0.1 0.3 0.1 0.6 0.1 0.9 0 2.4-1.6 4.4-6.1 4.4 -3.2 0-5.5-2-5.5-4.5 0-2.4 2.9-4.4 6.1-4.4 0.8 0 1.4 0.1 2.1 0.3C12.9 20.4 14.2 21.1 14.5 22.5zM9.4 13.4c-2.2-0.1-4.2-2.4-4.6-5.2 -0.4-2.8 1.1-5 3.2-4.9 2.2 0.1 4.2 2.3 4.6 5.2C13 11.2 11.6 13.4 9.4 13.4zM26 8L26 2 24 2 24 8 18 8 18 10 24 10 24 16 26 16 26 10 32 10 32 8z"/></svg> | |
35 | - </span> | |
36 | - <span class="text"> | |
37 | - Conectar pelo Google+ | |
38 | - </span> | |
39 | - </button> | |
40 | - </div> | |
41 | - </div> | |
42 | - </div> | |
43 | - <div class="row"> | |
44 | - <div class="col-sm-8 col-sm-offset-2"> | |
45 | - <hr class="separator-or"></hr> | |
46 | - </div> | |
47 | - </div> | |
48 | - <div class="row"> | |
49 | - <div class="col-sm-8 col-sm-offset-2"> | |
50 | - <h2>Faça o cadastro abaixo</h2> | |
51 | - </div> | |
52 | - </div> | |
53 | - </div> | |
54 | -</section> |
src/app/partials/footer/footer.html
src/app/partials/footer/footer.scss
src/app/partials/header/header.controller.js
... | ... | @@ -1,16 +0,0 @@ |
1 | -(function() { | |
2 | - 'use strict'; | |
3 | - | |
4 | - angular | |
5 | - .module('dialoga') | |
6 | - .controller('HeaderController', HeaderController); | |
7 | - | |
8 | - /** @ngInject */ | |
9 | - function HeaderController($log) { | |
10 | - var vm = this; | |
11 | - | |
12 | - vm.$log = $log; | |
13 | - vm.$log.debug('HeaderController'); | |
14 | - } | |
15 | - | |
16 | -})(); |
src/app/partials/header/header.html
... | ... | @@ -1,19 +0,0 @@ |
1 | -<header class="container" ng-controller="HeaderController as header"> | |
2 | - | |
3 | - <div class="row"> | |
4 | - <div class="accessibility-wrapper"> | |
5 | - <button type="button" id="display-contrast" class="btn btn-link" ng-click="toggleContrast()"> | |
6 | - <span class="glyphicon glyphicon-adjust" aria-hidden="true"></span> Alto Contraste | |
7 | - </button> | |
8 | - | |
9 | - <button type="button" class="btn btn-link pull-right" ui-sref="entrar"> | |
10 | - <span class="glyphicon glyphicon-user"></span> | |
11 | - Entrar | |
12 | - </button> | |
13 | - </div> | |
14 | - </div> | |
15 | - | |
16 | - <div class="row"> | |
17 | - <app-navbar></app-navbar> | |
18 | - </div> | |
19 | -</header> |