Start merging cytube3 account management
This commit is contained in:
parent
8d2587cebd
commit
b889f7b4c8
34 changed files with 20908 additions and 1 deletions
60
templates/account-channels.jade
Normal file
60
templates/account-channels.jade
Normal file
|
|
@ -0,0 +1,60 @@
|
|||
doctype 5
|
||||
html(lang="en")
|
||||
head
|
||||
include head
|
||||
+head()
|
||||
body
|
||||
#wrap
|
||||
nav.navbar.navbar-inverse.navbar-fixed-top(role="navigation")
|
||||
include nav
|
||||
+navheader()
|
||||
#nav-collapsible.collapse.navbar-collapse
|
||||
ul.nav.navbar-nav
|
||||
+navdefaultlinks("/account/channels")
|
||||
+navloginlogout("/account/channels")
|
||||
section#mainpage
|
||||
.container
|
||||
if !loggedIn
|
||||
.col-lg-6.col-lg-offset-3.col-md-6.col-md-offset-3
|
||||
.alert.alert-danger.messagebox.center
|
||||
strong Authorization Required
|
||||
p You must be <a href="/login">logged in</a> to view this page.
|
||||
else
|
||||
.col-lg-6.col-md-6
|
||||
h3 My Channels
|
||||
if deleteChannelError
|
||||
.alert.alert-danger.center.messagebox
|
||||
strong Channel Deletion Failed
|
||||
p= deleteChannelError
|
||||
if channels.length == 0
|
||||
.center
|
||||
strong You haven't registered any channels
|
||||
else
|
||||
table.table.table-bordered
|
||||
thead
|
||||
tr
|
||||
th Channel
|
||||
tbody
|
||||
for c in channels
|
||||
tr
|
||||
th
|
||||
form.form-inline.pull-right(action="/account/channels", method="post", onsubmit="return confirm('Are you sure you want to delete #{c.name}? This cannot be undone');")
|
||||
input(type="hidden", name="action", value="delete_channel")
|
||||
button.btn.btn-xs.btn-danger(type="submit") Delete
|
||||
span.glyphicon.glyphicon-trash
|
||||
a(href="/r/#{c.name}", style="margin-left: 5px")= c.name
|
||||
.col-lg-6.col-md-6
|
||||
h3 Register a new channel
|
||||
if newChannelError
|
||||
.alert.alert-danger.messagebox.center
|
||||
strong Channel Registration Failed
|
||||
p= newChannelError
|
||||
form(action="/account/channels", method="post")
|
||||
input(type="hidden", name="action", value="new_channel")
|
||||
.form-group
|
||||
label.control-label(for="channelname") Channel Name
|
||||
input#channelname.form-control(type="text", name="name")
|
||||
button.btn.btn-primary.btn-block(type="submit") Register
|
||||
|
||||
include footer
|
||||
+footer()
|
||||
94
templates/account-edit.jade
Normal file
94
templates/account-edit.jade
Normal file
|
|
@ -0,0 +1,94 @@
|
|||
doctype 5
|
||||
html(lang="en")
|
||||
head
|
||||
include head
|
||||
+head()
|
||||
body
|
||||
#wrap
|
||||
nav.navbar.navbar-inverse.navbar-fixed-top(role="navigation")
|
||||
include nav
|
||||
+navheader()
|
||||
#nav-collapsible.collapse.navbar-collapse
|
||||
ul.nav.navbar-nav
|
||||
+navdefaultlinks("/account/edit")
|
||||
+navloginlogout("/account/edit")
|
||||
section#mainpage
|
||||
.container
|
||||
if !loggedIn
|
||||
.col-lg-6.col-lg-offset-3.col-md-6.col-md-offset-3
|
||||
.alert.alert-danger.messagebox.center
|
||||
strong Authorization Required
|
||||
p You must be <a href="/login">logged in</a> to view this page.
|
||||
else
|
||||
.col-lg-6.col-lg-offset-3.col-md-6.col-md-offset-3
|
||||
if successMessage
|
||||
.alert.alert-success.center
|
||||
p= successMessage
|
||||
else if errorMessage
|
||||
.alert.alert-danger.center
|
||||
p= errorMessage
|
||||
h3 Change Password
|
||||
form(action="/account/edit", method="post", onsubmit="return validatePasswordChange()")
|
||||
input(type="hidden", name="action", value="change_password")
|
||||
.form-group
|
||||
label.control-label(for="username") Username
|
||||
input#username.form-control(type="text", name="name", value=loginName, disabled=true)
|
||||
.form-group
|
||||
label.control-label(for="oldpassword") Current Password
|
||||
input#oldpassword.form-control(type="password", name="oldpassword")
|
||||
.form-group
|
||||
label.control-label(for="newpassword") New Password
|
||||
input#newpassword.form-control(type="password", name="newpassword")
|
||||
.form-group
|
||||
label.control-label(for="newpassword_confirm") Confirm New Password
|
||||
input#newpassword_confirm.form-control(type="password", name="newpassword_confirm")
|
||||
button#changepassbtn.btn.btn-danger.btn-block(type="submit") Change Password
|
||||
hr
|
||||
h3 Change Email
|
||||
form(action="/account/edit", method="post", onsubmit="return submitEmail()")
|
||||
input(type="hidden", name="action", value="change_email")
|
||||
.form-group
|
||||
label.control-label(for="username2") Username
|
||||
input#username2.form-control(type="text", name="name", value=loginName, disabled=true)
|
||||
.form-group
|
||||
label.control-label(for="password2") Password
|
||||
input#password2.form-control(type="password", name="password")
|
||||
.form-group
|
||||
label.control-label(for="email") New Email
|
||||
input#email.form-control(type="email", name="email")
|
||||
button#changeemailbtn.btn.btn-danger.btn-block(type="submit") Change Email
|
||||
include footer
|
||||
+footer()
|
||||
script(type="text/javascript").
|
||||
function validatePasswordChange() {
|
||||
var pw = $("#newpassword").val();
|
||||
var pwc = $("#newpassword_confirm").val();
|
||||
$("#passwordempty").remove();
|
||||
$("#passwordmismatch").remove();
|
||||
|
||||
if (pw === '') {
|
||||
$("#newpassword").parent().addClass("has-error");
|
||||
$("<p/>").addClass("text-danger")
|
||||
.attr("id", "passwordempty")
|
||||
.text("Password must not be empty")
|
||||
.insertAfter($("#newpassword"));
|
||||
return false;
|
||||
} else {
|
||||
if (pw !== pwc) {
|
||||
$("#newpassword_confirm").parent().addClass("has-error");
|
||||
$("#newpassword").parent().addClass("has-error");
|
||||
$("<p/>").addClass("text-danger")
|
||||
.attr("id", "passwordmismatch")
|
||||
.text("Passwords do not match")
|
||||
.insertAfter($("#newpassword_confirm"));
|
||||
return false;
|
||||
} else {
|
||||
$("#username").attr("disabled", false);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
function submitEmail() {
|
||||
$("#username2").attr("disabled", false);
|
||||
return true;
|
||||
}
|
||||
108
templates/channel-hd.jade
Normal file
108
templates/channel-hd.jade
Normal file
|
|
@ -0,0 +1,108 @@
|
|||
doctype 5
|
||||
html(lang="en")
|
||||
head
|
||||
include head
|
||||
+head()
|
||||
body
|
||||
#wrap
|
||||
nav.navbar.navbar-inverse.navbar-fixed-top(role="navigation")
|
||||
include nav
|
||||
+navheader()
|
||||
#nav-collapsible.collapse.navbar-collapse
|
||||
- var cname = "/r/" + channelName
|
||||
ul.nav.navbar-nav
|
||||
+navdefaultlinks(cname)
|
||||
li: a(href="javascript:showUserOptions()") Options
|
||||
+navloginlogout(cname)
|
||||
section#mainpage
|
||||
.container
|
||||
#motdwrap.col-lg-12.col-md-12
|
||||
#motd
|
||||
#announcements.col-lg-12.col-md-12
|
||||
.alert.alert-info Demo announcement
|
||||
#drinkbar.col-lg-12.col-md-12
|
||||
#drinkcount
|
||||
#videowrap.hd-video-wrap.col-lg-8.col-lg-offset-2.col-md-8.col-md-offset-2
|
||||
#videoopts.col-lg-8.col-lg-offset-2.col-md-8.col-md-offset-2
|
||||
button#voteskip.btn.btn-sm.btn-default Voteskip
|
||||
.vertical-spacer.col-lg-8.col-md-8
|
||||
#playlistwrap.col-lg-6.col-md-6
|
||||
#playlistheader
|
||||
button#showimport.btn.btn-default.btn-xs.btn-block(data-toggle="collapse", data-target="#playlistcontrols") Playlist Controls
|
||||
#playlistcontrols.collapse
|
||||
strong Add from URL
|
||||
#fromurl.input-group
|
||||
input#urlinput.form-control(type="text")
|
||||
.input-group-btn
|
||||
button#queuenext.btn.btn-default(type="button") Next
|
||||
button#queueend.btn.btn-default(type="button") End
|
||||
hr
|
||||
#customembed
|
||||
strong Custom Embed
|
||||
br
|
||||
| Acceptable embed codes are <code><iframe></code> and <code><object></code> tags)
|
||||
textarea#customembedcode.form-control.input-block-level(rows="3")
|
||||
.input-group
|
||||
input#customembedtitle.form-control.input-block-level(placeholder="(Optional) Title")
|
||||
.input-group-btn
|
||||
button#customqueuenext.btn.btn-default(type="button") Next
|
||||
button#customqueueend.btn.btn-default(type="button") End
|
||||
hr
|
||||
#misccontrols
|
||||
strong Additional Controls
|
||||
button#clearplaylist.btn.btn-xs.btn-default.btn-block(type="button") Clear Playlist
|
||||
button#shuffleplaylist.btn.btn-xs.btn-default.btn-block(type="button") Shuffle Playlist
|
||||
hr
|
||||
|
||||
button#showsearch.btn.btn-default.btn-xs.btn-block(data-toggle="collapse", data-target="#fromsearch") Search Library/YouTube
|
||||
#fromsearch.collapse
|
||||
.input-group
|
||||
input#ytsearchtext.form-control(type="text")
|
||||
.input-group-btn
|
||||
button#libsearchbtn.btn.btn-default(type="button") Library
|
||||
button#ytsearchbtn.btn.btn-default(type="button") YouTube
|
||||
hr
|
||||
#searchresultswrap(style="display: none")
|
||||
#searchresults
|
||||
hr
|
||||
ul#playlist
|
||||
li
|
||||
.btn-group.video-buttons
|
||||
button.btn.btn-xs.btn-default
|
||||
span.glyphicon.glyphicon-play
|
||||
button.btn.btn-xs.btn-default
|
||||
span.glyphicon.glyphicon-share-alt
|
||||
button.btn.btn-xs.btn-default
|
||||
span.glyphicon.glyphicon-flag
|
||||
button.btn.btn-xs.btn-default
|
||||
span.glyphicon.glyphicon-trash
|
||||
a.video-title(href="#") Some Video Thing
|
||||
span.video-time 02:00
|
||||
span.clear
|
||||
li
|
||||
a.video-title(href="#") Some Video Thing
|
||||
span.video-time 02:00
|
||||
span.clear
|
||||
li
|
||||
a.video-title(href="#") Some Video Thing
|
||||
span.video-time 02:00
|
||||
span.clear
|
||||
#chatwrap.col-lg-6.col-md-6
|
||||
#chatheader
|
||||
span Not connected
|
||||
ul#chatlist.pull-right
|
||||
li Test
|
||||
li Test 2
|
||||
#chatbuffer.linewrap.
|
||||
sdfngjksdfngjnsdjkgfnjklsdngjksdngfsnjdfg
|
||||
sdgfsdjifgjksdfngjksdngfjksdfnjgfknsdjkgfnsdgsdbfasdhbfhjbasdhjfbsdhjbghjsdfbghjsdbhjgbsdhjfbghjdsfbghj
|
||||
fsdfgfnjksdgjnsdjgnfjksngjksngjnksjgnsjnfgsd
|
||||
gfsnjgfjsnjkg
|
||||
input#chatline.form-control.input-block-level(type="text")
|
||||
include footer
|
||||
+footer()
|
||||
script(src="#{ioUrl}/socket.io/socket.io.js")
|
||||
script(type="text/javascript").
|
||||
var IOSERVER = "#{ioUrl}";
|
||||
var SOCKET = io.connect(IOSERVER);
|
||||
script(src="/js/functions.js")
|
||||
183
templates/channel.jade
Normal file
183
templates/channel.jade
Normal file
|
|
@ -0,0 +1,183 @@
|
|||
doctype 5
|
||||
html(lang="en")
|
||||
head
|
||||
include head
|
||||
+head()
|
||||
body
|
||||
#wrap
|
||||
nav.navbar.navbar-inverse.navbar-fixed-top(role="navigation")
|
||||
include nav
|
||||
+navheader()
|
||||
#nav-collapsible.collapse.navbar-collapse
|
||||
- var cname = "/r/" + channelName
|
||||
ul.nav.navbar-nav
|
||||
+navdefaultlinks(cname)
|
||||
li: a(href="javascript:showUserOptions()") Options
|
||||
li: a(href="javascript:$('#channeloptions').modal()") Channel Settings
|
||||
+navloginlogout(cname)
|
||||
section#mainpage
|
||||
.container
|
||||
.row
|
||||
.col-lg-12.col-md-12
|
||||
#motdwrap.well
|
||||
button#togglemotd.close.pull-right(type="button")
|
||||
span.glyphicon.glyphicon-minus
|
||||
#motd
|
||||
.clear
|
||||
#announcements.row
|
||||
#drinkbarwrap.col-lg-12.col-md-12.row
|
||||
#drinkbar
|
||||
h1#drinkcount
|
||||
#main.row
|
||||
#chatwrap.col-lg-5.col-md-5
|
||||
#chatheader
|
||||
i#userlisttoggle.glyphicon.glyphicon-chevron-up.pull-left.pointer(title="Show/Hide Userlist")
|
||||
span#usercount.pointer Not Connected
|
||||
span#modflair.label.label-default.pull-right.pointer M
|
||||
span#adminflair.label.label-default.pull-right.pointer A
|
||||
#userlist
|
||||
#messagebuffer
|
||||
input#chatline.form-control(type="text", maxlength="240", style="display: none")
|
||||
#guestlogin.input-group
|
||||
span.input-group-addon Guest login
|
||||
input#guestname.form-control(type="text", placeholder="Name")
|
||||
#videowrap.col-lg-7.col-md-7
|
||||
p#currenttitle Nothing Playling
|
||||
#ytapiplayer
|
||||
.row
|
||||
#leftcontrols.col-lg-5.col-md-5
|
||||
button#newpollbtn.btn.btn-sm.btn-default New Poll
|
||||
#rightcontrols.col-lg-7.col-md-7
|
||||
#qualitywrap.dropdown.btn-group
|
||||
button#qdrop.btn.btn-sm.btn-default.dropdown-toggle(data-toggle="dropdown") Quality
|
||||
b.caret
|
||||
mixin quality_item(id, text)
|
||||
li(role="presentation")
|
||||
a(id="#{id}", role="menuitem", href="javascript:void(0)") #{text}
|
||||
ul.dropdown-menu(role="menu", aria-labelledby="qdrop")
|
||||
+quality_item("quality_auto", "Quality: Auto")
|
||||
+quality_item("quality_240p", "240p")
|
||||
+quality_item("quality_360p", "360p")
|
||||
+quality_item("quality_480p", "480p")
|
||||
+quality_item("quality_720p", "720p")
|
||||
+quality_item("quality_1080p", "1080p")
|
||||
button#mediarefresh.btn.btn-sm.btn-default Refresh Media
|
||||
|
||||
#playlistrow.row
|
||||
#leftpane.col-lg-5.col-md-5
|
||||
#leftpane-inner.row
|
||||
#pollwrap.col-lg-12.col-md-12
|
||||
#searchwrap.col-lg-12.col-md-12
|
||||
button#showsearch.btn.btn-default.btn-block(data-toggle="collapse", data-target="#searchcontrol") Search Library/YouTube
|
||||
#searchcontrol.collapse
|
||||
.row.vertical-spacer
|
||||
#querywrap.col-lg-12.col-md-12
|
||||
.input-group
|
||||
input#library_query.form-control(type="text")
|
||||
span.input-group-btn
|
||||
button#library_search.btn.btn-default Library
|
||||
span.input-group-btn
|
||||
button#youtube_search.btn.btn-default YouTube
|
||||
ul#library.videolist.col-lg-12.col-md-12
|
||||
#playlistmanagerwrap.col-lg-12.col-md-12
|
||||
button#showplaylistmanager.btn.btn-default.btn-block(data-toggle="collapse", data-target="#playlistmanager") Playlist Manager
|
||||
#playlistmanager.collapse
|
||||
.row.vertical-spacer
|
||||
.col-lg-12.col-md-12
|
||||
.input-group
|
||||
input#userpl_name.form-control(type="text", placeholder="Playlist Name")
|
||||
span.input-group-btn
|
||||
button#userpl_save.btn.btn-default Save
|
||||
ul#userpl_list.col-lg-12.col-md-12
|
||||
#rightpane.col-lg-7.col-md-7
|
||||
#rightpane-inner.row
|
||||
#playlistcontrolswrap.col-lg-12.col-md-12
|
||||
button#showplaylistcontrols.btn.btn-default.btn-block(data-toggle="collapse", data-target="#playlistcontrols") Playlist Controls
|
||||
#playlistcontrols.collapse
|
||||
.row.vertical-spacer
|
||||
.col-lg-12.col-md-12
|
||||
.input-group
|
||||
input#mediaurl.form-control.input-block-level(type="text", placeholder="Media URL")
|
||||
span.input-group-btn
|
||||
button#queue_next.btn.btn-default Next
|
||||
span.input-group-btn
|
||||
button#queue_end.btn.btn-default At End
|
||||
hr
|
||||
.row
|
||||
#customembedwrap.col-lg-12.col-md-12
|
||||
button#showcustomembed.btn.btn-default.btn-block(data-toggle="collapse", data-target="#customembed") Custom Embed
|
||||
#customembed.collapse
|
||||
| Paste the embed code below and click Next or At End.
|
||||
| Acceptable embed codes are <code><iframe></code> and <code><object></code> tags.
|
||||
textarea#customembed_code.input-block-level.form-control(rows="3")
|
||||
hr
|
||||
.row
|
||||
#extended_controls.col-lg-12.col-md-12
|
||||
button#clearplaylist.btn.btn-default.btn-block Clear Playlist
|
||||
button#shuffleplaylist.btn.btn-default.btn-block Shuffle Playlist
|
||||
#voteskipwrap.col-lg-12.col-md-12.col-sm-12.col-xs-12.btn-group
|
||||
button#voteskip.btn.btn-default Voteskip
|
||||
button#getplaylist.btn.btn-default Get Playlist URLs
|
||||
button#qlockbtn.btn.btn-danger(title="Playlist Locked")
|
||||
i.glyphicon.glyphicon-lock
|
||||
.col-lg-12.col-md-12
|
||||
#queue.videolist
|
||||
li.queue_entry
|
||||
a.qe_title(href="#") Derp
|
||||
span.qe_time 00:00
|
||||
div.qe_clear
|
||||
li.queue_entry.queue_active.queue_temp
|
||||
a.qe_title(href="#") Derp
|
||||
span.qe_time 00:00
|
||||
div.qe_clear
|
||||
#plmeta
|
||||
span#plcount 0 items
|
||||
span#pllength 00:00:00
|
||||
#resizewrap.row
|
||||
.col-lg-5.col-md-5
|
||||
#videowidth.col-lg-7.col-md-7
|
||||
#sitefooter
|
||||
#channeloptions.modal.fade(tabindex="-1", role="dialog", aria-hidden="true")
|
||||
.modal-dialog
|
||||
.modal-content
|
||||
.modal-header
|
||||
button.close(data-dismiss="modal", aria-hidden="true")×
|
||||
h4 Channel Settings
|
||||
ul.nav.nav-tabs
|
||||
li: a(href="#cs-miscoptions" data-toggle="tab") General Settings
|
||||
li: a(href="#cs-adminoptions" data-toggle="tab") Admin Settings
|
||||
li.dropdown
|
||||
a#cs-edit-dd-toggle(href="#", data-toggle="dropdown") Edit
|
||||
span.caret
|
||||
ul.dropdown-menu
|
||||
li: a(href="#cs-motdeditor", data-toggle="tab", tabindex="-1") Edit MOTD
|
||||
li: a(href="#cs-csseditor", data-toggle="tab", tabindex="-1") Edit CSS
|
||||
li: a(href="#cs-jseditor", data-toggle="tab", tabindex="-1") Edit Javascript
|
||||
li: a(href="#cs-chanranks", data-toggle="tab", tabindex="-1") Edit user ranks
|
||||
li: a(href="#cs-banlist", data-toggle="tab", tabindex="-1") Ban list
|
||||
.modal-body
|
||||
.tab-content
|
||||
include channeloptions
|
||||
+miscoptions()
|
||||
+adminoptions()
|
||||
+motdeditor()
|
||||
+csseditor()
|
||||
+jseditor()
|
||||
+banlist()
|
||||
+recentjoins()
|
||||
+chanranks()
|
||||
.modal-footer
|
||||
button.btn.btn-default(type="button", data-dismiss="modal") Close
|
||||
include footer
|
||||
+footer()
|
||||
script(src="/assets/js/iourl.js")
|
||||
//script(src="#{ioUrl}/socket.io/socket.io.js")
|
||||
//script(type="text/javascript").
|
||||
// var IOSERVER = "#{ioUrl}";
|
||||
// var SOCKET = io.connect(IOSERVER);
|
||||
// $('#channeloptions').modal();
|
||||
// $('#channeloptions a[href="#cs-miscoptions"]').tab('show');
|
||||
script(src="/assets/js/data.js")
|
||||
script(src="/assets/js/util.js")
|
||||
script(src="/assets/js/ui.js")
|
||||
script(src="/assets/js/callbacks.js")
|
||||
100
templates/channeloptions.jade
Normal file
100
templates/channeloptions.jade
Normal file
|
|
@ -0,0 +1,100 @@
|
|||
mixin lcheckbox(id, label)
|
||||
.form-group
|
||||
label.control-label.col-sm-4(for=id)= label
|
||||
.col-sm-8
|
||||
.checkbox
|
||||
input(type="checkbox", id=id)
|
||||
|
||||
mixin rcheckbox(id, label)
|
||||
.form-group
|
||||
.col-sm-8.col-sm-offset-4
|
||||
.checkbox
|
||||
label.control-label(for=id)= label
|
||||
input(type="checkbox", id=id)
|
||||
|
||||
mixin textbox(id, label, placeholder)
|
||||
.form-group
|
||||
label.control-label.col-sm-4(for=id)= label
|
||||
.col-sm-8
|
||||
if placeholder
|
||||
input.form-control(id=id, type="text", placeholder=placeholder)
|
||||
else
|
||||
input.form-control(id=id, type="text")
|
||||
|
||||
mixin miscoptions
|
||||
#cs-miscoptions.tab-pane
|
||||
h4 General Settings
|
||||
form.form-horizontal(action="javascript:void(0)")
|
||||
+rcheckbox("opt_enable_link_regex", "Convert URLs in chat to links")
|
||||
+rcheckbox("opt_allow_voteskip", "Allow voteskip")
|
||||
+textbox("opt_voteskip_ratio", "Voteskip ratio", "0.5")
|
||||
+textbox("opt_maxlength", "Max video length", "HH:MM:SS")
|
||||
+textbox("opt_afktimeout", "Auto-AFK Delay", "0 (disabled)")
|
||||
.form-group
|
||||
.col-sm-8.col-sm-offset-4
|
||||
button.btn.btn-default#cs-miscoptionssubmit Save
|
||||
|
||||
mixin adminoptions
|
||||
#cs-adminoptions.tab-pane
|
||||
h4 Admin-Only Settings
|
||||
form.form-horizontal(action="javascript:void(0)")
|
||||
- var defname = "CyTube - /r/" + channelName
|
||||
+textbox("opt_pagetitle", "Page title", defname)
|
||||
+textbox("opt_password", "Password", "leave blank to disable")
|
||||
+textbox("opt_externalcss", "External CSS", "Stylesheet URL")
|
||||
+textbox("opt_externaljs", "External Javascript", "Script URL")
|
||||
+rcheckbox("opt_show_public", "List channel publicly")
|
||||
.form-group
|
||||
.col-sm-8.col-sm-offset-4
|
||||
button.btn.btn-default#cs-adminoptionssubmit Save
|
||||
|
||||
mixin motdeditor
|
||||
#cs-motdeditor.tab-pane
|
||||
h4 MOTD editor
|
||||
p The MOTD can be formatted using a subset of HTML. Tags which attempt to execute Javascript will be removed.
|
||||
textarea.form-control#cs-motdtext(rows="10")
|
||||
button.btn.btn-default#cs-motdsubmit Save MOTD
|
||||
|
||||
mixin csseditor
|
||||
#cs-csseditor.tab-pane
|
||||
h4 CSS editor
|
||||
p Maximum size 20KB. If more space is required, use the External CSS option under General Settings to link to an externally hosted stylesheet.
|
||||
textarea.form-control#cs-csstext(rows="10")
|
||||
button.btn.btn-default#cs-csssubmit Save CSS
|
||||
|
||||
mixin jseditor
|
||||
#cs-jseditor.tab-pane
|
||||
h4 JS editor
|
||||
p Maximum size 20KB. If more space is required, use the External JS option under General Settings to link to an externally hosted stylesheet.
|
||||
textarea.form-control#cs-jstext(rows="10")
|
||||
button.btn.btn-default#cs-jssubmit Save JS
|
||||
|
||||
mixin banlist
|
||||
#cs-banlist.tab-pane
|
||||
h4 Ban list
|
||||
table.table.table-striped
|
||||
thead
|
||||
tr
|
||||
th Unban
|
||||
th IP
|
||||
th Name
|
||||
th Aliases
|
||||
th Banned by
|
||||
|
||||
mixin recentjoins
|
||||
#cs-recentjoins.tab-pane
|
||||
h4 Recent connections
|
||||
table.table.table-striped
|
||||
thead
|
||||
tr
|
||||
th Name
|
||||
th Aliases
|
||||
th Time
|
||||
|
||||
mixin chanranks
|
||||
#cs-chanranks.tab-pane
|
||||
table.table.table-striped
|
||||
thead
|
||||
tr
|
||||
th Name
|
||||
th Rank
|
||||
7
templates/footer.jade
Normal file
7
templates/footer.jade
Normal file
|
|
@ -0,0 +1,7 @@
|
|||
mixin footer
|
||||
footer#footer
|
||||
.container
|
||||
p.text-muted.credit.
|
||||
Copyright © 2013 Calvin Montgomery
|
||||
script(src="/js/jquery.js")
|
||||
script(src="/js/bootstrap.js")
|
||||
15
templates/head.jade
Normal file
15
templates/head.jade
Normal file
|
|
@ -0,0 +1,15 @@
|
|||
mixin head()
|
||||
meta(charset="utf-8")
|
||||
meta(name="viewport", content="width=device-width, initial-scale=1.0")
|
||||
meta(name="description", content="#{siteDescription}")
|
||||
meta(name="author", content="#{siteAuthor}")
|
||||
|
||||
title= siteTitle
|
||||
link(href="/css/bootstrap.css", rel="stylesheet")
|
||||
//link(href="/css/bootstrap-theme.min.css", rel="stylesheet")
|
||||
link(href="/css/sticky-footer-navbar.css", rel="stylesheet")
|
||||
link(href="/css/cytube.css", rel="stylesheet")
|
||||
//[if lt IE 9]
|
||||
<script src="https://oss.maxcdn.com/libs/html5shiv/3.7.0/html5shiv.js"></script>
|
||||
<script src="https://oss.maxcdn.com/libs/respond.js/1.3.0/respond.min.js"></script>
|
||||
//[endif]
|
||||
16
templates/index.jade
Normal file
16
templates/index.jade
Normal file
|
|
@ -0,0 +1,16 @@
|
|||
doctype 5
|
||||
html(lang="en")
|
||||
head
|
||||
include head
|
||||
+head()
|
||||
body
|
||||
#wrap
|
||||
nav.navbar.navbar-inverse.navbar-fixed-top(role="navigation")
|
||||
include nav
|
||||
+navheader()
|
||||
#nav-collapsible.collapse.navbar-collapse
|
||||
ul.nav.navbar-nav
|
||||
+navdefaultlinks("/")
|
||||
+navloginlogout("/")
|
||||
include footer
|
||||
+footer()
|
||||
46
templates/login.jade
Normal file
46
templates/login.jade
Normal file
|
|
@ -0,0 +1,46 @@
|
|||
doctype 5
|
||||
html(lang="en")
|
||||
head
|
||||
include head
|
||||
+head()
|
||||
body
|
||||
#wrap
|
||||
nav.navbar.navbar-inverse.navbar-fixed-top(role="navigation")
|
||||
include nav
|
||||
+navheader()
|
||||
#nav-collapsible.collapse.navbar-collapse
|
||||
ul.nav.navbar-nav
|
||||
+navdefaultlinks("/login")
|
||||
if loggedIn
|
||||
+navlogoutform("/login")
|
||||
section#mainpage.container
|
||||
if wasAlreadyLoggedIn
|
||||
.col-lg-6.col-lg-offset-3.col-md-6.col-md-offset-3
|
||||
.alert.alert-info.messagebox.center
|
||||
h3(style="margin: 5px auto") Logged in as #{loginName}
|
||||
// TODO Link to My Account page
|
||||
else if !loggedIn
|
||||
.col-lg-6.col-lg-offset-3.col-md-6.col-md-offset-3
|
||||
if loginError
|
||||
.alert.alert-danger.messagebox.center
|
||||
strong Login Failed
|
||||
p= loginError
|
||||
h2 Login
|
||||
form(role="form", action="/login", method="post")
|
||||
.form-group
|
||||
label(for="username") Username
|
||||
input#username.form-control(type="text", name="name")
|
||||
.form-group
|
||||
label(for="password") Password
|
||||
input#password.form-control(type="password", name="password")
|
||||
button.btn.btn-success.btn-block(type="submit") Login
|
||||
else
|
||||
.col-lg-6.col-lg-offset-3.col-md-6.col-md-offset-3
|
||||
.alert.alert-success.messagebox.center
|
||||
strong Login Successful
|
||||
p Logged in as #{loginName}
|
||||
if redirect
|
||||
br
|
||||
a(href=redirect) Return to previous page
|
||||
include footer
|
||||
+footer()
|
||||
23
templates/logout.jade
Normal file
23
templates/logout.jade
Normal file
|
|
@ -0,0 +1,23 @@
|
|||
doctype 5
|
||||
html(lang="en")
|
||||
head
|
||||
include head
|
||||
+head()
|
||||
body
|
||||
#wrap
|
||||
nav.navbar.navbar-inverse.navbar-fixed-top(role="navigation")
|
||||
include nav
|
||||
+navheader()
|
||||
#nav-collapsible.collapse.navbar-collapse
|
||||
ul.nav.navbar-nav
|
||||
+navdefaultlinks("/logout")
|
||||
+navloginform()
|
||||
section#mainpage.container
|
||||
.col-lg-6.col-lg-offset-3.col-md-6.col-md-offset-3
|
||||
.alert.alert-info.center.messagebox
|
||||
strong Logged out
|
||||
p
|
||||
if redirect
|
||||
a(href=redirect) Return to previous page
|
||||
include footer
|
||||
+footer()
|
||||
64
templates/nav.jade
Normal file
64
templates/nav.jade
Normal file
|
|
@ -0,0 +1,64 @@
|
|||
- var links = { "/": "Home" }
|
||||
|
||||
mixin navlink(page, title, active)
|
||||
if active
|
||||
li.active
|
||||
a(href=page)= title
|
||||
else
|
||||
li
|
||||
a(href=page)= title
|
||||
|
||||
mixin navheader()
|
||||
.navbar-header
|
||||
button.navbar-toggle(type="button", data-toggle="collapse", data-target="#nav-collapsible")
|
||||
span.icon-bar
|
||||
span.icon-bar
|
||||
span.icon-bar
|
||||
a.navbar-brand(href="/")= siteTitle
|
||||
|
||||
mixin navdefaultlinks(page)
|
||||
each t, p in links
|
||||
if p == page
|
||||
+navlink(p, t, true)
|
||||
else
|
||||
+navlink(p, t, false)
|
||||
li.dropdown
|
||||
a.dropdown-toggle(href="#", data-toggle="dropdown") Account
|
||||
b.caret
|
||||
ul.dropdown-menu
|
||||
if loggedIn
|
||||
li: a(href="/logout?redirect=#{page}") Logout
|
||||
li.divider
|
||||
li: a(href="/account/channels") My Channels
|
||||
li: a(href="/account/profile") Profile
|
||||
li: a(href="/account/edit") Change Password/Email
|
||||
else
|
||||
li: a(href="/login") Login
|
||||
li: a(href="/register") Register
|
||||
|
||||
|
||||
mixin navloginlogout(redirect)
|
||||
if loggedIn
|
||||
+navlogoutform(redirect)
|
||||
else
|
||||
+navloginform(redirect)
|
||||
|
||||
mixin navloginform(redirect)
|
||||
.visible-md.visible-lg
|
||||
form#loginform.navbar-form.navbar-right(action="/login", method="post")
|
||||
input(type="hidden", name="redirect", value=redirect)
|
||||
.form-group
|
||||
input#username.form-control(type="text", name="name", placeholder="Username")
|
||||
.form-group
|
||||
input#password.form-control(type="password", name="password", placeholder="Password")
|
||||
button#login.btn.btn-default(type="submit") Login
|
||||
|
||||
mixin navlogoutform(redirect)
|
||||
if redirect
|
||||
- url = "/logout?redirect=#{redirect}"
|
||||
else
|
||||
- url = "/logout"
|
||||
p#logoutform.navbar-text.pull-right
|
||||
span#welcome Welcome, #{loginName}
|
||||
span ·
|
||||
a#logout.navbar-link(href=url) Logout
|
||||
110
templates/register.jade
Normal file
110
templates/register.jade
Normal file
|
|
@ -0,0 +1,110 @@
|
|||
doctype 5
|
||||
html(lang="en")
|
||||
head
|
||||
include head
|
||||
+head()
|
||||
body
|
||||
#wrap
|
||||
nav.navbar.navbar-inverse.navbar-fixed-top(role="navigation")
|
||||
include nav
|
||||
+navheader()
|
||||
#nav-collapsible.collapse.navbar-collapse
|
||||
ul.nav.navbar-nav
|
||||
+navdefaultlinks("/register")
|
||||
if loggedIn
|
||||
+navlogoutform("/register")
|
||||
section#mainpage.container
|
||||
if loggedIn
|
||||
.col-lg-6.col-lg-offset-3.col-md-6.col-md-offset-3
|
||||
.alert.alert-danger.messagebox.center
|
||||
strong Already logged in
|
||||
p.
|
||||
You are already logged in. If you intend to register a new account, please <a href="/logout?redirect=/register">Logout</a> first.
|
||||
// TODO Link to My Account page
|
||||
else if !registered
|
||||
.col-lg-6.col-lg-offset-3.col-md-6.col-md-offset-3
|
||||
if registerError
|
||||
.alert.alert-danger.messagebox.center
|
||||
strong Registration Failed
|
||||
p= registerError
|
||||
h2 Register
|
||||
form(role="form", action="/register", method="post", onsubmit="return verify()")
|
||||
.form-group
|
||||
label.control-label(for="username") Username
|
||||
input#username.form-control(type="text", name="name")
|
||||
.form-group
|
||||
label.control-label(for="password") Password
|
||||
input#password.form-control(type="password", name="password", onkeyup="checkPasswords()")
|
||||
.form-group
|
||||
label.control-label(for="password_confirm") Confirm Password
|
||||
input#password_confirm.form-control(type="password", onkeyup="checkPasswords()")
|
||||
.form-group
|
||||
label.control-label(for="email") Email (optional)
|
||||
input#email.form-control(type="email", name="email")
|
||||
p Providing an email address is optional and will allow you to recover your account via email if you forget your password. Your address will not be shared with anyone.
|
||||
button#registerbtn.btn.btn-success.btn-block(type="submit") Register
|
||||
else
|
||||
.col-lg-6.col-lg-offset-3.col-md-6.col-md-offset-3
|
||||
.alert.alert-success.messagebox.center
|
||||
strong Registration Successful
|
||||
p Thanks for registering, #{registerName}! Now you can <a href="/login">Login</a> to use your account.
|
||||
include footer
|
||||
+footer()
|
||||
script(src="/js/jquery.js")
|
||||
script(type="text/javascript").
|
||||
function verify() {
|
||||
var valid = checkUsername();
|
||||
valid = checkPasswords() && valid;
|
||||
return valid;
|
||||
}
|
||||
function checkUsername() {
|
||||
var name = $("#username").val();
|
||||
$("#usernameerror").remove();
|
||||
if (name === "") {
|
||||
$("#username").parent().addClass("has-error");
|
||||
$("<p/>").addClass("text-danger")
|
||||
.attr("id", "usernameerror")
|
||||
.text("Username must not be empty")
|
||||
.insertAfter($("#username"));
|
||||
return false;
|
||||
} else if (!(/^[-\w\u00c0-\u00ff]{1,20}$/).test(name)) {
|
||||
$("#username").parent().addClass("has-error");
|
||||
$("<p/>").addClass("text-danger")
|
||||
.attr("id", "usernameerror")
|
||||
.text("Username must consist of 1-20 characters a-Z, A-Z, 0-9 " +
|
||||
", -, _, and accented letters.")
|
||||
.insertAfter($("#username"));
|
||||
return false;
|
||||
} else {
|
||||
$("#username").parent().removeClass("has-error")
|
||||
.addClass("has-success");
|
||||
}
|
||||
}
|
||||
function checkPasswords() {
|
||||
var pw = $("#password").val();
|
||||
var pwc = $("#password_confirm").val();
|
||||
$("#passwordempty").remove();
|
||||
$("#passwordmismatch").remove();
|
||||
if (pw === "") {
|
||||
$("#password").parent().addClass("has-error");
|
||||
$("<p/>").addClass("text-danger")
|
||||
.attr("id", "passwordempty")
|
||||
.text("Password must not be empty")
|
||||
.insertAfter($("#password"));
|
||||
return false;
|
||||
} else {
|
||||
$("#password").parent().removeClass("has-error")
|
||||
.addClass("has-success");
|
||||
if (pw !== pwc) {
|
||||
$("#password_confirm").parent().addClass("has-error");
|
||||
$("<p/>").addClass("text-danger")
|
||||
.attr("id", "passwordmismatch")
|
||||
.text("Passwords do not match")
|
||||
.insertAfter($("#password_confirm"));
|
||||
return false;
|
||||
} else {
|
||||
$("#password_confirm").parent().removeClass("has-error")
|
||||
.addClass("has-success");
|
||||
}
|
||||
}
|
||||
}
|
||||
17
templates/test.jade
Normal file
17
templates/test.jade
Normal file
|
|
@ -0,0 +1,17 @@
|
|||
doctype 5
|
||||
html(lang="en")
|
||||
head
|
||||
include head
|
||||
+head()
|
||||
body
|
||||
#wrap
|
||||
nav.navbar.navbar-inverse.navbar-fixed-top(role="navigation")
|
||||
include nav
|
||||
+navheader()
|
||||
#nav-collapsible.collapse.navbar-collapse
|
||||
ul.nav.navbar-nav
|
||||
+navdefaultlinks("/test")
|
||||
+navloginform("/test")
|
||||
|
||||
include footer
|
||||
+footer()
|
||||
Loading…
Add table
Add a link
Reference in a new issue