diff --git a/templates/captcha_script.html b/templates/captcha_script.html new file mode 100644 index 00000000..a511d51e --- /dev/null +++ b/templates/captcha_script.html @@ -0,0 +1,3 @@ +{% if config.turnstile %} + +{% endif %} diff --git a/templates/index.html b/templates/index.html index f36ff88b..f5b64c96 100644 --- a/templates/index.html +++ b/templates/index.html @@ -13,9 +13,7 @@ active_page = "ukko"; {% endif %} - {% if config.turnstile %} - - {% endif %} + {{ include('captcha_script.html', { form_action_type: 'post_thread' }) }} {% include 'header.html' %} {% set page_num %}{% for page in pages %}{% if page.selected %}{% if page.num != 1 %}{{ page.num }}{% endif %}{% endif %}{% endfor %}{% endset %} @@ -61,7 +59,7 @@ {{ config.ad.top }} {% if not no_post_form %} - {{ include('post_form.html', {form_action_type: 'post-thread'}) }} + {% include 'post_form.html' %} {% else %} {% include 'boardlist.html' %} {% endif %} diff --git a/templates/main.js b/templates/main.js index 1639175d..bd0a44c6 100755 --- a/templates/main.js +++ b/templates/main.js @@ -18,92 +18,92 @@ function _(s) { * > alert(fmt(_("{0} users"), [3])); * 3 uzytkownikow */ -function fmt(s,a) { +function fmt(s, a) { return s.replace(/\{([0-9]+)\}/g, function(x) { return a[x[1]]; }); } -function until($timestamp) { - var $difference = $timestamp - Date.now()/1000|0, $num; - switch(true){ - case ($difference < 60): - return "" + $difference + ' ' + _('second(s)'); - case ($difference < 3600): //60*60 = 3600 - return "" + ($num = Math.round($difference/(60))) + ' ' + _('minute(s)'); - case ($difference < 86400): //60*60*24 = 86400 - return "" + ($num = Math.round($difference/(3600))) + ' ' + _('hour(s)'); - case ($difference < 604800): //60*60*24*7 = 604800 - return "" + ($num = Math.round($difference/(86400))) + ' ' + _('day(s)'); - case ($difference < 31536000): //60*60*24*365 = 31536000 - return "" + ($num = Math.round($difference/(604800))) + ' ' + _('week(s)'); - default: - return "" + ($num = Math.round($difference/(31536000))) + ' ' + _('year(s)'); - } +function until(timestamp) { + let difference = timestamp - Date.now() / 1000 | 0; + switch (true) { + case (difference < 60): + return "" + difference + ' ' + _('second(s)'); + case (difference < 3600): // 60 * 60 = 3600 + return "" + Math.round(difference / 60) + ' ' + _('minute(s)'); + case (difference < 86400): // 60 * 60 * 24 = 86400 + return "" + Math.round(difference / 3600) + ' ' + _('hour(s)'); + case (difference < 604800): // 60 * 60 * 24 * 7 = 604800 + return "" + Math.round(difference / 86400) + ' ' + _('day(s)'); + case (difference < 31536000): // 60 * 60 * 24 * 365 = 31536000 + return "" + Math.round(difference / 604800) + ' ' + _('week(s)'); + default: + return "" + Math.round(difference / 31536000) + ' ' + _('year(s)'); + } } -function ago($timestamp) { - var $difference = (Date.now()/1000|0) - $timestamp, $num; - switch(true){ - case ($difference < 60) : - return "" + $difference + ' ' + _('second(s)'); - case ($difference < 3600): //60*60 = 3600 - return "" + ($num = Math.round($difference/(60))) + ' ' + _('minute(s)'); - case ($difference < 86400): //60*60*24 = 86400 - return "" + ($num = Math.round($difference/(3600))) + ' ' + _('hour(s)'); - case ($difference < 604800): //60*60*24*7 = 604800 - return "" + ($num = Math.round($difference/(86400))) + ' ' + _('day(s)'); - case ($difference < 31536000): //60*60*24*365 = 31536000 - return "" + ($num = Math.round($difference/(604800))) + ' ' + _('week(s)'); - default: - return "" + ($num = Math.round($difference/(31536000))) + ' ' + _('year(s)'); - } +function ago(timestamp) { + let difference = (Date.now() / 1000 | 0) - timestamp; + switch (true) { + case (difference < 60): + return "" + difference + ' ' + _('second(s)'); + case (difference < 3600): /// 60 * 60 = 3600 + return "" + Math.round(difference/(60)) + ' ' + _('minute(s)'); + case (difference < 86400): // 60 * 60 * 24 = 86400 + return "" + Math.round(difference/(3600)) + ' ' + _('hour(s)'); + case (difference < 604800): // 60 * 60 * 24 * 7 = 604800 + return "" + Math.round(difference/(86400)) + ' ' + _('day(s)'); + case (difference < 31536000): // 60 * 60 * 24 * 365 = 31536000 + return "" + Math.round(difference/(604800)) + ' ' + _('week(s)'); + default: + return "" + Math.round(difference/(31536000)) + ' ' + _('year(s)'); + } } var datelocale = - { days: [_('Sunday'), _('Monday'), _('Tuesday'), _('Wednesday'), _('Thursday'), _('Friday'), _('Saturday')] - , shortDays: [_("Sun"), _("Mon"), _("Tue"), _("Wed"), _("Thu"), _("Fri"), _("Sat")] - , months: [_('January'), _('February'), _('March'), _('April'), _('May'), _('June'), _('July'), _('August'), _('September'), _('October'), _('November'), _('December')] - , shortMonths: [_('Jan'), _('Feb'), _('Mar'), _('Apr'), _('May'), _('Jun'), _('Jul'), _('Aug'), _('Sep'), _('Oct'), _('Nov'), _('Dec')] - , AM: _('AM') - , PM: _('PM') - , am: _('am') - , pm: _('pm') - }; + { days: [_('Sunday'), _('Monday'), _('Tuesday'), _('Wednesday'), _('Thursday'), _('Friday'), _('Saturday')] + , shortDays: [_("Sun"), _("Mon"), _("Tue"), _("Wed"), _("Thu"), _("Fri"), _("Sat")] + , months: [_('January'), _('February'), _('March'), _('April'), _('May'), _('June'), _('July'), _('August'), _('September'), _('October'), _('November'), _('December')] + , shortMonths: [_('Jan'), _('Feb'), _('Mar'), _('Apr'), _('May'), _('Jun'), _('Jul'), _('Aug'), _('Sep'), _('Oct'), _('Nov'), _('Dec')] + , AM: _('AM') + , PM: _('PM') + , am: _('am') + , pm: _('pm') + }; function alert(a, do_confirm, confirm_ok_action, confirm_cancel_action) { - var handler, div, bg, closebtn, okbtn; - var close = function() { - handler.fadeOut(400, function() { handler.remove(); }); - return false; - }; + var handler, div, bg, closebtn, okbtn; + let close = function() { + handler.fadeOut(400, function() { handler.remove(); }); + return false; + }; - handler = $("
").hide().appendTo('body'); + handler = $("").hide().appendTo('body'); - bg = $("").appendTo(handler); + bg = $("").appendTo(handler); - div = $("").appendTo(handler); - closebtn = $("") - .appendTo(div); + div = $("").appendTo(handler); + closebtn = $("") + .appendTo(div); - $("").html(a).appendTo(div); + $("").html(a).appendTo(div); - okbtn = $("").appendTo(div); + okbtn = $("").appendTo(div); - if (do_confirm) { - confirm_ok_action = (typeof confirm_ok_action !== "function") ? function(){} : confirm_ok_action; - confirm_cancel_action = (typeof confirm_cancel_action !== "function") ? function(){} : confirm_cancel_action; - okbtn.click(confirm_ok_action); - $("").click(confirm_cancel_action).click(close).appendTo(div); - bg.click(confirm_cancel_action); - okbtn.click(confirm_cancel_action); - closebtn.click(confirm_cancel_action); - } + if (do_confirm) { + confirm_ok_action = (typeof confirm_ok_action !== "function") ? function(){} : confirm_ok_action; + confirm_cancel_action = (typeof confirm_cancel_action !== "function") ? function(){} : confirm_cancel_action; + okbtn.click(confirm_ok_action); + $("").click(confirm_cancel_action).click(close).appendTo(div); + bg.click(confirm_cancel_action); + okbtn.click(confirm_cancel_action); + closebtn.click(confirm_cancel_action); + } - bg.click(close); - okbtn.click(close); - closebtn.click(close); + bg.click(close); + okbtn.click(close); + closebtn.click(close); - handler.fadeIn(400); + handler.fadeIn(400); } var saved = {}; @@ -148,7 +148,7 @@ function changeStyle(styleName, link) { } document.getElementById('stylesheet').href = styles[styleName]; - selectedstyle = styleName; + selectedstyle = styleName; // Code stylesheet if (!document.getElementById('code_stylesheet')) { @@ -173,8 +173,9 @@ function changeStyle(styleName, link) { link.className = 'selected'; } - if (typeof $ != 'undefined') + if (typeof $ != 'undefined') { $(window).trigger('stylesheet', styleName); + } } @@ -210,7 +211,7 @@ function changeStyle(styleName, link) { {% endif %} {% raw %} -function init_stylechooser() { +function initStyleChooser() { var newElement = document.createElement('div'); newElement.className = 'styles'; @@ -230,45 +231,77 @@ function init_stylechooser() { document.getElementById('bottom-hud').before(newElement); } -function get_cookie(cookie_name) { - var results = document.cookie.match('(^|;) ?' + cookie_name + '=([^;]*)(;|$)'); - if (results) - return (unescape(results[2])); - else +function getCookie(cookie_name) { + let results = document.cookie.match('(^|;) ?' + cookie_name + '=([^;]*)(;|$)'); + if (results) { + return unescape(results[2]); + } else { return null; + } } {% endraw %} +{% if config.turnstile %} +// Wrapper function to be called from thread.html +window.onCaptchaLoadTurnstile_post_reply = function() { + onCaptchaLoadTurnstile('post-reply'); +} + +// Wrapper function to be called from index.html and catalog.html +window.onCaptchaLoadTurnstile_post_thread = function() { + onCaptchaLoadTurnstile('post-thread'); +} + +// Should be called by the captcha API when it's ready. Ugly I know... D: +function onCaptchaLoadTurnstile(action) { + let renderer = { + renderOn: function(container) { + let widgetId = turnstile.render(container, { + sitekey: "{{ config.turnstile_public }}", + action: action, + }); + if (widgetId === undefined) { + return null; + } + return widgetId; + }, + remove: function(widgetId) { + turnstile.remove(widgetId); + }, + reset: function(widgetId) { + turnstile.reset(widgetId); + } + }; + + onCaptchaLoad(renderer); +} +{% endif %} + +function onCaptchaLoad(renderer) { + let widgetId = renderer.renderOn('#captcha-container'); + if (widgetId === null) { + console.error('Could not render captcha!'); + } + document.addEventListener('afterdopost', function(e) { + // User posted! Reset the captcha. + renderer.reset(widgetId); + }); +} + {% if config.dynamic_captcha %} -function is_dynamic_captcha_enabled() { - let cookie = get_cookie('captcha-required'); +function isDynamicCaptchaEnabled() { + let cookie = getCookie('captcha-required'); return cookie === '1'; } -function get_captcha_pub_key() { -{% if config.recaptcha %} - return "{{ config.recaptcha_public }}"; -{% elseif config.turnstile_public %} - return "{{ config.turnstile_public }}"; -{% else %} - return null; -{% endif %} -} - -function init_dynamic_captcha() { - if (is_dynamic_captcha_enabled()) { - let pub_key = get_captcha_pub_key(); - if (!pub_key) { - console.error("Missing public captcha key!"); - return; - } - +function initDynamicCaptcha() { + if (isDynamicCaptchaEnabled()) { let captcha_hook = document.getElementById('captcha'); captcha_hook.style = ""; } } {% else %} -function init_dynamic_captcha() {} +function initDynamicCaptcha() {} {% endif %} {% raw %} @@ -278,32 +311,34 @@ function highlightReply(id) { return true; } - var divs = document.getElementsByTagName('div'); + let divs = document.getElementsByTagName('div'); for (var i = 0; i < divs.length; i++) { - if (divs[i].className.indexOf('post') != -1) + if (divs[i].className.indexOf('post') != -1) { divs[i].className = divs[i].className.replace(/highlighted/, ''); + } } if (id) { - var post = document.getElementById('reply_'+id); - if (post) + let post = document.getElementById('reply_' + id); + if (post) { post.className += ' highlighted'; - window.location.hash = id; + } + window.location.hash = id; } return true; } function generatePassword() { - var pass = ''; - var chars = '{% endraw %}{{ config.genpassword_chars }}{% raw %}'; - for (var i = 0; i < 8; i++) { - var rnd = Math.floor(Math.random() * chars.length); + let pass = ''; + let chars = '{% endraw %}{{ config.genpassword_chars }}{% raw %}'; + for (let i = 0; i < 8; i++) { + let rnd = Math.floor(Math.random() * chars.length); pass += chars.substring(rnd, rnd + 1); } return pass; } -function dopost(form) { +function doPost(form) { if (form.elements['name']) { localStorage.name = form.elements['name'].value.replace(/( |^)## .+$/, ''); } @@ -317,6 +352,8 @@ function dopost(form) { saved[document.location] = form.elements['body'].value; sessionStorage.body = JSON.stringify(saved); + // Needs to be delayed by at least 1 frame, otherwise it may reset the form (read captcha) fields before they're sent. + setTimeout(() => document.dispatchEvent(new Event('afterdopost'))); return form.elements['body'].value != "" || (form.elements['file'] && form.elements['file'].value != "") || (form.elements.file_url && form.elements['file_url'].value != ""); } @@ -324,26 +361,29 @@ function reloadCaptcha() { // Reload captcha images (date reduces chance of caching) // If no securimage captcha is enabled, no elements will be found captchaImgs = document.querySelectorAll('[id=captcha-img]'); - for (var i = 0; i < captchaImgs.length; ++i) - captchaImgs[i].src = "/captcha.php?"+Date.now(); + for (let i = 0; i < captchaImgs.length; ++i) { + captchaImgs[i].src = "/captcha.php?" + Date.now(); + } captchas = document.querySelectorAll('[id=captcha]'); - for (var i = 0; i < captchas.length; ++i) + for (let i = 0; i < captchas.length; ++i) { captchas[i].value = ""; + } } function citeReply(id, with_link) { - var textarea = document.getElementById('body'); - - if (!textarea) return false; + let textarea = document.getElementById('body'); + if (!textarea) { + return false; + } if (document.selection) { // IE textarea.focus(); - var sel = document.selection.createRange(); + let sel = document.selection.createRange(); sel.text = '>>' + id + '\n'; } else if (textarea.selectionStart || textarea.selectionStart == '0') { - var start = textarea.selectionStart; - var end = textarea.selectionEnd; + let start = textarea.selectionStart; + let end = textarea.selectionEnd; textarea.value = textarea.value.substring(0, start) + '>>' + id + '\n' + textarea.value.substring(end, textarea.value.length); textarea.selectionStart += ('>>' + id).length + 1; @@ -353,9 +393,9 @@ function citeReply(id, with_link) { textarea.value += '>>' + id + '\n'; } if (typeof $ != 'undefined') { - var select = document.getSelection().toString(); + let select = document.getSelection().toString(); if (select) { - var body = $('#reply_' + id + ', #op_' + id).find('div.body'); // TODO: support for OPs + let body = $('#reply_' + id + ', #op_' + id).find('div.body'); // TODO: support for OPs // commenting out this condition, not sure of the purpose and gets in the way of citing // var index = body.text().indexOf(select.replace('\n', '')); // for some reason this only works like this // if (index > -1) { @@ -374,25 +414,29 @@ function citeReply(id, with_link) { function rememberStuff() { if (document.forms.post) { if (document.forms.post.password) { - if (!localStorage.password) + if (!localStorage.password) { localStorage.password = generatePassword(); + } document.forms.post.password.value = localStorage.password; } - if (localStorage.name && document.forms.post.elements['name']) + if (localStorage.name && document.forms.post.elements['name']) { document.forms.post.elements['name'].value = localStorage.name; - if (localStorage.email && document.forms.post.elements['email']) + } + if (localStorage.email && document.forms.post.elements['email']) { document.forms.post.elements['email'].value = localStorage.email; + } - if (window.location.hash.indexOf('q') == 1) + if (window.location.hash.indexOf('q') == 1) { citeReply(window.location.hash.substring(2), true); + } if (sessionStorage.body) { - var saved = JSON.parse(sessionStorage.body); - if (get_cookie('{% endraw %}{{ config.cookies.js }}{% raw %}')) { + let saved = JSON.parse(sessionStorage.body); + if (getCookie('{% endraw %}{{ config.cookies.js }}{% raw %}')) { // Remove successful posts - var successful = JSON.parse(get_cookie('{% endraw %}{{ config.cookies.js }}{% raw %}')); - for (var url in successful) { + let successful = JSON.parse(getCookie('{% endraw %}{{ config.cookies.js }}{% raw %}')); + for (let url in successful) { saved[url] = null; } sessionStorage.body = JSON.stringify(saved); @@ -416,15 +460,16 @@ var script_settings = function(script_name) { this.get = function(var_name, default_val) { if (typeof tb_settings == 'undefined' || typeof tb_settings[this.script_name] == 'undefined' || - typeof tb_settings[this.script_name][var_name] == 'undefined') + typeof tb_settings[this.script_name][var_name] == 'undefined') { return default_val; + } return tb_settings[this.script_name][var_name]; } }; function init() { - init_stylechooser(); - init_dynamic_captcha(); + initStyleChooser(); + initDynamicCaptcha(); {% endraw %} {% if config.allow_delete %} @@ -443,12 +488,12 @@ var RecaptchaOptions = { }; onready_callbacks = []; -function onready(fnc) { +function onReady(fnc) { onready_callbacks.push(fnc); } function ready() { - for (var i = 0; i < onready_callbacks.length; i++) { + for (let i = 0; i < onready_callbacks.length; i++) { onready_callbacks[i](); } } @@ -458,7 +503,7 @@ function ready() { var post_date = "{{ config.post_date }}"; var max_images = {{ config.max_images }}; -onready(init); +onReady(init); {% if config.google_analytics %}{% raw %} diff --git a/templates/post_form.html b/templates/post_form.html index b3f1d8ce..6434b7e8 100644 --- a/templates/post_form.html +++ b/templates/post_form.html @@ -1,5 +1,5 @@