Get style settings and theme selection working.

This commit is contained in:
Zixaphir 2013-04-10 23:10:55 -07:00
parent 386e0c617d
commit 06d942a968
8 changed files with 467 additions and 426 deletions

File diff suppressed because one or more lines are too long

View File

@ -47,7 +47,7 @@ div.navLinks > a:first-of-type::after {
/* Thread Navigation Links */ /* Thread Navigation Links */
#navlinks a { #navlinks a {
margin: 2px; margin: 2px;
top: 0; top: 1px;
} }
#navlinks a:last-of-type { #navlinks a:last-of-type {
#{align}: #{position[i++]}px; #{align}: #{position[i++]}px;
@ -73,12 +73,12 @@ div.navLinks > a:first-of-type::after {
div.navLinks > a:first-of-type::after, div.navLinks > a:first-of-type::after,
#catalog::after, #catalog::after,
body > a[style="cursor: pointer; float: right;"]::after { body > a[style="cursor: pointer; float: right;"]::after {
top: 0 !important; top: 1px !important;
} }
#{if _conf["Announcements"] is "slideout" then "#globalMessage," else ""} #{if _conf["Announcements"] is "slideout" then "#globalMessage," else ""}
#{if _conf["Slideout Watcher"] then "#watcher," else ""} #{if _conf["Slideout Watcher"] then "#watcher," else ""}
#boardNavDesktopFoot { #boardNavDesktopFoot {
top: 17px !important; top: 16px !important;
} }
#{if _conf['Boards Navigation'] is 'top' or _conf['Boards Navigation'] is 'sticky top' then '#boardNavDesktop' else if _conf['Pagination'] is 'top' or _conf['Pagination'] is 'sticky top' then '.pagelist'} { #{if _conf['Boards Navigation'] is 'top' or _conf['Boards Navigation'] is 'sticky top' then '#boardNavDesktop' else if _conf['Pagination'] is 'top' or _conf['Pagination'] is 'sticky top' then '.pagelist'} {
#{if _conf['4chan SS Navigation'] #{if _conf['4chan SS Navigation']

View File

@ -5,5 +5,5 @@
#{Style.sidebarLocation[1]}: auto !important; #{Style.sidebarLocation[1]}: auto !important;
top: auto !important; top: auto !important;
bottom: auto !important; bottom: auto !important;
#{if _conf["Updater Position"] is 'top' then "top: 18px !important" else "bottom: 0 !important"}; #{if _conf["Updater Position"] is 'top' then "top: 16px !important" else "bottom: 0 !important"};
} }

View File

@ -79,6 +79,9 @@ body {
margin-#{Style.sidebarLocation[1]}: 2px; margin-#{Style.sidebarLocation[1]}: 2px;
padding: 0 #{parseInt(_conf["Right Thread Padding"], 10) + editSpace["right"]}px 0 #{parseInt(_conf["Left Thread Padding"], 10) + editSpace["left"]}px; padding: 0 #{parseInt(_conf["Right Thread Padding"], 10) + editSpace["right"]}px 0 #{parseInt(_conf["Left Thread Padding"], 10) + editSpace["left"]}px;
} }
body.unscroll {
overflow: hidden;
}
#{if _conf["4chan SS Sidebar"] and /^boards\.4chan\.org$/.test location.hostname then " #{if _conf["4chan SS Sidebar"] and /^boards\.4chan\.org$/.test location.hostname then "
body::before { body::before {
content: ''; content: '';
@ -86,7 +89,7 @@ body::before {
top: 0; top: 0;
bottom: 0; bottom: 0;
#{Style.sidebarLocation[0]}: 0; #{Style.sidebarLocation[0]}: 0;
width: #{if _conf["Sidebar"] is 'large' then 305 else if _conf['Sidebar'] is 'normal' then 254 else if _conf['Sidebar'] is 'minimal' then 27 else 0}px; width: #{if _conf['Sidebar'] is 'large' then 305 else if _conf['Sidebar'] is 'normal' then 254 else if _conf['Sidebar'] is 'minimal' then 27 else 0}px;
z-index: 1; z-index: 1;
#{Style.sizing}: border-box; #{Style.sizing}: border-box;
display: block; display: block;
@ -304,7 +307,7 @@ else "
"at sidebar top": " "at sidebar top": "
.boardBanner { .boardBanner {
position: fixed; position: fixed;
top: 18px; top: 16px;
#{Style.sidebarLocation[0]}: 2px; #{Style.sidebarLocation[0]}: 2px;
} }
.boardBanner img { .boardBanner img {
@ -1398,10 +1401,14 @@ a:only-of-type > .remove {
right: 15%; right: 15%;
top: 15%; top: 15%;
bottom: 15%; bottom: 15%;
position: absolute; position: fixed;
z-index: 31;
padding: .3em; padding: .3em;
#{if _conf["Rounded Edges"] then "border-radius: 3px;" else ""} #{if _conf["Rounded Edges"] then "border-radius: 3px;" else ""}
} }
.description {
display: none;
}
#appchanx-settings h3, #appchanx-settings h3,
.section-keybinds, .section-keybinds,
.section-mascots, .section-mascots,
@ -1418,11 +1425,10 @@ a:only-of-type > .remove {
margin: auto; margin: auto;
} }
#appchanx-settings fieldset { #appchanx-settings fieldset {
padding: 0; padding: 5px 0;
#{if _conf["Rounded Edges"] then "border-radius: 3px;" else ""} #{if _conf["Rounded Edges"] then "border-radius: 3px;" else ""}
vertical-align: top; vertical-align: top;
#{if _conf["Single Column Mode"] then "margin: 0 auto 6px;" else "margin: 0 3px 6px;\n display: inline-block;"} #{if _conf["Single Column Mode"] then "margin: 0 auto 6px;" else "margin: 0 3px 6px;\n display: inline-block;"}
padding: 0;
border: 0; border: 0;
} }
.section-container { .section-container {
@ -1487,11 +1493,11 @@ article li {
.rice + .optionlabel { .rice + .optionlabel {
padding-left: 0; padding-left: 0;
} }
.section-script fieldset > div, .section-script fieldset,
.styleoption { .styleoption {
text-align: left; text-align: left;
} }
.section-style fieldset > div { .section-style fieldset {
width: 370px; width: 370px;
} }
.section-script fieldset { .section-script fieldset {
@ -1532,7 +1538,7 @@ article li {
} }
/* Hover Functionality */ /* Hover Functionality */
#mouseover { #mouseover {
z-index: 32; z-index: 33;
position: fixed; position: fixed;
max-width: 70%; max-width: 70%;
} }

View File

@ -245,7 +245,7 @@ textarea {
color: #{theme["Text"]}; color: #{theme["Text"]};
} }
#exlinks-options-content > table, #exlinks-options-content > table,
#appchanx-settings ul, #appchanx-settings fieldset,
#selectrice { #selectrice {
border-bottom: 1px solid #{theme["Reply Border"]}; border-bottom: 1px solid #{theme["Reply Border"]};
box-shadow: inset #{theme["Shadow Color"]} 0 0 5px; box-shadow: inset #{theme["Shadow Color"]} 0 0 5px;
@ -376,7 +376,7 @@ a .name {
.placeholder { .placeholder {
color: #{if Style.lightTheme then "rgba(0,0,0,0.3)" else "rgba(255,255,255,0.2)"} !important; color: #{if Style.lightTheme then "rgba(0,0,0,0.3)" else "rgba(255,255,255,0.2)"} !important;
} }
#appchanx-settings ul, #appchanx-settings fieldset,
.boxcontent dd, .boxcontent dd,
.selectrice ul { .selectrice ul {
border-color: #{if Style.lightTheme then "rgba(0,0,0,0.1)" else "rgba(255,255,255,0.1)"}; border-color: #{if Style.lightTheme then "rgba(0,0,0,0.1)" else "rgba(255,255,255,0.1)"};

View File

@ -240,6 +240,16 @@ $.extend $,
# Round to an integer otherwise. # Round to an integer otherwise.
Math.round size Math.round size
"#{size} #{['B', 'KB', 'MB', 'GB'][unit]}" "#{size} #{['B', 'KB', 'MB', 'GB'][unit]}"
minmax: (value, min, max) ->
return (
if value < min
min
else
if value > max
max
else
value
)
syncing: {} syncing: {}
sync: do -> sync: do ->
<% if (type === 'crx') { %> <% if (type === 'crx') { %>

View File

@ -147,7 +147,7 @@ Style =
# Offsets various UI of the sidebar depending on the sidebar's width. # Offsets various UI of the sidebar depending on the sidebar's width.
# Only really used for the board banner or right sidebar. # Only really used for the board banner or right sidebar.
Style['sidebarOffset'] = if _conf["Sidebar"] is "large" Style['sidebarOffset'] = if _conf['Sidebar'] is "large"
{ {
W: 51 W: 51
H: 17 H: 17
@ -183,7 +183,7 @@ Style =
Style.sidebar = { Style.sidebar = {
minimal: 20 minimal: 20
hide: 2 hide: 2
}[_conf.Sidebar] or (252 + Style.sidebarOffset.W) }[_conf['Sidebar']] or (252 + Style.sidebarOffset.W)
Style.replyMargin = _conf["Post Spacing"] Style.replyMargin = _conf["Post Spacing"]
@ -207,7 +207,7 @@ Style =
align = Style.sidebarLocation[0] align = Style.sidebarLocation[0]
_conf = Conf _conf = Conf
notCatalog = !g.CATALOG notCatalog = g.VIEW isnt 'catalog'
notEither = notCatalog and g.BOARD isnt 'f' notEither = notCatalog and g.BOARD isnt 'f'
aligner = (first, checks) -> aligner = (first, checks) ->
@ -217,11 +217,12 @@ Style =
# Check which elements we actually have. Some are easy, because the script creates them so we'd know they're here # Check which elements we actually have. Some are easy, because the script creates them so we'd know they're here
# Some are hard, like 4sight, which we have no way of knowing if available without looking for it. # Some are hard, like 4sight, which we have no way of knowing if available without looking for it.
for enabled in checks for enabled in checks
position[position.length] = position.push(
if enabled if enabled
first += 19 first += 19
else else
first first
)
position position
@ -241,7 +242,7 @@ Style =
notEither notEither
g.VIEW is 'thread' g.VIEW is 'thread'
notEither and _conf['Fappe Tyme'] notEither and _conf['Fappe Tyme']
navlinks = ((!g.VIEW is 'thread' and _conf['Index Navigation']) or (g.VIEW is 'thread' and _conf['Reply Navigation'])) and notCatalog navlinks = ((g.VIEW isnt 'thread' and _conf['Index Navigation']) or (g.VIEW is 'thread' and _conf['Reply Navigation'])) and notCatalog
navlinks navlinks
] ]
) )
@ -524,56 +525,56 @@ Rice =
Post::callbacks.push Post::callbacks.push
name: 'Rice Checkboxes' name: 'Rice Checkboxes'
cb: @node cb: @node
cb: cb:
check: -> check: ->
@check.click() @check.click()
option: (e) -> option: (e) ->
e.stopPropagation() e.stopPropagation()
e.preventDefault()
select = Rice.input select = Rice.input
container = select.nextElementSibling container = select.nextElementSibling
container.firstChild.textContent = @textContent container.firstChild.textContent = @textContent
select.value = @getAttribute 'data-value' select.value = @getAttribute 'data-value'
ev = document.createEvent 'HTMLEvents' $.event 'change', null, select
ev.initEvent "change", true, true
$.event select, ev
Rice.cleanup() Rice.cleanup()
selectclick: (e) -> select: (e) ->
e.stopPropagation()
{ul} = Rice
unless ul
Rice.ul = ul = $.el 'ul',
id: "selectrice"
$.add d.body, ul
if ul.children.length > 0
return Rice.cleanup()
rect = @getBoundingClientRect()
{clientHeight} = d.documentElement
{style} = ul
style.cssText = "width: #{rect.width}px; left: #{rect.left}px;" + (if clientHeight - rect.bottom < 200 then "bottom: #{clientHeight - rect.top}px" else "top: #{rect.bottom}px")
Rice.input = select = @previousSibling
nodes = []
for option in select.options
li = $.el 'li',
textContent: option.textContent
li.setAttribute 'data-value', option.value
$.on li, 'click', Rice.cb.option
nodes.push li
$.add ul, nodes
$.on ul, 'click scroll blur', (e) ->
e.stopPropagation() e.stopPropagation()
e.preventDefault()
$.on d, 'click scroll blur resize', Rice.cleanup {ul} = Rice
unless ul
Rice.ul = ul = $.el 'ul',
id: "selectrice"
$.add d.body, ul
if ul.children.length > 0
return Rice.cleanup()
rect = @getBoundingClientRect()
{clientHeight} = d.documentElement
{style} = ul
style.cssText = "width: #{rect.width}px; left: #{rect.left}px;" + (if clientHeight - rect.bottom < 200 then "bottom: #{clientHeight - rect.top}px" else "top: #{rect.bottom}px")
Rice.input = select = @previousSibling
nodes = []
for option in select.options
li = $.el 'li',
textContent: option.textContent
li.setAttribute 'data-value', option.value
$.on li, 'click', Rice.cb.option
nodes.push li
$.add ul, nodes
$.on ul, 'click scroll blur', (e) ->
e.stopPropagation()
$.on d, 'click scroll blur resize', Rice.cleanup
cleanup: -> cleanup: ->
$.off d, 'click scroll blur resize', Rice.cleanup $.off d, 'click scroll blur resize', Rice.cleanup
@ -581,17 +582,21 @@ Rice =
$.rm child $.rm child
return return
nodes: (source) -> nodes: (root) ->
source or= d.body root or= d.body
checkboxes = $$('[type=checkbox]:not(.riced)', source)
checkboxes = $$('[type=checkbox]:not(.riced)', root)
checkrice = Rice.checkbox checkrice = Rice.checkbox
for input in checkboxes for input in checkboxes
checkrice input checkrice input
selects = $$('select:not(.riced)', source) selects = $$('select:not(.riced)', root)
selectrice = Rice.select selectrice = Rice.select
for input in selects
selectrice input for select in selects
selectrice select
return return
node: -> node: ->
@ -604,17 +609,17 @@ Rice =
className: 'rice' className: 'rice'
div.check = input div.check = input
$.after input, div $.after input, div
if div.parentElement.tagName.toLowerCase() != 'label' if div.parentElement.tagName isnt 'LABEL'
$.on div, 'click', Rice.cb.check $.on div, 'click', Rice.cb.check
select: (input) -> select: (select) ->
$.addClass input, 'riced' $.addClass select, 'riced'
div = $.el 'div', div = $.el 'div',
className: 'selectrice' className: 'selectrice'
innerHTML: "<div>#{input.options[input.selectedIndex].textContent or null}</div>" innerHTML: "<div>#{select.options[select.selectedIndex].textContent or null}</div>"
$.on div, "click", Rice.selectclick $.on div, "click", Rice.cb.select
$.after input, div $.after select, div
### ###
JSColor JSColor
@ -635,14 +640,13 @@ JSColor =
fetchElement: (mixed) -> fetchElement: (mixed) ->
if typeof mixed is "string" then $.id mixed else mixed if typeof mixed is "string" then $.id mixed else mixed
fireEvent: (el, evnt) -> fireEvent: (el, event) ->
return unless el return unless el
ev = document.createEvent 'HTMLEvents' $.event event, null, el
ev.initEvent evnt, true, true
el.dispatchEvent ev
getRelMousePos: (e = window.event) -> getRelMousePos: (e) ->
e or= window.event
x = 0 x = 0
y = 0 y = 0
if typeof e.offsetX is 'number' if typeof e.offsetX is 'number'
@ -1345,9 +1349,9 @@ MascotTools =
close: -> close: ->
Conf['editMode'] = false Conf['editMode'] = false
editMascot = {} editMascot = {}
$.rm $("#mascotConf", d.body) $.rm $.id mascotConf
Style.addStyle() Style.addStyle()
Options.dialog("mascot") Settings.open "mascots"
importMascot: (evt) -> importMascot: (evt) ->
file = evt.target.files[0] file = evt.target.files[0]
@ -1380,7 +1384,7 @@ MascotTools =
alert "Mascot \"#{name}\" imported!" alert "Mascot \"#{name}\" imported!"
$.rm $("#mascotContainer", d.body) $.rm $("#mascotContainer", d.body)
Options.mascotTab.dialog() Settings.open 'mascots'
reader.readAsText(file) reader.readAsText(file)
@ -1641,108 +1645,108 @@ ThemeTools =
bgRPA = ['no-repeat', 'bottom', 'left', 'fixed'] bgRPA = ['no-repeat', 'bottom', 'left', 'fixed']
if origin == "oneechan" if origin == "oneechan"
Themes[name] = { Themes[name] =
'Author' : "Anonymous" 'Author' : "Anonymous"
'Author Tripcode' : "!POMF.9waa" 'Author Tripcode' : "!POMF.9waa"
'Background Image' : 'url("' + (imported.bgImg or '') + '")' 'Background Image' : "url('#{imported.bgImg or ''}')"
'Background Attachment' : bgRPA[3] or '' 'Background Attachment' : "#{bgRPA[3] or ''}"
'Background Position' : ((bgRPA[1] + " ") or '') + (bgRPA[2] or '') 'Background Position' : "#{bgRPA[1] or ''} #{bgRPA[2] or ''}"
'Background Repeat' : bgRPA[0] or '' 'Background Repeat' : "#{bgRPA[0] or ''}"
'Background Color' : 'rgb(' + bgColor.rgb + ')' 'Background Color' : "rgb(#{bgColor.rgb})"
'Dialog Background' : 'rgba(' + mainColor.rgb + ',.98)' 'Dialog Background' : "rgba(#{mainColor.rgb},.98)"
'Dialog Border' : 'rgb(' + brderColor.rgb + ')' 'Dialog Border' : "rgb(#{brderColor.rgb})"
'Thread Wrapper Background' : 'rgba(0,0,0,0)' 'Thread Wrapper Background' : "rgba(0,0,0,0)"
'Thread Wrapper Border' : 'rgba(0,0,0,0)' 'Thread Wrapper Border' : "rgba(0,0,0,0)"
'Reply Background' : 'rgba(' + mainColor.rgb + ',' + imported.replyOp + ')' 'Reply Background' : "rgba(#{mainColor.rgb},#{imported.replyOp})"
'Reply Border' : 'rgb(' + brderColor.rgb + ')' 'Reply Border' : "rgb(#{brderColor.rgb})"
'Highlighted Reply Background': 'rgba(' + mainColor.shiftRGB(4, true) + ',' + imported.replyOp + ')' 'Highlighted Reply Background': "rgba(#{mainColor.shiftRGB(4, true)}, #{imported.replyOp})"
'Highlighted Reply Border' : 'rgb(' + linkColor.rgb + ')' 'Highlighted Reply Border' : "rgb(#{linkColor.rgb})"
'Backlinked Reply Outline' : 'rgb(' + linkColor.rgb + ')' 'Backlinked Reply Outline' : "rgb(#{linkColor.rgb})"
'Checkbox Background' : 'rgba(' + inputColor.rgb + ',' + imported.replyOp + ')' 'Checkbox Background' : "rgba(#{inputColor.rgb}, #{imported.replyOp})"
'Checkbox Border' : 'rgb(' + inputbColor.rgb + ')' 'Checkbox Border' : "rgb(#{inputbColor.rgb})"
'Checkbox Checked Background' : 'rgb(' + inputColor.rgb + ')' 'Checkbox Checked Background' : "rgb(#{inputColor.rgb})"
'Input Background' : 'rgba(' + inputColor.rgb + ',' + imported.replyOp + ')' 'Input Background' : "rgba(#{inputColor.rgb}, #{imported.replyOp})"
'Input Border' : 'rgb(' + inputbColor.rgb + ')' 'Input Border' : "rgb(#{inputbColor.rgb})"
'Hovered Input Background' : 'rgba(' + inputColor.hover + ',' + imported.replyOp + ')' 'Hovered Input Background' : "rgba(#{inputColor.hover}, #{imported.replyOp})"
'Hovered Input Border' : 'rgb(' + inputbColor.rgb + ')' 'Hovered Input Border' : "rgb(#{inputbColor.rgb})"
'Focused Input Background' : 'rgba(' + inputColor.hover + ',' + imported.replyOp + ')' 'Focused Input Background' : "rgba(#{inputColor.hover}, #{imported.replyOp})"
'Focused Input Border' : 'rgb(' + inputbColor.rgb + ')' 'Focused Input Border' : "rgb(#{inputbColor.rgb})"
'Buttons Background' : 'rgba(' + inputColor.rgb + ',' + imported.replyOp + ')' 'Buttons Background' : "rgba(#{inputColor.rgb}, #{imported.replyOp})"
'Buttons Border' : 'rgb(' + inputbColor.rgb + ')' 'Buttons Border' : "rgb(#{inputbColor.rgb})"
'Navigation Background' : 'rgba(' + bgColor.rgb + ',0.8)' 'Navigation Background' : "rgba(#{bgColor.rgb}, 0.8)"
'Navigation Border' : 'rgb(' + mainColor.rgb + ')' 'Navigation Border' : "rgb(#{mainColor.rgb})"
'Quotelinks' : 'rgb(' + linkColor.rgb + ')' 'Quotelinks' : "rgb(#{linkColor.rgb})"
'Links' : 'rgb(' + linkColor.rgb + ')' 'Links' : "rgb(#{linkColor.rgb})"
'Hovered Links' : 'rgb(' + linkHColor.rgb + ')' 'Hovered Links' : "rgb(#{linkHColor.rgb})"
'Navigation Links' : 'rgb(' + textColor.rgb + ')' 'Navigation Links' : "rgb(#{textColor.rgb})"
'Hovered Navigation Links' : 'rgb(' + linkHColor.rgb + ')' 'Hovered Navigation Links' : "rgb(#{linkHColor.rgb})"
'Subjects' : 'rgb(' + titleColor.rgb + ')' 'Subjects' : "rgb(#{titleColor.rgb})"
'Names' : 'rgb(' + nameColor.rgb + ')' 'Names' : "rgb(#{nameColor.rgb})"
'Sage' : 'rgb(' + sageColor.rgb + ')' 'Sage' : "rgb(#{sageColor.rgb})"
'Tripcodes' : 'rgb(' + tripColor.rgb + ')' 'Tripcodes' : "rgb(#{tripColor.rgb})"
'Emails' : 'rgb(' + linkColor.rgb + ')' 'Emails' : "rgb(#{linkColor.rgb})"
'Post Numbers' : 'rgb(' + linkColor.rgb + ')' 'Post Numbers' : "rgb(#{linkColor.rgb})"
'Text' : 'rgb(' + textColor.rgb + ')' 'Text' : "rgb(#{textColor.rgb})"
'Backlinks' : 'rgb(' + linkColor.rgb + ')' 'Backlinks' : "rgb(#{linkColor.rgb})"
'Greentext' : 'rgb(' + quoteColor.rgb + ')' 'Greentext' : "rgb(#{quoteColor.rgb})"
'Board Title' : 'rgb(' + textColor.rgb + ')' 'Board Title' : "rgb(#{textColor.rgb})"
'Timestamps' : 'rgb(' + timeColor.rgb + ')' 'Timestamps' : "rgb(#{timeColor.rgb})"
'Inputs' : 'rgb(' + textColor.rgb + ')' 'Inputs' : "rgb(#{textColor.rgb})"
'Warnings' : 'rgb(' + sageColor.rgb + ')' 'Warnings' : "rgb(#{sageColor.rgb})"
'Shadow Color' : 'rgba(0,0,0,0.1)' 'Shadow Color' : "rgba(0,0,0,0.1)"
'Custom CSS' : """<%= grunt.file.read('css/theme.oneechan.css') %>""" + (imported.customCSS or '') } 'Custom CSS' : """<%= grunt.file.read('css/theme.oneechan.css') %> #{imported.customCSS or ''}"""
else if origin == "SS" else if origin == "SS"
Themes[name] = { Themes[name] =
'Author' : "Anonymous" 'Author' : "Anonymous"
'Author Tripcode' : "!.pC/AHOKAg" 'Author Tripcode' : "!.pC/AHOKAg"
'Background Image' : 'url("' + (imported.bgImg or '') + '")' 'Background Image' : "url('#{imported.bgImg or ''}')"
'Background Attachment' : bgRPA[3] or '' 'Background Attachment' : "#{bgRPA[3] or ''}"
'Background Position' : ((bgRPA[1] + " ") or '') + (bgRPA[2] or '') 'Background Position' : "#{bgRPA[1] or ''} #{bgRPA[2] or ''}"
'Background Repeat' : bgRPA[0] or '' 'Background Repeat' : "#{bgRPA[0] or ''}"
'Background Color' : 'rgb(' + bgColor.rgb + ')' 'Background Color' : "rgb(#{bgColor.rgb})"
'Dialog Background' : 'rgba(' + mainColor.rgb + ',.98)' 'Dialog Background' : "rgba(#{mainColor.rgb}, .98)"
'Dialog Border' : 'rgb(' + brderColor.rgb + ')' 'Dialog Border' : "rgb(#{brderColor.rgb})"
'Thread Wrapper Background' : 'rgba(' + mainColor.rgb + ',.5)' 'Thread Wrapper Background' : "rgba(#{mainColor.rgb}, .5)"
'Thread Wrapper Border' : 'rgba(' + brderColor.rgb + ',.9)' 'Thread Wrapper Border' : "rgba(#{brderColor.rgb}, .9)"
'Reply Background' : 'rgba(' + mainColor.rgb + ',.9)' 'Reply Background' : "rgba(#{mainColor.rgb}, .9)"
'Reply Border' : 'rgb(' + brderColor.rgb + ')' 'Reply Border' : "rgb(#{brderColor.rgb})"
'Highlighted Reply Background': 'rgba(' + mainColor.shiftRGB(4, true) + ',.9)' 'Highlighted Reply Background': "rgba(#{mainColor.shiftRGB(4, true)}, .9)"
'Highlighted Reply Border' : 'rgb(' + linkColor.rgb + ')' 'Highlighted Reply Border' : "rgb(#{linkColor.rgb})"
'Backlinked Reply Outline' : 'rgb(' + linkColor.rgb + ')' 'Backlinked Reply Outline' : "rgb(#{linkColor.rgb})"
'Checkbox Background' : 'rgba(' + inputColor.rgb + ',.9)' 'Checkbox Background' : "rgba(#{inputColor.rgb}, .9)"
'Checkbox Border' : 'rgb(' + inputbColor.rgb + ')' 'Checkbox Border' : "rgb(#{inputbColor.rgb})"
'Checkbox Checked Background' : 'rgb(' + inputColor.rgb + ')' 'Checkbox Checked Background' : "rgb(#{inputColor.rgb})"
'Input Background' : 'rgba(' + inputColor.rgb + ',.9)' 'Input Background' : "rgba(#{inputColor.rgb}, .9)"
'Input Border' : 'rgb(' + inputbColor.rgb + ')' 'Input Border' : "rgb(#{inputbColor.rgb})"
'Hovered Input Background' : 'rgba(' + inputColor.hover + ',.9)' 'Hovered Input Background' : "rgba(#{inputColor.hover}, .9)"
'Hovered Input Border' : 'rgb(' + inputbColor.rgb + ')' 'Hovered Input Border' : "rgb(#{inputbColor.rgb})"
'Focused Input Background' : 'rgba(' + inputColor.hover + ',.9)' 'Focused Input Background' : "rgba(#{inputColor.hover}, .9)"
'Focused Input Border' : 'rgb(' + inputbColor.rgb + ')' 'Focused Input Border' : "rgb(#{inputbColor.rgb})"
'Buttons Background' : 'rgba(' + inputColor.rgb + ',.9)' 'Buttons Background' : "rgba(#{inputColor.rgb}, .9)"
'Buttons Border' : 'rgb(' + inputbColor.rgb + ')' 'Buttons Border' : "rgb(#{inputbColor.rgb})"
'Navigation Background' : 'rgba(' + bgColor.rgb + ',0.8)' 'Navigation Background' : "rgba(#{bgColor.rgb}', 0.8)"
'Navigation Border' : 'rgb(' + mainColor.rgb + ')' 'Navigation Border' : "rgb(#{mainColor.rgb})"
'Quotelinks' : 'rgb(' + linkColor.rgb + ')' 'Quotelinks' : "rgb(#{linkColor.rgb})"
'Links' : 'rgb(' + linkColor.rgb + ')' 'Links' : "rgb(#{linkColor.rgb})"
'Hovered Links' : 'rgb(' + linkHColor.rgb + ')' 'Hovered Links' : "rgb(#{linkHColor.rgb})"
'Navigation Links' : 'rgb(' + textColor.rgb + ')' 'Navigation Links' : "rgb(#{textColor.rgb})"
'Hovered Navigation Links' : 'rgb(' + linkHColor.rgb + ')' 'Hovered Navigation Links' : "rgb(#{linkHColor.rgb})"
'Subjects' : 'rgb(' + titleColor.rgb + ')' 'Subjects' : "rgb(#{titleColor.rgb})"
'Names' : 'rgb(' + nameColor.rgb + ')' 'Names' : "rgb(#{nameColor.rgb})"
'Sage' : 'rgb(' + sageColor.rgb + ')' 'Sage' : "rgb(#{sageColor.rgb})"
'Tripcodes' : 'rgb(' + tripColor.rgb + ')' 'Tripcodes' : "rgb(#{tripColor.rgb})"
'Emails' : 'rgb(' + linkColor.rgb + ')' 'Emails' : "rgb(#{linkColor.rgb})"
'Post Numbers' : 'rgb(' + linkColor.rgb + ')' 'Post Numbers' : "rgb(#{linkColor.rgb})"
'Text' : 'rgb(' + textColor.rgb + ')' 'Text' : "rgb(#{textColor.rgb})"
'Backlinks' : 'rgb(' + linkColor.rgb + ')' 'Backlinks' : "rgb(#{linkColor.rgb})"
'Greentext' : 'rgb(' + quoteColor.rgb + ')' 'Greentext' : "rgb(#{quoteColor.rgb})"
'Board Title' : 'rgb(' + textColor.rgb + ')' 'Board Title' : "rgb(#{textColor.rgb})"
'Timestamps' : 'rgb(' + timeColor.rgb + ')' 'Timestamps' : "rgb(#{timeColor.rgb})"
'Inputs' : 'rgb(' + textColor.rgb + ')' 'Inputs' : "rgb(#{textColor.rgb})"
'Warnings' : 'rgb(' + sageColor.rgb + ')' 'Warnings' : "rgb(#{sageColor.rgb})"
'Shadow Color' : 'rgba(0,0,0,0.1)' 'Shadow Color' : "rgba(0,0,0,0.1)"
'Custom CSS' : """<%= grunt.file.read('css/theme.4chanss.css') %>""" + (imported.customCSS or '') } 'Custom CSS' : """<%= grunt.file.read('css/theme.4chanss.css') %> #{imported.customCSS or ''}"""
else if origin == 'appchan' else if origin == 'appchan'
Themes[name] = imported Themes[name] = imported
@ -1752,7 +1756,7 @@ ThemeTools =
$.set 'userThemes', userThemes $.set 'userThemes', userThemes
alert "Theme \"#{name}\" imported!" alert "Theme \"#{name}\" imported!"
$.rm $("#themes", d.body) $.rm $("#themes", d.body)
Options.themeTab() Settings.open 'themes'
reader.readAsText(file) reader.readAsText(file)
@ -1775,6 +1779,6 @@ ThemeTools =
close: -> close: ->
Conf['editMode'] = false Conf['editMode'] = false
$.rm $("#themeConf", d.body) $.rm $id 'themeConf'
Style.addStyle() Style.addStyle()
Options.dialog("theme") Settings.open 'themes'

View File

@ -54,20 +54,20 @@ Settings =
if Conf['editMode'] is "theme" if Conf['editMode'] is "theme"
if confirm "Opening the options dialog will close and discard any theme changes made with the theme editor." if confirm "Opening the options dialog will close and discard any theme changes made with the theme editor."
ThemeTools.close() ThemeTools.close()
else return
return
if Conf['editMode'] is "mascot" if Conf['editMode'] is "mascot"
if confirm "Opening the options dialog will close and discard any mascot changes made with the mascot editor." if confirm "Opening the options dialog will close and discard any mascot changes made with the mascot editor."
MascotTools.close() MascotTools.close()
else return
return
return if Settings.dialog return if Settings.overlay
$.event 'CloseMenu' $.event 'CloseMenu'
html = """ Settings.dialog = dialog = $.el 'div',
<div id=appchanx-settings class=dialog> id: 'appchanx-settings'
class: 'dialog'
innerHTML: """
<nav> <nav>
<div class=sections-list></div> <div class=sections-list></div>
<div class=credits> <div class=credits>
@ -78,13 +78,10 @@ Settings =
</div> </div>
</nav> </nav>
<hr> <hr>
<div class=section-container><section></section></div> <div class=section-container><section></section></div>"""
</div>
"""
Settings.dialog = overlay = $.el 'div', Settings.overlay = overlay = $.el 'div',
id: 'overlay' id: 'overlay'
innerHTML: html
links = [] links = []
for section in Settings.sections for section in Settings.sections
@ -95,22 +92,23 @@ Settings =
$.on link, 'click', Settings.openSection.bind section $.on link, 'click', Settings.openSection.bind section
links.push link links.push link
sectionToOpen = link if section.title is openSection sectionToOpen = link if section.title is openSection
$.add $('.sections-list', overlay), links $.add $('.sections-list', dialog), links
(if sectionToOpen then sectionToOpen else links[0]).click() (if sectionToOpen then sectionToOpen else links[0]).click()
$.on $('.close', overlay), 'click', Settings.close $.on $('.close', dialog), 'click', Settings.close
$.on overlay, 'click', Settings.close $.on overlay, 'click', Settings.close
$.on overlay.firstElementChild, 'click', (e) -> e.stopPropagation()
d.body.style.width = "#{d.body.clientWidth}px" d.body.style.width = "#{d.body.clientWidth}px"
$.addClass d.body, 'unscroll' $.addClass d.body, 'unscroll'
$.add d.body, overlay $.add d.body, [overlay, dialog]
close: -> close: ->
return unless Settings.dialog return unless Settings.dialog
d.body.style.removeProperty 'width' d.body.style.removeProperty 'width'
$.rmClass d.body, 'unscroll' $.rmClass d.body, 'unscroll'
$.rm Settings.overlay
$.rm Settings.dialog $.rm Settings.dialog
delete Settings.overlay
delete Settings.dialog delete Settings.dialog
sections: [] sections: []
@ -152,8 +150,9 @@ Settings =
for key, arr of obj for key, arr of obj
description = arr[1] description = arr[1]
div = $.el 'div', div = $.el 'div',
innerHTML: "<label><input type=checkbox name='#{key}'>#{key}</label><span class=description>: #{description}</span>" innerHTML: "<label><input type=checkbox name='#{key}'>#{key}</label><span class=description>#{description}</span>"
input = $ 'input', div input = $ 'input', div
$.on $('label', div), 'mouseover', Settings.mouseover
$.on input, 'change', $.cb.checked $.on input, 'change', $.cb.checked
items[key] = Conf[key] items[key] = Conf[key]
inputs[key] = input inputs[key] = input
@ -551,6 +550,7 @@ Settings =
$.on input, 'keydown', Settings.keybind $.on input, 'keydown', Settings.keybind
Rice.nodes tr Rice.nodes tr
$.add tbody, tr $.add tbody, tr
$.get items, (items) -> $.get items, (items) ->
for key, val of items for key, val of items
inputs[key].value = val inputs[key].value = val
@ -565,7 +565,9 @@ Settings =
$.cb.value.call @ $.cb.value.call @
style: (section) -> style: (section) ->
nodes = [] nodes = $.frag()
items = {}
inputs = {}
for key, obj of Config.style for key, obj of Config.style
@ -582,44 +584,51 @@ Settings =
if type is 'text' if type is 'text'
div.innerHTML = "<div class=option><span class=optionlabel>#{key}</span></div><div style='display:none;'>#{description}</div><div class=option><input name='#{key}' style=width: 100%></div>" div.innerHTML = "<div class=option><span class=optionlabel>#{key}</span></div><div class=description>#{description}</div><div class=option><input name='#{key}' style=width: 100%></div>"
input = $ "input[name='#{key}']", div input = $ "input", div
else else
html = "<div class=option><span class=optionlabel>#{key}</span></div><div style='display:none;'>#{description}</div><div class=option><select name='#{key}'></div>" html = "<div class=option><span class=optionlabel>#{key}</span></div><div class=description>#{description}</div><div class=option><select name='#{key}'>"
for name, val in type for name in type
html += "<option value='#{val}'>#{name}</option>" html += "<option value='#{name}'>#{name}</option>"
html += "</select>" html += "</select></div>"
div.innerHTML = html div.innerHTML = html
input = $ "select", div input = $ "select", div
input.cb = 'value'
else else
div.innerHTML = "<div class=option><label><input type=checkbox name='#{key}'>#{key}</label></div><span style='display:none;'>#{description}</span>" div.innerHTML = "<div class=option><label><input type=checkbox name='#{key}'>#{key}</label></div><span style='display:none;'>#{description}</span>"
input = $ 'input', div input = $ 'input', div
input.cb = 'checked' input.bool = true
Settings.sandbox input, key, value, input.cb items[key] = Conf[key]
inputs[key] = input
$.on $('.option', div), 'mouseover', Settings.mouseover $.on $('.option', div), 'mouseover', Settings.mouseover
$.on input, 'change', -> $.on input, 'change', Settings.change
$.cb[@cb].call @
Style.addStyle()
$.add fs, div $.add fs, div
$.add nodes, fs
Rice.nodes fs $.get items, (items) ->
nodes.push fs for key, val of items
input = inputs[key]
if input.bool
input.checked = val
Rice.checkbox input
else
input.value = val
if input.nodeName is 'SELECT'
Rice.select input
$.add section, nodes $.add section, nodes
sandbox: (input, key, value, inputtype) ->
$.get key, value, (item) -> change: ->
input[inputtype] = item[key] $.cb[if @bool then 'checked' else 'value'].call @
Style.addStyle()
themes: (section, mode) -> themes: (section, mode) ->
if typeof mode isnt 'string' if typeof mode isnt 'string'