From a0182957e75b2e81ab5883ad0c920344fde79cde Mon Sep 17 00:00:00 2001 From: Berkeley Martinez Date: Thu, 8 Oct 2015 16:42:24 -0700 Subject: [PATCH 1/8] Add chat to challenges! --- client/commonFramework.js | 8 ++++++++ client/less/main.less | 5 +++++ server/middlewares/csp.js | 1 + server/views/coursewares/showBonfire.jade | 16 +++++++++++----- server/views/coursewares/showHTML.jade | 8 +++++++- server/views/coursewares/showJS.jade | 15 ++++++++++----- server/views/coursewares/showStep.jade | 2 ++ server/views/coursewares/showVideo.jade | 14 +++++++++----- .../views/coursewares/showZiplineOrBasejump.jade | 11 ++++++++++- server/views/partials/challenge-modals.jade | 14 -------------- 10 files changed, 63 insertions(+), 31 deletions(-) diff --git a/client/commonFramework.js b/client/commonFramework.js index a28a1e743d..5c5ebea6a5 100644 --- a/client/commonFramework.js +++ b/client/commonFramework.js @@ -49,6 +49,14 @@ var common = (function() { }); }; + // this will overwrite if gitter object is already present + common.createGitterOptions = function createGitterOptions(room) { + ((window.gitter = {}).chat = {}).options = { + room: room, + activationElement: document.createElement('div') + }; + }; + return common; })(); diff --git a/client/less/main.less b/client/less/main.less index 4340350da7..d71a96eba2 100644 --- a/client/less/main.less +++ b/client/less/main.less @@ -951,6 +951,11 @@ code { margin: 0!important; } +// gitter chat +.gitter-chat-embed { + z-index: 20000 !important; +} + //uncomment this to see the dimensions of all elements outlined in red //* { // border-color: red; diff --git a/server/middlewares/csp.js b/server/middlewares/csp.js index 74914f56b2..0c812e00c6 100644 --- a/server/middlewares/csp.js +++ b/server/middlewares/csp.js @@ -55,6 +55,7 @@ export default function csp() { return helmet.csp({ defaultSrc: trusted, scriptSrc: [ + 'https://*.gitter.im', '*.optimizely.com', '*.aspnetcdn.com', '*.d3js.org', diff --git a/server/views/coursewares/showBonfire.jade b/server/views/coursewares/showBonfire.jade index 1768bd4274..0facf90abf 100644 --- a/server/views/coursewares/showBonfire.jade +++ b/server/views/coursewares/showBonfire.jade @@ -52,7 +52,7 @@ block content label.btn.btn-success#trigger-reset-modal i.fa.fa-refresh |   Reset - label.btn.btn-success#trigger-help-modal + label.btn.btn-success.js-gitter-toggle-chat-button i.fa.fa-medkit |   Help label.btn.btn-success#trigger-issue-modal @@ -122,7 +122,13 @@ block content a.btn.btn-lg.btn-primary.btn-block(href='#', data-dismiss='modal', aria-hidden='true') Cancel include ../partials/challenge-modals script. - var MDNlinks = !{JSON.stringify(MDNlinks)}; - if (!MDNlinks.length) { - $('#MDN-links').addClass('collapse'); - } + // requires common framework + if (window.common) { + window.common.createGitterOptions('freecodecamp/helpbonfires', 'challenge-help-chat-btn'); + } + + var MDNlinks = !{JSON.stringify(MDNlinks)}; + if (!MDNlinks.length) { + $('#MDN-links').addClass('collapse'); + } + script(src="https://sidecar.gitter.im/dist/sidecar.v1.js" async defer) diff --git a/server/views/coursewares/showHTML.jade b/server/views/coursewares/showHTML.jade index f08d6997dc..f3a4b4ad11 100644 --- a/server/views/coursewares/showHTML.jade +++ b/server/views/coursewares/showHTML.jade @@ -38,7 +38,7 @@ block content label.btn.btn-success#trigger-reset-modal i.fa.fa-refresh |   Reset - label.btn.btn-success#trigger-help-modal + label.btn.btn-success.js-gitter-toggle-chat-button i.fa.fa-medkit |   Help label.btn.btn-success#trigger-issue-modal @@ -95,3 +95,9 @@ block content else a.btn.btn-lg.btn-primary.btn-block(href='/challenges/next-challenge?id=' + challengeId) Go to my next challenge include ../partials/challenge-modals + script. + // requires common framework + if (window.common) { + window.common.createGitterOptions('freecodecamp/help'); + } + script(src="https://sidecar.gitter.im/dist/sidecar.v1.js" async defer) diff --git a/server/views/coursewares/showJS.jade b/server/views/coursewares/showJS.jade index f4621b5b28..e8d693c8aa 100644 --- a/server/views/coursewares/showJS.jade +++ b/server/views/coursewares/showJS.jade @@ -43,7 +43,7 @@ block content label.btn.btn-success#trigger-reset-modal i.fa.fa-refresh |   Reset - label.btn.btn-success#trigger-help-modal + label.btn.btn-success.js-gitter-toggle-chat-button i.fa.fa-medkit |   Help label.btn.btn-success#trigger-issue-modal @@ -98,7 +98,12 @@ block content a.animated.fadeIn.btn.btn-lg.btn-primary.btn-block(href='/challenges/next-challenge?id=' + challengeId) Go to my next challenge include ../partials/challenge-modals script. - var MDNlinks = !{JSON.stringify(MDNlinks)}; - if (!MDNlinks.length) { - $('#MDN-links').addClass('collapse'); - } + // requires common framework + if (window.common) { + window.common.createGitterOptions('freecodecamp/help'); + } + var MDNlinks = !{JSON.stringify(MDNlinks)}; + if (!MDNlinks.length) { + $('#MDN-links').addClass('collapse'); + } + script(src="https://sidecar.gitter.im/dist/sidecar.v1.js" async defer) diff --git a/server/views/coursewares/showStep.jade b/server/views/coursewares/showStep.jade index 274b9e72b3..c524ab6e24 100644 --- a/server/views/coursewares/showStep.jade +++ b/server/views/coursewares/showStep.jade @@ -32,6 +32,7 @@ block content script(src=rev('/js', 'commonFramework.js')) script. var common = window.common || { init: [] }; + common.createGitterOptions('freecodecamp/help'); common.challengeId = !{JSON.stringify(challengeId)}; common.challengeName = !{JSON.stringify(name)}; common.challengeType = 7; @@ -40,3 +41,4 @@ block content common.isFrontEndCert = !{JSON.stringify(isFrontEndCert || false)}; common.isFullStackCert = !{JSON.stringify(isFullStackCert || false)}; common.challengeSeed = !{JSON.stringify(challengeSeed || [])}; + script(src="https://sidecar.gitter.im/dist/sidecar.v1.js" async defer) diff --git a/server/views/coursewares/showVideo.jade b/server/views/coursewares/showVideo.jade index bd7f42e5ed..5118a8624a 100644 --- a/server/views/coursewares/showVideo.jade +++ b/server/views/coursewares/showVideo.jade @@ -24,7 +24,7 @@ block content var userLoggedIn = true; .button-spacer .btn-group.input-group.btn-group-justified - .btn.btn-success.btn-big#trigger-help-modal + .btn.btn-success.btn-big.js-gitter-toggle-chat-button i.fa.fa-medkit |   Get help .btn.btn-success.btn-big#trigger-issue-modal @@ -74,8 +74,12 @@ block content script. $('body').bind('keypress', controlEnterHandler); script. - var challenge_Id = !{JSON.stringify(challengeId)}; - var challenge_Name = !{JSON.stringify(name)}; - var challengeType = !{JSON.stringify(challengeType)}; - var dashedName = !{JSON.stringify(dashedName)}; + var challenge_Id = !{JSON.stringify(challengeId)}; + var challenge_Name = !{JSON.stringify(name)}; + var challengeType = !{JSON.stringify(challengeType)}; + var dashedName = !{JSON.stringify(dashedName)}; + if (window.common) { + window.common.createGitterOptions('freecodecamp/help'); + } include ../partials/challenge-modals + script(src="https://sidecar.gitter.im/dist/sidecar.v1.js" async defer) diff --git a/server/views/coursewares/showZiplineOrBasejump.jade b/server/views/coursewares/showZiplineOrBasejump.jade index 174be42e3e..642599b702 100644 --- a/server/views/coursewares/showZiplineOrBasejump.jade +++ b/server/views/coursewares/showZiplineOrBasejump.jade @@ -24,7 +24,7 @@ block content a.btn.btn-big.btn-primary.btn-block(href='/challenges/next-challenge?id=' + challengeId) Go to my next challenge (ctrl + enter) .button-spacer .btn-group.input-group.btn-group-justified - .btn.btn-success.btn-big#trigger-help-modal + .btn.btn-success.btn-big.js-gitter-toggle-chat-button i.fa.fa-medkit |   Help .btn.btn-success.btn-big#trigger-issue-modal @@ -96,3 +96,12 @@ block content script. $('body').on('keypress', controlEnterHandler); include ../partials/challenge-modals + script. + if (window.common) { + window.common.createGitterOptions( + !{JSON.stringify(challengeType)} === 3 ? + 'freecodecamp/helpZiplines' : + 'freecodecamp/helpBonfires' + ); + } + script(src="https://sidecar.gitter.im/dist/sidecar.v1.js" async defer) diff --git a/server/views/partials/challenge-modals.jade b/server/views/partials/challenge-modals.jade index 46f6eae7ee..7510fbeef3 100644 --- a/server/views/partials/challenge-modals.jade +++ b/server/views/partials/challenge-modals.jade @@ -10,20 +10,6 @@ a.btn.btn-lg.btn-primary.btn-block#report-issue(name='_csrf', value=_csrf) Create my GitHub issue a.btn.btn-lg.btn-info.btn-block(href='#', data-dismiss='modal', aria-hidden='true') Cancel -#help-modal.modal(tabindex='-1') - .modal-dialog.animated.fadeIn.fast-animation - .modal-content - .modal-header.challenge-list-header Need some help? - a.close.closing-x(href='#', data-dismiss='modal', aria-hidden='true') × - .modal-body.text-center - h3 Remember to use   - a(href='//github.com/FreeCodeCamp/freecodecamp/wiki/How-to-get-help-when-you-get-stuck', target='_blank') Read-Search-Ask - | . - h3 If you've already read the errors and searched Google, you should ask for help. - h3 This will take you to our help room. - a.btn.btn-lg.btn-primary.btn-block.close-modal(href='https://gitter.im/FreeCodeCamp/help', target='_blank') Take me to the help room - a.btn.btn-lg.btn-info.btn-block(href='#', data-dismiss='modal', aria-hidden='true') Cancel - #reset-modal.modal(tabindex='-1') .modal-dialog.animated.fadeInUp.fast-animation .modal-content From 35219cdce33e459867a4abfbfacf1105dfd14e38 Mon Sep 17 00:00:00 2001 From: Berkeley Martinez Date: Fri, 16 Oct 2015 11:57:33 -0700 Subject: [PATCH 2/8] Add main chat window on nav bar chat click --- client/commonFramework.js | 8 ---- client/main.js | 47 ++++++++++++++++++- server/views/coursewares/showBonfire.jade | 13 ++--- server/views/coursewares/showHTML.jade | 12 ++--- server/views/coursewares/showJS.jade | 12 ++--- server/views/coursewares/showStep.jade | 2 - server/views/coursewares/showVideo.jade | 12 +++-- .../coursewares/showZiplineOrBasejump.jade | 20 ++++---- server/views/partials/footer.jade | 3 ++ server/views/partials/navbar.jade | 2 +- 10 files changed, 87 insertions(+), 44 deletions(-) diff --git a/client/commonFramework.js b/client/commonFramework.js index 5c5ebea6a5..a28a1e743d 100644 --- a/client/commonFramework.js +++ b/client/commonFramework.js @@ -49,14 +49,6 @@ var common = (function() { }); }; - // this will overwrite if gitter object is already present - common.createGitterOptions = function createGitterOptions(room) { - ((window.gitter = {}).chat = {}).options = { - room: room, - activationElement: document.createElement('div') - }; - }; - return common; })(); diff --git a/client/main.js b/client/main.js index 892610e1eb..6415c90d2d 100644 --- a/client/main.js +++ b/client/main.js @@ -4,6 +4,50 @@ main.mapShareKey = 'map-shares'; main.ga = window.ga || function() {}; +main = (function(main) { + + ((window.gitter = {}).chat = {}).options = { + disableDefaultChat: true + }; + // wait for sidecar to load + + main.chat = {}; + main.chat.isOpen = false; + main.chat.createHelpChat = function createHelpChat() { + throw new Error('Sidecar chat has not initialized'); + }; + + document.addEventListener('gitter-sidecar-ready', function(e) { + main.chat.GitterChat = e.detail.Chat; + + main.chat.createHelpChat = function(room, helpChatBtnClass) { + main.chat.helpChat = new main.chat.GitterChat({ + room: room, + activationElement: document.createElement('div') + }); + + $(helpChatBtnClass).on('click', function() { + main.chat.helpChat.toggleChat(true); + }); + }; + + main.chat.mainChat = new main.chat.GitterChat({ + room: 'freecodecamp/freecodecamp', + activationElement: document.createElement('div') + }); + + $('#nav-chat-btn').on('click', function() { + console.log('Create'); + if (!main.chat.isOpen) { + + main.chat.mainChat.toggleChat(true); + } + }); + }); + + return main; +}(main)); + var lastCompleted = typeof lastCompleted !== 'undefined' ? lastCompleted : ''; @@ -38,9 +82,10 @@ function setMapShare(id) { $(document).ready(function() { + var challengeName = typeof challengeName !== 'undefined' ? challengeName : - 'Untitled'; + ''; if (challengeName) { ga('send', 'event', 'Challenge', 'load', challengeName); diff --git a/server/views/coursewares/showBonfire.jade b/server/views/coursewares/showBonfire.jade index 0facf90abf..bc407a5f1d 100644 --- a/server/views/coursewares/showBonfire.jade +++ b/server/views/coursewares/showBonfire.jade @@ -52,7 +52,7 @@ block content label.btn.btn-success#trigger-reset-modal i.fa.fa-refresh |   Reset - label.btn.btn-success.js-gitter-toggle-chat-button + label.btn.btn-success#challenge-help-btn i.fa.fa-medkit |   Help label.btn.btn-success#trigger-issue-modal @@ -122,13 +122,14 @@ block content a.btn.btn-lg.btn-primary.btn-block(href='#', data-dismiss='modal', aria-hidden='true') Cancel include ../partials/challenge-modals script. - // requires common framework - if (window.common) { - window.common.createGitterOptions('freecodecamp/helpbonfires', 'challenge-help-chat-btn'); - } + + document.addEventListener('gitter-sidecar-ready', function(e) { + if (window.main) { + window.main.chat.createHelpChat('freecodecamp/helpbonfires', '#challenge-help-btn'); + } + }); var MDNlinks = !{JSON.stringify(MDNlinks)}; if (!MDNlinks.length) { $('#MDN-links').addClass('collapse'); } - script(src="https://sidecar.gitter.im/dist/sidecar.v1.js" async defer) diff --git a/server/views/coursewares/showHTML.jade b/server/views/coursewares/showHTML.jade index f3a4b4ad11..643e79cd06 100644 --- a/server/views/coursewares/showHTML.jade +++ b/server/views/coursewares/showHTML.jade @@ -38,7 +38,7 @@ block content label.btn.btn-success#trigger-reset-modal i.fa.fa-refresh |   Reset - label.btn.btn-success.js-gitter-toggle-chat-button + label.btn.btn-success#challenge-help-btn i.fa.fa-medkit |   Help label.btn.btn-success#trigger-issue-modal @@ -96,8 +96,8 @@ block content a.btn.btn-lg.btn-primary.btn-block(href='/challenges/next-challenge?id=' + challengeId) Go to my next challenge include ../partials/challenge-modals script. - // requires common framework - if (window.common) { - window.common.createGitterOptions('freecodecamp/help'); - } - script(src="https://sidecar.gitter.im/dist/sidecar.v1.js" async defer) + document.addEventListener('gitter-sidecar-ready', function(e) { + if (window.main) { + window.main.chat.createHelpChat('freecodecamp/help', '#challenge-help-btn'); + } + }); diff --git a/server/views/coursewares/showJS.jade b/server/views/coursewares/showJS.jade index e8d693c8aa..887e44c964 100644 --- a/server/views/coursewares/showJS.jade +++ b/server/views/coursewares/showJS.jade @@ -43,7 +43,7 @@ block content label.btn.btn-success#trigger-reset-modal i.fa.fa-refresh |   Reset - label.btn.btn-success.js-gitter-toggle-chat-button + label.btn.btn-success#challenge-help-btn i.fa.fa-medkit |   Help label.btn.btn-success#trigger-issue-modal @@ -98,12 +98,12 @@ block content a.animated.fadeIn.btn.btn-lg.btn-primary.btn-block(href='/challenges/next-challenge?id=' + challengeId) Go to my next challenge include ../partials/challenge-modals script. - // requires common framework - if (window.common) { - window.common.createGitterOptions('freecodecamp/help'); - } var MDNlinks = !{JSON.stringify(MDNlinks)}; if (!MDNlinks.length) { $('#MDN-links').addClass('collapse'); } - script(src="https://sidecar.gitter.im/dist/sidecar.v1.js" async defer) + document.addEventListener('gitter-sidecar-ready', function(e) { + if (window.main) { + window.main.chat.createHelpChat('freecodecamp/help', '#challenge-help-btn'); + } + }); diff --git a/server/views/coursewares/showStep.jade b/server/views/coursewares/showStep.jade index c524ab6e24..274b9e72b3 100644 --- a/server/views/coursewares/showStep.jade +++ b/server/views/coursewares/showStep.jade @@ -32,7 +32,6 @@ block content script(src=rev('/js', 'commonFramework.js')) script. var common = window.common || { init: [] }; - common.createGitterOptions('freecodecamp/help'); common.challengeId = !{JSON.stringify(challengeId)}; common.challengeName = !{JSON.stringify(name)}; common.challengeType = 7; @@ -41,4 +40,3 @@ block content common.isFrontEndCert = !{JSON.stringify(isFrontEndCert || false)}; common.isFullStackCert = !{JSON.stringify(isFullStackCert || false)}; common.challengeSeed = !{JSON.stringify(challengeSeed || [])}; - script(src="https://sidecar.gitter.im/dist/sidecar.v1.js" async defer) diff --git a/server/views/coursewares/showVideo.jade b/server/views/coursewares/showVideo.jade index 5118a8624a..90292e742d 100644 --- a/server/views/coursewares/showVideo.jade +++ b/server/views/coursewares/showVideo.jade @@ -24,7 +24,7 @@ block content var userLoggedIn = true; .button-spacer .btn-group.input-group.btn-group-justified - .btn.btn-success.btn-big.js-gitter-toggle-chat-button + .btn.btn-success.btn-big#challenge-help-btn i.fa.fa-medkit |   Get help .btn.btn-success.btn-big#trigger-issue-modal @@ -78,8 +78,10 @@ block content var challenge_Name = !{JSON.stringify(name)}; var challengeType = !{JSON.stringify(challengeType)}; var dashedName = !{JSON.stringify(dashedName)}; - if (window.common) { - window.common.createGitterOptions('freecodecamp/help'); - } + document.addEventListener('gitter-sidecar-ready', function(e) { + if (window.main) { + window.main.chat.createHelpChat('freecodecamp/help', '#challenge-help-btn'); + } + }); include ../partials/challenge-modals - script(src="https://sidecar.gitter.im/dist/sidecar.v1.js" async defer) + diff --git a/server/views/coursewares/showZiplineOrBasejump.jade b/server/views/coursewares/showZiplineOrBasejump.jade index 642599b702..2fff6c4b96 100644 --- a/server/views/coursewares/showZiplineOrBasejump.jade +++ b/server/views/coursewares/showZiplineOrBasejump.jade @@ -24,7 +24,7 @@ block content a.btn.btn-big.btn-primary.btn-block(href='/challenges/next-challenge?id=' + challengeId) Go to my next challenge (ctrl + enter) .button-spacer .btn-group.input-group.btn-group-justified - .btn.btn-success.btn-big.js-gitter-toggle-chat-button + .btn.btn-success.btn-big#challenge-help-btn i.fa.fa-medkit |   Help .btn.btn-success.btn-big#trigger-issue-modal @@ -97,11 +97,13 @@ block content $('body').on('keypress', controlEnterHandler); include ../partials/challenge-modals script. - if (window.common) { - window.common.createGitterOptions( - !{JSON.stringify(challengeType)} === 3 ? - 'freecodecamp/helpZiplines' : - 'freecodecamp/helpBonfires' - ); - } - script(src="https://sidecar.gitter.im/dist/sidecar.v1.js" async defer) + document.addEventListener('gitter-sidecar-ready', function(e) { + if (window.main) { + window.main.chat.createHelpChat( + !{JSON.stringify(challengeType)} === 3 ? + 'freecodecamp/helpZiplines' : + 'freecodecamp/helpBonfires', + '#challenge-help-btn' + ); + } + }); diff --git a/server/views/partials/footer.jade b/server/views/partials/footer.jade index 8bdc9e80b7..025b59a647 100644 --- a/server/views/partials/footer.jade +++ b/server/views/partials/footer.jade @@ -22,3 +22,6 @@ span.sr-only Free Code Camp on Twitter a.ion-locked(href="//github.com/FreeCodeCamp/freecodecamp/wiki/Free-Code-Camp's-Privacy-Policy") span.sr-only Free Code Camp's Privacy Policy + +// scripts should be moved here +script(src="https://sidecar.gitter.im/dist/sidecar.v1.js" async defer) diff --git a/server/views/partials/navbar.jade b/server/views/partials/navbar.jade index 18f3320315..73cc49dabf 100644 --- a/server/views/partials/navbar.jade +++ b/server/views/partials/navbar.jade @@ -12,7 +12,7 @@ nav.navbar.navbar-default.navbar-fixed-top.nav-height li a(href='/map') Map li - a(href='//gitter.im/FreeCodeCamp/FreeCodeCamp', target='_blank') Chat + a#nav-chat-btn(href='#' onclick="return false") Chat li a(href='/news', target='_blank') News li From 465a3e399c5969215fe65a52c609e681632b4ae4 Mon Sep 17 00:00:00 2001 From: Berkeley Martinez Date: Fri, 16 Oct 2015 13:28:53 -0700 Subject: [PATCH 3/8] Add identifiers to chat embed divs --- client/less/chat.less | 17 +++++++++++++++++ client/less/main.less | 2 ++ client/main.js | 26 ++++++++++++++++++-------- gulpfile.js | 3 ++- 4 files changed, 39 insertions(+), 9 deletions(-) create mode 100644 client/less/chat.less diff --git a/client/less/chat.less b/client/less/chat.less new file mode 100644 index 0000000000..207ab294b1 --- /dev/null +++ b/client/less/chat.less @@ -0,0 +1,17 @@ +.gitter-chat-embed { + z-index: 100; + position: fixed; + + top: 0; + left: 60%; + bottom: 0; + right: 0; + + display: flex; + flex-direction: row; + transition: transform 0.3s cubic-bezier(0.16, 0.22, 0.22, 1.7); +} + +.gitter-chat-embed.is-collapsed:not(.is-loading) { + transform: translateX(110%); +} diff --git a/client/less/main.less b/client/less/main.less index d71a96eba2..540aa96c95 100644 --- a/client/less/main.less +++ b/client/less/main.less @@ -1063,3 +1063,5 @@ code { transform: rotate(0deg); } } + +@import "chat.less"; diff --git a/client/main.js b/client/main.js index 6415c90d2d..924585623a 100644 --- a/client/main.js +++ b/client/main.js @@ -21,9 +21,15 @@ main = (function(main) { main.chat.GitterChat = e.detail.Chat; main.chat.createHelpChat = function(room, helpChatBtnClass) { + + $('body').append( + '