FUCK
This commit is contained in:
parent
0dc204fcb3
commit
3d8c30e8b6
32 changed files with 178 additions and 89 deletions
|
@ -34,7 +34,7 @@ class Controller
|
|||
}
|
||||
}
|
||||
|
||||
public function json($object, $operators = JSON_FORCE_OBJECT | JSON_NUMERIC_CHECK | JSON_BIGINT_AS_STRING)
|
||||
public function json($object, $operators = null)
|
||||
{
|
||||
header('Content-Type: application/json; charset=utf-8');
|
||||
return json_encode($object, $operators);
|
||||
|
|
|
@ -36,15 +36,15 @@ class Notification
|
|||
if ($data) {
|
||||
$data = $data[0];
|
||||
|
||||
$this->id = $data->alert_id;
|
||||
$this->user = $data->user_id;
|
||||
$this->time = $data->alert_timestamp;
|
||||
$this->id = intval($data->alert_id);
|
||||
$this->user = intval($data->user_id);
|
||||
$this->time = intval($data->alert_timestamp);
|
||||
$this->read = intval($data->alert_read) !== 0;
|
||||
$this->title = $data->alert_title;
|
||||
$this->text = $data->alert_text;
|
||||
$this->link = $data->alert_link;
|
||||
$this->image = $data->alert_img;
|
||||
$this->timeout = $data->alert_timeout;
|
||||
$this->timeout = intval($data->alert_timeout);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
10
app/User.php
10
app/User.php
|
@ -214,13 +214,6 @@ class User
|
|||
*/
|
||||
public $youtube = '';
|
||||
|
||||
/**
|
||||
* The thing that indicates if it's an id or a name.
|
||||
*
|
||||
* @var int
|
||||
*/
|
||||
public $youtubeType = 0;
|
||||
|
||||
/**
|
||||
* The user's steam community username.
|
||||
*
|
||||
|
@ -369,7 +362,6 @@ class User
|
|||
$this->skype = $userRow->user_skype;
|
||||
$this->discord = $userRow->user_discord;
|
||||
$this->youtube = $userRow->user_youtube;
|
||||
$this->youtubeType = intval($userRow->user_youtube_type);
|
||||
$this->steam = $userRow->user_steam;
|
||||
$this->osu = $userRow->user_osu;
|
||||
$this->lastfm = $userRow->user_lastfm;
|
||||
|
@ -1089,7 +1081,7 @@ class User
|
|||
$alerts = [];
|
||||
|
||||
foreach ($alertIds as $alertId) {
|
||||
$alerts[$alertId] = new Notification($alertId);
|
||||
$alerts[] = new Notification($alertId);
|
||||
}
|
||||
|
||||
return $alerts;
|
||||
|
|
|
@ -47,9 +47,6 @@ class MoveOptionsAndProfileIntoUsers extends Migration
|
|||
->nullable()
|
||||
->default(null);
|
||||
|
||||
$table->tinyInteger('user_youtube_type')
|
||||
->default(0);
|
||||
|
||||
$table->string('user_steam', 255)
|
||||
->nullable()
|
||||
->default(null);
|
||||
|
@ -82,7 +79,6 @@ class MoveOptionsAndProfileIntoUsers extends Migration
|
|||
'user_skype',
|
||||
'user_discord',
|
||||
'user_youtube',
|
||||
'user_youtube_type',
|
||||
'user_steam',
|
||||
'user_osu',
|
||||
'user_lastfm',
|
||||
|
|
|
@ -7,9 +7,9 @@ elixir(function(mix) {
|
|||
mix
|
||||
.less('aitemu/master.less', 'public/css/aitemu.css')
|
||||
.less('yuuno/master.less', 'public/css/yuuno.css')
|
||||
.typescript('app/**/*.ts', 'public/js/app.js')
|
||||
.typescript('aitemu/**/*.ts', 'public/js/aitemu.js')
|
||||
.typescript('yuuno/**/*.ts', 'public/js/yuuno.js')
|
||||
.typescript('Sakura/**/*.ts', 'public/js/app.js')
|
||||
.typescript('Aitemu/**/*.ts', 'public/js/aitemu.js')
|
||||
.typescript('Yuuno/**/*.ts', 'public/js/yuuno.js')
|
||||
.scripts([
|
||||
nodePath + 'turbolinks/dist/turbolinks.js',
|
||||
], 'public/js/libraries.js');
|
||||
|
|
|
@ -3,6 +3,7 @@ namespace Sakura
|
|||
export class Config
|
||||
{
|
||||
public static Revision: number = 0;
|
||||
public static UserId: number = 0;
|
||||
public static SessionId: string = "";
|
||||
public static UserNameMinLength: number = 3;
|
||||
public static UserNameMaxLength: number = 16;
|
15
resources/assets/typescript/Sakura/INotification.ts
Normal file
15
resources/assets/typescript/Sakura/INotification.ts
Normal file
|
@ -0,0 +1,15 @@
|
|||
namespace Sakura
|
||||
{
|
||||
export interface INotification
|
||||
{
|
||||
id: number;
|
||||
user: number;
|
||||
time: number;
|
||||
read: boolean;
|
||||
title: string;
|
||||
text: string;
|
||||
link: string;
|
||||
image: string;
|
||||
timeout: number;
|
||||
}
|
||||
}
|
|
@ -6,6 +6,7 @@ namespace Sakura
|
|||
console.log(this.Supported());
|
||||
TimeAgo.Init();
|
||||
Friend.Init();
|
||||
Notifications.Init();
|
||||
}
|
||||
|
||||
public static Supported(): boolean {
|
51
resources/assets/typescript/Sakura/Notifications.ts
Normal file
51
resources/assets/typescript/Sakura/Notifications.ts
Normal file
|
@ -0,0 +1,51 @@
|
|||
namespace Sakura
|
||||
{
|
||||
export class Notifications
|
||||
{
|
||||
private static Client: AJAX;
|
||||
private static IntervalContainer: number;
|
||||
public static DisplayMethod: Function = (alert: INotification) => {
|
||||
console.log(alert);
|
||||
};
|
||||
|
||||
public static Init(): void
|
||||
{
|
||||
this.Client = new AJAX;
|
||||
this.Client.SetUrl("/notifications");
|
||||
this.Client.AddCallback(200, (client: AJAX) => {
|
||||
Notifications.Load(<INotification[]>client.JSON());
|
||||
});
|
||||
this.Poll();
|
||||
this.Start();
|
||||
}
|
||||
|
||||
public static Poll(): void
|
||||
{
|
||||
this.Client.Start(HTTPMethod.GET);
|
||||
}
|
||||
|
||||
public static Start(): void
|
||||
{
|
||||
this.IntervalContainer = setInterval(() => {
|
||||
if (document.hidden) {
|
||||
return;
|
||||
}
|
||||
|
||||
Notifications.Poll();
|
||||
}, 5000);
|
||||
}
|
||||
|
||||
public static Stop(): void
|
||||
{
|
||||
this.Client.Stop();
|
||||
clearInterval(this.IntervalContainer);
|
||||
}
|
||||
|
||||
private static Load(alerts: INotification[]): void
|
||||
{
|
||||
for (var i in alerts) {
|
||||
this.DisplayMethod(alerts[i]);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
28
resources/assets/typescript/Yuuno/Notifications.ts
Normal file
28
resources/assets/typescript/Yuuno/Notifications.ts
Normal file
|
@ -0,0 +1,28 @@
|
|||
/// <reference path="../Sakura/INotification.ts" />
|
||||
|
||||
namespace Yuuno
|
||||
{
|
||||
export class Notifications
|
||||
{
|
||||
private static Container;
|
||||
|
||||
public static RegisterDisplay(): void
|
||||
{
|
||||
this.Container = new Sakura.DOM('notifications', Sakura.DOMSelector.ID);
|
||||
Sakura.Notifications.DisplayMethod = this.Display;
|
||||
}
|
||||
|
||||
public static Display(alert: Sakura.INotification): void
|
||||
{
|
||||
var id = 'yuuno-alert-' + Date.now(),
|
||||
container = Sakura.DOM.Create('div', 'notification-enter', id),
|
||||
icon = Sakura.DOM.Create('div', 'notification-icon'),
|
||||
inner = Sakura.DOM.Create('div', 'notification-content'),
|
||||
title = Sakura.DOM.Create('div', 'notification-title'),
|
||||
text = Sakura.DOM.Create('div', 'notification-text'),
|
||||
close = Sakura.DOM.Create('div', 'notification-close'),
|
||||
closeIcon = Sakura.DOM.Create('div'),
|
||||
clear = Sakura.DOM.Create('div');
|
||||
}
|
||||
}
|
||||
}
|
|
@ -5,6 +5,7 @@ namespace Yuuno
|
|||
public static Startup()
|
||||
{
|
||||
Sakura.Main.Startup();
|
||||
Notifications.RegisterDisplay();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
@ -114,37 +114,6 @@ function notifyOpen(id: string): void {
|
|||
}
|
||||
}
|
||||
|
||||
// Request notifications
|
||||
function notifyRequest(session: string): void {
|
||||
// Check if the document isn't hidden
|
||||
if (document.hidden) {
|
||||
return;
|
||||
}
|
||||
|
||||
// Create AJAX object
|
||||
var get = new Sakura.AJAX();
|
||||
get.SetUrl('/notifications');
|
||||
|
||||
// Add callbacks
|
||||
get.AddCallback(200, () => {
|
||||
// Assign the parsed JSON
|
||||
var data: Notification = JSON.parse(get.Response());
|
||||
|
||||
// Check if nothing went wrong
|
||||
if ((typeof data).toLowerCase() === 'undefined') {
|
||||
// Inform the user
|
||||
throw "No or invalid data was returned";
|
||||
}
|
||||
|
||||
// Create an object for every notification
|
||||
for (var id in data) {
|
||||
notifyUI(data[id]);
|
||||
}
|
||||
});
|
||||
|
||||
get.Start(Sakura.HTTPMethod.GET);
|
||||
}
|
||||
|
||||
// Show the full page busy window
|
||||
function ajaxBusyView(show: boolean, message: string = null, type: string = null): void {
|
||||
// Get elements
|
||||
|
|
|
@ -39,9 +39,6 @@
|
|||
<div class="centreAlign">
|
||||
<input class="inputStyling" type="password" id="registerPassword" name="password" onkeyup="registerVarCheck(this.id, 'password');" placeholder="Using special characters is recommended">
|
||||
</div>
|
||||
<div class="subLinks centreAlign">
|
||||
<input class="inputStyling" name="tos" type="checkbox" id="registerToS"><label for="registerToS">I agree to the <a class="default" href="{{ route('info.terms') }}" target="_blank">Terms of Service</a>.
|
||||
</div>
|
||||
<div class="centreAlign">
|
||||
<input class="inputStyling" type="submit" name="submit" value="Register" id="registerAccBtn">
|
||||
</div>
|
||||
|
|
|
@ -167,6 +167,7 @@
|
|||
UserNameMaxLength: {{ config('user.name_max') }},
|
||||
PasswordMinEntropy: {{ config('user.pass_min_entropy') }},
|
||||
LoggedIn: {{ user.isActive ? 'true' : 'false' }},
|
||||
UserId: {{ user.id }},
|
||||
SessionId: "{{ session_id() }}",
|
||||
});
|
||||
|
||||
|
@ -175,12 +176,6 @@
|
|||
{% if config('dev.show_changelog', true) and stats %}
|
||||
Sakura.Changelog.Build(new Sakura.DOM('indexPanel', Sakura.DOMSelector.ID));
|
||||
{% endif %}
|
||||
|
||||
notifyRequest(Sakura.Config.SessionId);
|
||||
|
||||
setInterval(function() {
|
||||
notifyRequest(Sakura.Config.SessionId);
|
||||
}, 60000);
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
||||
|
|
|
@ -4,9 +4,58 @@
|
|||
|
||||
{% set noUserpage = profile.userPage|length < 1 %}
|
||||
|
||||
{% set profileView = noUserpage and profileView == 'index' ? 'comments' : profileView %}
|
||||
{% set title = profileHidden ? 'User not found!' : 'Profile of ' ~ profile.username %}
|
||||
|
||||
{% set title %}{% if profileHidden %}User not found!{% else %}Profile of {{ profile.username }}{% endif %}{% endset %}
|
||||
{% set youtubeIsChannelId = profile.youtube|slice(0, 2) == 'UC' and profile.youtube|length == 24 %}
|
||||
|
||||
{% set fields = {
|
||||
"website": {
|
||||
"title": "Website",
|
||||
"value": profile.website,
|
||||
"link": "%s",
|
||||
},
|
||||
"twitter": {
|
||||
"title": "Twitter",
|
||||
"value": profile.twitter,
|
||||
"link": "https://twitter.com/%s",
|
||||
"disp": "@%s",
|
||||
},
|
||||
"github": {
|
||||
"title": "GitHub",
|
||||
"value": profile.github,
|
||||
"link": "https://github.com/%s",
|
||||
},
|
||||
"skype": {
|
||||
"title": "Skype",
|
||||
"value": profile.skype,
|
||||
"link": "skype:%s?userinfo",
|
||||
},
|
||||
"discord": {
|
||||
"title": "Discord",
|
||||
"value": profile.discord,
|
||||
},
|
||||
"youtube": {
|
||||
"title": "YouTube",
|
||||
"value": profile.youtube,
|
||||
"link": "https://youtube.com/" ~ (youtubeIsChannelId ? 'channel/' : '') ~ "%s",
|
||||
"disp": youtubeIsChannelId ? profile.username ~ "'s channel" : "%s",
|
||||
},
|
||||
"steam": {
|
||||
"title": "Steam",
|
||||
"value": profile.steam,
|
||||
"link": "https://steamcommunity.com/id/%s",
|
||||
},
|
||||
"osu": {
|
||||
"title": "osu!",
|
||||
"value": profile.osu,
|
||||
"link": "https://osu.ppy.sh/u/%s",
|
||||
},
|
||||
"lastfm": {
|
||||
"title": "Last.fm",
|
||||
"value": profile.lastfm,
|
||||
"link": "http://last.fm/user/%s",
|
||||
},
|
||||
} %}
|
||||
|
||||
{% block js %}
|
||||
{% if not profileHidden %}
|
||||
|
@ -102,10 +151,9 @@
|
|||
{% if not noUserpage %}
|
||||
<a class="fa fa-file-text-o" title="View {{ profile.username }}'s user page" href="#_userpage" onclick="profileMode('userpage');"></a>
|
||||
{% endif %}
|
||||
{#<a class="fa fa-list" title="View {{ profile.username }}'s topics" href="#_topics" onclick="profileMode('topics');"></a>
|
||||
<a class="fa fa-reply" title="View {{ profile.username }}'s posts" href="#_posts" onclick="profileMode('posts');"></a>#}
|
||||
<a class="fa fa-list" title="View {{ profile.username }}'s topics" href="#_topics" onclick="profileMode('topics');"></a>
|
||||
<a class="fa fa-reply" title="View {{ profile.username }}'s posts" href="#_posts" onclick="profileMode('posts');"></a>
|
||||
<a class="fa fa-star" title="View {{ profile.username }}'s friends" href="#_friends" onclick="profileMode('friends');"></a>
|
||||
{#<a class="fa fa-users" title="View {{ profile.username }}'s groups" href="#_groups" onclick="profileMode('groups');"></a>#}
|
||||
<a class="fa fa-comments-o" title="View {{ profile.username }}'s profile comments" href="#_comments" onclick="profileMode('comments');"></a>
|
||||
</div>
|
||||
{% if user.isActive %}
|
||||
|
@ -164,25 +212,21 @@
|
|||
{% if profile.profileFields or user.permission(constant('Sakura\\Perms\\Manage::USE_MANAGE'), constant('Sakura\\Perms::MANAGE')) %}
|
||||
{% if user.isActive %}
|
||||
<table style="width: 100%;">
|
||||
{% for name,field in profile.profileFields %}
|
||||
<tr>
|
||||
<td style="text-align: left; font-weight: bold;">
|
||||
{{ field.name }}
|
||||
</td>
|
||||
<td style="text-align: right;">
|
||||
{% if name == 'youtube' %}
|
||||
<a href="https://youtube.com/{% if field.youtubetype == true %}channel{% else %}user{% endif %}/{{ field.value }}" class="default">{% if field.youtubetype == true %}{{ profile.username }}'s Channel{% else %}{{ field.value }}{% endif %}</a>
|
||||
{% else %}
|
||||
{% if field.islink %}
|
||||
<a href="{{ field.link }}" class="default">
|
||||
{% for id, data in fields %}
|
||||
{% if data.value != null %}
|
||||
<tr>
|
||||
<td style="text-align: left; font-weight: bold;">
|
||||
{{ data.title }}
|
||||
</td>
|
||||
<td style="text-align: right;">
|
||||
{% if data.link %}
|
||||
<a href="{{ data.link|format(data.value) }}" class="default">{{ (data.disp ? data.disp : '%s')|format(data.value) }}</a>
|
||||
{% else %}
|
||||
{{ (data.disp ? data.disp : '%s')|format(data.value) }}
|
||||
{% endif %}
|
||||
{{ field.value }}
|
||||
{% if field.islink %}
|
||||
</a>
|
||||
{% endif %}
|
||||
{% endif %}
|
||||
</td>
|
||||
</tr>
|
||||
</td>
|
||||
</tr>
|
||||
{% endif %}
|
||||
{% endfor %}
|
||||
{% if user.permission(constant('Sakura\\Perms\\Manage::USE_MANAGE'), constant('Sakura\\Perms::MANAGE')) %}
|
||||
<tr>
|
||||
|
|
|
@ -3,9 +3,8 @@
|
|||
"module": "commonjs",
|
||||
"noImplicitAny": false,
|
||||
"removeComments": true,
|
||||
"preserveConstEnums": true
|
||||
},
|
||||
"exclude": [
|
||||
"public"
|
||||
]
|
||||
"preserveConstEnums": true,
|
||||
"moduleResolution": "node",
|
||||
"rootDir": "resources/assets/typescript"
|
||||
}
|
||||
}
|
||||
|
|
Reference in a new issue