diff options
| author | czaks <marcin@6irc.net> | 2013-08-05 06:03:40 -0400 |
|---|---|---|
| committer | czaks <marcin@6irc.net> | 2013-08-05 06:03:40 -0400 |
| commit | a84c4510fccfdc0cfb6f187633daea10dc70f326 (patch) | |
| tree | 6077f5211196ae40cac0184bb7cc67b81d320b0b /templates | |
| parent | 33c7abf11f3a9b5c0964a2d7a25533c2849dbc78 (diff) | |
| parent | a8327c3a37fd22d2aa5d63061c9d3eaa30ae425a (diff) | |
Merge branch 'master' of github.com:vichan-devel/Tinyboard
Conflicts:
js/post-hider.js
Diffstat (limited to 'templates')
33 files changed, 1132 insertions, 642 deletions
diff --git a/templates/error.html b/templates/error.html new file mode 100644 index 00000000..3b8eb693 --- /dev/null +++ b/templates/error.html @@ -0,0 +1,18 @@ +<div style="text-align:center"> + <h2 style="margin:20px 0">{{ message }}</h2> + {% if board %} + <p> + <a href="{{ config.root }}{% if mod %}{{ config.file_mod }}?/{% endif %}{{ board.dir }}{{ config.file_index }}"> + {% trans 'Go back' %} + </a> + </p> + {% endif %} +</div> +{% if debug and config.debug %} + <hr> + <h3>{% trans 'Error information' %}</h3> + <pre style="white-space:pre-wrap;font-size: 10px;"> + {{ debug }} + </pre> + <hr> +{% endif %}
\ No newline at end of file diff --git a/templates/generic_page.html b/templates/generic_page.html index 41300f6b..70cb15aa 100644 --- a/templates/generic_page.html +++ b/templates/generic_page.html @@ -22,7 +22,8 @@ {% include 'attention_bar.html' %} {% include 'post_form.html' %} - {% if config.blotter %}<hr /><div class="blotter">{{ config.blotter }}</div>{% endif %} + + {% if config.global_message %}<hr /><div class="blotter">{{ config.global_message }}</div>{% endif %} <hr /> <form name="postcontrols" action="{{ config.post_url }}" method="post"> <input type="hidden" name="board" value="{{ board.uri }}" /> diff --git a/templates/header.html b/templates/header.html index 95e0bc09..d054fd6d 100644 --- a/templates/header.html +++ b/templates/header.html @@ -4,6 +4,7 @@ <meta name="viewport" content="width=device-width, initial-scale=1, maximum-scale=1, user-scalable=yes"> {% if config.meta_keywords %}<meta name="keywords" content="{{ config.meta_keywords }}">{% endif %} {% if config.default_stylesheet.1 != '' %}<link rel="stylesheet" type="text/css" id="stylesheet" href="{{ config.uri_stylesheets }}{{ config.default_stylesheet.1 }}">{% endif %} + {% if config.font_awesome %}<link rel="stylesheet" media="screen" href="{{ config.root }}{{ config.font_awesome_css }}">{% endif %} <script type="text/javascript">var configRoot="{{ config.root }}";</script> {% if not nojavascript %} <script type="text/javascript" src="{{ config.url_javascript }}"></script> @@ -12,17 +13,31 @@ {% endif %} {% endif %} {% if config.recaptcha %}<style type="text/css">{% raw %} - .recaptcha_image_cell { - background: none !important; + #recaptcha_area { + float: none !important; + padding: 0 !important; } - table.recaptchatable { + #recaptcha_logo, #recaptcha_privacy { + display: none; + } + #recaptcha_table { border: none !important; } - #recaptcha_logo, #recaptcha_tagline { - display: none; - float: right; + #recaptcha_table tr:first-child { + height: auto; + } + .recaptchatable img { + float: none !important; + } + #recaptcha_response_field { + font-size: 10pt !important; + border: 1px solid #a9a9a9 !important; + padding: 1px !important; + } + td.recaptcha_image_cell { + background: transparent !important; } - .recaptchatable a { - display: block; + .recaptchatable, #recaptcha_area tr, #recaptcha_area td, #recaptcha_area th { + padding: 0 !important; } {% endraw %}</style>{% endif %} diff --git a/templates/index.html b/templates/index.html index 451ca8b1..12150d0b 100644 --- a/templates/index.html +++ b/templates/index.html @@ -1,61 +1,61 @@ -<!doctype html>
-<html>
-<head>
- <meta charset="utf-8">
-
- <script type="text/javascript">
- {% if config.quick_reply %}
- var new_reply_string = "{{ config.button_reply }}";
- {% endif %}
- {% if not no_post_form %}
- var active_page = "index";
- {% else %}
- var active_page = "ukko";
- {% endif %}
- </script>
-
- {% include 'header.html' %}
- <title>{{ board.url }} - {{ board.title|e }}</title>
-</head>
-<body>
- {{ boardlist.top }}
- {% if pm %}<div class="top_notice">You have <a href="?/PM/{{ pm.id }}">an unread PM</a>{% if pm.waiting > 0 %}, plus {{ pm.waiting }} more waiting{% endif %}.</div><hr />{% endif %}
- {% if config.url_banner %}<img class="banner" src="{{ config.url_banner }}" {% if config.banner_width or config.banner_height %}style="{% if config.banner_width %}width:{{ config.banner_width }}px{% endif %};{% if config.banner_width %}height:{{ config.banner_height }}px{% endif %}" {% endif %}alt="" />{% endif %}
- <header>
- <h1>{{ board.url }} - {{ board.title|e }}</h1>
- <div class="subtitle">
- {% if board.subtitle %}
- {{ board.subtitle|e }}
- {% endif %}
- {% if mod %}<p><a href="?/">{% trans %}Return to dashboard{% endtrans %}</a></p>{% endif %}
- </div>
- </header>
-
- {% include 'attention_bar.html' %}
- {% if not no_post_form %}
- {% include 'post_form.html' %}
- {% else %}
- {% include 'boardlist.html' %}
- {% endif %}
-
- {% if config.blotter %}<hr /><div class="blotter">{{ config.blotter }}</div>{% endif %}
- <hr />
- <form name="postcontrols" action="{{ config.post_url }}" method="post">
- <input type="hidden" name="board" value="{{ board.uri }}" />
- {% if mod %}<input type="hidden" name="mod" value="1" />{% endif %}
- {{ body }}
- {% include 'report_delete.html' %}
- </form>
- <div class="pages">{{ btn.prev }} {% for page in pages %}
- [<a {% if page.selected %}class="selected"{% endif %}{% if not page.selected %}href="{{ page.link }}"{% endif %}>{{ page.num }}</a>]{% if loop.last %} {% endif %}
- {% endfor %} {{ btn.next }}</div>
- {{ boardlist.bottom }}
- <footer>
- <p class="unimportant" style="margin-top:20px;text-align:center;">Powered by <a href="http://tinyboard.org/">Tinyboard</a> {{ config.version }} | <a href="http://tinyboard.org/">Tinyboard</a> Copyright © 2010-2013 Tinyboard Development Group</p>
- {% for footer in config.footer %}<p class="unimportant" style="text-align:center;">{{ footer }}</p>{% endfor %}
- </footer>
- <script type="text/javascript">{% raw %}
- ready();
- {% endraw %}</script>
-</body>
-</html>
+<!doctype html> +<html> +<head> + <meta charset="utf-8"> + + <script type="text/javascript"> + {% if config.quick_reply %} + var new_reply_string = "{{ config.button_reply }}"; + {% endif %} + {% if not no_post_form %} + var active_page = "index"; + {% else %} + var active_page = "ukko"; + {% endif %} + </script> + + {% include 'header.html' %} + <title>{{ board.url }} - {{ board.title|e }}</title> +</head> +<body> + {{ boardlist.top }} + {% if pm %}<div class="top_notice">You have <a href="?/PM/{{ pm.id }}">an unread PM</a>{% if pm.waiting > 0 %}, plus {{ pm.waiting }} more waiting{% endif %}.</div><hr />{% endif %} + {% if config.url_banner %}<img class="banner" src="{{ config.url_banner }}" {% if config.banner_width or config.banner_height %}style="{% if config.banner_width %}width:{{ config.banner_width }}px{% endif %};{% if config.banner_width %}height:{{ config.banner_height }}px{% endif %}" {% endif %}alt="" />{% endif %} + <header> + <h1>{{ board.url }} - {{ board.title|e }}</h1> + <div class="subtitle"> + {% if board.subtitle %} + {{ board.subtitle|e }} + {% endif %} + {% if mod %}<p><a href="?/">{% trans %}Return to dashboard{% endtrans %}</a></p>{% endif %} + </div> + </header> + + {% include 'attention_bar.html' %} + {% if not no_post_form %} + {% include 'post_form.html' %} + {% else %} + {% include 'boardlist.html' %} + {% endif %} + + {% if config.global_message %}<hr /><div class="blotter">{{ config.global_message }}</div>{% endif %} + <hr /> + <form name="postcontrols" action="{{ config.post_url }}" method="post"> + <input type="hidden" name="board" value="{{ board.uri }}" /> + {% if mod %}<input type="hidden" name="mod" value="1" />{% endif %} + {{ body }} + {% include 'report_delete.html' %} + </form> + <div class="pages">{{ btn.prev }} {% for page in pages %} + [<a {% if page.selected %}class="selected"{% endif %}{% if not page.selected %}href="{{ page.link }}"{% endif %}>{{ page.num }}</a>]{% if loop.last %} {% endif %} + {% endfor %} {{ btn.next }}</div> + {{ boardlist.bottom }} + <footer> + <p class="unimportant" style="margin-top:20px;text-align:center;">Powered by <a href="http://tinyboard.org/">Tinyboard</a> {{ config.version }} | <a href="http://tinyboard.org/">Tinyboard</a> Copyright © 2010-2013 Tinyboard Development Group</p> + {% for footer in config.footer %}<p class="unimportant" style="text-align:center;">{{ footer }}</p>{% endfor %} + </footer> + <script type="text/javascript">{% raw %} + ready(); + {% endraw %}</script> +</body> +</html> diff --git a/templates/installer/check-requirements.html b/templates/installer/check-requirements.html new file mode 100644 index 00000000..b6003f3a --- /dev/null +++ b/templates/installer/check-requirements.html @@ -0,0 +1,54 @@ +<div style="max-width:700px;margin:auto"> + <h2 style="text-align:center">Pre-installation tests</h2> + <table class="modlog" style="margin-top:10px;max-width:600px"> + <tr> + <th>Category</th> + <th>Test</th> + <th>Result</th> + </tr> + {% set errors = 0 %} + {% set warnings = 0 %} + {% for test in tests %} + <tr> + <td class="minimal"><strong>{{ test.category }}</strong></td> + <td>{{ test.name }}</td> + <td class="minimal" style="text-align:center"> + {% if test.result %} + <i style="font-size:11pt;color:#090" class="icon-check-sign"></i> + {% else %} + {% if test.required %} + {% set errors = errors + 1 %} + <i style="font-size:11pt;color:#d00" class="icon-exclamation-sign"></i> + {% else %} + {% set warnings = warnings + 1 %} + <i style="font-size:11pt;color:#f80" class="icon-warning-sign"></i> + {% endif %} + {% endif %} + </td> + </tr> + {% endfor %} + </table> + {% if errors or warnings %} + <p><strong>There were {{ errors }} error(s) and {{ warnings }} warning(s).</strong></p> + <ul> + {% for test in tests if not test.result%} + <li style="margin-bottom:5px"> + {% if test.required %} + <i style="font-size:11pt;color:#d00" class="icon-exclamation-sign"></i> <strong>Error:</strong> + {% else %} + <i style="font-size:11pt;color:#f80" class="icon-warning-sign"></i> <strong>Warning:</strong> + {% endif %} + {{ test.message }} + </li> + {% endfor %} + </ul> + {% if errors %} + <p style="text-align:center"><a href="?step=2">Clik here to ignore errors and attempt installing anyway (not recommended).</a></p> + {% else %} + <p style="text-align:center"><a href="?step=2">Clik here to proceed with installation.</a></p> + {% endif %} + {% else %} + <p>There were no errors or warnings. Good!</p> + <p style="text-align:center"><a href="?step=2">Clik here to proceed with installation.</a></p> + {% endif %} +</div> diff --git a/templates/installer/config.html b/templates/installer/config.html new file mode 100644 index 00000000..193bb98b --- /dev/null +++ b/templates/installer/config.html @@ -0,0 +1,95 @@ +<form action="?step=3" method="post" autocomplete="off"> + <fieldset> + <legend>Database (MySQL)</legend> + <label for="db_server">Server:</label> + <input type="text" id="db_server" name="db[server]" value="{{ config.db.server }}"> + + <label for="db_db">Database:</label> + <input type="text" id="db_db" name="db[database]" value="{{ config.db.database }}"> + + <label for="db_prefix">Table prefix (optional):</label> + <input type="text" id="db_prefix" name="db[prefix]" value="{{ config.db.prefix }}"> + + <label for="db_user">Username:</label> + <input type="text" id="db_user" name="db[user]" value="{{ config.db.user }}"> + + <label for="db_pass">Password:</label> + <input type="password" id="db_pass" name="db[password]" value=""> + </fieldset> + <p style="text-align:center" class="unimportant">The following is all later configurable. For more options, <a href="http://tinyboard.org/docs/?p=Config">edit your configuration files</a> after installing.</p> + <fieldset> + <legend>Cookies</legend> + <label for="cookies_mod">Moderator cookie:</label> + <input type="text" id="cookies_mod" name="cookies[mod]" value="{{ config.cookies.mod }}"> + + <label for="cookies_salt">Secure salt:</label> + <input type="text" id="cookies_salt" name="cookies[salt]" value="{{ config.cookies.salt }}" size="40"> + </fieldset> + + <fieldset> + <legend>Flood control</legend> + <label for="flood_time">Seconds before each post:</label> + <input type="text" id="flood_time" name="flood_time" value="{{ config.flood_time }}"> + + <label for="flood_time_ip">Seconds before you can repost something (post the exact same text):</label> + <input type="text" id="flood_time_ip" name="flood_time_ip" value="{{ config.flood_time_ip }}"> + + <label for="flood_time_same">Same as above, but with a different IP address:</label> + <input type="text" id="flood_time_same" name="flood_time_same" value="{{ config.flood_time_same }}"> + + <label for="max_body">Maximum post body length:</label> + <input type="text" id="max_body" name="max_body" value="{{ config.max_body }}"> + + <label for="reply_limit">Replies in a thread before it can no longer be bumped:</label> + <input type="text" id="reply_limit" name="reply_limit" value="{{ config.reply_limit }}"> + + <label for="max_links">Maximum number of links in a single post:</label> + <input type="text" id="max_links" name="max_links" value="{{ config.max_links }}"> + </fieldset> + + <fieldset> + <legend>Images</legend> + <label for="max_filesize">Maximum image filesize (bytes):</label> + <input type="text" id="max_filesize" name="max_filesize" value="{{ config.max_filesize }}"> + + <label for="thumb_width">Thumbnail width:</label> + <input type="text" id="thumb_width" name="thumb_width" value="{{ config.thumb_width }}"> + + <label for="thumb_height">Thumbnail height:</label> + <input type="text" id="thumb_height" name="thumb_height" value="{{ config.thumb_height }}"> + + <label for="max_width">Maximum image width:</label> + <input type="text" id="max_width" name="max_width" value="{{ config.max_width }}"> + + <label for="max_height">Maximum image height:</label> + <input type="text" id="max_height" name="max_height" value="{{ config.max_height }}"> + </fieldset> + + <fieldset> + <legend>Display</legend> + <label for="threads_per_page">Threads per page:</label> + <input type="text" id="threads_per_page" name="threads_per_page" value="{{ config.threads_per_page }}"> + + <label for="max_pages">Page limit:</label> + <input type="text" id="max_pages" name="max_pages" value="{{ config.max_pages }}"> + + <label for="threads_preview">Number of replies to show per thread on the index page:</label> + <input type="text" id="threads_preview" name="threads_preview" value="{{ config.threads_preview }}"> + </fieldset> + + <fieldset> + <legend>Directories</legend> + <label for="root">Root URI (include trailing slash):</label> + <input type="text" id="root" name="root" value="{{ config.root }}" size="40"> + </fieldset> + + <fieldset> + <legend>Miscellaneous</legend> + <label for="secure_trip_salt">Secure trip (##) salt:</label> + <input type="text" id="secure_trip_salt" name="secure_trip_salt" value="{{ config.secure_trip_salt }}" size="40"> + </fieldset> + + <p style="text-align:center"> + <input type="submit" value="Complete installation"> + </p> +</form> diff --git a/templates/main.js b/templates/main.js index 31c0254a..71dcd92a 100644 --- a/templates/main.js +++ b/templates/main.js @@ -1,232 +1,271 @@ -{% raw %}
-
-/* gettext-compatible _ function, example of usage:
- *
- * > // Loading pl_PL.json here (containing polish translation strings generated by tools/i18n_compile.php)
- * > alert(_("Hello!"));
- * Witaj!
- */
-function _(s) {
- return (typeof l10n != 'undefined' && typeof l10n[s] != 'undefined') ? l10n[s] : s;
-}
-
-/* printf-like formatting function, example of usage:
- *
- * > alert(fmt("There are {0} birds on {1} trees", [3,4]));
- * There are 3 birds on 4 trees
- * > // Loading pl_PL.json here (containing polish translation strings generated by tools/locale_compile.php)
- * > alert(fmt(_("{0} users"), [3]));
- * 3 uzytkownikow
- */
-function fmt(s,a) {
- return s.replace(/\{([0-9]+)\}/g, function(x) { return a[x[1]]; });
-}
-
-var saved = {};
-
-
-var selectedstyle = '{% endraw %}{{ config.default_stylesheet.0|addslashes }}{% raw %}';
-var styles = {
- {% endraw %}
- {% for stylesheet in stylesheets %}{% raw %}'{% endraw %}{{ stylesheet.name|addslashes }}{% raw %}' : '{% endraw %}{{ stylesheet.uri|addslashes }}{% raw %}',
- {% endraw %}{% endfor %}{% raw %}
-};
-
-function changeStyle(styleName, link) {
- localStorage.stylesheet = styleName;
-
- if (!document.getElementById('stylesheet')) {
- var s = document.createElement('link');
- s.rel = 'stylesheet';
- s.type = 'text/css';
- s.id = 'stylesheet';
- var x = document.getElementsByTagName('head')[0];
- x.appendChild(s);
- }
-
- document.getElementById('stylesheet').href = styles[styleName];
- selectedstyle = styleName;
-
- if (document.getElementsByClassName('styles').length != 0) {
- var styleLinks = document.getElementsByClassName('styles')[0].childNodes;
- for (i = 0; i < styleLinks.length; i++) {
- styleLinks[i].className = '';
- }
- }
-
- if (link) {
- link.className = 'selected';
- }
-}
-
-if (localStorage.stylesheet) {
- for (styleName in styles) {
- if (styleName == localStorage.stylesheet) {
- changeStyle(styleName);
- break;
- }
- }
-}
-
-function init_stylechooser() {
- var newElement = document.createElement('div');
- newElement.className = 'styles';
-
- for (styleName in styles) {
- var style = document.createElement('a');
- style.innerHTML = '[' + styleName + ']';
- style.onclick = function() {
- changeStyle(this.innerHTML.substring(1, this.innerHTML.length - 1), this);
- };
- if (styleName == selectedstyle) {
- style.className = 'selected';
- }
- style.href = 'javascript:void(0);';
- newElement.appendChild(style);
- }
-
- document.getElementsByTagName('body')[0].insertBefore(newElement, document.getElementsByTagName('body')[0].lastChild.nextSibling);
-}
-
-function get_cookie(cookie_name) {
- var results = document.cookie.match ( '(^|;) ?' + cookie_name + '=([^;]*)(;|$)');
- if (results)
- return (unescape(results[2]));
- else
- return null;
-}
-
-function highlightReply(id) {
- if (typeof window.event != "undefined" && event.which == 2) {
- // don't highlight on middle click
- return true;
- }
-
- var divs = document.getElementsByTagName('div');
- for (var i = 0; i < divs.length; i++)
- {
- 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)
- post.className += ' highlighted';
- }
-}
-
-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);
- pass += chars.substring(rnd, rnd + 1);
- }
- return pass;
-}
-
-function dopost(form) {
- if (form.elements['name']) {
- localStorage.name = form.elements['name'].value.replace(/( |^)## .+$/, '');
- }
- if (form.elements['email'] && form.elements['email'].value != 'sage') {
- localStorage.email = form.elements['email'].value;
- }
-
- saved[document.location] = form.elements['body'].value;
- sessionStorage.body = JSON.stringify(saved);
-
- return form.elements['body'].value != "" || form.elements['file'].value != "";
-}
-
-function citeReply(id) {
- var body = document.getElementById('body');
-
- if (document.selection) {
- // IE
- body.focus();
- var sel = document.selection.createRange();
- sel.text = '>>' + id + '\n';
- } else if (body.selectionStart || body.selectionStart == '0') {
- // Mozilla
- var start = body.selectionStart;
- var end = body.selectionEnd;
- body.value = body.value.substring(0, start) + '>>' + id + '\n' + body.value.substring(end, body.value.length);
- } else {
- // ???
- body.value += '>>' + id + '\n';
- }
-}
-
-function rememberStuff() {
- if (document.forms.post) {
- if (document.forms.post.password) {
- if (!localStorage.password)
- localStorage.password = generatePassword();
- document.forms.post.password.value = localStorage.password;
- }
-
- if (localStorage.name && document.forms.post.elements['name'])
- document.forms.post.elements['name'].value = localStorage.name;
- if (localStorage.email && document.forms.post.elements['email'])
- document.forms.post.elements['email'].value = localStorage.email;
-
- if (window.location.hash.indexOf('q') == 1)
- citeReply(window.location.hash.substring(2));
-
- if (sessionStorage.body) {
- var saved = JSON.parse(sessionStorage.body);
- if (get_cookie('{% endraw %}{{ config.cookies.js }}{% raw %}')) {
- // Remove successful posts
- var successful = JSON.parse(get_cookie('{% endraw %}{{ config.cookies.js }}{% raw %}'));
- for (var url in successful) {
- saved[url] = null;
- }
- sessionStorage.body = JSON.stringify(saved);
-
- document.cookie = '{% endraw %}{{ config.cookies.js }}{% raw %}={};expires=0;path=/;';
- }
- if (saved[document.location]) {
- document.forms.post.body.value = saved[document.location];
- }
- }
-
- if (localStorage.body) {
- document.forms.post.body.value = localStorage.body;
- localStorage.body = '';
- }
- }
-}
-
-function init() {
- init_stylechooser();
-
- if (document.forms.postcontrols) {
- document.forms.postcontrols.password.value = localStorage.password;
- }
-
- if (window.location.hash.indexOf('q') != 1 && window.location.hash.substring(1))
- highlightReply(window.location.hash.substring(1));
-}
-
-var RecaptchaOptions = {
- theme : 'clean'
-};
-
-onready_callbacks = [];
-function onready(fnc) {
- onready_callbacks.push(fnc);
-}
-
-function ready() {
- for (var i = 0; i < onready_callbacks.length; i++) {
- onready_callbacks[i]();
- }
-}
-
-onready(init);
-
-{% endraw %}{% if config.google_analytics %}{% raw %}
-
-var _gaq = _gaq || [];_gaq.push(['_setAccount', '{% endraw %}{{ config.google_analytics }}{% raw %}']);{% endraw %}{% if config.google_analytics_domain %}{% raw %}_gaq.push(['_setDomainName', '{% endraw %}{{ config.google_analytics_domain }}{% raw %}']){% endraw %}{% endif %}{% if not config.google_analytics_domain %}{% raw %}_gaq.push(['_setDomainName', 'none']){% endraw %}{% endif %}{% raw %};_gaq.push(['_trackPageview']);(function() {var ga = document.createElement('script'); ga.type = 'text/javascript'; ga.async = true;ga.src = ('https:' == document.location.protocol ? 'https://ssl' : 'http://www') + '.google-analytics.com/ga.js';var s = document.getElementsByTagName('script')[0]; s.parentNode.insertBefore(ga, s);})();{% endraw %}{% endif %}
-
+{% raw %} + +/* gettext-compatible _ function, example of usage: + * + * > // Loading pl_PL.json here (containing polish translation strings generated by tools/i18n_compile.php) + * > alert(_("Hello!")); + * Witaj! + */ +function _(s) { + return (typeof l10n != 'undefined' && typeof l10n[s] != 'undefined') ? l10n[s] : s; +} + +/* printf-like formatting function, example of usage: + * + * > alert(fmt("There are {0} birds on {1} trees", [3,4])); + * There are 3 birds on 4 trees + * > // Loading pl_PL.json here (containing polish translation strings generated by tools/locale_compile.php) + * > alert(fmt(_("{0} users"), [3])); + * 3 uzytkownikow + */ +function fmt(s,a) { + return s.replace(/\{([0-9]+)\}/g, function(x) { return a[x[1]]; }); +} + +var saved = {}; + + +var selectedstyle = '{% endraw %}{{ config.default_stylesheet.0|addslashes }}{% raw %}'; +var styles = { + {% endraw %} + {% for stylesheet in stylesheets %}{% raw %}'{% endraw %}{{ stylesheet.name|addslashes }}{% raw %}' : '{% endraw %}{{ stylesheet.uri|addslashes }}{% raw %}', + {% endraw %}{% endfor %}{% raw %} +}; +var board_name = false; + +function changeStyle(styleName, link) { + {% endraw %} + {% if config.stylesheets_board %}{% raw %} + if (board_name) { + stylesheet_choices[board_name] = styleName; + localStorage.board_stylesheets = JSON.stringify(stylesheet_choices); + } + {% endraw %}{% else %} + localStorage.stylesheet = styleName; + {% endif %} + {% raw %} + + if (!document.getElementById('stylesheet')) { + var s = document.createElement('link'); + s.rel = 'stylesheet'; + s.type = 'text/css'; + s.id = 'stylesheet'; + var x = document.getElementsByTagName('head')[0]; + x.appendChild(s); + } + + document.getElementById('stylesheet').href = styles[styleName]; + selectedstyle = styleName; + + if (document.getElementsByClassName('styles').length != 0) { + var styleLinks = document.getElementsByClassName('styles')[0].childNodes; + for (var i = 0; i < styleLinks.length; i++) { + styleLinks[i].className = ''; + } + } + + if (link) { + link.className = 'selected'; + } +} + + +{% endraw %} +{% if config.stylesheets_board %} + {# This is such an unacceptable mess. There needs to be an easier way. #} + var matches = document.URL.match(/\/(\w+)\/($|{{ config.dir.res|replace({'/': '\\/'}) }}{{ config.file_page|replace({'%d': '\\d+', '.': '\\.'}) }}|{{ config.file_index|replace({'.': '\\.'}) }}|{{ config.file_page|replace({'%d': '\\d+', '.': '\\.'}) }})/); + {% raw %} + if (matches) { + board_name = matches[1]; + } + + if (!localStorage.board_stylesheets) { + localStorage.board_stylesheets = '{}'; + } + + var stylesheet_choices = JSON.parse(localStorage.board_stylesheets); + if (board_name && stylesheet_choices[board_name]) { + for (var styleName in styles) { + if (styleName == stylesheet_choices[board_name]) { + changeStyle(styleName); + break; + } + } + } + {% endraw%} +{% else %} + {% raw %} + if (localStorage.stylesheet) { + for (var styleName in styles) { + if (styleName == localStorage.stylesheet) { + changeStyle(styleName); + break; + } + } + } + {% endraw %} +{% endif %} +{% raw %} + +function init_stylechooser() { + var newElement = document.createElement('div'); + newElement.className = 'styles'; + + for (styleName in styles) { + var style = document.createElement('a'); + style.innerHTML = '[' + styleName + ']'; + style.onclick = function() { + changeStyle(this.innerHTML.substring(1, this.innerHTML.length - 1), this); + }; + if (styleName == selectedstyle) { + style.className = 'selected'; + } + style.href = 'javascript:void(0);'; + newElement.appendChild(style); + } + + document.getElementsByTagName('body')[0].insertBefore(newElement, document.getElementsByTagName('body')[0].lastChild.nextSibling); +} + +function get_cookie(cookie_name) { + var results = document.cookie.match ( '(^|;) ?' + cookie_name + '=([^;]*)(;|$)'); + if (results) + return (unescape(results[2])); + else + return null; +} + +function highlightReply(id) { + if (typeof window.event != "undefined" && event.which == 2) { + // don't highlight on middle click + return true; + } + + var divs = document.getElementsByTagName('div'); + for (var i = 0; i < divs.length; i++) + { + 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) + post.className += ' highlighted'; + } +} + +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); + pass += chars.substring(rnd, rnd + 1); + } + return pass; +} + +function dopost(form) { + if (form.elements['name']) { + localStorage.name = form.elements['name'].value.replace(/( |^)## .+$/, ''); + } + if (form.elements['email'] && form.elements['email'].value != 'sage') { + localStorage.email = form.elements['email'].value; + } + + saved[document.location] = form.elements['body'].value; + sessionStorage.body = JSON.stringify(saved); + + return form.elements['body'].value != "" || form.elements['file'].value != ""; +} + +function citeReply(id) { + var body = document.getElementById('body'); + + if (document.selection) { + // IE + body.focus(); + var sel = document.selection.createRange(); + sel.text = '>>' + id + '\n'; + } else if (body.selectionStart || body.selectionStart == '0') { + // Mozilla + var start = body.selectionStart; + var end = body.selectionEnd; + body.value = body.value.substring(0, start) + '>>' + id + '\n' + body.value.substring(end, body.value.length); + } else { + // ??? + body.value += '>>' + id + '\n'; + } +} + +function rememberStuff() { + if (document.forms.post) { + if (document.forms.post.password) { + if (!localStorage.password) + localStorage.password = generatePassword(); + document.forms.post.password.value = localStorage.password; + } + + if (localStorage.name && document.forms.post.elements['name']) + document.forms.post.elements['name'].value = localStorage.name; + if (localStorage.email && document.forms.post.elements['email']) + document.forms.post.elements['email'].value = localStorage.email; + + if (window.location.hash.indexOf('q') == 1) + citeReply(window.location.hash.substring(2)); + + if (sessionStorage.body) { + var saved = JSON.parse(sessionStorage.body); + if (get_cookie('{% endraw %}{{ config.cookies.js }}{% raw %}')) { + // Remove successful posts + var successful = JSON.parse(get_cookie('{% endraw %}{{ config.cookies.js }}{% raw %}')); + for (var url in successful) { + saved[url] = null; + } + sessionStorage.body = JSON.stringify(saved); + + document.cookie = '{% endraw %}{{ config.cookies.js }}{% raw %}={};expires=0;path=/;'; + } + if (saved[document.location]) { + document.forms.post.body.value = saved[document.location]; + } + } + + if (localStorage.body) { + document.forms.post.body.value = localStorage.body; + localStorage.body = ''; + } + } +} + +function init() { + init_stylechooser(); + + if (document.forms.postcontrols) { + document.forms.postcontrols.password.value = localStorage.password; + } + + if (window.location.hash.indexOf('q') != 1 && window.location.hash.substring(1)) + highlightReply(window.location.hash.substring(1)); +} + +var RecaptchaOptions = { + theme : 'clean' +}; + +onready_callbacks = []; +function onready(fnc) { + onready_callbacks.push(fnc); +} + +function ready() { + for (var i = 0; i < onready_callbacks.length; i++) { + onready_callbacks[i](); + } +} + +onready(init); + +{% endraw %}{% if config.google_analytics %}{% raw %} + +var _gaq = _gaq || [];_gaq.push(['_setAccount', '{% endraw %}{{ config.google_analytics }}{% raw %}']);{% endraw %}{% if config.google_analytics_domain %}{% raw %}_gaq.push(['_setDomainName', '{% endraw %}{{ config.google_analytics_domain }}{% raw %}']){% endraw %}{% endif %}{% if not config.google_analytics_domain %}{% raw %}_gaq.push(['_setDomainName', 'none']){% endraw %}{% endif %}{% raw %};_gaq.push(['_trackPageview']);(function() {var ga = document.createElement('script'); ga.type = 'text/javascript'; ga.async = true;ga.src = ('https:' == document.location.protocol ? 'https://ssl' : 'http://www') + '.google-analytics.com/ga.js';var s = document.getElementsByTagName('script')[0]; s.parentNode.insertBefore(ga, s);})();{% endraw %}{% endif %} + diff --git a/templates/mod/ban_form.html b/templates/mod/ban_form.html index edc1ab3b..6c7560ad 100644 --- a/templates/mod/ban_form.html +++ b/templates/mod/ban_form.html @@ -41,11 +41,11 @@ <label for="reason">{% trans 'Message' %}</label> </th> <td> - <input type="checkbox" id="public_message" name="public_message"> + <input type="checkbox" id="public_message" name="public_message"{% if config.mod.check_ban_message %} checked{% endif %}> <input type="text" name="message" id="message" size="35" maxlength="200" value="{{ config.mod.default_ban_message|e }}"> <span class="unimportant">({% trans 'public; attached to post' %})</span> <script type="text/javascript"> - document.getElementById('message').disabled = true; + document.getElementById('message').disabled = !document.getElementById('public_message').checked; document.getElementById('public_message').onchange = function() { document.getElementById('message').disabled = !this.checked; } diff --git a/templates/mod/config-editor-php.html b/templates/mod/config-editor-php.html new file mode 100644 index 00000000..4f76b5dd --- /dev/null +++ b/templates/mod/config-editor-php.html @@ -0,0 +1,63 @@ +<div style="max-width:800px;margin:auto"> + <p> + Any changes you make here will simply be appended to <code>{{ file }}</code>. If you wish to make the most of Tinyboard's customizability, you can instead edit the file directly. This page is intended for making quick changes and for those who don't have a basic understanding of PHP code. + </p> + {% if boards|count %} + <ul> + {% if board %} + <li><a href="?/config">Edit site-wide config</a></li> + {% endif %} + {% for _board in boards if _board.uri != board %} + <li> + <a href="?/config/{{ _board.uri }}">Edit config for {{ config.board_abbreviation|sprintf(_board.uri) }}</a> + </li> + {% endfor %} + </ul> + {% endif %} + + {% if readonly %} + <p>Tinyboard does not have the required permissions to edit <code>{{ file }}</code>. To make changes, you will need to change the file's permissions first or manually edit the code.</p> + {% endif %} + + + {% if not readonly %}<form method="post" action="">{% endif %} + <textarea name="code" id="code" style="margin:auto;width:100%;height:500px{% if readonly %};background:#eee" readonly{% else %}"{% endif %}> + {{ php }} + </textarea> + + <ul style="padding:0;text-align:center;list-style:none"> + <li><input name="save" type="submit" value="{% trans 'Save changes' %}"{% if readonly %} disabled{% endif %}></li> + </ul> + {% if not readonly %}</form>{% endif %} +</div> + +<script type="text/javascript"> +var observe; +if (window.attachEvent) { + observe = function (element, event, handler) { + element.attachEvent('on'+event, handler); + }; +} +else { + observe = function (element, event, handler) { + element.addEventListener(event, handler, false); + }; +} + +var text = document.getElementById('code'); +function resize () { + text.style.height = 'auto'; + text.style.height = text.scrollHeight+'px'; +} +/* 0-timeout to get the already changed text */ +function delayedResize () { + window.setTimeout(resize, 0); +} +observe(text, 'change', resize); +observe(text, 'cut', delayedResize); +observe(text, 'paste', delayedResize); +observe(text, 'drop', delayedResize); +observe(text, 'keydown', delayedResize); + +resize(); +</script>
\ No newline at end of file diff --git a/templates/mod/config-editor.html b/templates/mod/config-editor.html index ec7213bb..a43f8cf7 100644 --- a/templates/mod/config-editor.html +++ b/templates/mod/config-editor.html @@ -1,10 +1,25 @@ +<p> + Any changes you make here will simply be appended to <code>{{ file }}</code>. If you wish to make the most of Tinyboard's customizability, you can instead edit the file directly. This page is intended for making quick changes and for those who don't have a basic understanding of PHP code. +</p> +{% if boards|count %} + <ul> + {% if board %} + <li><a href="?/config">Edit site-wide config</a></li> + {% endif %} + {% for _board in boards if _board.uri != board %} + <li> + <a href="?/config/{{ _board.uri }}">Edit config for {{ config.board_abbreviation|sprintf(_board.uri) }}</a> + </li> + {% endfor %} + </ul> +{% endif %} <form method="post" action=""> <table class="mod config-editor"> <tr> - <th class="minimal">Name</th> - <th>Value</th> - <th class="minimal">Type</th> - <th>Description</th> + <th class="minimal">{% trans 'Name' %}</th> + <th>{% trans 'Value' %}</th> + <th class="minimal">{% trans 'Type' %}</th> + <th>{% trans 'Description' %}</th> </tr> {% for var in conf if var.type != 'array' %} {% if var.name|count == 1 %} @@ -25,6 +40,13 @@ <td> {% if var.type == 'string' %} <input name="{{ name }}" type="text" value="{{ var.value|e }}"> + {% elseif var.permissions %} + <select name="{{ name }}"> + <option value="{{ constant('JANITOR') }}"{% if var.value == constant('JANITOR')%} selected{% endif %}>JANITOR</option> + <option value="{{ constant('MOD') }}"{% if var.value == constant('MOD')%} selected{% endif %}>MOD</option> + <option value="{{ constant('ADMIN') }}"{% if var.value == constant('ADMIN')%} selected{% endif %}>ADMIN</option> + <option value="{{ constant('DISABLED') }}"{% if var.value == constant('DISABLED')%} selected{% endif %}>DISABLED</option> + </select> {% elseif var.type == 'integer' %} <input name="{{ name }}" type="number" value="{{ var.value|e }}"> {% elseif var.type == 'boolean' %} @@ -42,8 +64,8 @@ {{ var.type|e }} </td> - <td> - {{ var.comment|join('<br>') }} + <td style="word-wrap:break-word;width:50%"> + {{ var.comment|join(' ') }} </td> </tr> {% endfor %} diff --git a/templates/mod/dashboard.html b/templates/mod/dashboard.html index 619663f5..e9fb7c9c 100644 --- a/templates/mod/dashboard.html +++ b/templates/mod/dashboard.html @@ -94,7 +94,7 @@ {% if mod|hasPermission(config.mod.rebuild) %} <li><a href="?/rebuild">{% trans 'Rebuild' %}</a></li> {% endif %} - {% if mod|hasPermission(config.mod.show_config) %} + {% if mod|hasPermission(config.mod.edit_config) %} <li><a href="?/config">{% trans 'Configuration' %}</a></li> {% endif %} @@ -102,17 +102,29 @@ </fieldset> {% if mod|hasPermission(config.mod.search) %} -<fieldset> - <legend>{% trans 'Search' %}</legend> - - <ul> - <li> - {% include 'mod/search_form.html' %} - </li> - </ul> -</fieldset> + <fieldset> + <legend>{% trans 'Search' %}</legend> + + <ul> + <li> + {% include 'mod/search_form.html' %} + </li> + </ul> + </fieldset> {% endif %} +{% if config.mod.dashboard_links|count %} + <fieldset> + <legend>{% trans 'Other' %}</legend> + + <ul> + {% for label,link in config.mod.dashboard_links %} + <li><a href="{{ link }}">{{ label }}</a></li> + {% endfor %} + </ul> + </fieldset> +{% endif %} + {% if config.debug %} <fieldset> <legend>{% trans 'Debug' %}</legend> diff --git a/templates/mod/debug/recent_posts.html b/templates/mod/debug/recent_posts.html index 740ed21e..b84d24ab 100644 --- a/templates/mod/debug/recent_posts.html +++ b/templates/mod/debug/recent_posts.html @@ -1,4 +1,4 @@ -<table class="modlog"> +<table class="modlog" style="word-wrap: break-word;"> <tr> <th>Time</th> <th>Board</th> @@ -24,7 +24,7 @@ {% else %} {% set thread = post.id %} {% endif %} - <a href="{{ config.root ~ post.board ~ '/' ~ config.dir.res}}{{ config.file_page|sprintf(thread) }}#{{ post.id }}"> + <a href="?/{{ post.board ~ '/' ~ config.dir.res}}{{ config.file_page|sprintf(thread) }}#{{ post.id }}"> {{ post.id }} </a> </td> diff --git a/templates/mod/edit_post_form.html b/templates/mod/edit_post_form.html index 146e725b..a2980d35 100644 --- a/templates/mod/edit_post_form.html +++ b/templates/mod/edit_post_form.html @@ -32,7 +32,7 @@ {% trans %}Comment{% endtrans %} </th> <td> - <textarea name="body" id="body" rows="8" cols="35">{% if raw %}{{ post.body | e }}{% else %}{{ post.body_nomarkup }}{% endif %}</textarea> + <textarea name="body" id="body" rows="8" cols="35">{% if raw %}{{ post.body }}{% else %}{{ post.body_nomarkup }}{% endif %}</textarea> </td> </tr> </table> diff --git a/templates/mod/log.html b/templates/mod/log.html index e75330b5..0aa3f110 100644 --- a/templates/mod/log.html +++ b/templates/mod/log.html @@ -18,7 +18,11 @@ {% endif %} </td> <td class="minimal"> - <a href="?/IP/{{ log.ip }}">{{ log.ip }}</a> + {% if mod|hasPermission(config.mod.show_ip_modlog) %} + <a href="?/IP/{{ log.ip }}">{{ log.ip }}</a> + {% else %} + <em>hidden</em> + {% endif %} </td> <td class="minimal"> <span title="{{ log.time|date(config.post_date) }}">{{ log.time|ago }}</span> diff --git a/templates/mod/login.html b/templates/mod/login.html index 43a28d56..476897a6 100644 --- a/templates/mod/login.html +++ b/templates/mod/login.html @@ -1,26 +1,26 @@ -{% if error %}<h2 style="text-align:center">{{ error }}</h2>{% endif %}
-<form action="" method="post">
-<table style="margin-top:25px;">
- <tr>
- <th>
- {% trans 'Username' %}
- </th>
- <td>
- <input type="text" name="username" size="20" maxlength="30" value="{{ username|e }}">
- </td>
- </tr>
- <tr>
- <th>
- {% trans 'Password' %}
- </th>
- <td>
- <input type="password" name="password" size="20" maxlength="30" value="">
- </td>
- </tr>
- <tr>
- <td></td>
- <td>
- <input type="submit" name="login" value="{% trans %}Continue{% endtrans %}" />
- </td>
-</table>
-</form>
+{% if error %}<h2 style="text-align:center">{{ error }}</h2>{% endif %} +<form action="" method="post"> +<table style="margin-top:25px;"> + <tr> + <th> + {% trans 'Username' %} + </th> + <td> + <input type="text" name="username" size="20" maxlength="30" value="{{ username|e }}"> + </td> + </tr> + <tr> + <th> + {% trans 'Password' %} + </th> + <td> + <input type="password" name="password" size="20" maxlength="30" value=""> + </td> + </tr> + <tr> + <td></td> + <td> + <input type="submit" name="login" value="{% trans %}Continue{% endtrans %}" /> + </td> +</table> +</form> diff --git a/templates/mod/news.html b/templates/mod/news.html index b6c35798..b0335e0a 100644 --- a/templates/mod/news.html +++ b/templates/mod/news.html @@ -52,7 +52,7 @@ <em>{% trans 'no subject' %}</em> {% endif %} <small class="unimportant"> - — {% trans 'by' %} {{ post.name }} {% trans 'at' %} {{ notice.time|date(config.post_date) }} + — {% trans 'by' %} {{ post.name }} {% trans 'at' %} {{ post.time|date(config.post_date) }} </small> </h2> <p> diff --git a/templates/mod/search_results.html b/templates/mod/search_results.html index b441a28f..0c87f75f 100644 --- a/templates/mod/search_results.html +++ b/templates/mod/search_results.html @@ -39,7 +39,7 @@ </tr> {% endfor %} </table> -{% endif %} +{% endif %} {% if search_type == 'bans' %} <table class="modlog" style="width:100%"> @@ -125,7 +125,7 @@ </tr> {% endfor %} </table> -{% endif %} +{% endif %} {% if search_type == 'log' %} <table class="modlog"> @@ -166,7 +166,98 @@ </tr> {% endfor %} </table> -{% endif %} +{% endif %} + +{% if search_type == 'posts' %} + <table class="modlog" style="word-wrap: break-word;"> + <tr> + <th>Time</th> + <th>Board</th> + <th>ID</th> + <th>Thread</th> + <th>IP</th> + <th>Name</th> + <th>Subject</th> + <th>File</th> + <th>Body (snippet)</th> + </tr> + {% for post in results %} + <tr> + <td class="minimal"> + <small>{{ post.time | ago }} ago</small> + </td> + <td class="minimal"> + <a href="?/{{ config.board_path|sprintf(post.board) }}{{ config.file_index }}">{{ config.board_abbreviation|sprintf(post.board) }}</a> + </td> + <td class="minimal"> + {% if post.thread %} + {% set thread = post.thread %} + {% else %} + {% set thread = post.id %} + {% endif %} + <a href="?/{{ post.board ~ '/' ~ config.dir.res}}{{ config.file_page|sprintf(thread) }}#{{ post.id }}"> + {{ post.id }} + </a> + </td> + <td class="minimal"> + <small> + {% if post.thread %} + {{ post.thread }} + {% else %} + (OP) + {% endif %} + </small> + </td> + <td class="minimal"> + {% if mod|hasPermission(config.mod.show_ip, post.board) %} + <a href="?/IP/{{ post.ip }}"> + {{ post.ip }} + </a> + {% else %} + <em>hidden</em> + {% endif %} + </td> + <td style="max-width:100px"> + <small> + {% if post.email|length > 0 %} + {# start email #} + <a class="email" href="mailto:{{ post.email }}"> + {% endif %} + {% set capcode = post.capcode|capcode %} + <span {% if capcode.name %}style="{{ capcode.name }}" {% endif %}class="name">{{ post.name }}</span> + {% if post.trip|length > 0 %} + <span {% if capcode.trip %}style="{{ capcode.trip }}" {% endif %}class="trip">{{ post.trip }}</span> + {% endif %} + {% if post.email|length > 0 %} + {# end email #} + </a> + {% endif %} + {% if capcode %} + {{ capcode.cap }} + {% endif %} + </small> + </td> + <td style="max-width:250px"> + {% if post.subject %} + <small>{{ post.subject }}</small> + {% else %} + – + {% endif %} + </td> + <td style="max-width:200px"> + {% if post.file %} + <small>{{ post.filename }} ({{ post.filesize | filesize }})</small> + {% else %} + – + {% endif %} + </td> + <td> + <small><em>{{ post.snippet }}</em></small> + </td> + </tr> + {% endfor %} + </table> +{% endif %} {% if result_count > results|count %} <p class="unimportant" style="text-align:center;word-wrap:break-word"> diff --git a/templates/page.html b/templates/page.html index 07eea62e..0d33c16f 100644 --- a/templates/page.html +++ b/templates/page.html @@ -1,25 +1,25 @@ -<!doctype html>
-<html>
-<head>
- <meta charset="utf-8">
- {% include 'header.html' %}
- <title>{{ title }}</title>
-</head>
-<body>
- {% if pm %}<div class="top_notice">You have <a href="?/PM/{{ pm.id }}">an unread PM</a>{% if pm.waiting > 0 %}, plus {{ pm.waiting }} more waiting{% endif %}.</div><hr>{% endif %}
- <header>
- <h1>{{ title }}</h1>
- <div class="subtitle">
- {% if subtitle %}
- {{ subtitle }}
- {% endif %}
- {% if mod and not hide_dashboard_link %}<p><a href="?/">{% trans %}Return to dashboard{% endtrans %}</a></p>{% endif %}
- </div>
- </header>
- {{ body }}
- <hr>
- <footer>
- <p class="unimportant" style="margin-top:20px;text-align:center;">Powered by <a href="http://tinyboard.org/">Tinyboard</a> {{ config.version }} | <a href="http://tinyboard.org/">Tinyboard</a> Copyright © 2010-2013 Tinyboard Development Group</p>
- </footer>
-</body>
-</html>
+<!doctype html> +<html> +<head> + <meta charset="utf-8"> + {% include 'header.html' %} + <title>{{ title }}</title> +</head> +<body> + {% if pm %}<div class="top_notice">You have <a href="?/PM/{{ pm.id }}">an unread PM</a>{% if pm.waiting > 0 %}, plus {{ pm.waiting }} more waiting{% endif %}.</div><hr>{% endif %} + <header> + <h1>{{ title }}</h1> + <div class="subtitle"> + {% if subtitle %} + {{ subtitle }} + {% endif %} + {% if mod and not hide_dashboard_link %}<p><a href="?/">{% trans %}Return to dashboard{% endtrans %}</a></p>{% endif %} + </div> + </header> + {{ body }} + <hr> + <footer> + <p class="unimportant" style="margin-top:20px;text-align:center;">Powered by <a href="http://tinyboard.org/">Tinyboard</a> {{ config.version }} | <a href="http://tinyboard.org/">Tinyboard</a> Copyright © 2010-2013 Tinyboard Development Group</p> + </footer> +</body> +</html>
\ No newline at end of file diff --git a/templates/post_form.html b/templates/post_form.html index 64451fb9..fa486263 100755 --- a/templates/post_form.html +++ b/templates/post_form.html @@ -4,6 +4,9 @@ {{ antibot.html() }} <input type="hidden" name="board" value="{{ board.uri }}"> {{ antibot.html() }} +{% if current_page %} + <input type="hidden" name="page" value="{{ current_page }}"> +{% endif %} {% if mod %}<input type="hidden" name="mod" value="1">{% endif %} <table> {% if not config.field_disable_name or (mod and post.mod|hasPermission(config.mod.bypass_field_disable, board.uri)) %}<tr> @@ -67,21 +70,6 @@ </td> </tr> {% endif %} - {% if config.imgcaptcha %} - <tr> - <th> - {% trans %}Verification{% endtrans %} - {{ antibot.html() }} - </th> - <td> - <input type="hidden" name="imgcaptcha_hash" id="imgcaptcha_hash" value="kucaj stad, kucu hakierze"> - <img src="{{ config.imgcaptcha_filler }}" width="{{ config.imgcaptcha_width }}px" height="{{ config.imgcaptcha_height }}px" id="imgcaptcha_img"></img><br> - {{ config.imgcaptcha_question }} <input type="text" name="imgcaptcha_verify" id="imgcaptcha_verify" value=""></input><br> - <a href="javascript:ic_odswiezKapcze()">Odswiez</a> - {{ antibot.html() }} - </td> - </tr> - {% endif %} <tr> <th> {% trans %}File{% endtrans %} @@ -103,7 +91,7 @@ </td> </tr> {% endif %} - {% if mod %} + {% if mod and ((not id and post.mod|hasPermission(config.mod.sticky, board.uri)) or (not id and post.mod|hasPermission(config.mod.lock, board.uri)) or post.mod|hasPermission(config.mod.rawhtml, board.uri)) %} <tr> <th> {% trans %}Flags{% endtrans %} diff --git a/templates/post_reply.html b/templates/post_reply.html index 450f8246..b0391f19 100644 --- a/templates/post_reply.html +++ b/templates/post_reply.html @@ -1,111 +1,111 @@ -{% filter remove_whitespace %}
-{# tabs and new lines will be ignored #}
-<div class="post reply" id="reply_{{ post.id }}">
-
-<p class="intro"{% if not index %} id="{{ post.id }}"{% endif %}>
- <input type="checkbox" class="delete" name="delete_{{ post.id }}" id="delete_{{ post.id }}" />
- <label for="delete_{{ post.id }}">
- {% if post.subject|length > 0 %}
- {# show subject #}
- <span class="subject">{{ post.subject|bidi_cleanup }}</span>
- {% endif %}
- {% if post.email|length > 0 %}
- {# start email #}
- <a class="email" href="mailto:{{ post.email }}">
- {% endif %}
- {% set capcode = post.capcode|capcode %}
- <span {% if capcode.name %}style="{{ capcode.name }}" {% endif %}class="name">{{ post.name|bidi_cleanup }}</span>
- {% if post.trip|length > 0 %}
- <span {% if capcode.trip %}style="{{ capcode.trip }}" {% endif %}class="trip">{{ post.trip }}</span>
- {% endif %}
- {% if post.email|length > 0 %}
- {# end email #}
- </a>
- {% endif %}
- {% if capcode %}
- {{ capcode.cap }}
- {% endif %}
- {% if post.mod and post.mod|hasPermission(config.mod.show_ip, board.uri) %}
- [<a style="margin:0;" href="?/IP/{{ post.ip }}">{{ post.ip }}</a>]
- {% endif %}
- <time datetime="{{ post.time|date('%Y-%m-%dT%H:%M:%S') }}{{ timezone() }}">{{ post.time|date(config.post_date) }}</time>
- </label>
- {% if config.poster_ids %}
- ID: {{ post.ip|poster_id(post.thread) }}
- {% endif %}
- <a class="post_no" {% if not index %}onclick="highlightReply({{ post.id }})" {% endif %}href="{{ post.link }}">No.</a>
- <a class="post_no"
- {% if not index %}
- onclick="citeReply({{ post.id }});"
- {% endif %}
- href="{% if index %}
- {{ post.link('q') }}
- {% else %}
- javascript:void(0);
- {% endif %}">
- {{ post.id }}
- </a>
- </p>
- {% if post.embed %}
- {{ post.embed }}
- {% elseif post.file == 'deleted' %}
- <img src="{{ config.image_deleted }}" alt="" />
- {% elseif post.file and post.file %}
- <p class="fileinfo">File: <a href="{{ config.uri_img }}{{ post.file }}">{{ post.file }}</a> <span class="unimportant">
- (
- {% if post.thumb == 'spoiler' %}
- Spoiler Image,
- {% endif %}
- {{ post.filesize|filesize }}
- {% if post.filex and post.filey %}
- , {{ post.filex}}x{{ post.filey }}
- {% if config.show_ratio %}
- , {{ post.ratio }}
- {% endif %}
- {% endif %}
- {% if config.show_filename and post.filename %}
- ,
- {% if post.filename|length > config.max_filename_display %}
- <span class="postfilename" title="{{ post.filename|bidi_cleanup }}">{{ post.filename|truncate(config.max_filename_display)|bidi_cleanup }}</span>
- {% else %}
- <span class="postfilename">{{ post.filename|bidi_cleanup }}</span>
- {% endif %}
- {% endif %}
- {% if post.thumb != 'file' and config.image_identification %}
- ,
- <span class='image_id'>
- <a href="http://imgops.com/{{ config.domain }}{{ config.uri_img }}{{ post.file }}">io</a>
- {% if post.file|extension == 'jpg' %}
- <a href="http://regex.info/exif.cgi?url={{ config.domain }}{{ config.uri_img }}{{ post.file }}">e</a>
- {% endif %}
- <a href="http://www.google.com/searchbyimage?image_url={{ config.domain }}{{ config.uri_img }}{{ post.file }}">g</a>
- <a href="http://www.tineye.com/search?url={{ config.domain }}{{ config.uri_img }}{{ post.file }}">t</a>
- </span>
- {% endif %}
-
- )
- </span>
-</p>
- <a href="{{ config.uri_img }}{{ post.file }}" target="_blank"{% if post.thumb == 'file' %} class="file"{% endif %}>
- <img src="
- {% if post.thumb == 'file' %}
- {{ config.root }}
- {% if config.file_icons[post.filename|extension] %}
- {{ config.file_thumb|sprintf(config.file_icons[post.filename|extension]) }}
- {% else %}
- {{ config.file_thumb|sprintf(config.file_icons.default) }}
- {% endif %}
- {% elseif post.thumb == 'spoiler' %}
- {{ config.root }}{{ config.spoiler_image }}
- {% else %}
- {{ config.uri_thumb }}{{ post.thumb }}
- {% endif %}" style="width:{{ post.thumbx }}px;height:{{ post.thumby }}px" alt="" />
- </a>
- {% endif %}
- {{ post.postControls }}
- <div class="body">
- {% endfilter %}{% if index %}{{ post.body|truncate_body(post.link) }}{% else %}{{ post.body }}{% endif %}{% filter remove_whitespace %}
- </div>
-</div>
-<br/>
-{% endfilter %}
+{% filter remove_whitespace %} +{# tabs and new lines will be ignored #} +<div class="post reply" id="reply_{{ post.id }}"> + +<p class="intro"{% if not index %} id="{{ post.id }}"{% endif %}> + <input type="checkbox" class="delete" name="delete_{{ post.id }}" id="delete_{{ post.id }}" /> + <label for="delete_{{ post.id }}"> + {% if post.subject|length > 0 %} + {# show subject #} + <span class="subject">{{ post.subject|bidi_cleanup }}</span> + {% endif %} + {% if post.email|length > 0 %} + {# start email #} + <a class="email" href="mailto:{{ post.email }}"> + {% endif %} + {% set capcode = post.capcode|capcode %} + <span {% if capcode.name %}style="{{ capcode.name }}" {% endif %}class="name">{{ post.name|bidi_cleanup }}</span> + {% if post.trip|length > 0 %} + <span {% if capcode.trip %}style="{{ capcode.trip }}" {% endif %}class="trip">{{ post.trip }}</span> + {% endif %} + {% if post.email|length > 0 %} + {# end email #} + </a> + {% endif %} + {% if capcode %} + {{ capcode.cap }} + {% endif %} + {% if post.mod and post.mod|hasPermission(config.mod.show_ip, board.uri) %} + [<a style="margin:0;" href="?/IP/{{ post.ip }}">{{ post.ip }}</a>] + {% endif %} + <time datetime="{{ post.time|date('%Y-%m-%dT%H:%M:%S') }}{{ timezone() }}">{{ post.time|date(config.post_date) }}</time> + </label> + {% if config.poster_ids %} + ID: {{ post.ip|poster_id(post.thread) }} + {% endif %} + <a class="post_no" {% if not index %}onclick="highlightReply({{ post.id }})" {% endif %}href="{{ post.link }}">No.</a> + <a class="post_no" + {% if not index %} + onclick="citeReply({{ post.id }});" + {% endif %} + href="{% if index %} + {{ post.link('q') }} + {% else %} + javascript:void(0); + {% endif %}"> + {{ post.id }} + </a> + </p> + {% if post.embed %} + {{ post.embed }} + {% elseif post.file == 'deleted' %} + <img src="{{ config.image_deleted }}" alt="" /> + {% elseif post.file and post.file %} + <p class="fileinfo">File: <a href="{{ config.uri_img }}{{ post.file }}">{{ post.file }}</a> <span class="unimportant"> + ( + {% if post.thumb == 'spoiler' %} + Spoiler Image, + {% endif %} + {{ post.filesize|filesize }} + {% if post.filex and post.filey %} + , {{ post.filex}}x{{ post.filey }} + {% if config.show_ratio %} + , {{ post.ratio }} + {% endif %} + {% endif %} + {% if config.show_filename and post.filename %} + , + {% if post.filename|length > config.max_filename_display %} + <span class="postfilename" title="{{ post.filename|e|bidi_cleanup }}">{{ post.filename|truncate(config.max_filename_display)|bidi_cleanup }}</span> + {% else %} + <span class="postfilename">{{ post.filename|e|bidi_cleanup }}</span> + {% endif %} + {% endif %} + {% if post.thumb != 'file' and config.image_identification %} + , + <span class='image_id'> + <a href="http://imgops.com/{{ config.domain }}{{ config.uri_img }}{{ post.file }}">io</a> + {% if post.file|extension == 'jpg' %} + <a href="http://regex.info/exif.cgi?url={{ config.domain }}{{ config.uri_img }}{{ post.file }}">e</a> + {% endif %} + <a href="http://www.google.com/searchbyimage?image_url={{ config.domain }}{{ config.uri_img }}{{ post.file }}">g</a> + <a href="http://www.tineye.com/search?url={{ config.domain }}{{ config.uri_img }}{{ post.file }}">t</a> + </span> + {% endif %} + + ) + </span> +</p> + <a href="{{ config.uri_img }}{{ post.file }}" target="_blank"{% if post.thumb == 'file' %} class="file"{% endif %}> + <img src=" + {% if post.thumb == 'file' %} + {{ config.root }} + {% if config.file_icons[post.filename|extension] %} + {{ config.file_thumb|sprintf(config.file_icons[post.filename|extension]) }} + {% else %} + {{ config.file_thumb|sprintf(config.file_icons.default) }} + {% endif %} + {% elseif post.thumb == 'spoiler' %} + {{ config.root }}{{ config.spoiler_image }} + {% else %} + {{ config.uri_thumb }}{{ post.thumb }} + {% endif %}" style="width:{{ post.thumbx }}px;height:{{ post.thumby }}px" alt="" /> + </a> + {% endif %} + {{ post.postControls }} + <div class="body"> + {% endfilter %}{% if index %}{{ post.body|truncate_body(post.link) }}{% else %}{{ post.body }}{% endif %}{% filter remove_whitespace %} + </div> +</div> +<br/> +{% endfilter %} diff --git a/templates/post_thread.html b/templates/post_thread.html index edc07011..a24d7557 100644 --- a/templates/post_thread.html +++ b/templates/post_thread.html @@ -23,9 +23,9 @@ {% if config.show_filename and post.filename %} , {% if post.filename|length > config.max_filename_display %} - <span class="postfilename" title="{{ post.filename|bidi_cleanup }}">{{ post.filename|truncate(config.max_filename_display)|bidi_cleanup }}</span> + <span class="postfilename" title="{{ post.filename|e|bidi_cleanup }}">{{ post.filename|truncate(config.max_filename_display)|bidi_cleanup }}</span> {% else %} - <span class="postfilename">{{ post.filename|bidi_cleanup }}</span> + <span class="postfilename">{{ post.filename|e|bidi_cleanup }}</span> {% endif %} {% endif %} {% if post.thumb != 'file' and config.image_identification %} @@ -100,13 +100,25 @@ {{ post.id }} </a> {% if post.sticky %} - <img class="icon" title="Sticky" src="{{ config.image_sticky }}" alt="Sticky" /> + {% if config.font_awesome %} + <i class="icon-pushpin icon"></i> + {% else %} + <img class="icon" title="Sticky" src="{{ config.image_sticky }}" alt="Sticky" /> + {% endif %} {% endif %} {% if post.locked %} - <img class="icon" title="Locked" src="{{ config.image_locked }}" alt="Locked" /> + {% if config.font_awesome %} + <i class="icon-lock icon"></i> + {% else %} + <img class="icon" title="Locked" src="{{ config.image_locked }}" alt="Locked" /> + {% endif %} {% endif %} {% if post.bumplocked and (config.mod.view_bumplock < 0 or (post.mod and post.mod|hasPermission(config.mod.view_bumplock, board.uri))) %} - <img class="icon" title="Bumplocked" src="{{ config.image_bumplocked }}" alt="Bumplocked" /> + {% if config.font_awesome %} + <i class="icon-anchor icon"></i> + {% else %} + <img class="icon" title="Bumplocked" src="{{ config.image_bumplocked }}" alt="Bumplocked" /> + {% endif %} {% endif %} {% if index %} <a href="{{ post.root }}{{ board.dir }}{{ config.dir.res }}{{ config.file_page|sprintf(post.id) }}">[{% trans %}Reply{% endtrans %}]</a> @@ -145,4 +157,4 @@ {% include 'post_reply.html' %} {% endfor %} <br class="clear"/>{% if hr %}<hr/>{% endif %} -</div>
\ No newline at end of file +</div> diff --git a/templates/posts.sql b/templates/posts.sql index c766d38e..ca2ec304 100644 --- a/templates/posts.sql +++ b/templates/posts.sql @@ -1,32 +1,33 @@ -CREATE TABLE IF NOT EXISTS `posts_{{ board }}` (
- `id` int(11) UNSIGNED NOT NULL AUTO_INCREMENT,
- `thread` int(11) DEFAULT NULL,
- `subject` varchar(100) DEFAULT NULL,
- `email` varchar(30) DEFAULT NULL,
- `name` varchar(35) DEFAULT NULL,
- `trip` varchar(15) DEFAULT NULL,
- `capcode` varchar(50) DEFAULT NULL,
- `body` text NOT NULL,
- `body_nomarkup` text DEFAULT NULL,
- `time` int(11) NOT NULL,
- `bump` int(11) DEFAULT NULL,
- `thumb` varchar(50) DEFAULT NULL,
- `thumbwidth` int(11) DEFAULT NULL,
- `thumbheight` int(11) DEFAULT NULL,
- `file` varchar(50) DEFAULT NULL,
- `filewidth` int(11) DEFAULT NULL,
- `fileheight` int(11) DEFAULT NULL,
- `filesize` int(11) DEFAULT NULL,
- `filename` text DEFAULT NULL,
- `filehash` text DEFAULT NULL,
- `password` varchar(20) DEFAULT NULL,
- `ip` varchar(45) NOT NULL,
- `sticky` int(1) NOT NULL,
- `locked` int(1) NOT NULL,
- `sage` int(1) NOT NULL,
- `embed` text,
- UNIQUE KEY `id` (`id`),
- KEY `thread_id` (`thread`, `id`),
- KEY `time` (`time`),
- FULLTEXT KEY `body` (`body`)
-) ENGINE=MyISAM DEFAULT CHARSET=utf8 AUTO_INCREMENT=1 ;
+CREATE TABLE IF NOT EXISTS ``posts_{{ board }}`` ( + `id` int(11) unsigned NOT NULL AUTO_INCREMENT, + `thread` int(11) DEFAULT NULL, + `subject` varchar(100) DEFAULT NULL, + `email` varchar(30) DEFAULT NULL, + `name` varchar(35) DEFAULT NULL, + `trip` varchar(15) DEFAULT NULL, + `capcode` varchar(50) DEFAULT NULL, + `body` text NOT NULL, + `body_nomarkup` text, + `time` int(11) NOT NULL, + `bump` int(11) DEFAULT NULL, + `thumb` varchar(50) DEFAULT NULL, + `thumbwidth` int(11) DEFAULT NULL, + `thumbheight` int(11) DEFAULT NULL, + `file` varchar(50) DEFAULT NULL, + `filewidth` int(11) DEFAULT NULL, + `fileheight` int(11) DEFAULT NULL, + `filesize` int(11) DEFAULT NULL, + `filename` text, + `filehash` text CHARACTER SET ascii, + `password` varchar(20) DEFAULT NULL, + `ip` varchar(39) CHARACTER SET ascii NOT NULL, + `sticky` int(1) NOT NULL, + `locked` int(1) NOT NULL, + `sage` int(1) NOT NULL, + `embed` text, + UNIQUE KEY `id` (`id`), + KEY `thread_id` (`thread`,`id`), + KEY `time` (`time`), + FULLTEXT KEY `body` (`body`) + ) ENGINE=MyISAM DEFAULT CHARSET=utf8mb4 AUTO_INCREMENT=1 ; +
\ No newline at end of file diff --git a/templates/themes/basic/theme.php b/templates/themes/basic/theme.php index 7ba0d1e7..6ba09ce6 100644 --- a/templates/themes/basic/theme.php +++ b/templates/themes/basic/theme.php @@ -25,7 +25,7 @@ $settings['no_recent'] = (int) $settings['no_recent']; - $query = query("SELECT * FROM `news` ORDER BY `time` DESC" . ($settings['no_recent'] ? ' LIMIT ' . $settings['no_recent'] : '')) or error(db_error()); + $query = query("SELECT * FROM ``news`` ORDER BY `time` DESC" . ($settings['no_recent'] ? ' LIMIT ' . $settings['no_recent'] : '')) or error(db_error()); $news = $query->fetchAll(PDO::FETCH_ASSOC); return Element('themes/basic/index.html', Array( diff --git a/templates/themes/catalog/theme.php b/templates/themes/catalog/theme.php index e585cf17..4e2d40db 100644 --- a/templates/themes/catalog/theme.php +++ b/templates/themes/catalog/theme.php @@ -37,9 +37,9 @@ $recent_posts = array(); $stats = array(); - $query = query(sprintf("SELECT *, `id` AS `thread_id`, (SELECT COUNT(*) FROM `posts_%s` WHERE `thread` = `thread_id`) AS `reply_count`, '%s' AS `board` FROM `posts_%s` WHERE `thread` IS NULL ORDER BY `bump` DESC", $board_name, $board_name, $board_name)) or error(db_error()); + $query = query(sprintf("SELECT *, `id` AS `thread_id`, (SELECT COUNT(*) FROM ``posts_%s`` WHERE `thread` = `thread_id`) AS `reply_count`, '%s' AS `board` FROM ``posts_%s`` WHERE `thread` IS NULL ORDER BY `bump` DESC", $board_name, $board_name, $board_name)) or error(db_error()); - while ($post = $query->fetch()) { + while ($post = $query->fetch(PDO::FETCH_ASSOC)) { $post['link'] = $config['root'] . $board['dir'] . $config['dir']['res'] . sprintf($config['file_page'], ($post['thread'] ? $post['thread'] : $post['id'])); $post['board_name'] = $board['name']; $post['file'] = $config['uri_thumb'] . $post['thumb']; diff --git a/templates/themes/categories/news.html b/templates/themes/categories/news.html index 9c7d8340..b3bea2b1 100644 --- a/templates/themes/categories/news.html +++ b/templates/themes/categories/news.html @@ -7,7 +7,7 @@ <link rel="stylesheet" media="screen" href="{{ config.url_stylesheet }}"/> </head> <body> - <h1>{{ settings.title }}</h1> + {{ boardlist.top }} <header> <h1>{{ settings.title }}</h1> <div class="subtitle">{{ settings.subtitle }}</div> @@ -15,16 +15,16 @@ <div class="ban"> {% if news|count == 0 %} - <p style="text-align:center" class="unimportant">(No news to show.)</p> + <p style="text-align:center" class="unimportant">{% trans %}(No news to show.){% endtrans %}</p> {% else %} {% for entry in news %} <h2 id="{{ entry.id }}"> {% if entry.subject %} {{ entry.subject }} {% else %} - <em>no subject</em> + <em>{% trans %}no subject{% endtrans %}</em> {% endif %} - <span class="unimportant"> — by {{ entry.name }} at {{ entry.time|date(config.post_date) }}</span> + <span class="unimportant"> — {% trans %}by{% endtrans %} {{ entry.name }} {% trans %}at{% endtrans %} {{ entry.time|date(config.post_date) }}</span> </h2> <p>{{ entry.body }}</p> {% endfor %} diff --git a/templates/themes/categories/theme.php b/templates/themes/categories/theme.php index 7d468d0d..74ed61ed 100644 --- a/templates/themes/categories/theme.php +++ b/templates/themes/categories/theme.php @@ -36,7 +36,7 @@ public static function news($settings) { global $config; - $query = query("SELECT * FROM `news` ORDER BY `time` DESC") or error(db_error()); + $query = query("SELECT * FROM ``news`` ORDER BY `time` DESC") or error(db_error()); $news = $query->fetchAll(PDO::FETCH_ASSOC); return Element('themes/categories/news.html', Array( diff --git a/templates/themes/frameset/theme.php b/templates/themes/frameset/theme.php index 5fd9d29e..ffab0538 100644 --- a/templates/themes/frameset/theme.php +++ b/templates/themes/frameset/theme.php @@ -36,7 +36,7 @@ public static function news($settings) { global $config; - $query = query("SELECT * FROM `news` ORDER BY `time` DESC") or error(db_error()); + $query = query("SELECT * FROM ``news`` ORDER BY `time` DESC") or error(db_error()); $news = $query->fetchAll(PDO::FETCH_ASSOC); return Element('themes/frameset/news.html', Array( diff --git a/templates/themes/recent/theme.php b/templates/themes/recent/theme.php index 75907e77..08d910f8 100644 --- a/templates/themes/recent/theme.php +++ b/templates/themes/recent/theme.php @@ -42,12 +42,12 @@ foreach ($boards as &$_board) { if (in_array($_board['uri'], $this->excluded)) continue; - $query .= sprintf("SELECT *, '%s' AS `board` FROM `posts_%s` WHERE `file` IS NOT NULL AND `file` != 'deleted' AND `thumb` != 'spoiler' UNION ALL ", $_board['uri'], $_board['uri']); + $query .= sprintf("SELECT *, '%s' AS `board` FROM ``posts_%s`` WHERE `file` IS NOT NULL AND `file` != 'deleted' AND `thumb` != 'spoiler' UNION ALL ", $_board['uri'], $_board['uri']); } $query = preg_replace('/UNION ALL $/', 'ORDER BY `time` DESC LIMIT ' . (int)$settings['limit_images'], $query); $query = query($query) or error(db_error()); - while ($post = $query->fetch()) { + while ($post = $query->fetch(PDO::FETCH_ASSOC)) { openBoard($post['board']); // board settings won't be available in the template file, so generate links now @@ -62,12 +62,12 @@ foreach ($boards as &$_board) { if (in_array($_board['uri'], $this->excluded)) continue; - $query .= sprintf("SELECT *, '%s' AS `board` FROM `posts_%s` UNION ALL ", $_board['uri'], $_board['uri']); + $query .= sprintf("SELECT *, '%s' AS `board` FROM ``posts_%s`` UNION ALL ", $_board['uri'], $_board['uri']); } $query = preg_replace('/UNION ALL $/', 'ORDER BY `time` DESC LIMIT ' . (int)$settings['limit_posts'], $query); $query = query($query) or error(db_error()); - while ($post = $query->fetch()) { + while ($post = $query->fetch(PDO::FETCH_ASSOC)) { openBoard($post['board']); $post['link'] = $config['root'] . $board['dir'] . $config['dir']['res'] . sprintf($config['file_page'], ($post['thread'] ? $post['thread'] : $post['id'])) . '#' . $post['id']; @@ -78,40 +78,37 @@ } // Total posts - $query = 'SELECT SUM(`top`) AS `count` FROM ('; + $query = 'SELECT SUM(`top`) FROM ('; foreach ($boards as &$_board) { if (in_array($_board['uri'], $this->excluded)) continue; - $query .= sprintf("SELECT MAX(`id`) AS `top` FROM `posts_%s` UNION ALL ", $_board['uri']); + $query .= sprintf("SELECT MAX(`id`) AS `top` FROM ``posts_%s`` UNION ALL ", $_board['uri']); } $query = preg_replace('/UNION ALL $/', ') AS `posts_all`', $query); $query = query($query) or error(db_error()); - $res = $query->fetch(); - $stats['total_posts'] = number_format($res['count']); + $stats['total_posts'] = number_format($query->fetchColumn()); // Unique IPs - $query = 'SELECT COUNT(DISTINCT(`ip`)) AS `count` FROM ('; + $query = 'SELECT COUNT(DISTINCT(`ip`)) FROM ('; foreach ($boards as &$_board) { if (in_array($_board['uri'], $this->excluded)) continue; - $query .= sprintf("SELECT `ip` FROM `posts_%s` UNION ALL ", $_board['uri']); + $query .= sprintf("SELECT `ip` FROM ``posts_%s`` UNION ALL ", $_board['uri']); } $query = preg_replace('/UNION ALL $/', ') AS `posts_all`', $query); $query = query($query) or error(db_error()); - $res = $query->fetch(); - $stats['unique_posters'] = number_format($res['count']); + $stats['unique_posters'] = number_format($query->fetchColumn()); // Active content - $query = 'SELECT SUM(`filesize`) AS `count` FROM ('; + $query = 'SELECT SUM(`filesize`) FROM ('; foreach ($boards as &$_board) { if (in_array($_board['uri'], $this->excluded)) continue; - $query .= sprintf("SELECT `filesize` FROM `posts_%s` UNION ALL ", $_board['uri']); + $query .= sprintf("SELECT `filesize` FROM ``posts_%s`` UNION ALL ", $_board['uri']); } $query = preg_replace('/UNION ALL $/', ') AS `posts_all`', $query); $query = query($query) or error(db_error()); - $res = $query->fetch(); - $stats['active_content'] = $res['count']; + $stats['active_content'] = $query->fetchColumn(); return Element('themes/recent/recent.html', Array( 'settings' => $settings, diff --git a/templates/themes/rrdtool/theme.php b/templates/themes/rrdtool/theme.php index 68fc1850..a14169a3 100644 --- a/templates/themes/rrdtool/theme.php +++ b/templates/themes/rrdtool/theme.php @@ -61,9 +61,8 @@ // debug just the graphing (not updating) with the --debug switch if (!isset($argv[1]) || $argv[1] != '--debug') { // Update graph - $query = query(sprintf("SELECT MAX(`id`) AS `count` FROM `posts_%s`", $board)); - $count = $query->fetch(); - $count = $count['count']; + $query = query(sprintf("SELECT MAX(`id`) FROM ``posts_%s``", $board)); + $count = $query->fetchColumn(); if (!rrd_update($file, Array( '-t', diff --git a/templates/themes/sitemap/theme.php b/templates/themes/sitemap/theme.php index e210316b..226f8357 100644 --- a/templates/themes/sitemap/theme.php +++ b/templates/themes/sitemap/theme.php @@ -19,7 +19,7 @@ $threads = array(); foreach ($boards as $board) { - $query = query(sprintf("SELECT `id` AS `thread_id`, (SELECT `time` FROM `posts_%s` WHERE `thread` = `thread_id` OR `id` = `thread_id` ORDER BY `time` DESC LIMIT 1) AS `lastmod` FROM `posts_%s` WHERE `thread` IS NULL", $board, $board)) or error(db_error()); + $query = query(sprintf("SELECT `id` AS `thread_id`, (SELECT `time` FROM ``posts_%s`` WHERE `thread` = `thread_id` OR `id` = `thread_id` ORDER BY `time` DESC LIMIT 1) AS `lastmod` FROM ``posts_%s`` WHERE `thread` IS NULL", $board, $board)) or error(db_error()); $threads[$board] = $query->fetchAll(PDO::FETCH_ASSOC); } diff --git a/templates/themes/ukko/theme.php b/templates/themes/ukko/theme.php index 6fa5fa7e..1682b4ec 100644 --- a/templates/themes/ukko/theme.php +++ b/templates/themes/ukko/theme.php @@ -25,7 +25,7 @@ foreach($boards as &$_board) { if(in_array($_board['uri'], explode(' ', $this->settings['exclude']))) continue; - $query .= sprintf("SELECT *, '%s' AS `board` FROM `posts_%s` WHERE `thread` IS NULL UNION ALL ", $_board['uri'], $_board['uri']); + $query .= sprintf("SELECT *, '%s' AS `board` FROM ``posts_%s`` WHERE `thread` IS NULL UNION ALL ", $_board['uri'], $_board['uri']); } $query = preg_replace('/UNION ALL $/', 'ORDER BY `bump` DESC', $query); $query = query($query) or error(db_error()); @@ -48,7 +48,7 @@ $post['filename'], $post['ip'], $post['sticky'], $post['locked'], $post['sage'], $post['embed'], $mod ? '?/' : $config['root'], $mod ); - $posts = prepare(sprintf("SELECT * FROM `posts_%s` WHERE `thread` = :id ORDER BY `id` DESC LIMIT :limit", $post['board'])); + $posts = prepare(sprintf("SELECT * FROM ``posts_%s`` WHERE `thread` = :id ORDER BY `id` DESC LIMIT :limit", $post['board'])); $posts->bindValue(':id', $post['id']); $posts->bindValue(':limit', ($post['sticky'] ? $config['threads_preview_sticky'] : $config['threads_preview']), PDO::PARAM_INT); $posts->execute() or error(db_error($posts)); @@ -66,7 +66,7 @@ } if ($posts->rowCount() == ($post['sticky'] ? $config['threads_preview_sticky'] : $config['threads_preview'])) { - $ct = prepare(sprintf("SELECT COUNT(`id`) as `num` FROM `posts_%s` WHERE `thread` = :thread UNION ALL SELECT COUNT(`id`) FROM `posts_%s` WHERE `file` IS NOT NULL AND `thread` = :thread", $post['board'], $post['board'])); + $ct = prepare(sprintf("SELECT COUNT(`id`) as `num` FROM ``posts_%s`` WHERE `thread` = :thread UNION ALL SELECT COUNT(`id`) FROM `posts_%s` WHERE `file` IS NOT NULL AND `thread` = :thread", $post['board'], $post['board'])); $ct->bindValue(':thread', $post['id'], PDO::PARAM_INT); $ct->execute() or error(db_error($count)); diff --git a/templates/themes/ukko/ukko.js b/templates/themes/ukko/ukko.js index baf0f78d..4a36b394 100644 --- a/templates/themes/ukko/ukko.js +++ b/templates/themes/ukko/ukko.js @@ -1,37 +1,115 @@ +(function(){ + var cache = new Array(), thread = false, - loading = false; + loading = false, + ukkotimer = false; +if (localStorage.hiddenboards !== null) { + localStorage.hiddenboards = "{}"; +} + +// Load data from HTML5 localStorage +var hiddenboards = JSON.parse(localStorage.hiddenboards); + +var storeboards = function() { + localStorage.hiddenboards = JSON.stringify(hiddenboards); +}; + $(document).ready(function() { - $(window).on('scroll', function() { - if($(window).scrollTop() + $(window).height() + 100 > $(document).height() && !loading && overflow.length > 0) { + var addukkohide = function() { + var ukkohide = $('<a href="javascript:void(0);" class="unimportant ukkohide"></a>'); + var board = $(this).next().data("board"); + var hr = $("<hr />"); + + $(this).append(ukkohide); + $(this).append(hr); + + if (hiddenboards[board] !== true) { + ukkohide.html(_("(hide threads from this board)")); + hr.hide(); + } + else { + ukkohide.html(_("(show threads from this board)")); + $(this).next().hide(); + } + ukkohide.click(function() { + hiddenboards[board] = (hiddenboards[board] !== true); + if (hiddenboards[board] !== true) { + $('[data-board="'+board+'"]:not([data-cached="yes"])').show().prev(). + find('.ukkohide').html(_("(hide threads from this board)")). + parent().find('hr').hide(); + } + else { + $('[data-board="'+board+'"]:not([data-cached="yes"])').hide().prev(). + find('.ukkohide').html(_("(show threads from this board)")) + .parent().find('hr').show(); + } + storeboards(); + return false; + }); + + }; + $("h2").each(addukkohide); + + $('.pages').hide(); + var loadnext = function() { + if (overflow.length == 0) { + $('.pages').show().html(_("No more threads to display")); + } + while($(window).scrollTop() + $(window).height() + 1000 > $(document).height() && !loading && overflow.length > 0) { var page = '../' + overflow[0].board + '/' + overflow[0].page; + thread = $('div#thread_' + overflow[0].id + '[data-board="' + overflow[0].board + '"]'); + if (thread.length > 0 && thread.attr("data-cached") !== 'yes') { // already present + overflow.shift(); + continue; + } + + var boardheader = $('<h2><a href="/' + overflow[0].board + '/">/' + overflow[0].board + '/</a> </h2>'); + if($.inArray(page, cache) != -1) { - thread = $('div#thread_' + overflow[0].id); - if(thread.length > 0) { - thread.prepend('<h2><a href="/' + overflow[0].board + '/">/' + overflow[0].board + '/</a></h2>'); - $('div[id*="thread_"]').last().after(thread.attr('data-board', overflow[0].board).css('display', 'block')); - overflow.shift(); + if (thread.length > 0) { + $('div[id*="thread_"]').last().after(thread.attr('data-board', overflow[0].board).attr("data-cached", "no").css('display', 'block')); + boardheader.insertBefore(thread); + addukkohide.call(boardheader); + $(document).trigger('new_post', thread); } + overflow.shift(); } else { loading = true; + $('.pages').show().html(_("Loading...")); $.get(page, function(data) { cache.push(page); $(data).find('div[id*="thread_"]').each(function() { - $('body').prepend($(this).css('display', 'none').attr('data-board', overflow[0].board)); + var checkout = $(this).attr('id').replace('thread_', ''); + if ($('div#thread_' + checkout + '[data-board="' + overflow[0].board + '"]').length == 0) { + $('form[name="postcontrols"]').prepend($(this).css('display', 'none').attr("data-cached", "yes").attr('data-board', overflow[0].board)); + } }); - thread = $('div#thread_' + overflow[0].id + '[data-board="' + overflow[0].board + '"]'); + thread = $('div#thread_' + overflow[0].id + '[data-board="' + overflow[0].board + '"][data-cached="yes"]'); + if(thread.length > 0) { - thread.prepend('<h2><a href="/' + overflow[0].board + '/">/' + overflow[0].board + '/</a></h2>'); - $('div[id*="thread_"]').last().after(thread.attr('data-board', overflow[0].board).css('display', 'block')); - overflow.shift(); + $('div[id*="thread_"]').last().after(thread.attr('data-board', overflow[0].board).attr("data-cached", "no").css('display', 'block')); + boardheader.insertBefore(thread); + addukkohide.call(boardheader); + $(document).trigger('new_post', thread); } + overflow.shift(); loading = false; + $('.pages').hide().html(""); }); + break; } } - }); + clearTimeout(ukkotimer); + ukkotimer = setTimeout(loadnext, 1000); + }; + + $(window).on('scroll', loadnext); + + ukkotimer = setTimeout(loadnext, 1000); +}); -});
\ No newline at end of file +})(); diff --git a/templates/thread.html b/templates/thread.html index 1b217c2f..7fe60a39 100644 --- a/templates/thread.html +++ b/templates/thread.html @@ -1,51 +1,52 @@ -<!doctype html>
-<html>
-<head>
- <meta charset="utf-8">
-
- <script type="text/javascript">
- var active_page = "thread";
- </script>
-
- {% include 'header.html' %}
- <title>{{ board.url }} - {% if config.thread_subject_in_title and thread.subject %}{{ thread.subject }}{% else %}{{ board.title|e }}{% endif %}</title>
-</head>
-<body>
- {{ boardlist.top }}
- {% if pm %}<div class="top_notice">You have <a href="?/PM/{{ pm.id }}">an unread PM</a>{% if pm.waiting > 0 %}, plus {{ pm.waiting }} more waiting{% endif %}.</div><hr />{% endif %}
- {% if config.url_banner %}<img class="banner" src="{{ config.url_banner }}" {% if config.banner_width or config.banner_height %}style="{% if config.banner_width %}width:{{ config.banner_width }}px{% endif %};{% if config.banner_width %}height:{{ config.banner_height }}px{% endif %}" {% endif %}alt="" />{% endif %}
- <header>
- <h1>{{ board.url }} - {{ board.title|e }}</h1>
- <div class="subtitle">
- {% if board.subtitle %}
- {{ board.subtitle|e }}
- {% endif %}
- {% if mod %}<p><a href="?/">{% trans %}Return to dashboard{% endtrans %}</a></p>{% endif %}
- </div>
- </header>
-
- <div class="banner">{% trans %}Posting mode: Reply{% endtrans %} <a class="unimportant" href="{{ return }}">[{% trans %}Return{% endtrans %}]</a></div>
-
- {% include 'attention_bar.html' %}
- {% include 'post_form.html' %}
-
- {% if config.blotter %}<hr /><div class="blotter">{{ config.blotter }}</div>{% endif %}
- <hr />
- <form name="postcontrols" action="{{ config.post_url }}" method="post">
- <input type="hidden" name="board" value="{{ board.uri }}" />
- {% if mod %}<input type="hidden" name="mod" value="1" />{% endif %}
- {{ body }}
- {% include 'report_delete.html' %}
- </form>
- <a href="{{ return }}">[{% trans %}Return{% endtrans %}]</a>
-
- {{ boardlist.bottom }}
- <footer>
- <p class="unimportant" style="margin-top:20px;text-align:center;">Powered by <a href="http://tinyboard.org/">Tinyboard</a> {{ config.version }} | <a href="http://tinyboard.org/">Tinyboard</a> Copyright © 2010-2013 Tinyboard Development Group</p>
- {% for footer in config.footer %}<p class="unimportant" style="text-align:center;">{{ footer }}</p>{% endfor %}
- </footer>
- <script type="text/javascript">{% raw %}
- ready();
- {% endraw %}</script>
-</body>
-</html>
+<!doctype html> +<html> +<head> + <meta charset="utf-8"> + + <script type="text/javascript"> + var active_page = "thread"; + </script> + + {% include 'header.html' %} + <title>{{ board.url }} - {% if config.thread_subject_in_title and thread.subject %}{{ thread.subject }}{% else %}{{ board.title|e }}{% endif %}</title> +</head> +<body> + {{ boardlist.top }} + {% if pm %}<div class="top_notice">You have <a href="?/PM/{{ pm.id }}">an unread PM</a>{% if pm.waiting > 0 %}, plus {{ pm.waiting }} more waiting{% endif %}.</div><hr />{% endif %} + {% if config.url_banner %}<img class="banner" src="{{ config.url_banner }}" {% if config.banner_width or config.banner_height %}style="{% if config.banner_width %}width:{{ config.banner_width }}px{% endif %};{% if config.banner_width %}height:{{ config.banner_height }}px{% endif %}" {% endif %}alt="" />{% endif %} + <header> + <h1>{{ board.url }} - {{ board.title|e }}</h1> + <div class="subtitle"> + {% if board.subtitle %} + {{ board.subtitle|e }} + {% endif %} + {% if mod %}<p><a href="?/">{% trans %}Return to dashboard{% endtrans %}</a></p>{% endif %} + </div> + </header> + + <div class="banner">{% trans %}Posting mode: Reply{% endtrans %} <a class="unimportant" href="{{ return }}">[{% trans %}Return{% endtrans %}]</a></div> + + {% include 'attention_bar.html' %} + + {% include 'post_form.html' %} + + {% if config.global_message %}<hr /><div class="blotter">{{ config.global_message }}</div>{% endif %} + <hr /> + <form name="postcontrols" action="{{ config.post_url }}" method="post"> + <input type="hidden" name="board" value="{{ board.uri }}" /> + {% if mod %}<input type="hidden" name="mod" value="1" />{% endif %} + {{ body }} + {% include 'report_delete.html' %} + </form> + <a href="{{ return }}">[{% trans %}Return{% endtrans %}]</a> + + {{ boardlist.bottom }} + <footer> + <p class="unimportant" style="margin-top:20px;text-align:center;">Powered by <a href="http://tinyboard.org/">Tinyboard</a> {{ config.version }} | <a href="http://tinyboard.org/">Tinyboard</a> Copyright © 2010-2013 Tinyboard Development Group</p> + {% for footer in config.footer %}<p class="unimportant" style="text-align:center;">{{ footer }}</p>{% endfor %} + </footer> + <script type="text/javascript">{% raw %} + ready(); + {% endraw %}</script> +</body> +</html> |
