Revamped supporting page

This commit is contained in:
flash 2015-07-01 19:20:20 +02:00
parent a1b1999c44
commit 5bd78b73fa
9 changed files with 184 additions and 174 deletions

View file

@ -209,15 +209,17 @@ CREATE TABLE `sakura_posts` (
DROP TABLE IF EXISTS `sakura_premium`;
CREATE TABLE `sakura_premium` (
`id` bigint(255) unsigned NOT NULL AUTO_INCREMENT COMMENT 'Automatically generated ID by MySQL for management.',
`uid` bigint(255) unsigned NOT NULL COMMENT 'ID of the user that purchased Tenshi.',
`startdate` int(11) unsigned NOT NULL COMMENT 'Timestamp of first purchase.',
`expiredate` int(11) unsigned NOT NULL COMMENT 'Expiration timestamp.',
PRIMARY KEY (`id`),
UNIQUE KEY `uid` (`uid`),
CONSTRAINT `sakura_premium_ibfk_1` FOREIGN KEY (`uid`) REFERENCES `sakura_users` (`id`) ON DELETE CASCADE ON UPDATE CASCADE
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_bin;
INSERT INTO `sakura_premium` (`uid`, `startdate`, `expiredate`) VALUES
(2, 1435756632, 1441012632),
(18, 1435760007, 1443644007)
ON DUPLICATE KEY UPDATE `uid` = VALUES(`uid`), `startdate` = VALUES(`startdate`), `expiredate` = VALUES(`expiredate`);
DROP TABLE IF EXISTS `sakura_profilefields`;
CREATE TABLE `sakura_profilefields` (
@ -412,4 +414,4 @@ CREATE TABLE `sock_online_users` (
) ENGINE=InnoDB DEFAULT CHARSET=latin1;
-- 2015-07-01 14:27:30
-- 2015-07-01 14:42:04

View file

@ -1389,6 +1389,14 @@
{
"type": "ADD",
"change": "Added automatic rank management for premium."
},
{
"type": "UPD",
"change": "Redid the supporter page."
},
{
"type": "FIX",
"change": "Moved expire variable for the complete page out of the url and take the data straight from the database."
}
]

View file

@ -1005,6 +1005,10 @@ class Users {
// Check if user has Premium
public static function checkUserPremium($id) {
// Check if the user has static premium
if(Permissions::check('SITE', 'STATIC_PREMIUM', $id, 1))
return [1, 0, time() + 1];
// Attempt to retrieve the premium record from the database
$getRecord = Database::fetch('premium', false, [
'uid' => [$id, '=']

View file

@ -2,6 +2,6 @@
<div class="content standalone" style="text-align: center;">
<h1 class="stylised" style="margin: 1em auto;">Thank you for your contribution!</h1>
<h1 class="fa fa-heart stylised" style="font-size: 20em;"></h1>
<h3>Your Tenshi will expire on {{ page.expiration|date("l \\t\\h\\e jS F o") }}.</h3>
<h3>Your Tenshi will expire on {{ page.expiration|date("l \\t\\h\\e jS \\o\\f F o") }}.</h3>
</div>
{% include 'global/footer.tpl' %}

View file

@ -5,63 +5,113 @@
<p>Something went wrong while processing the transaction, your PayPal account wasn't charged.</p>
</div>
{% endif %}
<div class="content donate">
<div class="content support">
<div class="head">Support Flashii</div>
<div style="font-size: .9em; margin-bottom: 10px;">
<p>In order to keep the site, its services and improvements on it going I need money but I'm not that big of a fan of asking for money without really giving anything special in return.</p>
<p>Thus Tenshi exists. Tenshi is the &quot;premium&quot; user group on Flashii which gives you access to an extra set of features (which are listed further down on this page).</p>
<p>A set of new features is planned as well! Be sure to look out for them.</p>
<p>In order to keep the site, its services and improvements on it going I need money but I'm not that big of a fan of asking for money without giving anything special in return thus Tenshi exists. Tenshi is the name for our supporter rank which gives you access to an extra set of features (which are listed further down on this page). With your help we can keep adding new stuff, get new hardware and keep the site awesome!</p>
</div>
{% if page.current[0] %}
<div class="sectionHeader">
Your current Tenshi tag
</div>
<div style="margin-bottom: 10px;">
<h3>Your Tenshi tag is valid till {{ page.current[2]|date("l \\t\\h\\e jS \\o\\f F o") }}.</h3>
<progress value="{{ page.current[1] / page.current[2] * 100 }}" max="100" style="width: 100%"></progress>
</div>
{% endif %}
<div class="sectionHeader">
Why should I get Tenshi?
<div style="float: right; font-size: 10px; text-align: right;">
Click a box to expand its contents.
</div>
</div>
<div class="featureParent">
{% for id,box in page.whytenshi %}
<div class="featureBox" id="fbw{{ id }}" onclick="donatePage(this.id);">
<div class="featureBoxHeader">
{{ box[0]|raw }}
</div>
<div class="featureBoxDesc">
{{ box[1]|raw }}
</div>
<div class="featureBox">
<div class="featureBoxIcon fa fa-money"></div>
<div class="featureBoxDesc">Helping us pay for the bills to survive</div>
<div class="clear"></div>
</div>
<div class="featureBox">
<div class="featureBoxIcon fa fa-certificate"></div>
<div class="featureBoxDesc">A <span style="font-weight: bold; color: #EE9400">special</span> name colour to stand out in the crowd</div>
<div class="clear"></div>
</div>
<div class="featureBox">
<div class="featureBoxIcon fa fa-magic"></div>
<div class="featureBoxDesc">The ability to change your username once a month</div>
<div class="clear"></div>
</div>
<div class="featureBox">
<div class="featureBoxIcon fa fa-pencil"></div>
<div class="featureBoxDesc">You can set a custom user title</div>
<div class="clear"></div>
</div>
<div class="featureBox">
<div class="featureBoxIcon fa fa-archive"></div>
<div class="featureBoxDesc">You'll be able to read the chat logs</div>
<div class="clear"></div>
</div>
<div class="featureBox">
<div class="featureBoxIcon fa fa-eye-slash"></div>
<div class="featureBoxDesc">You can create temporary channels in the chat</div>
<div class="clear"></div>
</div>
<div class="featureBox">
<div class="featureBoxIcon fa fa-users"></div>
<div class="featureBoxDesc">You get to create a user group</div>
<div class="clear"></div>
</div>
<div class="featureBox">
<div class="featureBoxIcon fa fa-picture-o"></div>
<div class="featureBoxDesc">You get the ability to set a profile background</div>
<div class="clear"></div>
</div>
<div class="featureBox final">
<div class="featureBoxIcon fa fa-heart"></div>
<div class="featureBoxIcon right fa fa-heart"></div>
<div class="featureBoxDesc">The good feeling of helping the staff of your favourite site keep it up and awesome</div>
<div class="clear"></div>
</div>
{% endfor %}
</div>
<div class="sectionHeader">
What do I get in return?
Payment Options
<div style="float: right; font-size: 10px; text-align: right;">
Click a box to expand its contents.
</div>
</div>
<div class="featureParent">
{% for id,box in page.tenshifeatures %}
<div class="featureBox" id="fbr{{ id }}" onclick="donatePage(this.id);">
<div class="featureBoxHeader">
{{ box[0]|raw }}
</div>
<div class="featureBoxDesc">
{{ box[1]|raw }}
Our transactions are handled through PayPal.
<div class="paymentOptions fa">
<div class="fa-cc-paypal"></div>
<div class="fa-cc-visa"></div>
<div class="fa-cc-mastercard"></div>
<div class="fa-cc-discover"></div>
<div class="fa-cc-amex"></div>
<div class="clear"></div>
</div>
</div>
{% endfor %}
</div>
<div class="sectionHeader">Payment Options</div>
{% if user.checklogin and perms.canGetPremium %}
<span style="font-size: 8pt;">Our transactions are handled through PayPal.</span>
<form action="/support" method="post" style="text-align: center;">
<input type="hidden" name="mode" value="purchase" />
<input type="hidden" name="time" value="{{ php.time }}" />
<input type="hidden" name="session" value="{{ php.sessionid }}" />
<input type="number" name="months" /> <input type="submit" value="throw money at flashwave" />
</form>
<div class="slider">
<input class="inputStyling" type="range" min="1" max="24" value="1" onchange="document.getElementById('monthsNo').value = this.value; document.getElementById('monthNoBtn').innerHTML = this.value; document.getElementById('monthsTrailingS').innerHTML = (this.value == 1 ? '' : 's'); document.getElementById('totalAmount').innerHTML = (this.value * {{ page.price }}).formatMoney(2);" />
</div>
<div class="checkout" style="line-height: 28px;">
<div style="float: left;">
<h1 class="stylised">Total: &#8364;<span id="totalAmount"></span></h1>
</div>
<div style="float: right;">
<button class="inputStyling" onclick="document.getElementById('purchaseForm').submit();">Get <span id="monthNoBtn">1</span> month<span id="monthsTrailingS"></span> of Tenshi</button>
</div>
<div class="clear"></div>
</div>
{% elseif user.checklogin %}
<h1 style="text-align: center; margin: 1em auto;" class="stylised">You can't get Tenshi at the current moment!</h1>
{% else %}
<h1 style="text-align: center; margin: 1em auto;" class="stylised">You need to be logged in to get Tenshi!</h1>
{% endif %}
</div>
<script type="text/javascript">window.onload = function() {donatePage();}</script>
{% if user.checklogin and perms.canGetPremium %}
<form action="/support" method="post" id="purchaseForm" class="hidden">
<input type="hidden" name="mode" value="purchase" />
<input type="hidden" name="time" value="{{ php.time }}" />
<input type="hidden" name="session" value="{{ php.sessionid }}" />
<input type="hidden" name="months" id="monthsNo" value="1" />
</form>
<script type="text/javascript">
window.onload = function() { document.getElementById('totalAmount').innerHTML = ({{ page.price }}).formatMoney(2); };
</script>
{% endif %}
{% include 'global/footer.tpl' %}

View file

@ -330,7 +330,7 @@ a.gotop.exit {
.content-left .head,
.news .head,
.donate .head,
.support .head,
.viewforum .head,
.viewtopic .head,
.loginPage > .loginCont .head,
@ -1348,9 +1348,9 @@ a.gotop.exit {
}
/*
* Donation page Styling
* Support page Styling
*/
.donate .sectionHeader {
.support .sectionHeader {
margin: -1px -2px;
background: linear-gradient(270deg, rgba(148, 117, 178, .7), rgba(148, 117, 178, 0), rgba(148, 117, 178, .7)) #C2AFFE;
padding: 2px;
@ -1359,56 +1359,68 @@ a.gotop.exit {
color: #306;
}
.donate .featureParent {
.support .featureParent {
width: 100%;
padding: 10px 0;
overflow: hidden;
text-align: center;
}
.donate .featureBox {
.support .featureBox {
background: linear-gradient(180deg, #C2AFFE, #B19EED) no-repeat scroll left top / cover #C2AFFE;
margin: 7px;
border-radius: 5px;
text-align: center;
box-shadow: 0 0 .5em #000;
text-shadow: 0 0 .5em #9475B2;
display: inline-block;
vertical-align: top;
transition: box-shadow .2s;
width: 320px;
padding: 5px 0;
transition: .2s;
width: 400px;
height: 50px;
cursor: default;
color: #503170;
}
.donate .featureBox:hover {
box-shadow: 0 0 1em #000;
cursor: pointer;
.support .featureBox.final {
width: 818px;
}
.donate .featureBox:active {
.support .featureBox.final .featureBoxDesc {
font-size: 1.3em;
}
.support .featureBox:hover {
box-shadow: 0 0 1.5em #609;
text-shadow: 0 0 .7em #9475B2;
}
.donate .featureBoxHeader {
font-weight: 700;
font-size: 15px;
}
.donate .featureBoxDesc {
padding: 1px 2px;
}
.donate .featureBoxDesc.donateClosed {
display: none;
}
.donate .featureBoxDesc.donateOpened {
display: block;
}
.donate .paypal-donate-form {
margin: 10px auto;
display: block;
.support .featureBoxIcon {
float: left;
line-height: 50px;
width: 60px;
text-align: center;
font-size: 2.8em;
}
.support .featureBoxIcon.right {
float: right;
}
.support .featureBoxDesc {
display: block;
line-height: 50px;
}
.support .paymentOptions {
float: right;
font-size: 2em;
margin-left: 6px;
}
.support .paymentOptions div {
float: left;
margin: 0 1px;
}
/*
@ -1416,7 +1428,8 @@ a.gotop.exit {
*/
input[type="submit"].inputStyling,
input[type="button"].inputStyling,
input[type="reset"].inputStyling {
input[type="reset"].inputStyling,
button.inputStyling {
padding: 3px 10px;
cursor: pointer;
border: 0;
@ -1443,21 +1456,23 @@ input[type="reset"].inputStyling.small {
input[type="submit"].inputStyling:hover,
input[type="button"].inputStyling:hover,
input[type="reset"].inputStyling:hover {
input[type="reset"].inputStyling:hover,
button.inputStyling:hover {
box-shadow: inset #222 0 0 3px;
text-shadow: #F1F1F1 0 0 5px;
}
input[type="submit"].inputStyling:active,
input[type="button"].inputStyling:active,
input[type="reset"].inputStyling:active {
input[type="reset"].inputStyling:active,
button.inputStyling:active {
box-shadow: inset #222 0 0 5px;
text-shadow: #F1F1F1 0 0 3px;
transition: text-shadow .2s, box-shadow .2s;
}
input[type="text"].inputStyling,
input[type="password"].inputStyling ,
input[type="password"].inputStyling,
input[type="date"].inputStyling {
padding: 3px 4px;
border: 1px solid #CCC;
@ -1477,6 +1492,13 @@ input[type="date"].inputStyling.green {
box-shadow: inset 0px 0px 7px #A9EC8B;
}
input[type="range"].inputStyling {
border: 0;
width: 100%;
font-size: 1.5em;
margin: 5px 0;
}
textarea.inputStyling {
padding: 3px 4px;
border: 1px solid #CCC;

View file

@ -271,47 +271,6 @@ function notifyRequest(session) {
}
// Donate page specific features
function donatePage(id) {
// Get the featureBoxDesc elements
var featureBoxDesc = document.getElementsByClassName('featureBoxDesc');
// If an id wasn't set assume that we're doing initialisation
if(!id) {
// Go over every element and add donateClosed to the end of the class
for(var i = 0; i < featureBoxDesc.length; i++) {
featureBoxDesc[i].className = featureBoxDesc[i].className + ' donateClosed';
}
// Then stop the execution of the function
return;
}
// Get the second child of the featureBox (which is the description)
var featureBox = document.getElementById(id).children[1];
// Search for donateOpened in the class and if found...
if(featureBox.className.search('donateOpened') > 0) {
// replace it with nothing and add donateClosed to the class
featureBox.className = featureBox.className.replace(' donateOpened', '');
featureBox.className = featureBox.className + ' donateClosed';
} else {
// Else do the opposite of what was described above
featureBox.className = featureBox.className.replace(' donateClosed', '');
featureBox.className = featureBox.className + ' donateOpened';
}
}
// Removing all elements with a certain class
function removeClass(className) {
@ -827,6 +786,18 @@ function scrollToTop() {
}
// Formatting money
Number.prototype.formatMoney = function(c, d, t) {
var n = this,
c = isNaN(c = Math.abs(c)) ? 2 : c,
d = d == undefined ? "." : d,
t = t == undefined ? "," : t,
s = n < 0 ? "-" : "",
i = parseInt(n = Math.abs(+n || 0).toFixed(c)) + "",
j = (j = i.length) > 3 ? j % 3 : 0;
return s + (j ? i.substr(0, j) + t : "") + i.substr(j).replace(/(\d{3})(?=\d)/g, "$1" + t) + (c ? d + Math.abs(n - i).toFixed(c).slice(2) : "");
};
// Event watcher for the scroll-to-top button
window.onscroll = function() {

View file

@ -9,8 +9,6 @@ namespace Sakura;
// Include components
require_once str_replace(basename(__DIR__), '', dirname(__FILE__)) .'_sakura/sakura.php';
print Permissions::check('SITE', 'USE_CHAT', Session::$userId, 1);
// Are we in forum mode?
$forumMode = isset($_GET['forums']) ? ($_GET['forums'] == true) : false;

View file

@ -103,7 +103,12 @@ if(isset($_REQUEST['mode']) && Users::checkLogin() && Permissions::check('SITE',
break;
case 'complete':
print Templates::render('errors/premiumComplete.tpl', array_merge(['page' => ['title' => 'Premium purchase complete!', 'expiration' => isset($_GET['expire']) ? $_GET['expire'] : 0]], $renderData));
print Templates::render('errors/premiumComplete.tpl', array_merge([
'page' => [
'title' => 'Premium purchase complete!',
'expiration' => ($prem = Users::checkUserPremium(Session::$userId)[2]) !== null ? $prem : 0
]
], $renderData));
break;
default:
@ -122,58 +127,8 @@ if(isset($_REQUEST['mode']) && Users::checkLogin() && Permissions::check('SITE',
$renderData['page'] = [
'title' => 'Support Flashii',
'fail' => isset($_GET['fail']),
'whytenshi' => [
[
'Maintained by one person!',
'The site, server and it\'s code are all maintained and paid for by one guy in the Netherlands.'
],
[
'No ads!',
'Unlike a good chunk of the internet we don\'t make money by shoving ads in your face.'
],
[
'Helping us survive!',
'It helps us with getting new hardware to make your Flashii Experience&trade; better and paying the bills to stay alive.'
],
[
'Extra features!',
'You get some extra things to play with if you donate more than $5!'
]
],
'tenshifeatures' => [
[
'A special colour',
'Your username will be <span style="font-weight:bold;color:#EE9400;">orange</span> so you can be recognised in chat and elsewhere on the site!'
],
[
'Early access',
'You get early access to new features before regular users such as access the developement domain.'
],
[
'Username',
'You get the ability to change your username once a month.'
],
[
'User title',
'You get the ability to change your user title whenever you wish to.'
],
[
'Chat logs',
'<del>You can read the <a class="default" href="http://chat.flashii.net/logs" target="_blank">chat logs</a> where all the messages since the original launch are saved.</del><br />Temporarily unavailable due to permissioning issues, <a href="/u/303" class="default">go yell at malloc</a>.'
],
[
'Private channel',
'You get your own Private Channel in the Chat.'
],
[
'Profile background',
'You get the ability to set a custom background on your profile.'
],
[
'A good feeling',
'You get the good feeling of helping me keep Flashii alive and growing (and of course the fact that you get all your special stuff that you can brag about to regular users).'
]
]
'price' => Configuration::getConfig('premium_price_per_month'),
'current' => Users::checkUserPremium(Session::$userId)
];
// Print page contents