Compare commits

...

249 commits

Author SHA1 Message Date
a3debba954
Fixed accidental checkbox behaviour change in messages. 2025-06-18 00:47:43 +00:00
a2cdedb03c
Fixed some detections. 2025-06-18 00:37:21 +00:00
9a28ec0a77
Cleaned up the code for the remaining macros. 2025-06-18 00:32:34 +00:00
c681e2699e
Switched to correct auth data fetcher. 2025-06-17 16:12:54 +00:00
c0a838773d
why was this using a macro????? 2025-06-17 15:18:20 +00:00
ce9272b935
Replaced all forum macros with includes. 2025-06-17 15:15:08 +00:00
0babeb9390
First batch of Twig macro reduction, forum ones will probably take as long as these combined. 2025-06-17 01:20:14 +00:00
8ef46fe475
Minor spacing fixes. 2025-06-16 20:59:05 +00:00
c8db915142
Increased base font size and switched to Inter, Victor Mono and Zen Kaku Gothic New.
You'll likely run into some jank with this update, and this is also the first in a series of visual overhauls to come.

I've been wanting to increase the base font size from 12px to 16px for a while now but never actually got around to it until getting really tired of the limits imposed on me by Verdana.
It will require some getting used to, even for me, though!
The only thing that really stands out is that big walls of text like news and forum posts are a bit bigger and actually have a non-claustrophobic amount of spacing inbetween them.

My efforts to avoid shoving too much spacing into things have severely backfired into making me afraid to introduce any in the first place.
Personally, I think this reads a lot nicer!

Verdana won't be gone for good though.
Once enough of the API is ready it will be featured on the Flashii Fundamentals for Legacy PCs subsite!!
2025-06-16 20:52:25 +00:00
a0e719c2d1
Updated libraries. 2025-06-12 20:17:54 +00:00
d8dbfaa7ab
Added leeway to the device code token polling process. 2025-05-18 15:55:06 +00:00
4e66852db1
Fixed tag script, potentially. 2025-05-13 17:28:26 +00:00
40a96029ff
Switched to the railgun/jwt library. 2025-05-13 17:27:04 +00:00
dd8ec7c8dd
Cleaned up forum templates. 2025-04-24 19:17:38 +00:00
5ec7dddd0e
Fixed categories without topics not being browseable. 2025-04-24 18:40:41 +00:00
af476491b2
Made OAuth2 IDs snowflakes and also removed the client_id field. 2025-04-24 00:17:35 +00:00
c91fa69362
Altered default token lifetimes and also made them configurable. 2025-04-23 21:56:33 +00:00
093266eb1e
Allow access and refresh tokens to not be associated with an app. 2025-04-23 21:24:02 +00:00
d9cf9674f3
Check for empty array. 2025-04-22 22:20:13 +00:00
e1155158d9
Should probably also bump the version. 2025-04-22 21:58:24 +00:00
86578c9ff4
Forgot to update the migration, oops. 2025-04-22 21:58:07 +00:00
3bd556fba9
Added chat server selection endpoints. 2025-04-22 21:55:51 +00:00
52632b42eb
Fixed oversights. 2025-04-22 21:10:47 +00:00
ca2c192330
Added new token/login endpoints for chat. 2025-04-22 20:16:55 +00:00
85c71f604a
Use URI instead of URL in the API.
URL equivalent of a field can still be requested using the fields parameter for the existing routes.
2025-04-22 18:33:47 +00:00
1d57fc3b45
Added kaomoji list to the database. 2025-04-21 01:25:02 +00:00
45635ddc5b
Updated libraries. 2025-04-21 00:52:00 +00:00
d675f1410f
Ported removeChild util. 2025-04-13 00:46:51 +00:00
a6b3cef7b4
Fixed incorrect path being used for CORS credentials check. 2025-04-12 21:15:14 +00:00
4b4ae1c820
Added Cache-Control rules for existing APIs. 2025-04-12 20:33:44 +00:00
d15e074674
Use --env-file-if-exists instead. 2025-04-11 19:28:57 +00:00
c7dc5de306
That should've been install, not update. 2025-04-11 19:02:37 +00:00
e8dcd5b878
Removed push. 2025-04-11 18:59:15 +00:00
4da099ca74
Use make for calling various scripts correctly. 2025-04-11 18:57:13 +00:00
0d8283495d
Allow filtering to a specific type of asset task. 2025-04-11 18:15:50 +00:00
99e3e3111a
Share .env file with the NodeJS build script. 2025-04-11 18:02:38 +00:00
35dce01323
Fixed authentication oversights. 2025-04-03 20:35:57 +00:00
277afa5b19
Removed SameSite=Strict. 2025-04-03 20:26:04 +00:00
55dc011df6
Also check folder permissions for the EEPROM scripts. 2025-04-03 20:09:18 +00:00
9d70505ad8
Added utility to nuke the templating cache directory. 2025-04-03 20:01:27 +00:00
155b301405
Fixed this thing being a layer up too high. 2025-04-03 19:42:43 +00:00
83068a4183
Replaced timings in the footer with a visual for the Server-Timing header. 2025-04-03 19:40:10 +00:00
ceb6bece09
Improved templating engine wrapping. 2025-04-03 14:37:19 +00:00
e4c3e4c052
Authn/z rework. 2025-03-31 15:35:24 +00:00
28be4f16c2
Added optional alphaless RGB field. 2025-03-30 19:26:54 +00:00
16a7e20441
Logging cleanup. 2025-03-28 20:19:54 +00:00
d1fad37022
Added new tables to data exports. 2025-03-28 02:05:40 +00:00
a1398fb179
Added field filtering to API endpoints and store colour presets in the database. 2025-03-28 01:47:24 +00:00
12d40e69a5
Tighter client side integrations for uploads. 2025-03-27 21:27:49 +00:00
41e27cdffa
Ensure storage folder exists. 2025-03-27 00:57:53 +00:00
104bf379b0
One day I won't forgot to bump VERSION. 2025-03-27 00:45:46 +00:00
5f6133c007
Shoved EEPROM into Misuzu. 2025-03-27 00:44:42 +00:00
0b7031959b
Removed RPCii dependency. 2025-03-25 14:28:04 +00:00
6c50a582cb
:))) 2025-03-25 14:22:28 +00:00
238bb3f48e
Updated leftovers from rebase. 2025-03-25 13:51:39 +00:00
5ba8b30047 Updated to latest Index as well as some minor bug fixes. 2025-03-25 14:27:48 +01:00
ad89d45cf0
Fixed oversight. 2025-03-25 12:23:40 +00:00
e3707bf2b4
Moved /v1/me over. 2025-03-24 22:15:52 +00:00
649968814a
Forgot the VERSION bump again (its gonna get confusing). 2025-03-24 19:04:16 +00:00
477210411d
Moved /v1/emotes. 2025-03-24 19:03:05 +00:00
b6f5a4e0cc
Styled landing, Bluesky and Fedi redirect pages. 2025-02-27 00:17:00 +00:00
7e75a71bd2
Fixed oversight. 2025-02-26 22:06:00 +00:00
61ab586df8
Bumped VERSION. 2025-02-26 22:03:55 +00:00
17251cf750
PHPStan fixes. 2025-02-26 22:03:13 +00:00
446c675613
JWT out of the OpenID namespace and merged the remainder with the OAuth namespace. 2025-02-26 21:01:32 +00:00
b2f8347526
OAuth metadata endpoints. 2025-02-26 18:06:46 +00:00
e5a947e973
Moved user agent string creation thingy into a method. 2025-02-26 15:14:30 +00:00
676e3fb217
Switched Xrpc client to Guzzle. 2025-02-26 14:57:19 +00:00
d3bdd8f3a2
Removed Awaki from the source code list.
(Excuse to test GPG signing)
2025-02-25 19:34:40 +00:00
b1d9f88549 Don't use X-Accel-Redirect for the maintenance page, it overrides the status code. 2025-02-25 15:14:17 +00:00
aaba24894c Added OpenID Connect. 2025-02-25 02:30:24 +00:00
24d93a5dbf Slight adjustment to style assignment. 2025-02-20 19:17:17 +00:00
55fca7b945 Adjusted fragment creation. 2025-02-20 18:21:36 +00:00
eb72573121 Reverted to the old removeChildren implementation. 2025-02-20 18:09:17 +00:00
604771aac3 Bumped VERSION. 2025-02-20 02:23:25 +00:00
7353553de7 Rewrote the comments system. ()
old one basically bitrotted to death, may it rinse in prosciutto

Reviewed-on: 
Co-authored-by: flashwave <me@flash.moe>
Co-committed-by: flashwave <me@flash.moe>
2025-02-20 02:19:32 +00:00
6b2bfb726f Added ability to filter search by topic. 2025-02-11 02:41:49 +00:00
e1cb500f99 Use .env file instead of local config. 2025-02-09 23:34:28 +00:00
4110cd5190 Moved constants out of misuzu.php. 2025-02-09 20:44:10 +00:00
1d54d41f6b No longer use random anonymous object for asset info. 2025-02-09 19:58:09 +00:00
bac889787a Moved database methods into own context class. 2025-02-09 17:39:48 +00:00
21a730d189 Cleaned up use statements in misuzu context. 2025-02-09 16:52:46 +00:00
7bf9a7eedd Made certain strings less ugly. 2025-02-09 16:41:09 +00:00
cc37b7cad3 Added user name history beginnings. 2025-02-09 01:32:35 +00:00
7f7e644069 Fixed detections. 2025-02-09 00:28:28 +00:00
f39e1230c5 Moved passwords out of the users table. 2025-02-09 00:26:12 +00:00
7f85abba6e Made timestamps be at the end of the users table like every other table. 2025-02-08 23:24:29 +00:00
372797c564 Moved profile about sections into their own table. 2025-02-08 23:20:53 +00:00
8bb2400d3f Moved forum signatures into dedicated table. 2025-02-08 22:52:36 +00:00
d1173c6e0f Fixed collections on the ENUM columns. 2025-02-08 21:27:50 +00:00
31d89a08bf Moved profile background settings out of the users table. 2025-02-08 21:20:44 +00:00
9f5076cc77 Fixed missing closing parenthesis. 2025-02-08 18:00:07 +00:00
d9f35594e7 Changed internal parser selection value from integers to a string enum. 2025-02-08 17:51:18 +00:00
4d53565139 Fixed query oversights. 2025-02-08 15:17:03 +00:00
179b9aaa08 Included new tables in account data exports. 2025-02-08 03:08:08 +00:00
a0f5444292 Added id to the audit logs table. 2025-02-08 02:51:03 +00:00
4a3d63c065 Ran PHPstan checks. 2025-02-08 02:45:41 +00:00
c28e0a90dd Moved birthdate into separate table. 2025-02-08 02:43:54 +00:00
2c4d35e2dd That's not nullable, oops. 2025-02-08 01:50:59 +00:00
b13cc7804d Moved TOTP codes out of the main users table. 2025-02-08 01:36:33 +00:00
3897dc13fe Removed bogus data scripts. 2025-02-08 01:29:25 +00:00
e46a4ffe1d Bumped minimum MariaDB version. 2025-02-08 01:11:53 +00:00
497bc5323d Made database column names more consistent across the board. 2025-02-07 23:10:41 +00:00
22f216a6a9 Removed unused CSS stuff. 2025-02-07 00:12:13 +00:00
b49868e9c7 Removed 'is'. 2025-02-06 21:12:13 +00:00
2d6f9d0f1b Moved common JS and CSS to separate file. 2025-02-02 21:27:31 +00:00
584546a8f7 Removed RPC stuff for Flashii ID. 2025-02-02 20:25:58 +00:00
8f63b57c0c Improved flow for using OAuth2 while logged out. 2025-02-02 19:51:05 +00:00
8be630531a Only serve ID stuff on main domain and just redirect the id.flashii.net URLs. 2025-02-02 19:31:06 +00:00
6e0726fd3f Fixed chat login using Bearer token. 2025-02-02 02:34:51 +00:00
ab1bcaebc0 Added missing housekeeping cronjob. 2025-02-02 02:28:09 +00:00
534e947522 Merged OAuth2 handling into Misuzu. 2025-02-02 02:09:56 +00:00
1994a9892d Updated lockfile. 2025-01-30 21:33:20 +00:00
b3112ce433 Speedrunned Bluesky integration for news posts. 2025-01-30 21:31:38 +00:00
0701298fa1 Explicitly disable templating cache for tools/render-tpl. 2025-01-30 14:59:02 +00:00
269dc78919 Fixed broom closet index being visible while logged out??? 2025-01-30 14:55:20 +00:00
3e14f63bdb Redid HTTP error pages. 2025-01-30 14:52:01 +00:00
312be0e7fe Added Bluesky link where the Twitter link used to be. 2025-01-30 13:04:43 +00:00
eb88cc0999 Updated Font Awesome. 2025-01-30 13:03:25 +00:00
a09bdb5fc3 Added template layer below the master template in preparation for other things. 2025-01-30 12:07:59 +00:00
720d36dd23 Added script for rendering templates in console. 2025-01-30 11:46:04 +00:00
8f532492c4 Bump VERSION. 2025-01-29 23:57:50 +00:00
9e5945cbd4 Initial implementation of the dependency injector thingy. 2025-01-29 23:56:56 +00:00
d462ee0594 Added Data suffix where applicable. 2025-01-29 23:36:35 +00:00
6c7568e261 Updated Index version. 2025-01-29 23:13:17 +00:00
f2233c5390 Built redirector service into Misuzu. 2025-01-29 21:08:13 +00:00
a83cfdc595 Updated libraries. 2025-01-29 19:32:27 +00:00
1176fbce16 Removed old build script leftovers. 2025-01-29 19:31:24 +00:00
5333a3277f Read remote address from the right place. 2025-01-29 18:19:33 +00:00
33344541d6 Added ability to scope RoutingContext. 2025-01-29 00:25:53 +00:00
06d0413976 Replaced all / reads with filter_input in public/index.php. 2025-01-28 21:14:48 +00:00
e43ba4572f Bumped VERSION. 2025-01-04 02:51:07 +00:00
c16c122aef Switched to integrated EEPROM client. 2025-01-04 02:50:21 +00:00
72e821fc24 Updated libraries. 2025-01-04 02:47:54 +00:00
2b3e0aa6f1 Updated LICENCE year. 2025-01-03 19:15:56 +00:00
e8db4feb39 Update VERSION. 2025-01-03 19:15:21 +00:00
32c9a09d4a Alter output of /v1/me if banned. 2025-01-03 19:14:48 +00:00
ba79bb81d1 Bumped VERSION. 2024-12-23 01:49:03 +00:00
5443ea331e Fixed PM actions not doing anything. 2024-12-23 01:48:32 +00:00
7f7b198007 Updated libraries. 2024-12-20 00:40:15 +00:00
3c2adfdbd5 Bumped VERSION. 2024-12-20 00:30:03 +00:00
20ed8cd59f Moved topic listing into the router. 2024-12-20 00:29:14 +00:00
50b2322c8c p= -> page= for forum categories. 2024-12-20 00:10:20 +00:00
471a054030 Moved forum category views into the router. 2024-12-19 23:41:52 +00:00
72361d1e29 Bumped VERSION. 2024-12-19 02:27:51 +00:00
b5f0f6cda6 Shortcut for pagination appending. 2024-12-19 02:27:28 +00:00
7d710e2d02 Use nextParameter instead of addParameter and manually counting where possible. 2024-12-19 02:23:05 +00:00
d3f9c299af Rewrote the Pagination handler. 2024-12-19 01:22:26 +00:00
02adfa1f4f Moved forum index into the router. 2024-12-18 23:58:53 +00:00
10a377f90f Minor design update for roles list in settings. 2024-12-18 03:26:44 +00:00
d10fa29d3c Bumped VERSION. 2024-12-18 03:08:17 +00:00
265e8f2d4b Replaced confirm pages with dynamic requests on the forum. 2024-12-18 03:07:48 +00:00
a8c777d725 Added global <noscript> notice. 2024-12-17 21:44:48 +00:00
928fe4047a Made use significantly less ugly. 2024-12-17 21:37:28 +00:00
312c4d2968 Final set of CSRFP -> CSRF renames, use headers instead of POST fields and build CSRF handling into the XHR wrapper. 2024-12-17 21:23:38 +00:00
45b75a92ee Fixed migrations being impossible to run on a clean database. 2024-12-17 20:32:09 +00:00
8a1bee10a4 Updated .gitignore. 2024-12-15 17:14:43 +00:00
0e64d85393 Raised checking level from 5 to 6. 2024-12-02 21:33:15 +00:00
3c10fb0de0 Fixed PHPstan detections. 2024-12-02 02:28:08 +00:00
96cc58f820 Forgot to remove one of the vs. 2024-12-02 00:37:46 +00:00
37cbb925ad Imported tag creation script with VERSION file. 2024-12-02 00:36:27 +00:00
bb60d91bd5 Fixed oversight on memberlist. 2024-12-02 00:34:00 +00:00
9ec54e9296 Fixed omegadumb oversight. 2024-12-01 01:37:53 +00:00
db427363f7 Fixed oversight... 2024-11-30 15:30:30 +00:00
163e54def1 Forgot half of it. 2024-11-30 04:20:20 +00:00
d103477fe1 Removed getter/setter methods in favour of property hooks and asymmetric visibility. 2024-11-30 04:09:29 +00:00
2cb2918533 Added simpler avatar URL field. 2024-11-22 20:57:02 +00:00
4569911739 Reordered output cus it was bothering me. 2024-11-21 20:05:56 +00:00
29c7766793 Added option to include e-mail address in user rpc call. 2024-11-21 19:37:04 +00:00
6efda5a1a7 Count loads of old emote endpoint in case I forgot to replace anywhere. 2024-11-14 04:13:57 +00:00
06b9d28a47 Added RPC for emotes list. 2024-11-14 02:44:02 +00:00
8fc998621b Updated RPC library. 2024-11-13 23:30:34 +00:00
5e5e45db1e Ensure content passed to the parse_text filter is escaped. 2024-11-07 00:33:42 +00:00
518a9b6bcc Updated libraries. 2024-10-28 18:35:19 +00:00
db9e60a018 Fixed some URLs not getting registered properly. 2024-10-05 15:28:56 +00:00
2f5db64982 Fixed casing oversight. 2024-10-05 14:39:43 +00:00
99a592dcce Removed all references to the IPAddress class. 2024-10-05 14:22:14 +00:00
1d62db8de6 Fixed undropkicked I. 2024-10-05 03:36:53 +00:00
55a2424fee Updated to latest Index version. 2024-10-05 02:40:29 +00:00
83f94debc7 Use attributes for JSON encoding. 2024-09-30 17:38:08 +00:00
3a42f51614 Updated libraries. 2024-09-30 17:37:41 +00:00
aabffb7b30 Added optional string role IDs for the API. 2024-09-16 21:44:37 +00:00
f373690b12 Updated libraries. 2024-09-16 20:51:46 +00:00
2b1691ae26 Added RPC endpoint for fetching user info. 2024-09-05 20:08:31 +00:00
76443a5d1a Added auth RPC routes. 2024-08-25 23:03:46 +00:00
bed2216717 Fixed return type. 2024-08-18 20:54:39 +00:00
ccaca7eaac Replaced internal Flashii ID routes with RPC library. 2024-08-16 19:29:57 +00:00
e708f99fee Updated Index and switched to Carbon for date handling. 2024-08-04 21:37:12 +00:00
e2ee567711 Removed stray Jeff. 2024-07-27 20:11:06 +00:00
e0fea668a1 Added very preliminary support for Bearer tokens to chat authentication. 2024-07-21 01:50:42 +00:00
ab81e1bcf7 Added interop endpoints for Hanyuu. 2024-07-20 19:35:50 +00:00
0a6f30f290 Updated libraries. 2024-07-18 03:42:16 +00:00
aa22815008 Updated build script. 2024-06-11 00:48:44 +00:00
e804e00139 SharpConfig -> FileConfig 2024-06-03 23:04:59 +00:00
c3162f4013 Updated libraries. 2024-06-03 23:04:21 +00:00
07d93e0023 Prevent access to private messages when impersonating a user. 2024-06-02 19:57:58 +00:00
90f3fd1c88 Base64 encode PM titles and bodies in the database.
To prevent personal discomfort with having to do database messages and seeing people's personal conversations.
I haven't run into it yet, but I'd rather avoid it altogether.
2024-06-02 19:54:33 +00:00
f5c8a2cc5e Added broom closet PM stats. 2024-06-02 19:43:57 +00:00
43c2734e74 Updated libraries. 2024-05-30 22:02:09 +00:00
38975e8004 Built Playpen icon updating into Misuzu.
Was previously handled by a stinky script.
2024-05-30 22:00:41 +00:00
6af4e8b1e5 Fixed wrong HTTP verb. 2024-03-30 15:22:11 +00:00
6e1977d4e9 Fixed various oversights. 2024-03-30 03:19:08 +00:00
0da002d6d2 Updated Misuzu to new HTTP router. 2024-03-30 03:14:03 +00:00
af100649d2 Fixed error when trying to access a topic with no posts associated. 2024-02-24 22:03:32 +00:00
73ffd22fe6 hurr 2024-02-21 00:31:25 +00:00
fa093b86b7 Stinky fix for impersonation in chat auth. 2024-02-20 23:56:43 +00:00
db29a33d20 Fixed bans no longer working. 2024-02-15 22:55:24 +00:00
c876bc2710 Fixed Forum Activity section always showing up. 2024-02-13 21:22:56 +00:00
3d56d27227 Fixed profile fields not showing up anymore. 2024-02-11 02:22:22 +00:00
712ed3e0c8 Missed one! 2024-02-09 16:07:43 +00:00
1a678f54c6 Fixed forum/topic breadcrumbs. 2024-02-08 15:20:44 +00:00
2278ecab38 Fixed use of wrong BanInfo constructor. 2024-02-08 15:18:57 +00:00
b0e9f4a167 Fixed oversights on landing page. 2024-02-08 00:06:23 +00:00
ba7fb5e15a Added lazy database object creation. 2024-02-07 00:04:45 +00:00
eb596d0fee Added PMs to data export. 2024-02-05 22:56:51 +00:00
73d5456e9a whoops 2024-02-02 21:53:36 +00:00
e7d97ad9ac Updated to new EEPROM script. 2024-02-02 21:42:40 +00:00
1a7922ba6e Added notice when recipient is banned. 2024-02-02 02:16:37 +00:00
d64eb69e22 Check if recipient is actually able to receive messages. 2024-02-02 02:07:29 +00:00
a649b8b9a6 Prevent banned users from sending messages. 2024-02-02 01:59:21 +00:00
3e7935fb79 Added private messages. 2024-01-30 23:47:02 +00:00
4e38a537ea Use accent-color and color-scheme CSS directives. 2024-01-25 18:17:54 +00:00
a65f8dc8dd Fixed Ctrl+Enter submission not working anymore either. 2024-01-25 00:18:56 +00:00
27b3e49e14 Fixed forum post form throwing up the navigation confirmation when it isn't supposed to. 2024-01-25 00:12:53 +00:00
c9ef6e4112 Include SameSite attribute on cookies. 2024-01-24 22:14:48 +00:00
85f77eb566 Rewrote Javascript code. 2024-01-24 21:53:26 +00:00
a430568925 Fixed error when trying to add a new change. 2024-01-24 18:28:13 +00:00
3f867af99b Imported new asset build script. 2024-01-24 18:24:40 +00:00
f41c24638d Added links to Amimami repositories. 2024-01-18 20:31:08 +00:00
40fe809389 Adjusted CORS handling for emoticon endpoint. 2024-01-17 19:57:46 +00:00
cbd7d070fc Updated browserlists. 2024-01-08 13:43:34 +00:00
b81f934e8f Added server side image map support. 2024-01-08 13:42:22 +00:00
d81ac56076 Ported boolean attribute support. 2024-01-08 13:36:47 +00:00
42d4e1f238 Removed broken CONSTRAINT from perms table creation. 2023-12-16 18:51:17 +00:00
42671db410 Fixed markdown styling issues. 2023-12-15 12:56:08 +00:00
7acfa8b30e Updated highlight.js and created new code theme. 2023-12-15 12:47:01 +00:00
676810e143 Updated Sentry library to 4.0 in Misuzu. 2023-12-15 01:03:57 +00:00
262ba10694 Fixed error when trying to create a new role. 2023-12-02 02:57:46 +00:00
774494ac33 Fixed undefined variable. 2023-11-26 22:23:47 +00:00
a25621802e Libraries have been updated once more. 2023-11-20 19:10:47 +00:00
14f1c4d5e9 git.flash.moe -> patchii.net 2023-11-20 19:04:59 +00:00
d63a7f53a4 Updated source.md. 2023-11-09 20:58:56 +00:00
bbabce0e49 Supply super user status in auth data. 2023-11-07 14:38:53 +00:00
d221a1ce8f Return to purple. 2023-11-01 09:36:49 +00:00
2077099e7e moguu? 2023-10-21 23:54:41 +00:00
b221904866 Use SharpConfig format for the pre-database config. 2023-10-21 23:45:40 +00:00
727d0650ce Updated to use Syokuhou config library. 2023-10-20 22:29:28 +00:00
dc90787214 Fixed oversight on members list. 2023-10-18 10:16:32 +00:00
383af93c9c Fixed overly eager url encoding on the search page. 2023-10-18 10:11:21 +00:00
726 changed files with 37533 additions and 18964 deletions

View file

@ -6,3 +6,6 @@ insert_final_newline = true
charset = utf-8
indent_style = space
indent_size = 4
[Makefile]
indent_style = tab

41
.env.example Normal file
View file

@ -0,0 +1,41 @@
# Enable debug mode
# Useful for debugging
MSZ_DEBUG=1
# Database connection setting
# This uses the Index library's DSN syntax
# Currently Misuzu only supports MariaDB, or Null of course since that does nothing
#
# For normal TCP connection you can use the following syntax:
#DATABASE_DSN="mariadb://username:password@hostname/dbname?charset=utf8mb4"
#
# For a UNIX socket connection you can use the following syntax:
#DATABASE_DSN="mariadb://username:password@:unix:/dbname?socket=/path/to/mysqld.sock&charset=utf8mb4"
#
# And here's your unsensible default:
DATABASE_DSN="null:"
# Sentry error reporting setting
# I have not idea this works, just shove the value Sentry gives you in here.
# You can also leave it commented.
#SENTRY_DSN="https://6e41e3a2507d1542fd1e9aaf54f05d87@o4505858016870400.ingest.sentry.io/4505858023751680"
# Domain roles
# This assigns what domain has what role, domains can also have multiple roles!
# Pairs are split by ;, domain and role pairs are split by =, roles are split by , and if you want a prefix use :
# The example below maps everything to localhost for development.
# But to make things more understandable, the value for Flashii is also included
#DOMAIN_ROLES="flashii.net=main; fii.moe=redirect"
DOMAIN_ROLES="localhost=main,redirect:/go"
# Local storage path
# This determines where uploaded files are stored. If left unset, the storage folder in the project tree will be used.
#STORAGE_PATH_LOCAL="/path/to/storage"
# Remote storage path
# Path on which the storage folder is exposed to the web for NGINX.
#STORAGE_PATH_REMOTE="/_storage"
# Template cache directory
# Writeable directory path to which template files are cached.
#TEMPLATE_CACHE="/tmp/msz-tpl-cache"

18
.gitignore vendored
View file

@ -11,12 +11,18 @@
/composer.local.json
# Configuration
/.env
/config/config.cfg
/config/github.cfg
/config/config.ini
/config/github.ini
/config/keys/*.pem
/.debug
/.migrating
# Storage
/storage/*
!/storage/.gitkeep
/store
# OS specific
@ -40,6 +46,18 @@
/public/css
/public/webfonts
/assets/typescript/*.d.ts
/public/errors.css
/public/error-*.html
# Google
/public/robots.txt
# Well known
/public/.well-known
# moguu?
/public/moguu.swf
/public/moguu.html
# admin
/public/admin

View file

@ -1,4 +1,4 @@
Copyright (c) 2017-2023, flashwave <me@flash.moe>
Copyright (c) 2017-2025, flashwave <me@flash.moe>
All rights reserved.
Redistribution and use in source and binary forms, with or without

58
Makefile Normal file
View file

@ -0,0 +1,58 @@
PHP_EXE := $(shell which php8.4)
COMPOSER_EXE := $(shell which composer)
NODE_EXE := $(shell which node)
NPM_EXE := $(shell which npm)
SUDO_EXE := $(shell which sudo)
WWW_USER := www-data
BUILD_EXE := build.js
ENV_FILE := .env
TOOLS_DIR := tools
VENDOR_DIR := vendor
all: install migrate clear-cache build cron
install: composer_install npm_install
composer_install:
${PHP_EXE} ${COMPOSER_EXE} install
npm_install:
${NPM_EXE} ci
update: composer_update npm_update
composer_update:
${PHP_EXE} ${COMPOSER_EXE} update
npm_update:
${NPM_EXE} update --save
migrate:
${SUDO_EXE} -u ${WWW_USER} ${PHP_EXE} ${TOOLS_DIR}/migrate
clear-cache:
${SUDO_EXE} -u ${WWW_USER} ${PHP_EXE} ${TOOLS_DIR}/nuke-tpl-cache
cron:
${SUDO_EXE} -u ${WWW_USER} ${PHP_EXE} ${TOOLS_DIR}/cron slow
build:
${NODE_EXE} --env-file-if-exists ${ENV_FILE} ${BUILD_EXE}
rebuild-css:
${NODE_EXE} --env-file-if-exists ${ENV_FILE} ${BUILD_EXE} css
rebuild-js:
${NODE_EXE} --env-file-if-exists ${ENV_FILE} ${BUILD_EXE} js
rebuild-twig:
${NODE_EXE} --env-file-if-exists ${ENV_FILE} ${BUILD_EXE} twig
analyse:
${PHP_EXE} ${VENDOR_DIR}/bin/phpstan
tag: analyse
${PHP_EXE} ${TOOLS_DIR}/create-tag
.PHONY: all update composer npm build rebuild-css rebuild-js rebuild-twig migrate clear-cache cron analyse tag

View file

@ -2,6 +2,6 @@
> Misuzu can and will steal your lunch money.
## Requirements
- PHP 8.2 (64-bit)
- MariaDB 10.6
- PHP 8.4
- MariaDB 11.4
- [Composer](https://getcomposer.org/)

1
VERSION Normal file
View file

@ -0,0 +1 @@
20250617.1

View file

@ -1,100 +0,0 @@
const fs = require('fs');
const path = require('path');
const readline = require('readline');
const utils = require('./utils.js');
exports.process = async function(root, options) {
const macroPrefix = options.prefix || '#';
const entryPoint = options.entry || '';
root = fs.realpathSync(root);
const included = [];
const processFile = async function(fileName) {
const fullPath = path.join(root, fileName);
if(included.includes(fullPath))
return '';
included.push(fullPath);
if(!fullPath.startsWith(root)) {
console.error('INVALID PATH: ' + fullPath);
return '/* *** INVALID PATH: ' + fullPath + ' */';
}
if(!fs.existsSync(fullPath)) {
console.error('FILE NOT FOUND: ' + fullPath);
return '/* *** FILE NOT FOUND: ' + fullPath + ' */';
}
const lines = readline.createInterface({
input: fs.createReadStream(fullPath),
crlfDelay: Infinity,
});
let output = '';
let lastWasEmpty = false;
if(options.showPath)
output += "/* *** PATH: " + fullPath + " */\n";
for await(const line of lines) {
const lineTrimmed = utils.trim(line);
if(lineTrimmed === '')
continue;
if(line.startsWith(macroPrefix)) {
const args = lineTrimmed.split(' ');
const macro = utils.trim(utils.trimStart(args.shift(), macroPrefix));
switch(macro) {
case 'comment':
break;
case 'include': {
const includePath = utils.trimEnd(args.join(' '), ';');
output += utils.trim(await processFile(includePath));
output += "\n";
break;
}
default:
output += line;
output += "\n";
break;
}
} else {
output += line;
output += "\n";
}
}
return output;
};
return await processFile(entryPoint);
};
exports.housekeep = function(assetsPath) {
const files = fs.readdirSync(assetsPath).map(fileName => {
const stats = fs.statSync(path.join(assetsPath, fileName));
return {
name: fileName,
lastMod: stats.mtimeMs,
};
}).sort((a, b) => b.lastMod - a.lastMod).map(info => info.name);
const regex = /^(.+)-([a-f0-9]+)\.(.+)$/i;
const counts = {};
for(const fileName of files) {
const match = fileName.match(regex);
if(match) {
const name = match[1] + '-' + match[3];
counts[name] = (counts[name] || 0) + 1;
if(counts[name] > 5)
fs.unlinkSync(path.join(assetsPath, fileName));
} else console.log(`Encountered file name in assets folder with unexpected format: ${fileName}`);
}
};

View file

@ -0,0 +1,36 @@
.msz-loading {
display: flex;
justify-content: center;
flex-direction: column;
min-width: var(--msz-loading-container-width, calc(var(--msz-loading-size, 1) * 100px));
min-height: var(--msz-loading-container-height, calc(var(--msz-loading-size, 1) * 100px));
}
.msz-loading-inline {
display: inline-flex;
min-width: 0;
min-height: 0;
}
.msz-loading-frame {
display: flex;
justify-content: center;
flex: 0 0 auto;
}
.msz-loading-icon {
display: grid;
grid-template-columns: repeat(3, 1fr);
grid-template-rows: repeat(3, 1fr);
gap: var(--msz-loading-gap, calc(var(--msz-loading-size, 1) * 1px));
margin: var(--msz-loading-margin, calc(var(--msz-loading-size, 1) * 10px));
}
.msz-loading-icon-block {
background: var(--msz-loading-colour, currentColor);
width: var(--msz-loading-width, calc(var(--msz-loading-size, 1) * 10px));
height: var(--msz-loading-height, calc(var(--msz-loading-size, 1) * 10px));
}
.msz-loading-icon-block-hidden {
opacity: 0;
}

View file

@ -0,0 +1,33 @@
* {
margin: 0;
padding: 0;
box-sizing: border-box;
position: relative;
}
html, body {
width: 100%;
height: 100%;
}
[hidden],
.hidden {
display: none !important;
visibility: hidden !important;
}
:root {
--font-regular: Inter, 'Zen Kaku Gothic New', sans-serif;
--font-monospace: 'Victor Mono', monospace;
font-feature-settings: 'calt' 1, 'dlig' 1, 'ss01' 1;
font-optical-sizing: auto;
}
@supports (font-variation-settings: normal) {
:root {
--font-regular: InterVariable, 'Zen Kaku Gothic New', sans-serif;
}
}
@include loading.css;
@include perf.css;

101
assets/common.css/perf.css Normal file
View file

@ -0,0 +1,101 @@
.msz-perfs {
position: fixed;
bottom: 4px;
left: 4px;
display: flex;
gap: 2px;
flex-direction: column-reverse;
align-items: flex-start;
opacity: .5;
}
.msz-perfs-right {
left: initial;
right: 4px;
}
.msz-perfs:hover {
opacity: 1;
}
.msz-perf {
background-color: #111d;
color: #fff;
font-family: var(--font-monospace);
font-feature-settings: 'ss07' 1;
font-size: 12px;
line-height: 20px;
padding: 4px 8px;
border-radius: 6px;
}
.msz-perfs:hover .msz-perf {
backdrop-filter: blur(10px);
}
.msz-perf-number {
color: #fff;
}
.msz-perf-unit {
color: #888;
}
.msz-perf-header {
display: flex;
flex: 0 0 auto;
gap: 4px;
}
.msz-perf:hover .msz-perf-header {
border-bottom: 1px solid #888;
margin-bottom: 2px;
}
.msz-perf-type {
flex: 0 0 auto;
font-weight: 700;
min-width: 60px;
}
.msz-perf-type-navigation {
color: #f0f;
}
.msz-perf-type-other {
color: #0ff;
}
.msz-perf-target {
flex: 1 0 auto;
min-width: 200px;
}
.msz-perf-target-host,
.msz-perf-target-path,
.msz-perf-target-query {
display: inline-block;
}
.msz-perf-target-host,
.msz-perf-target-query {
color: #888;
}
.msz-perf-total {
flex: 0 0 auto;
min-width: 80px;
text-align: right;
}
.msz-perf-timings {
display: none;
border-collapse: collapse;
width: 100%;
}
.msz-perf:hover .msz-perf-timings {
display: table;
}
.msz-perf-timing-name {
font-weight: 700;
min-width: 60px;
}
.msz-perf-timing-comment {
color: #888;
}
.msz-perf-timing-duration {
min-width: 80px;
text-align: right;
}

27
assets/common.js/array.js Normal file
View file

@ -0,0 +1,27 @@
const $arrayRemoveAt = function(array, index) {
array.splice(index, 1);
};
const $arrayRemoveValue = function(array, item) {
let index;
while(array.length > 0 && (index = array.indexOf(item)) >= 0)
$arrayRemoveAt(array, index);
};
const $arrayRemoveAny = function(array, predicate) {
let index;
while(array.length > 0 && (index = array.findIndex(predicate)) >= 0)
$arrayRemoveAt(array, index);
};
const $arrayShuffle = function(array) {
if(array.length < 2)
return;
for(let i = array.length - 1; i > 0; --i) {
const j = Math.floor(Math.random() * (i + 1));
const tmp = array[i];
array[i] = array[j];
array[j] = tmp;
}
};

24
assets/common.js/csrf.js Normal file
View file

@ -0,0 +1,24 @@
#include html.js
const $csrf = (() => {
let elem;
const getElement = () => {
if(elem === undefined)
elem = $query('meta[name="csrf-token"]');
return elem;
};
return {
get token() {
return getElement()?.content ?? '';
},
set token(token) {
if(typeof token !== 'string')
throw 'token must be a string';
const elem = getElement();
if(elem instanceof HTMLMetaElement)
elem.content = token;
},
};
})();

157
assets/common.js/html.js Normal file
View file

@ -0,0 +1,157 @@
const $id = document.getElementById.bind(document);
const $query = document.querySelector.bind(document);
const $queryAll = document.querySelectorAll.bind(document);
const $text = document.createTextNode.bind(document);
const $insertBefore = function(target, element) {
target.parentNode.insertBefore(element, target);
};
const $appendChild = function(element, child) {
switch(typeof child) {
case 'undefined':
break;
case 'string':
element.appendChild($text(child));
break;
case 'function':
$appendChild(element, child());
break;
case 'object':
if(child === null)
break;
if(child instanceof Node)
element.appendChild(child);
else if(child?.element instanceof Node)
element.appendChild(child.element);
else if(typeof child?.toString === 'function')
element.appendChild($text(child.toString()));
break;
default:
element.appendChild($text(child.toString()));
break;
}
};
const $appendChildren = function(element, ...children) {
for(const child of children)
$appendChild(element, child);
};
const $removeChild = function(element, child) {
switch(typeof child) {
case 'function':
$removeChild(element, child());
break;
case 'object':
if(child === null)
break;
if(child instanceof Node)
element.removeChild(child);
else if(child?.element instanceof Node)
element.removeChild(child.element);
break;
}
};
const $removeChildren = function(element) {
while(element.lastChild)
element.removeChild(element.lastChild);
};
const $fragment = function(props, ...children) {
const fragment = document.createDocumentFragment();
$appendChildren(fragment, ...children);
return fragment;
};
const $element = function(type, props, ...children) {
if(typeof type === 'function')
return new type(props ?? {}, ...children);
const element = document.createElement(type ?? 'div');
if(props)
for(let key in props) {
const prop = props[key];
if(prop === undefined || prop === null)
continue;
switch(typeof prop) {
case 'function':
if(key.substring(0, 2) === 'on')
key = key.substring(2).toLowerCase();
element.addEventListener(key, prop);
break;
case 'object':
if(prop instanceof Array) {
if(key === 'class')
key = 'classList';
const attr = element[key];
let addFunc = null;
if(attr instanceof Array)
addFunc = attr.push.bind(attr);
else if(attr instanceof DOMTokenList)
addFunc = attr.add.bind(attr);
if(addFunc !== null) {
for(let j = 0; j < prop.length; ++j)
addFunc(prop[j]);
} else {
if(key === 'classList')
key = 'class';
element.setAttribute(key, prop.toString());
}
} else {
if(key === 'class' || key === 'className')
key = 'classList';
let setFunc = null;
if(element[key] instanceof DOMTokenList)
setFunc = (ak, av) => { if(av) element[key].add(ak); };
else if(element[key] instanceof CSSStyleDeclaration)
setFunc = (ak, av) => {
if(ak.includes('-'))
element[key].setProperty(ak, av);
else
element[key][ak] = av;
};
else
setFunc = (ak, av) => { element[key][ak] = av; };
for(const attrKey in prop) {
const attrValue = prop[attrKey];
if(attrValue)
setFunc(attrKey, attrValue);
}
}
break;
case 'boolean':
if(prop)
element.setAttribute(key, '');
break;
default:
if(key === 'className')
key = 'class';
element.setAttribute(key, prop.toString());
break;
}
}
$appendChildren(element, ...children);
return element;
};

View file

@ -0,0 +1,183 @@
const MszLoadingIcon = function() {
const element = <div class="msz-loading-icon"/>;
for(let i = 0; i < 9; ++i)
element.appendChild(<div class="msz-loading-icon-block"/>);
// this is moderately cursed but it'll do
const blocks = [
element.children[3],
element.children[0],
element.children[1],
element.children[2],
element.children[5],
element.children[8],
element.children[7],
element.children[6],
];
let tsLastUpdate;
let counter = 0;
let playing = false;
let delay = 50;
let playResolve;
let pauseResolve;
const update = tsCurrent => {
try {
if(tsLastUpdate !== undefined && (tsCurrent - tsLastUpdate) < delay)
return;
tsLastUpdate = tsCurrent;
for(let i = 0; i < blocks.length; ++i)
blocks[(counter + i) % blocks.length].classList.toggle('msz-loading-icon-block-hidden', i < 3);
++counter;
} finally {
if(playResolve)
try {
playResolve();
} finally {
playResolve = undefined;
playing = true;
}
if(pauseResolve)
try {
pauseResolve();
} finally {
pauseResolve = undefined;
playing = false;
}
if(playing)
requestAnimationFrame(update);
}
};
const play = () => {
return new Promise(resolve => {
if(playing || playResolve) {
resolve();
return;
}
playResolve = resolve;
requestAnimationFrame(update);
});
};
const pause = () => {
return new Promise(resolve => {
if(!playing || pauseResolve) {
resolve();
return;
}
pauseResolve = resolve;
});
};
const stop = async () => {
await pause();
counter = 0;
};
const restart = async () => {
await stop();
await play();
};
const reverse = () => {
blocks.reverse();
};
const setBlock = (num, state=null) => {
element.children[num].classList.toggle('msz-loading-icon-block-hidden', !state);
};
const batsu = () => {
setBlock(0, true);setBlock(1, false);setBlock(2, true);
setBlock(3, false);setBlock(4, true);setBlock(5, false);
setBlock(6, true);setBlock(7, false);setBlock(8, true);
};
const maru = () => {
setBlock(0, true);setBlock(1, true);setBlock(2, true);
setBlock(3, true);setBlock(4, false);setBlock(5, true);
setBlock(6, true);setBlock(7, true);setBlock(8, true);
};
return {
get element() { return element; },
get playing() { return playing; },
get delay() { return delay; },
set delay(value) {
if(typeof value !== 'number')
value = parseFloat(value);
if(isNaN(value) || !isFinite(value))
return;
if(value < 0)
value = Math.abs(value);
delay = value;
},
play,
pause,
stop,
restart,
reverse,
batsu,
maru,
};
};
const MszLoading = function(options=null) {
if(typeof options !== 'object')
throw 'options must be an object';
let {
element, size, colour,
width, height, inline,
containerWidth, containerHeight,
gap, margin, hidden,
} = options ?? {};
if(typeof element === 'string')
element = document.querySelector(element);
if(!(element instanceof HTMLElement))
element = <div class="msz-loading"/>;
if(!element.classList.contains('msz-loading'))
element.classList.add('msz-loading');
if(inline)
element.classList.add('msz-loading-inline');
if(hidden)
element.classList.add('hidden');
if(typeof size === 'number' && size > 0)
element.style.setProperty('--msz-loading-size', size);
if(typeof containerWidth === 'string')
element.style.setProperty('--msz-loading-container-width', containerWidth);
if(typeof containerHeight === 'string')
element.style.setProperty('--msz-loading-container-height', containerHeight);
if(typeof gap === 'string')
element.style.setProperty('--msz-loading-gap', gap);
if(typeof margin === 'string')
element.style.setProperty('--msz-loading-margin', margin);
if(typeof width === 'string')
element.style.setProperty('--msz-loading-width', width);
if(typeof height === 'string')
element.style.setProperty('--msz-loading-height', height);
if(typeof colour === 'string')
element.style.setProperty('--msz-loading-colour', colour);
let icon;
if(element.childElementCount < 1) {
icon = new MszLoadingIcon;
icon.play();
element.appendChild(<div class="msz-loading-frame">{icon}</div>);
}
return {
get element() { return element; },
get hasIcon() { return icon !== undefined; },
get icon() { return icon; },
get visible() { return !element.classList.contains('hidden'); },
set visible(state) { element.classList.toggle('hidden', !state); },
};
};

9
assets/common.js/main.js Normal file
View file

@ -0,0 +1,9 @@
#include array.js
#include csrf.js
#include html.js
#include meta.js
#include perf.jsx
#include uniqstr.js
#include xhr.js
#include loading.jsx

36
assets/common.js/meta.js Normal file
View file

@ -0,0 +1,36 @@
#include html.js
const $meta = (() => {
return {
get(name, prefixed=true) {
if(!name) return;
if(prefixed) name = `msz-${name}`;
const elem = $query(`meta[name="${name}"]`);
if(elem instanceof HTMLMetaElement && typeof elem.content === 'string')
return elem.content;
return null;
},
set(name, value, prefixed=true) {
if(!name) return;
if(prefixed) name = `msz-${name}`;
let elem = $query(`meta[name="${name}"]`);
if(elem instanceof HTMLMetaElement) {
if(typeof value === 'string')
elem.content = value;
else
elem.remove();
} else {
if(typeof value !== 'string')
return;
elem = document.createElement('meta');
elem.name = name;
elem.content = value;
document.head.appendChild(elem);
}
},
};
})();

72
assets/common.js/perf.jsx Normal file
View file

@ -0,0 +1,72 @@
#include html.js
(() => {
const perfs = <div class="msz-perfs"/>;
perfs.ondblclick = () => {
perfs.classList.toggle('msz-perfs-right');
};
const appendReal = elem => {
$appendChild(perfs, elem);
};
let append = elem => {
append = appendReal;
$appendChild(document.body, perfs);
appendReal(elem);
};
(new PerformanceObserver(list => {
for(const entry of list.getEntries()) {
if(entry.serverTiming.length < 1)
break;
const url = new URL(entry.name);
let total = 0;
let queries = -1;
const timings = <table class="msz-perf-timings"/>;
for(const timing of entry.serverTiming) {
if(timing.name === 'msz-queries') {
queries = Math.ceil(timing.duration);
continue;
}
total += timing.duration;
$appendChild(timings, <tr class="msz-perf-timing">
<td class="msz-perf-timing-name">{timing.name}</td>
<td class="msz-perf-timing-comment">{decodeURIComponent(timing.description)}</td>
<td class="msz-perf-timing-duration">
<span class="msz-perf-number">{timing.duration}</span>
<span class="msz-perf-unit">ms</span>
</td>
</tr>);
}
append(<div class="msz-perf">
<div class="msz-perf-header">
<div class={`msz-perf-type msz-perf-type-${entry instanceof PerformanceNavigationTiming ? 'navigation' : 'other'}`}>
{entry instanceof PerformanceNavigationTiming ? entry.type : (
entry.initiatorType === 'xmlhttprequest' ? 'xhr' : entry.initiatorType
)}
</div>
<div class="msz-perf-target">
{url.host !== location.host ? <div class="msz-perf-target-host">{url.host}</div> : null}
<div class="msz-perf-target-path">{url.pathname}</div>
{url.search !== '' ? <div class="msz-perf-target-query">{url.search}</div> : null}
</div>
{queries > 0 ? <div class="msz-perf-total">
<span class="msz-perf-number">{queries}</span>
{' '}
<span class="msz-perf-unit">{queries === 1 ? 'query' : 'queries'}</span>
</div> : null}
<div class="msz-perf-total">
<span class="msz-perf-number">{total.toFixed(5)}</span>
<span class="msz-perf-unit">ms</span>
</div>
</div>
{timings}
</div>);
}
})).observe({ entryTypes: ['navigation', 'resource'] });
})();

View file

@ -1,4 +1,4 @@
const MszRandomInt = function(min, max) {
const $rngi = function(min, max) {
let ret = 0;
const range = max - min;
@ -21,18 +21,18 @@ const MszRandomInt = function(min, max) {
ret &= mask;
if(ret >= range)
return MszRandomInt(min, max);
return $rngi(min, max);
return min + ret;
};
const MszUniqueStr = (function() {
const $rngs = (function() {
const chars = 'AaBbCcDdEeFfGgHhIiJjKkLlMmNnOoPpQqRrSsTtUuVvWwXxYyZz0123456789';
return function(length) {
let str = '';
for(let i = 0; i < length; ++i)
str += chars[MszRandomInt(0, chars.length)];
str += chars[$rngi(0, chars.length)];
return str;
};
})();

117
assets/common.js/xhr.js Normal file
View file

@ -0,0 +1,117 @@
#include csrf.js
const $xhr = (function() {
const send = function(method, url, options, body) {
if(options === undefined)
options = {};
else if(typeof options !== 'object')
throw 'options must be undefined or an object';
Object.freeze(options);
const xhr = new XMLHttpRequest;
const requestHeaders = new Map;
if('headers' in options && typeof options.headers === 'object')
for(const name in options.headers)
if(options.headers.hasOwnProperty(name))
requestHeaders.set(name.toLowerCase(), options.headers[name]);
if(options.csrf)
requestHeaders.set('x-csrf-token', $csrf.token);
if(typeof options.download === 'function') {
xhr.onloadstart = ev => options.download(ev);
xhr.onprogress = ev => options.download(ev);
xhr.onloadend = ev => options.download(ev);
}
if(typeof options.upload === 'function') {
xhr.upload.onloadstart = ev => options.upload(ev);
xhr.upload.onprogress = ev => options.upload(ev);
xhr.upload.onloadend = ev => options.upload(ev);
}
if(options.authed)
xhr.withCredentials = true;
if(typeof options.timeout === 'number')
xhr.timeout = options.timeout;
if(typeof options.type === 'string')
xhr.responseType = options.type;
if(typeof options.abort === 'function')
options.abort(() => xhr.abort());
if(typeof options.xhr === 'function')
options.xhr(() => xhr);
if(typeof body === 'object') {
if(body instanceof URLSearchParams) {
requestHeaders.set('content-type', 'application/x-www-form-urlencoded');
} else if(body instanceof FormData) {
// content-type is implicitly set
} else if(body instanceof Blob || body instanceof ArrayBuffer || body instanceof DataView) {
if(!requestHeaders.has('content-type'))
requestHeaders.set('content-type', 'application/octet-stream');
} else if(!requestHeaders.has('content-type')) {
const bodyParts = [];
for(const name in body)
if(body.hasOwnProperty(name))
bodyParts.push(encodeURIComponent(name) + '=' + encodeURIComponent(body[name]));
body = bodyParts.join('&');
requestHeaders.set('content-type', 'application/x-www-form-urlencoded');
}
}
return new Promise((resolve, reject) => {
xhr.onload = ev => {
const headers = (headersString => {
const headers = new Map;
const raw = headersString.trim().split(/[\r\n]+/);
for(const name in raw)
if(raw.hasOwnProperty(name)) {
const parts = raw[name].split(': ');
headers.set(parts.shift(), parts.join(': '));
}
return headers;
})(xhr.getAllResponseHeaders());
if(headers.has('x-csrf-token'))
$csrf.token = headers.get('x-csrf-token');
resolve({
get ev() { return ev; },
get xhr() { return xhr; },
get status() { return xhr.status; },
get headers() { return headers; },
get body() { return xhr.response; },
get text() { return xhr.responseText; },
});
};
xhr.onerror = ev => reject({
xhr: xhr,
ev: ev,
});
xhr.open(method, url);
for(const [name, value] of requestHeaders)
xhr.setRequestHeader(name, value);
xhr.send(body);
});
};
return {
send: send,
get: (url, options, body) => send('GET', url, options, body),
post: (url, options, body) => send('POST', url, options, body),
delete: (url, options, body) => send('DELETE', url, options, body),
patch: (url, options, body) => send('PATCH', url, options, body),
put: (url, options, body) => send('PUT', url, options, body),
};
})();

157
assets/errors.css/main.css Normal file
View file

@ -0,0 +1,157 @@
* {
margin: 0;
padding: 0;
box-sizing: border-box;
position: relative;
}
html,
body {
width: 100%;
height: 100%;
}
html {
scrollbar-color: #8559a5;
scrollbar-color: var(--error-colour, #8559a5) #111;
}
body {
color: #fff;
font-size: 16px;
line-height: 25px;
font-family: Inter, 'Zen Kaku Gothic New', sans-serif;
font-feature-settings: 'calt' 1, 'dlig' 1, 'ss01' 1;
font-optical-sizing: auto;
background-color: #8559a5;
background-color: var(--error-colour, #8559a5);
background-image: url('/images/clouds.png');
background-blend-mode: multiply;
position: static;
display: flex;
flex-direction: column;
}
@supports (font-variation-settings: normal) {
body {
--font-regular: InterVariable, 'Zen Kaku Gothic New', sans-serif;
}
}
.error {
display: flex;
flex-direction: column;
flex: 1 0 auto;
margin-bottom: 10px;
}
.error-wrapper {
display: flex;
flex: 1 0 auto;
padding: 10px;
width: 100%;
align-items: center;
justify-content: center;
}
.error-container {
max-width: 700px;
width: 100%;
margin: 0 auto;
padding: 4px;
background-color: #111;
box-shadow: 0 2px 4px #000;
overflow: hidden;
word-wrap: break-word;
}
.error-top {
display: flex;
align-items: center;
gap: 4px;
padding-bottom: 4px;
border-bottom: 1px solid #444;
}
.error-top a {
color: #fff;
text-decoration: none;
}
.error-top a:hover,
.error-top a:focus {
text-decoration: underline;
}
.error-logo {
width: 50px;
height: 50px;
}
.error-logo a {
color: inherit !important;
text-decoration: none !important;
}
.error-logo img {
width: 100%;
height: 100%;
vertical-align: middle;
border-width: 0;
object-fit: contain;
}
.error-home {
font-size: 1.5rem;
line-height: 1.375rem;
}
.error-nav {
margin-left: auto; /* lmao */
display: flex;
gap: 8px;
padding: 4px;
}
.error-body {
text-align: center;
height: 300px;
display: flex;
flex-direction: column;
justify-content: center;
}
.error-title {
line-height: 3rem;
}
.error-icon {
font-size: 4rem;
line-height: 1.5rem;
}
.error-blerb {
font-size: .875rem;
line-height: 1rem;
}
.error-footer {
text-align: center;
font-size: .75rem;
line-height: 1.375em;
color: #888;
border-top: 1px solid #444;
padding-top: 4px;
}
.error-footer a {
color: #88a;
text-decoration: underline;
text-decoration-style: dotted;
}
.error-footer a:hover,
.error-footer a:focus {
text-decoration-style: solid;
}
.error-footer a:active {
color: #a88;
}

View file

@ -1,9 +1,7 @@
.input__button {
background-color: var(--background-colour);
font-family: var(--font-regular);
font-size: 1.2em;
line-height: 1.4em;
padding: 5px 10px;
padding: 4px 12px;
min-width: 80px;
text-align: center;
cursor: pointer;
@ -15,6 +13,8 @@
align-items: center;
justify-content: center;
text-decoration: none;
font-size: inherit;
line-height: inherit;
}
.input__button:hover, .input__button:active,
.input__button:focus, .input__button:checked,

View file

@ -49,6 +49,8 @@
.input__checkbox__text {
display: inline-block;
margin-left: 4px;
font-size: .875em;
line-height: 1.375em;
}
.input__checkbox--disabled {
opacity: .5;

View file

@ -4,10 +4,12 @@
background: #222;
color: #fff;
min-width: 150px;
font-size: 1.2em;
border-radius: 2px;
box-shadow: inset 0 0 4px #111;
transition: border-color .2s;
font-family: inherit;
font-size: 1em;
line-height: 1.25em;
}
.input__select:focus {
border-color: var(--accent-colour);

View file

@ -1,5 +1,4 @@
.input__text {
font-size: 1.2em;
border: 1px solid #222;
padding: 5px 10px;
background: #222;
@ -7,8 +6,11 @@
border-radius: 2px;
box-shadow: inset 0 0 4px #111;
transition: border-color .2s;
font-family: inherit;
font-size: 1em;
line-height: 1.25em;
}
.input__text:focus { border-color: var(--accent-colour); }
.input__text--readonly { color: #888; }
.input__text--monospace { font-family: var(--font-monospace); }
.input__text--monospace { font-family: var(--font-monospace); font-feature-settings: 'ss07' 1; }
.input__text--centre { text-align: center; }

View file

@ -1,11 +1,11 @@
.input__textarea {
font-size: 1.2em;
border: 1px solid #222;
padding: 5px 10px;
padding: 4px 12px;
vertical-align: bottom;
background: #222;
color: #fff;
font-family: var(--font-monospace);
font-feature-settings: 'ss07' 1;
border-radius: 2px;
box-shadow: inset 0 0 4px #111;
transition: border-color .2s;

View file

@ -10,9 +10,8 @@
}
.input__upload__selection {
text-align: center;
font-size: 1.2em;
border: 1px solid #222;
padding: 5px 10px;
padding: 4px 12px;
background: #222;
color: #fff;
border-radius: 2px;

View file

@ -43,7 +43,7 @@
.changelog__change__username {
color: inherit;
font-size: 1.4em;
font-size: 1.375em;
line-height: 1.5em;
text-decoration: none;
}
@ -52,7 +52,7 @@
}
.changelog__change__userrole {
font-size: .9em;
font-size: .875em;
line-height: 1.5em;
color: inherit;
text-decoration: none;
@ -64,15 +64,13 @@
.changelog__change__date {
color: inherit;
text-decoration: none;
font-size: 1.1em;
line-height: 1.5em;
}
.changelog__change__date:hover {
text-decoration: underline;
}
.changelog__change__text {
line-height: 1.2em;
line-height: 1.25em;
flex: 1 1 auto;
word-wrap: break-word;
overflow: hidden;

View file

@ -1,6 +1,8 @@
.changelog__entry {
display: flex;
margin: 5px;
font-size: .875em;
line-height: 1.5em;
}
.changelog__entry__info { display: flex; }
@ -68,7 +70,7 @@
.changelog__entry__tags {
display: flex;
flex-wrap: wrap;
font-size: .9em;
font-size: .75em;
line-height: 1.5em;
}

View file

@ -6,8 +6,6 @@
text-decoration: none;
padding: 1px 3px;
color: var(--accent-colour);
font-size: 1.2em;
line-height: 1.5em;
}
.changelog__listing__date:hover {
text-decoration: underline;

View file

@ -21,8 +21,8 @@
}
.changelog__log__text {
padding: 8px 12px;
font-size: 1.5em;
line-height: 1.3em;
font-size: 1.375em;
line-height: 1.25em;
align-self: center;
flex: 1 1 auto;
overflow: hidden;

View file

@ -1,159 +0,0 @@
.comment {
margin: 10px;
}
.comment__reply-toggle {
display: none;
}
.comment__reply-toggle:checked ~ .comment--reply {
display: block;
}
.comment--reply {
display: none;
}
.comment--deleted > .comment__container {
opacity: .5;
transition: opacity .2s;
}
.comment--deleted > .comment__container:hover {
opacity: .9;
}
.comment__container {
display: flex;
margin-bottom: 3px;
}
.comment__mention {
color: var(--user-colour);
text-decoration: none;
font-weight: 700;
}
.comment__mention:hover {
text-decoration: underline;
}
.comment__actions {
list-style: none;
display: flex;
font-size: .9em;
align-items: center;
}
.comment__action {
color: inherit;
text-decoration: none;
vertical-align: middle;
cursor: pointer;
}
.comment__action:not(:last-child) {
margin-right: 6px;
}
.comment__action--link:hover {
text-decoration: underline;
}
.comment__action--post {
margin-left: auto;
}
.comment__action--button {
cursor: pointer;
font: 12px/20px var(--font-regular);
padding: 0 10px;
}
.comment__action--hide {
opacity: 0;
transition: opacity .2s;
}
.comment__action--voted {
font-weight: 700;
}
.comment__action__checkbox {
vertical-align: text-top;
margin-right: 2px;
}
.comment__replies .comment--indent-1,
.comment__replies .comment--indent-2,
.comment__replies .comment--indent-3,
.comment__replies .comment--indent-4,
.comment__replies .comment--indent-5 {
margin-left: 20px;
}
.comment__avatar {
flex: 0 0 auto;
height: 50px;
width: 50px;
margin-right: 5px;
}
.comment__replies .comment__avatar {
width: 40px;
height: 40px;
}
.comment__content {
flex: 1 1 auto;
display: flex;
flex-direction: column;
overflow: hidden;
word-wrap: break-word;
padding-left: 5px;
}
.comment__content:hover .comment__action--hide {
opacity: 1;
}
.comment__info {
display: inline-flex;
}
.comment__text {
margin-right: 2px;
}
.comment__text--input {
min-width: 100%;
max-width: 100%;
min-height: 50px;
font: 12px/20px var(--font-regular);
margin-right: 1px;
}
.comment__user {
color: var(--user-colour);
text-decoration: none;
}
.comment__user--link:hover {
text-decoration: underline;
}
.comment__date,
.comment__pin {
color: #666;
font-size: .9em;
margin-left: 8px;
}
.comment__link {
color: #666;
display: inline-flex;
text-decoration: none;
&:hover {
text-decoration: underline;
}
}
.comment__pin {
margin-left: 4px;
}
.comment__pin:before {
content: "-";
padding-right: 4px;
}

View file

@ -1,36 +0,0 @@
.comments {
--comments-max-height: 600px;
margin: 1px;
overflow: hidden;
word-wrap: break-word;
}
.comments__listing {
overflow-y: auto;
}
.comments__listing--limit {
max-height: var(--comments-max-height);
}
/*.comments__input,*/
.comments__javascript,
.comments__notice--staff {
border-bottom: 1px solid var(--accent-colour);
padding-bottom: 1px;
margin-bottom: 1px;
}
.comments__none,
.comments__javascript,
.comments__notice {
padding: 10px;
font-size: 1.2em;
text-align: center;
}
.comments__notice__link {
color: var(--accent-colour);
text-decoration: none;
}
.comments__notice__link:hover {
text-decoration: underline;
}

View file

@ -0,0 +1,121 @@
.comments-entry-main {
display: grid;
grid-template-columns: 46px 1fr;
gap: 2px;
}
.comments-entry-root {
padding-bottom: 2px;
border-top: 1px solid var(--accent-colour);
}
.comments-entry-replies {
margin-left: 25px;
}
.comments-entry-avatar {
flex: 0 0 auto;
padding: 4px;
}
.comments-entry-wrap {
flex: 0 1 auto;
display: flex;
flex-direction: column;
gap: 2px;
}
.comments-entry-meta {
display: flex;
gap: 4px;
margin-top: 4px;
}
.comments-entry-user {
display: flex;
}
.comments-entry-user-link {
text-decoration: none;
}
.comments-entry-user-link:hover,
.comments-entry-user-link:focus {
text-decoration: underline solid var(--user-colour, var(--text-colour, #fff));
}
.comments-entry-user-dead {
text-decoration: line-through;
}
.comments-entry-time {
display: flex;
gap: 6px;
}
.comments-entry-time-edited,
.comments-entry-time-pinned,
.comments-entry-time-deleted {
margin-left: 6px;
}
.comments-entry-time-pinned .comments-entry-time-icon {
rotate: 45deg;
}
.comments-entry-time-link {
color: inherit;
text-decoration: none;
}
.comments-entry-time-link:hover,
.comments-entry-time-link:focus {
text-decoration: underline;
}
.comments-entry-actions {
display: flex;
gap: 2px;
margin-top: 2px;
}
.comments-entry-actions-group {
display: flex;
border-radius: 3px;
padding: 1px;
gap: 1px;
transition: opacity .1s;
}
.comments-entry-actions-group-votes,
.comments-entry-actions-group-replies {
border: 1px solid var(--accent-colour);
}
.comments-entry-actions-group-disabled {
opacity: .5;
}
.comments-entry-action {
background: transparent;
border-width: 0;
border-radius: 2px;
display: flex;
align-items: center;
justify-content: center;
gap: 6px;
padding: 3px 6px;
cursor: pointer;
transition: background-color .1s;
min-width: 24px;
min-height: 22px;
color: inherit;
}
.comments-entry-action:not([disabled]):hover,
.comments-entry-action:not([disabled]):focus {
background: var(--comments-entry-action-background-hover, #fff4);
}
.comments-entry-action-reply-active {
background: #fff2;
}
.comments-entry-action-vote-like.comments-entry-action-vote-cast {
background: #0808;
}
.comments-entry-action-vote-like {
--comments-entry-action-background-hover: #0804;
}
.comments-entry-action-vote-dislike.comments-entry-action-vote-cast {
background: #c008;
}
.comments-entry-action-vote-dislike {
--comments-entry-action-background-hover: #c004;
}

View file

@ -0,0 +1,73 @@
.comments-form {
border: 1px solid var(--accent-colour);
border-radius: 3px;
margin: 2px 0;
display: grid;
grid-template-columns: 46px 1fr;
transition: opacity .1s;
}
.comments-form-root {
margin: 2px;
}
.comments-form-disabled {
opacity: .5;
}
.comments-form-avatar {
flex: 0 0 auto;
padding: 3px;
}
.comments-form-wrap {
display: grid;
grid-template-rows: 1fr 35px;
gap: 2px;
margin: 3px;
margin-left: 0;
overflow: hidden;
}
.comments-form-input {
overflow: hidden;
}
.comments-form-input textarea {
min-width: 100%;
max-width: 100%;
width: 100%;
min-height: 40px;
height: 0;
}
.comments-form-root .comments-form-input textarea {
min-height: 60px;
}
.comments-form-actions {
display: flex;
align-items: center;
overflow: hidden;
gap: 6px;
}
.comments-form-status {
flex: 1 1 auto;
padding: 0 6px;
overflow: hidden;
transition: color .2s;
}
.comments-form-status-text {
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
}
.comments-form-status-error {
color: #c00;
}
.comments-form-pin {
flex: 0 0 auto;
font-size: 1.25em;
line-height: 1.375em;
}
.comments-form-post {
flex: 0 0 auto;
}

View file

@ -0,0 +1,8 @@
.comments-listing {
display: flex;
flex-direction: column;
gap: 2px;
}
.comments-listing-root {
margin: 2px;
}

View file

@ -0,0 +1,5 @@
@include comments/form.css;
@include comments/entry.css;
@include comments/listing.css;
@include comments/notice.css;
@include comments/options.css;

View file

@ -0,0 +1,14 @@
.comments-notice {
display: flex;
justify-content: center;
align-items: center;
flex-wrap: wrap;
font-size: 1.25em;
line-height: 1.375em;
gap: 6px;
padding: 12px;
margin: 2px;
}
.comments-notice-inner {
flex: 0 1 auto;
}

View file

@ -0,0 +1,32 @@
.comments-options {
display: flex;
justify-content: flex-end;
margin: 2px;
padding: 6px;
gap: 6px;
}
.comments-options-actions {
display: flex;
gap: 6px;
}
.comments-options-action {
color: inherit;
display: flex;
align-items: center;
justify-content: center;
gap: 6px;
padding: 4px 8px;
background-color: transparent;
border-width: 0;
border-radius: 4px;
transition: background-color .1s, opacity .1s;
}
.comments-options-action[disabled] {
opacity: .5;
}
.comments-options-action:not([disabled]):hover,
.comments-options-action:not([disabled]):focus {
background-color: #fff4;
}

View file

@ -1,11 +0,0 @@
.confirm {
max-width: 400px;
margin: 0 auto;
}
.confirm__buttons {
display: flex;
padding: 5px;
justify-content: center;
}
.confirm__message { padding: 2px 5px; }
.confirm__button { margin-right: 5px; }

View file

@ -13,10 +13,12 @@
overflow: hidden;
}
.container__title__text {
font-size: 1.5em;
font-size: 1.125rem;
line-height: 1.5em;
padding: 8px 10px;
word-wrap: break-word;
font-weight: 500;
min-height: 44px;
}
.container__title__link {
color: inherit;
@ -30,7 +32,6 @@
width: 100%;
height: 100%;
mask-image: linear-gradient(0deg, transparent 10%, var(--background-colour) 100%);
-webkit-mask-image: linear-gradient(0deg, transparent 10%, var(--background-colour) 100%);
background: var(--background-pattern);
background-color: var(--accent-colour);
background-blend-mode: multiply;

View file

@ -21,7 +21,7 @@
visibility: hidden;
}
.eeprom-widget-form-text {
font-size: 1.4em;
font-size: 1.325em;
line-height: 1.5em;
}
.eeprom-widget-form:focus,
@ -70,8 +70,8 @@
text-decoration: underline;
}
.eeprom-widget-file-progress {
font-size: .9em;
line-height: 1.4em;
font-size: .875em;
line-height: 1.325em;
text-align: right;
padding: 0 2px;
white-space: nowrap;

View file

@ -88,30 +88,26 @@
margin-left: 5px;
}
.embedph-info-title {
font-size: 2em !important;
font-weight: 400 !important;
line-height: 1.2em !important;
margin-bottom: 5px;
font-size: 1.5rem !important;
font-weight: 500 !important;
line-height: 1.5rem !important;
margin: 5px 0;
word-break: break-word;
margin: 0 !important;
padding: 0 !important;
border-width: 0 !important;
}
.embedph-info-desc {
line-height: 1.4em;
margin: .5em 0;
font-size: .875rem;
line-height: 1.5rem;
margin: .25rem 0;
word-break: break-word;
}
.embedph-info-site {
font-size: .9em;
line-height: 1.2em;
font-size: .75rem;
}
@media (max-width: 640px) {
.embedph-info-title {
font-size: 1.5em;
line-height: 1.2em;
}
.embedph-info-desc {
display: none;
}
@ -135,9 +131,7 @@
margin-bottom: 20px;
}
.embedph-play-external {
padding: 5px 10px;
font-size: 1.2em;
line-height: 1.5em;
padding: 4px 8px;
text-decoration: none !important;
color: var(--text-colour) !important;
background-color: var(--background-colour-translucent-6);
@ -225,6 +219,7 @@
height: 70px;
border-radius: 5px;
margin: 5px;
font-size: .75rem;
}
.aembedph:hover .aembedph-play,
.aembedph:active .aembedph-play,
@ -293,9 +288,9 @@
padding: 0 5px;
}
.aembedph-info-title {
font-size: 1.4em !important;
font-weight: 400 !important;
line-height: 1.2em !important;
font-size: 1.25em !important;
font-weight: 500 !important;
line-height: 1.25em !important;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
@ -309,10 +304,10 @@
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
font-weight: 700;
font-weight: 600;
}
.aembedph-info-album {
line-height: 1.4em;
line-height: 1.5em;
word-break: break-word;
white-space: nowrap;
overflow: hidden;
@ -321,7 +316,7 @@
}
.aembedph-info-site {
font-size: .9em;
line-height: 1.2em;
line-height: 1.25em;
}
.aembedph-play {

View file

@ -129,7 +129,7 @@
/* Ix */
.flag--id { background-position: top -96px left -48px; }
.flag--ie { background-position: top -96px left -64px; }
.flag--il { background-position: top -96px left -176px; }
.flag--il { background-position: top -180px left -288px; }
.flag--in { background-position: top -96px left -208px; }
.flag--io { background-position: top -96px left -224px; }
.flag--iq { background-position: top -96px left -256px; }

View file

@ -13,8 +13,8 @@
max-width: var(--site-max-width);
margin: 0 auto;
text-align: center;
font-size: .9em;
line-height: 1.5em;
font-size: .875rem;
line-height: 1.5rem;
padding: 1em 0;
}
.footer__background {

View file

@ -4,8 +4,6 @@
overflow: auto;
}
.forum__categories__empty {
font-size: 1.2em;
line-height: 1.5em;
text-align: center;
padding: 10px;
}
@ -63,8 +61,8 @@
background-size: 80px 80px;
background-image: radial-gradient(ellipse at center, rgba(255, 255, 255, .2) 0%, rgba(0, 0, 0, .4) 100%);
box-shadow: 0 1px 4px #111;
font-size: 2em;
line-height: 1.5em;
font-size: 1.5em;
line-height: 1.25em;
color: #fff;
display: flex;
justify-content: center;
@ -82,22 +80,25 @@
justify-content: center;
flex-direction: column;
line-height: 1.5em;
gap: 2px;
}
.forum__category__title {
font-size: 1.3em;
font-size: 1.125em;
line-height: 1.25em;
}
.forum__category__description,
.forum__category__subforums {
font-size: .9em;
font-size: .875em;
line-height: 1.25em;
}
.forum__category__subforums {
display: flex;
gap: 6px;
}
.forum__category__subforum {
padding: 2px;
pointer-events: initial;
color: var(--accent-colour);
text-decoration: none;
@ -125,21 +126,23 @@
}
.forum__category__stat {
font-size: .9em;
line-height: 1.3em;
font-size: .875em;
line-height: 1.25em;
opacity: .7;
pointer-events: auto;
font-feature-settings: 'ss01' 1, 'tnum' 1;
}
.forum__category__stat:first-child {
font-size: 1.5em;
font-size: 1.25em;
opacity: 1;
}
.forum__category__activity {
text-align: right;
min-width: 270px;
line-height: 1.4em;
min-width: 300px;
font-size: .875em;
line-height: 1.375em;
}
.forum__category__activity__none,
.forum__category__activity__details {
@ -160,7 +163,7 @@
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
max-width: 200px;
max-width: 230px;
}
.forum__category__activity__post:hover,
.forum__category__activity__post:focus {
@ -194,7 +197,7 @@
flex-wrap: wrap;
}
.forum__category__details {
flex-basis: calc(100% - 100px);
flex-basis: calc(100% - 8em); /* god knows what this does */
}
.forum__category__stats {
min-width: initial;

View file

@ -1,15 +0,0 @@
.forum__confirm {
max-width: 400px;
margin: 0 auto;
}
.forum__confirm__message {
padding: 2px 5px;
}
.forum__confirm__buttons {
display: flex;
padding: 5px;
justify-content: center;
}
.forum__confirm__button {
margin-right: 5px;
}

View file

@ -7,8 +7,8 @@
}
.forum__header__title {
font-size: 2em;
line-height: 1.5em;
font-size: 1.5em;
line-height: 1.25em;
color: inherit;
text-decoration: none;
padding: 0 5px;
@ -28,19 +28,18 @@
margin: 0;
box-shadow: initial;
font-size: 1em;
font-family: inherit;
font-family: var(--font-regular);
}
.forum__header__breadcrumbs {
display: flex;
font-size: 1.1em;
line-height: 1.5em;
align-items: center;
}
.forum__header__breadcrumb {
color: var(--accent-colour);
text-decoration: none;
padding: 2px 5px;
padding: 2px 6px;
}
.forum__header__breadcrumb:hover {
text-decoration: underline;
@ -48,7 +47,7 @@
.forum__header__breadcrumb__separator {
color: var(--accent-colour);
margin: 0 4px;
font-size: .9em;
font-size: .875em;
}
.forum__header__actions {

View file

@ -36,14 +36,13 @@
.forum__leaderboard__user {
margin: 2px 0;
font-size: 1.2em;
}
.forum__leaderboard__user--rank-1 {
font-size: 1.6em;
font-size: 1.5em;
}
.forum__leaderboard__user--rank-2,
.forum__leaderboard__user--rank-3 {
font-size: 1.4em;
font-size: 1.25em;
}
.forum__leaderboard__user__background {
@ -69,6 +68,7 @@
justify-content: center;
font-weight: 700;
flex: 0 0 auto;
font-feature-settings: 'ss01' 1, 'tnum' 1;
}
.forum__leaderboard__user__rank:before {
content: "#";

View file

@ -1,104 +0,0 @@
.forum__poll__container {
margin: 2px 0;
padding: 5px;
display: flex;
flex-direction: column;
align-items: center;
}
.forum__poll__toggle,
.forum__poll__toggle:checked ~ .forum__poll__container--poll,
.forum__poll__toggle:not(:checked) ~ .forum__poll__container--results {
display: none;
}
.forum__poll__options {
display: flex;
flex-direction: column;
max-width: 500px;
min-width: 100%;
}
.forum__poll__results {
max-width: 800px;
width: 100%;
padding: 0 1px;
}
.forum__poll__option {
padding: 2px;
}
.forum__poll__remaining,
.forum__poll__expires {
line-height: 1.5em;
}
.forum__poll__remaining__num,
.forum__poll__expires__num,
.forum__poll__remaining__datetime,
.forum__poll__expires__datetime {
font-weight: 700;
}
.forum__poll__buttons {
display: flex;
margin-top: 2px;
}
.forum__poll__button {
margin: 0 2px;
}
.forum__poll__result {
overflow: hidden;
border-radius: 5px;
margin: 4px 0;
border: 1px solid var(--accent-colour);
width: 100%;
}
.forum__poll__result__background {
position: absolute;
top: 0;
left: 0;
height: 100%;
background: var(--accent-colour);
opacity: .2;
}
.forum__poll__result--voted .forum__poll__result__background {
opacity: .4;
}
.forum__poll__result__container {
display: flex;
justify-content: center;
}
.forum__poll__result__text {
flex: 1 1 auto;
padding: 5px;
}
.forum__poll__result--voted .forum__poll__result__text {
font-weight: 700;
}
.forum__poll__result__votes {
flex: 0 0 auto;
padding: 5px;
text-align: right;
}
.forum__poll__result__percent {
flex: 0 0 auto;
padding: 5px;
min-width: 60px;
text-align: right;
}
@media (min-width: 400px) {
.forum__poll__options {
min-width: 300px;
}
}

View file

@ -22,8 +22,8 @@
}
.forum__post__details {
font-size: .9em;
line-height: 1.7em;
font-size: .875em;
line-height: 1.75em;
padding: 0 2px;
display: flex;
justify-content: space-between;
@ -36,6 +36,9 @@
color: inherit;
text-decoration: none;
}
.forum__post__id {
font-feature-settings: 'ss01' 1, 'tnum' 1;
}
.forum__post__datetime:hover,
.forum__post__datetime:focus,
.forum__post__id:hover,
@ -47,7 +50,7 @@
.forum__post__text {
padding: 2px;
line-height: 1.4em;
line-height: 1.5em;
flex: 1 1 auto;
}
.forum__post__text--edit {
@ -97,14 +100,14 @@
}
.forum__post__posts-count {
font-size: .9em;
margin-left: 4px;
font-size: .75em;
margin-left: 8px;
}
.forum__post__joined {
flex: 1 1 auto;
max-width: 170px;
font-size: .9em;
font-size: .75em;
justify-self: flex-end;
}
@ -117,7 +120,7 @@
.forum__post__username {
color: inherit;
font-size: 1.4em;
font-size: 1.25em;
line-height: 2em;
text-decoration: none;
}
@ -127,8 +130,8 @@
}
.forum__post__usertitle {
font-size: .9em;
line-height: 1.5em;
font-size: .75em;
line-height: 1.25em;
margin-bottom: 4px;
}
@ -154,6 +157,9 @@
}
.forum__post__action {
background-color: transparent;
border: 0;
display: block;
padding: 5px 10px;
margin: 1px;
color: inherit;
@ -161,6 +167,9 @@
transition: background-color .2s;
border-radius: 3px;
cursor: pointer;
font-family: inherit;
font-size: inherit;
line-height: inherit;
}
.forum__post__action:hover,
.forum__post__action:focus {
@ -181,12 +190,13 @@
.forum__post__badge {
background-color: var(--accent-colour);
border-radius: 12px;
border-radius: 24px;
width: 100%;
padding: 2px;
box-shadow: 0 2px 3px #000A;
margin: 4px;
overflow: hidden;
font-size: .875em;
}
.forum__post__badge__desktop {
display: block;
@ -201,13 +211,11 @@
}
.forum__post__text {
margin: 4px;
font-size: 1.2em;
line-height: 1.3em;
}
.forum__post__info {
flex-direction: row;
margin: 0;
padding: 5px;
padding: 4px;
}
.forum__post__info__content {
width: 100%;
@ -246,8 +254,8 @@
padding: 2px 10px;
margin: 0;
align-self: flex-start;
margin-left: 5px;
font-size: .9em;
margin-left: 10px;
font-size: .875em;
}
.forum__post__badge__desktop {
display: none;

View file

@ -1,37 +0,0 @@
.forum__priority__votes {
text-align: center;
margin: 5px 16px 5px 5px;
-webkit-touch-callout: none !important;
-webkit-user-select: none !important;
-khtml-user-select: none !important;
-moz-user-select: none !important;
-ms-user-select: none !important;
user-select: none !important;
cursor: default;
}
.forum__priority__vote {
font-size: 14px;
display: inline;
}
.forum__priority__star {
margin-right: -.9em;
opacity: .6;
text-shadow: 0 1px 1px #000;
color: var(--user-colour);
transition: text-shadow .2s;
}
.forum__priority__star:last-child {
margin-right: 0;
opacity: 1;
}
.forum__priority__vote:hover .forum__priority__star {
text-shadow: 0 0 1px #fff;
}
.forum__priority__input {
margin: 5px;
text-align: center;
}

View file

@ -12,7 +12,7 @@
display: flex;
justify-content: center;
align-items: center;
font-size: 2em;
font-size: 1.5em;
padding-bottom: 1px;
}
.forum__status__icon__background {

View file

@ -4,8 +4,6 @@
overflow: auto;
}
.forum__topics__empty {
font-size: 1.2em;
line-height: 1.5em;
text-align: center;
padding: 10px;
}
@ -76,7 +74,7 @@
background-size: 60px 60px;
background-image: radial-gradient(ellipse at center, rgba(255, 255, 255, .2) 0%, rgba(0, 0, 0, .4) 100%);
box-shadow: 0 1px 4px #111;
font-size: 1.5em;
font-size: 1.125em;
line-height: 1.5em;
color: #fff;
display: flex;
@ -91,9 +89,6 @@
.forum__topic__icon--unread {
background-color: var(--accent-colour);
}
.forum__topic__icon--faded {
opacity: .3;
}
.forum__topic__icon__participated {
position: absolute;
bottom: 2px;
@ -105,16 +100,6 @@
box-shadow: 0 1px 2px #111;
pointer-events: initial;
}
.forum__topic__icon__priority {
position: absolute;
top: 0;
left: 0;
width: 100%;
height: 100%;
line-height: 30px;
font-size: .9em;
text-align: center;
}
.forum__topic__details {
margin: 0 4px;
@ -127,14 +112,15 @@
}
.forum__topic__title {
font-size: 1.3em;
font-size: 1.125em;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
}
.forum__topic__info {
font-size: .9em;
font-size: .875em;
line-height: 1.25em;
}
.forum__topic__stats,
@ -150,14 +136,15 @@
}
.forum__topic__stat {
font-size: .9em;
line-height: 1.3em;
font-size: .875em;
line-height: 1.25em;
opacity: .7;
pointer-events: auto;
cursor: default;
font-feature-settings: 'ss01' 1, 'tnum' 1;
}
.forum__topic__stat:first-child {
font-size: 1.4em;
font-size: 1.25em;
opacity: 1;
}
@ -166,7 +153,7 @@
align-items: center;
text-align: right;
min-width: 200px;
line-height: 1.5em;
line-height: 1.25em;
}
.forum__topic__activity__details {
display: flex;
@ -211,8 +198,9 @@
.forum__topic__pagination {
display: flex;
align-items: center;
font-size: .9em;
line-height: 1.2em;
font-size: .875em;
line-height: 1.25em;
font-feature-settings: 'ss01' 1, 'tnum' 1;
}
.forum__topic__pagination__separator {
margin: 0 8px;
@ -222,7 +210,7 @@
text-decoration: none;
pointer-events: initial;
margin: 0 1px;
padding: 2px 4px;
padding: 3px;
border-radius: 2px;
min-width: 25px;
height: 25px;
@ -275,8 +263,8 @@
.forum__topic__pagination__item {
min-width: 30px;
height: 30px;
line-height: 26px;
font-size: 1.2em;
line-height: 1.375em;
font-size: 1.25em;
}
}
@ -285,4 +273,4 @@
position: absolute;
right: 0;
}
}
}

View file

@ -69,8 +69,7 @@
}
.header__desktop__menu__link {
margin: var(--header-link-margin) 0;
font-size: 1.2em;
padding: 6px 10px;
padding: 4px 10px;
text-align: center;
}
@ -86,6 +85,8 @@
}
.header__desktop__submenu__link {
margin: 5px;
font-size: .875em;
line-height: 1.5em;
}
.header__desktop__submenu__background {
background: var(--header-accent-colour);
@ -128,8 +129,8 @@
margin: 2px;
color: inherit;
text-decoration: none;
font-size: 1.5em;
line-height: 32px;
font-size: 1.125rem;
line-height: 2rem;
width: 32px;
height: 32px;
transition: background-color .2s;
@ -146,14 +147,20 @@
}
.header__desktop__user__button__count {
position: absolute;
bottom: 1px;
right: 1px;
font-size: 10px;
top: -5px;
right: -3px;
z-index: 1;
font-size: .625rem;
line-height: 1.375rem;
text-align: right;
padding: 2px 2px 0;
border-radius: 4px;
background-color: var(--header-accent-colour);
opacity: .9;
border-radius: 4px;
line-height: 12px;
padding: 2px 4px;
padding: 2px 3px;
font-feature-settings: 'ss01' 1, 'tnum' 1;
}
/** MOBILE HEADER **/
@ -181,18 +188,12 @@
.header__mobile__icon {
flex: 0 0 auto;
cursor: pointer;
font-size: 32px;
font-size: 1.5rem;
width: var(--header-icon-px);
height: var(--header-icon-px);
display: flex;
justify-content: center;
align-items: center;
-webkit-touch-callout: none !important;
-webkit-user-select: none !important;
-khtml-user-select: none !important;
-moz-user-select: none !important;
-ms-user-select: none !important;
user-select: none !important;
}
@ -222,7 +223,7 @@
background: var(--background-pattern);
background-color: var(--header-accent-colour);
background-blend-mode: multiply;
transition: max-height .2s;
transition: max-height .3s;
box-shadow: 0 1px 2px rgba(0, 0, 0, 0.6);
max-height: 0;
overflow: hidden;
@ -232,7 +233,7 @@
}
.header__mobile__toggle:checked ~ .header__mobile__menu {
max-height: 600px;
max-height: 100vh;
}
.header__mobile__user {
@ -250,24 +251,23 @@
color: inherit;
text-decoration: none;
display: block;
padding: 8px;
padding-left: 20px;
padding: 6px;
padding-left: 24px;
cursor: pointer;
border-radius: 2px;
transition: background-color .2s, margin .1s, opacity .1s;
font-size: 1.2em;
}
.header__mobile__link:not(:last-child) {
margin-bottom: 2px;
}
.header__mobile__link--primary {
font-size: 1.5em;
padding: 10px;
font-size: 1.25rem;
padding: 8px;
}
.header__mobile__link--user {
margin: 2px;
font-size: 1.5em;
padding: 10px;
font-size: 1.25rem;
padding: 8px;
}
.header__mobile__link:hover,
.header__mobile__link:focus {

View file

@ -0,0 +1,92 @@
pre code.hljs {
display: block;
overflow-x: auto;
padding: 1em;
font-family: var(--font-monospace);
font-feature-settings: 'ss07' 1;
}
code.hljs {
padding: 2px 5px;
}
.hljs {
color: #eee;
background: #121212;
}
.hljs-strong,
.hljs-emphasis,
.hljs-section {
font-weight: 700;
}
.hljs-bullet,
.hljs-quote,
.hljs-number,
.hljs-regexp,
.hljs-literal {
color: #b2b376;
}
.hljs-code {
background-color: #242424;
}
.hljs-comment,
.hljs-meta,
.hljs-emphasis,
.hljs-stronge,
.hljs-type,
.hljs-attribute,
.hljs-params {
font-style: italic;
}
.hljs-keyword,
.hljs-selector-tag,
.hljs-section,
.hljs-symbol,
.hljs-name {
color: #9475b2;
}
.hljs-built_in,
.hljs-subst,
.hljs-tag,
.hljs-title,
.hljs-selector-attr {
color: #c8b9d7;
}
.hljs-variable,
.hljs-class .hljs-title,
.hljs-selector-class,
.hljs-selector-id,
.hljs-selector-pseudo {
color: #b37fae;
}
.hljs-string {
color: #76b38a;
}
.hljs-type,
.hljs-template-tag,
.hljs-template-variable,
.hljs-link {
color: #b39a76;
}
.hljs-comment,
.hljs-meta {
color: #70647b;
}
.hljs-addition {
background: #0e4d0e;
}
.hljs-deletion {
background: #4d0e0e;
}

View file

@ -46,8 +46,8 @@
.landingv2-footer-copyright {
text-align: right;
line-height: 1.8em;
font-size: .9em;
line-height: 1.5em;
font-size: .875em;
align-self: flex-end;
}

View file

@ -52,8 +52,8 @@
display: flex;
align-items: center;
min-height: 70px;
font-size: 1.4em;
padding: 10px 16px;
font-size: 1.5em;
padding: 8px 16px;
grid-column: 1;
}
.landingv2-header-menu-link:hover,

View file

@ -13,7 +13,6 @@
display: flex;
align-items: center;
margin: 10px;
text-shadow: 0 1px 4px #000;
}
.landingv2-stat-icon {
font-size: 4em;
@ -25,6 +24,7 @@
}
.landingv2-stat-value-num {
font-weight: 700;
font-feature-settings: 'ss01' 1, 'tnum' 1;
}
.landingv2-forum {
@ -37,7 +37,6 @@
.landingv2-forum-topics {
background-color: var(--container-colour);
box-shadow: 0 1px 2px #0009;
text-shadow: 0 1px 4px #000;
overflow: hidden;
word-wrap: break-word;
}
@ -95,7 +94,7 @@
background-size: 60px 60px;
background-image: radial-gradient(ellipse at center, rgba(255, 255, 255, .2) 0%, rgba(0, 0, 0, .4) 100%);
box-shadow: 0 1px 4px #111;
font-size: 1.5em;
font-size: 1.25em;
line-height: 1.5em;
color: #fff;
display: flex;
@ -110,34 +109,35 @@
display: flex;
justify-content: center;
flex-direction: column;
line-height: 1.6em;
line-height: 1.625em;
overflow: hidden;
}
.landingv2-forum-topic-info-details-title {
font-size: 1.3em;
font-size: 1.25em;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
}
.landingv2-forum-topic-info-stats {
font-size: .9em;
font-size: .875em;
display: flex;
flex: 0 0 auto;
text-align: center;
min-width: 60px;
flex-direction: column;
font-feature-settings: 'ss01' 1, 'tnum' 1;
}
.landingv2-forum-topic-info-stats-posts,
.landingv2-forum-topic-info-stats-views {
font-size: .9em;
line-height: 1.3em;
font-size: .875em;
line-height: 1.25em;
opacity: .7;
pointer-events: auto;
cursor: default;
}
.landingv2-forum-topic-info-stats-posts {
font-size: 1.4em;
font-size: 1.25em;
opacity: 1;
}
@ -150,7 +150,6 @@
.landingv2-news-post {
background-color: var(--container-colour);
box-shadow: 0 1px 2px #0009;
text-shadow: 0 1px 4px #000;
overflow: hidden;
word-wrap: break-word;
padding: 0 10px 10px 10px;
@ -167,7 +166,6 @@
.landingv2-online {
background-color: var(--container-colour);
box-shadow: 0 1px 2px #0009;
text-shadow: 0 1px 4px #000;
margin: 4px 0;
}
.landingv2-online-users {

View file

@ -37,7 +37,6 @@
height: 30px;
line-height: 29px;
text-align: center;
font-size: 1.5em;
background-color: #222d;
display: block;
color: var(--text-colour);

View file

@ -57,13 +57,10 @@
width: 45%;
padding: 4px 0;
}
.landing__statistic__name {
font-size: 1.3em;
line-height: 2em;
}
.landing__statistic__value {
font-size: 1.5em;
line-height: 1.5em;
font-size: 1.25em;
line-height: 1.625em;
font-feature-settings: 'ss01' 1, 'tnum' 1;
}
.landing__latest {
@ -91,13 +88,13 @@
padding-left: 8px;
}
.landing__latest__username {
font-size: 1.5em;
line-height: 1.4em;
font-size: 1.25em;
line-height: 1.375em;
color: var(--user-colour);
}
.landing__latest__joined {
font-size: .9em;
line-height: 1.2em;
font-size: .875em;
line-height: 1.25em;
}
@media (max-width: 800px) {

View file

@ -1,28 +1,6 @@
* {
margin: 0;
padding: 0;
box-sizing: border-box;
position: relative;
outline-style: none;
}
html,
body {
width: 100%;
height: 100%;
}
[hidden],
.hidden {
display: none !important;
visibility: hidden !important;
}
:root {
--font-size: 12px;
--line-height: 20px;
--font-regular: Verdana, Geneva, 'Dejavu Sans', Arial, Helvetica, sans-serif;
--font-monospace: Consolas, 'Liberation Mono', Menlo, Courier, monospace;
--font-size: 16px;
--line-height: 25px;
--site-max-width: 1200px;
--site-mobile-width: 800px;
@ -53,13 +31,12 @@ body {
--user-header: url('/images/pixel.png');
--accent-colour: #8559a5;
--header-accent-colour: var(--accent-colour);
--accent-colour: #ff9600;
--site-logo: url('/images/logos/imouto-halloween.png');
}
html {
scrollbar-color: var(--accent-colour) var(--background-colour);
accent-color: var(--accent-colour);
color-scheme: dark;
}
.main {
@ -102,7 +79,6 @@ html {
@include animations.css;
@include avatar.css;
@include bb.css;
@include confirm.css;
@include container.css;
@include eeprom.css;
@include embed.css;
@ -115,11 +91,12 @@ html {
@include main.css;
@include markdown.css;
@include messagebox.css;
@include navigation.css;
@include pagination.css;
@include permissions.css;
@include warning.css;
@include hljs.css;
@include _input/button.css;
@include _input/checkbox.css;
@include _input/colour.css;
@ -144,17 +121,13 @@ html {
@include changelog/log.css;
@include changelog/pagination.css;
@include comments/comment.css;
@include comments/comments.css;
@include comments/main.css;
@include forum/actions.css;
@include forum/categories.css;
@include forum/confirm.css;
@include forum/header.css;
@include forum/leaderboard.css;
@include forum/poll.css;
@include forum/post.css;
@include forum/priority.css;
@include forum/status.css;
@include forum/topics.css;
@ -164,6 +137,8 @@ html {
@include manage/_manage.css;
@include messages/messages.css;
@include news/container.css;
@include news/feeds.css;
@include news/list.css;

View file

@ -9,10 +9,10 @@
flex: 1 1 auto;
}
.manage__description {
font-size: .9em;
font-size: .875em;
margin: 1px 2px;
border-bottom: 1px solid var(--accent-colour);
padding: 2px 5px;
padding: 2px 4px;
}
@media (max-width: 800px) {

View file

@ -4,13 +4,13 @@
}
.manage__ban__title {
font-size: 1.4em;
font-size: 1.25em;
line-height: 1.5em;
padding: 0 4px;
}
.manage__ban__desc {
font-size: .9em;
font-size: .875em;
line-height: 1.5em;
font-style: italic;
border-bottom: 1px solid var(--accent-colour);

View file

@ -107,7 +107,7 @@
border-top: 1px solid var(--accent-colour);
}
.manage__bans__item__reason__title {
font-size: .9em;
font-size: .875em;
line-height: 1.5em;
font-style: italic;
}
@ -117,6 +117,6 @@
}
.manage__bans__item__noreason {
font-size: .9em;
font-size: .875em;
font-style: italic;
}

View file

@ -13,7 +13,8 @@
.manage__blacklist__textarea {
margin: 0;
padding: 5px 10px;
font-family: monospace;
font-family: var(--font-monospace);
font-feature-settings: 'ss07' 1;
width: 100%;
min-width: 100%;
max-width: 100%;

View file

@ -4,13 +4,11 @@
.manage__navigation__links {
display: flex;
flex-direction: column;
font-size: 1.2em;
}
.manage__navigation__link {
color: inherit;
text-decoration: none;
padding: 2px 5px;
margin-bottom: 2px;
padding: 2px 8px;
}
.manage__navigation__link:hover {
text-decoration: underline;

View file

@ -17,11 +17,11 @@
.manage__note__title {
flex-grow: 1;
flex-shrink: 1;
font-size: 1.4em;
line-height: 1.3em;
font-size: 1.375em;
line-height: 1.25em;
}
.manage__note__title__text {
padding: 2px 5px;
padding: 2px 6px;
}
.manage__note__title input {
width: 100%;
@ -73,7 +73,7 @@
.manage__note__nobody {
text-align: center;
font-size: .9em;
font-size: .875em;
font-style: italic;
}

View file

@ -24,9 +24,9 @@
.manage__notes__item__title {
flex-grow: 1;
flex-shrink: 1;
font-size: 1.4em;
line-height: 1.3em;
padding: 2px 5px;
font-size: 1.25em;
line-height: 1.25em;
padding: 2px 6px;
}
.manage__notes__item__title a {
color: inherit;
@ -96,7 +96,7 @@
.manage__notes__item__nobody {
text-align: center;
font-size: .9em;
font-size: .875em;
font-style: italic;
}

View file

@ -49,7 +49,7 @@
justify-content: center;
width: 100%;
height: 100%;
font-size: 1.5em;
font-size: 1.25em;
transition: background-color .2s;
}
.manage__role-item__icon__background {
@ -73,14 +73,9 @@
flex: 1 1 auto;
}
.manage__role-item__name {
font-size: 1.4em;
line-height: 1.4em;
}
.manage__role-item__details {
font-size: .9em;
line-height: 1.3em;
font-size: .875em;
line-height: 1.25em;
display: inline-flex;
align-items: center;
padding: 1px 0;
@ -90,11 +85,11 @@
border-radius: 10px;
background-color: var(--accent-colour);
box-shadow: 0 1px 4px #111;
padding: 2px 5px;
padding: 2px 6px;
}
.manage__role-item__title {
padding: 2px 5px;
padding: 2px 6px;
}
.manage__role-item__actions {

View file

@ -27,6 +27,7 @@
}
.manage-list-setting-key-text {
font-family: var(--font-monospace);
font-feature-settings: 'ss07' 1;
}
.manage-list-setting-type {
@ -53,7 +54,7 @@
border-radius: 5px;
font-weight: 700;
padding: 0 5px;
font-size: .9em;
font-size: .75em;
display: inline-block;
}
@ -63,6 +64,7 @@
}
.manage-list-setting-value-text {
font-family: var(--font-monospace);
font-feature-settings: 'ss07' 1;
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;

View file

@ -1,20 +1,21 @@
.manage__statistic {
border: 1px solid var(--accent-colour);
border-radius: 2px;
padding: 2px 5px;
padding: 2px 6px;
}
.manage__statistic__name {
font-size: 1.1em;
font-size: 1.125em;
line-height: 1.5em;
}
.manage__statistic__value {
text-align: right;
font-size: 1.4em;
font-size: 1.375em;
line-height: 1.5em;
font-feature-settings: 'ss01' 1, 'tnum' 1;
}
.manage__statistic__updated {
text-align: right;
font-size: .9em;
font-size: .75em;
font-style: italic;
line-height: 1.5em;
}

View file

@ -57,25 +57,26 @@
}
.manage__user-item__name {
font-size: 1.4em;
line-height: 1.4em;
font-size: 1.125em;
line-height: 1.5em;
max-width: 600px; /* whatever */
}
.manage__user-item__details {
font-size: .9em;
line-height: 1.3em;
font-size: .875em;
line-height: 1.25em;
display: inline-flex;
align-items: center;
}
.manage__user-item__detail {
border-radius: 10px;
border-radius: 16px;
background-color: var(--accent-colour);
box-shadow: 0 1px 4px #111;
padding: 3px 8px;
padding: 2px 8px;
pointer-events: initial;
margin: 2px;
font-feature-settings: 'ss01' 1, 'tnum' 1;
}
.manage__user-item__actions {
@ -88,7 +89,7 @@
width: 32px;
height: 32px;
line-height: 32px;
font-size: 1.5em;
font-size: 1.25em;
border-radius: 2px;
margin: 5px;
margin-right: 0;

View file

@ -4,13 +4,13 @@
}
.manage__warning__title {
font-size: 1.4em;
font-size: 1.25em;
line-height: 1.5em;
padding: 0 4px;
}
.manage__warning__desc {
font-size: .9em;
font-size: .875em;
line-height: 1.5em;
font-style: italic;
border-bottom: 1px solid var(--accent-colour);

View file

@ -1,5 +1,5 @@
.markdown {
line-height: 1.7em;
line-height: 1.5em;
}
.markdown a {
@ -53,7 +53,6 @@
.markdown code {
padding: .2em .4em;
margin: 0;
background-color: rgba(0, 0, 0, .7);
border-radius: 2px;
}
.markdown del code { text-decoration: inherit; }
@ -65,7 +64,6 @@
overflow: hidden;
line-height: inherit;
word-wrap: break-word;
background: transparent;
border: 0;
}
@ -80,8 +78,7 @@
.markdown h1, .markdown h2,
.markdown h3, .markdown h4,
.markdown h5, .markdown h6 {
margin-top: calc(var(--font-size) * 1.2);
margin-bottom: var(--font-size);
margin: calc(var(--font-size) * 0.875) 0;
font-weight: 700;
line-height: 1em;
}

View file

@ -17,4 +17,5 @@
display: flex;
justify-content: center;
padding: 5px;
gap: 5px;
}

View file

@ -0,0 +1,36 @@
.messages-actions-item {
display: flex;
align-items: center;
height: 30px;
margin: 1px;
color: #fff;
text-decoration: none;
transition: background-color .1s;
width: 100%;
border: 0;
background-color: inherit;
text-align: left;
font-size: 1rem;
}
.messages-actions-item:hover,
.messages-actions-item:focus {
background-color: #444f;
}
.messages-actions-item:active,
.messages-actions-item-current {
background-color: var(--accent-colour) !important;
}
.messages-actions-item[disabled] {
background-color: inherit !important;
opacity: .4;
}
.messages-actions-item-icon {
text-align: center;
width: 30px;
flex-grow: 0;
flex-shrink: 0;
}
.messages-actions-item-label {
flex-grow: 1;
flex-shrink: 1;
}

View file

@ -0,0 +1,26 @@
.messages-columns {
display: flex;
gap: 2px;
}
.messages-columns-sidebar {
width: 200px;
flex-shrink: 0;
flex-grow: 0;
}
.messages-columns-content {
flex-shrink: 1;
flex-grow: 1;
overflow: hidden;
}
@media (max-width: 800px) {
.messages-columns {
flex-direction: column;
}
.messages-columns-sidebar {
width: 100%;
}
}

View file

@ -0,0 +1,78 @@
.messages-entry {
color: inherit;
text-decoration: none;
display: flex;
flex-direction: column;
padding: 2px 4px;
gap: 4px;
overflow: hidden;
cursor: pointer;
}
.messages-entry-header {
display: flex;
border-bottom: 2px solid #9999;
gap: 2px;
}
.messages-entry-check {
flex-grow: 0;
flex-shrink: 0;
display: flex;
align-items: center;
justify-content: center;
width: 20px;
}
.messages-entry-check input {
display: block;
}
.messages-entry-unread {
flex-grow: 0;
flex-shrink: 0;
display: flex;
align-items: center;
justify-content: center;
width: 20px;
}
.messages-entry-unread-orb {
width: 8px;
height: 8px;
background-color: var(--accent-colour);
border-radius: 100%;
}
.messages-entry-author {
font-weight: bold;
border-bottom: 2px solid var(--user-colour, currentColor);
margin: 0 0 -2px;
flex-grow: 0;
flex-shrink: 1;
overflow: hidden;
white-space: nowrap;
}
.messages-entry-spacing {
flex-grow: 1;
flex-shrink: 1;
}
.messages-entry-datetime {
flex-grow: 0;
flex-shrink: 0;
color: #aaa;
align-self: flex-end;
}
.messages-entry-subject {
line-height: 1.5em;
color: #fff;
overflow: hidden;
}
.messages-entry-preview {
line-height: 1.5em;
color: #888;
overflow: hidden;
}
.messages-entry-preview .messages-entry-overflow {
display: -webkit-box;
-webkit-line-clamp: 2;
-webkit-box-orient: vertical;
}
.messages-entry-overflow {
overflow: hidden;
text-overflow: ellipsis;
}

View file

@ -0,0 +1,33 @@
.messages-folder {
margin: 1px;
display: flex;
flex-direction: column;
gap: 1px;
padding: 1px;
}
.messages-folder-item {
background-color: #161616;
transition: background-color .1s;
}
.messages-folder-item:nth-child(2n) {
background-color: #1f1f1f;
}
.messages-folder-item:hover,
.messages-folder-item:focus {
background-color: #262626;
}
.messages-folder-item:active,
.messages-folder-item-current {
background-color: var(--accent-colour) !important;
}
.messages-folder-notice {
text-align: center;
margin: 10px;
}
.messages-folder-notice-text {
font-size: 1.375em;
line-height: 1.5em;
}
.messages-folder .pagination {
margin-top: 2px;
}

View file

@ -0,0 +1,135 @@
.messages-message {
display: flex;
flex-direction: column;
gap: 10px;
padding: 10px;
}
.messages-message-snippet {
cursor: pointer;
font-size: .875em;
line-height: 1.5em;
color: #888;
gap: 5px;
opacity: .8;
transition: opacity .1s;
}
.messages-message-snippet:hover,
.messages-message-snippet:focus,
.messages-message-snippet:focus-within {
opacity: 1;
}
.messages-message-draft {
border-top: 2px solid var(--accent-colour) !important;
border-left: 2px solid var(--accent-colour) !important;
border-right: 2px solid var(--accent-colour);
border-bottom: 2px solid var(--accent-colour);
}
.messages-message-deleted {
border-top: 2px solid red;
border-left: 2px solid red;
border-right: 2px solid red !important;
border-bottom: 2px solid red !important;
}
.messages-message-overflow {
display: block;
overflow: hidden;
text-overflow: ellipsis;
}
.messages-message-header {
display: flex;
gap: 10px;
border-bottom: 1px #444 solid;
padding-bottom: 10px;
align-items: center;
}
.messages-message-sender-avatar {
flex-shrink: 0;
flex-grow: 0;
width: 40px;
height: 40px;
}
.messages-message-sender-avatar img {
object-fit: cover;
}
.messages-message-details {
display: flex;
flex-direction: column;
flex-shrink: 1;
flex-grow: 1;
overflow: hidden;
gap: 2px;
}
.messages-message-details-spacing {
flex-grow: 1;
flex-shrink: 1;
}
.messages-message-header-columns {
display: flex;
gap: 2px;
}
.messages-message-sender-name {
flex-grow: 0;
flex-shrink: 1;
overflow: hidden;
white-space: nowrap;
}
.messages-message-sender-name a {
color: inherit;
text-decoration: none;
font-weight: 700;
border-bottom: 2px solid var(--user-colour, currentColor);
}
.messages-message-datetime {
flex-shrink: 0;
flex-grow: 0;
align-self: flex-end;
padding-bottom: 2px;
}
.messages-message-addressee {
display: flex;
gap: 4px;
}
.messages-message-addressee-to {
flex-shrink: 0;
flex-grow: 0;
}
.messages-message-addressee-user {
flex-shrink: 1;
flex-grow: 0;
overflow: hidden;
white-space: nowrap;
}
.messages-message-addressee-user a {
color: inherit;
text-decoration: none;
font-weight: 700;
border-bottom: 2px solid var(--user-colour, currentColor);
}
.messages-message-subject {
line-height: 2em;
}
.messages-message-body {
line-height: 1.5em;
}
.messages-message-body p:first-child {
margin-top: 0 !important;
}
.messages-message-body p:last-child {
margin-bottom: 0 !important;
}
.messages-message-snippet-body {
display: -webkit-box;
-webkit-line-clamp: 2;
-webkit-box-orient: vertical;
overflow: hidden;
line-height: 1.5em;
}

View file

@ -0,0 +1,9 @@
@include messages/actions.css;
@include messages/columns.css;
@include messages/entry.css;
@include messages/folder.css;
@include messages/message.css;
@include messages/recipient.css;
@include messages/reply.css;
@include messages/sidebar.css;
@include messages/thread.css;

View file

@ -0,0 +1,17 @@
.messages-recipient {
display: flex;
flex-direction: column;
}
.messages-recipient-avatar {
display: flex;
justify-content: center;
padding: 10px;
}
.messages-recipient-name {
padding: 5px;
}
.messages-recipient-name-input {
width: 100%;
}

View file

@ -0,0 +1,52 @@
.messages-reply-form {
display: flex;
flex-direction: column;
width: 100%;
gap: 5px;
padding: 5px;
}
.messages-reply-subject-input {
width: 100%;
}
.messages-reply-body-input {
min-width: 100%;
max-width: 100%;
min-height: 100px;
}
.messages-reply-compose .messages-reply-body-input {
min-height: 300px;
}
.messages-reply-actions {
display: flex;
padding: 1px;
gap: 1px;
}
.messages-reply-action {
background-color: transparent;
border: 0;
display: block;
padding: 5px 10px;
color: inherit;
text-decoration: none;
transition: background-color .2s;
border-radius: 3px;
cursor: pointer;
}
.messages-reply-action:hover,
.messages-reply-action:focus {
background-color: rgba(0, 0, 0, .2);
}
.messages-reply-options {
display: flex;
align-items: center;
justify-content: space-between;
}
.messages-reply-settings {
display: flex;
align-items: center;
gap: 5px;
}

View file

@ -0,0 +1,11 @@
.messages-sidebar {
position: sticky;
top: 0;
display: flex;
flex-direction: column;
gap: 2px;
}
.messages-sidebar-button {
text-align: center;
padding: 10px;
}

View file

@ -0,0 +1,5 @@
.messages-thread {
display: flex;
flex-direction: column;
gap: 1px;
}

View file

@ -1,85 +0,0 @@
.navigation {
margin: 2px 0;
width: 100%;
display: flex;
border-width: 0;
border-color: var(--text-colour);
border-style: solid;
border-top-width: 1px;
align-items: flex-start;
justify-content: center;
}
.navigation--top {
border-top-width: 0;
border-bottom-width: 1px;
align-items: flex-end;
}
.navigation--top .navigation__option {
border-top-width: 1px;
border-bottom-width: 0;
}
.navigation__option {
list-style: none;
background-color: #c9bbcc;
border: 1px solid var(--text-colour);
border-top-width: 0;
flex-grow: 0;
}
.navigation__option:not(:first-child) { border-left-width: 0; }
.navigation__option--selected {
background-color: var(--accent-colour);
top: -1px;
}
.navigation__option--selected:not(:first-child) {
margin-left: -1px;
border-left-width: 1px;
}
.navigation__link {
display: block;
padding: 2px 1em;
color: var(--text-colour);
text-decoration: none;
}
.navigation__link:hover, .navigation__link:focus { color: #609; }
@media (max-width: 1000px) {
.navigation {
border: none;
align-items: center;
flex-direction: column;
}
.navigation--left {
justify-content: left;
padding-left: 25px;
}
.navigation--right {
justify-content: right;
padding-right: 25px;
}
.navigation--top .navigation__option--selected { top: 1px; }
.navigation__link {
padding: 10px 15px;
font-size: 1.5em;
}
.navigation__option {
background-color: var(--accent-colour);
width: 100%;
border: none;
flex-grow: 1;
margin-bottom: 1px;
}
.navigation__option--selected {
background-color: #a586c3;
top: 0;
}
.navigation__option--selected .navigation__link {
padding: 3px 1em;
}
}

View file

@ -1,6 +1,6 @@
.news__feeds {
display: grid;
grid-template-columns: 1fr 1fr;
grid-template-columns: 1fr;
grid-gap: 2px;
padding: 2px;
}
@ -9,7 +9,7 @@
display: flex;
color: inherit;
text-decoration: none;
font-size: 1.5em;
font-size: 1.25em;
line-height: 32px;
height: 32px;
transition: background-color .2s;

View file

@ -44,7 +44,7 @@
.news__post__username {
color: inherit;
font-size: 1.4em;
font-size: 1.25em;
line-height: 1.5em;
text-decoration: none;
}
@ -53,14 +53,14 @@
}
.news__post__date {
font-size: 1.1em;
font-size: .875em;
line-height: 1.5em;
}
.news__post__category {
color: inherit;
text-decoration: none;
font-size: 1.1em;
font-size: 1.125em;
line-height: 1.5em;
margin: 6px 0;
}
@ -69,7 +69,6 @@
}
.news__post__text {
line-height: 1.2em;
flex: 1 1 auto;
word-wrap: break-word;
overflow: hidden;
@ -101,4 +100,4 @@
width: 50px;
height: 50px;
}
}
}

View file

@ -23,8 +23,8 @@
}
.news__preview__title h1 {
font-size: 2em;
line-height: 1.5em;
font-weight: 700;
line-height: 1.375em;
}
.news__preview__attrs {
@ -32,7 +32,7 @@
flex-shrink: 0;
display: flex;
gap: 4px;
font-size: .9em;
font-size: .875em;
}
.news__preview__attr {
@ -62,7 +62,7 @@
}
.news__preview__content {
line-height: 1.4em;
line-height: 1.5em;
word-wrap: break-word;
overflow: hidden;
}
@ -73,5 +73,5 @@
}
.news__preview__link {
font-size: .9em;
font-size: .875em;
}

View file

@ -23,9 +23,7 @@
.pagination__link {
display: flex;
min-width: 40px;
font-size: 1.2em;
line-height: 1.5em;
padding: 3px 10px 4px;
min-height: 36px;
text-align: center;
text-decoration: none;
background-color: var(--background-colour);
@ -37,13 +35,17 @@
align-items: center;
justify-content: center;
flex: 1 0 auto;
font-feature-settings: 'ss01' 1, 'tnum' 1;
}
.pagination__link:not(:last-child) { margin-right: 1px; }
.pagination__link--disabled { --accent-colour: #555; }
.pagination__link--first, .pagination__link--last,
.pagination__link--next, .pagination__link--prev {
padding-top: 5px;
.pagination__link:not(:last-child) {
margin-right: 1px;
}
.pagination__link--disabled {
--accent-colour: #555;
}
.pagination__link--current,
.pagination__link:not(.pagination__link--disabled):hover,
.pagination__link:not(.pagination__link--disabled):active,
@ -53,5 +55,7 @@
}
@media (max-width: 800px) {
.pagination__section--pages { display: none; }
.pagination__section--pages {
display: none;
}
}

View file

@ -6,12 +6,12 @@
.permissions__line {
display: flex;
font-size: .9em;
line-height: 1.7em;
font-size: .8rem;
line-height: 1.5rem;
}
.permissions__line--header {
font-size: 1.2em;
line-height: 1.4em;
font-size: 1rem;
line-height: 1.25rem;
border-bottom: 1px solid rgba(255, 255, 255, .1);
padding-bottom: 1px;
font-weight: 700;

View file

@ -1,30 +1,26 @@
.profile__accounts__content {
display: flex;
flex-direction: column;
padding: 2px 5px;
padding: 2px 6px;
}
.profile__accounts__item {
padding-bottom: 5px;
padding-bottom: 4px;
}
.profile__accounts__item:not(:last-child) {
border-bottom: 1px solid #222;
}
.profile__accounts__notice {
font-size: 1.2em;
line-height: 1.5em;
text-align: center;
padding: 10px;
}
.profile__accounts__title {
font-size: .9em;
line-height: 1.8em;
font-size: .875em;
line-height: 1.5em;
}
.profile__accounts__value {
font-size: 1.2em;
line-height: 1.2em;
color: inherit;
text-decoration: none;
}

View file

@ -1,5 +1,5 @@
.profile__birthdate__content {
padding: 2px 5px;
padding: 2px 6px;
}
.profile__birthdate__select {
min-width: auto;
@ -8,6 +8,6 @@
display: inline-block;
}
.profile__birthdate__title {
font-size: .9em;
line-height: 1.8em;
font-size: .875em;
line-height: 1.75em;
}

View file

@ -7,14 +7,14 @@
}
.profile__forum-activity__leader {
font-size: .9em;
margin: 0 5px;
font-size: .875em;
margin: 0 4px;
}
.profile__forum-activity .forum__category__icon {
width: 30px;
height: 30px;
font-size: 1.5em;
font-size: 1.25em;
line-height: 1.5em;
flex: 0 0 30px;
}

View file

@ -14,20 +14,18 @@
padding: 1px;
}
.profile__guidelines__line--header {
font-size: 1.2em;
line-height: 1.5em;
font-weight: 700;
font-weight: 600;
margin-bottom: 2px;
border-bottom: 1px solid var(--accent-colour);
padding-bottom: 2px;
}
.profile__guidelines__line:not(&--header) {
margin-left: 1.3em;
.profile__guidelines__line:not(.profile__guidelines__line--header) {
margin-left: 1.25em;
list-style: square;
}
.profile__guidelines__emphasis {
font-weight: 700;
font-weight: 600;
}
.profile__guidelines__link {

View file

@ -19,15 +19,6 @@
background-blend-mode: multiply;
}
.profile__header--has-header {
--profile-header-overlay-start: var(--background-colour-translucent-3);
}
.profile__header--has-header .profile__header__background {
background: var(--user-header) center / cover no-repeat;
background-blend-mode: unset;
}
.profile__header__avatar {
display: flex;
}
@ -78,15 +69,6 @@
flex: 1 1 auto;
}
.profile__header__details__relation {
font-variant: all-small-caps;
background: var(--profile-header-overlay-stop);
border-radius: 2px;
line-height: 1.2em;
padding: 1px 5px 4px;
cursor: default;
}
.profile__header__options {
min-height: 62px;
background-color: var(--profile-header-overlay-stop);
@ -119,12 +101,11 @@
min-width: 130px;
}
.profile__header__stat__name {
font-size: .9em;
font-variant: small-caps;
font-size: .875em;
cursor: inherit;
}
.profile__header__stat__value {
font-size: 1.3em;
font-size: 1.125em;
text-align: right;
cursor: inherit;
display: block;
@ -132,6 +113,9 @@
.profile__header__stat--date .profile__header__stat__value {
text-align: left;
}
.profile__header__stat:not(.profile__header__stat--date) .profile__header__stat__value {
font-feature-settings: 'ss01' 1, 'tnum' 1;
}
.profile__header__stat--link {
cursor: pointer;
}
@ -140,17 +124,18 @@
.profile__header__stat--link:focus,
.profile__header__stat--link:active,
.profile__header__stat--active {
padding-bottom: 8px;
border-bottom: 2px solid var(--accent-colour);
}
.profile__header__username {
font-size: 2em;
line-height: 1.5em;
font-size: 1.75em;
line-height: 1.125em;
}
.profile__header__title {
font-size: .9em;
line-height: 1.2em;
font-size: .875em;
line-height: 1.25em;
}
.profile__header__country {
@ -158,9 +143,9 @@
align-items: center;
}
.profile__header__country__name {
font-size: .9em;
font-size: .875em;
margin-left: 4px;
line-height: 1.2em;
line-height: 1.25em;
}
@media (max-width: 800px) {

View file

@ -12,15 +12,15 @@
}
.profile__warnings__datetime {
font-size: .9em;
font-size: .875em;
line-height: 1.5em;
font-style: italic;
padding-top: 2px;
}
.profile__warnings__body {
padding: 0 5px;
padding: 0 6px;
}
.profile__warnings__body p {
line-height: 1.4em;
line-height: 1.375em;
}

View file

@ -11,7 +11,6 @@
overflow: hidden;
border: 1px solid transparent;
border-radius: 5px;
font-size: 1.1em;
margin: 1px 1px 1px 0;
}
@ -33,5 +32,5 @@
}
.search__category__content {
padding: 2px 5px;
padding: 2px 6px;
}

View file

@ -4,7 +4,8 @@
overflow: hidden;
border: 1px solid transparent;
border-radius: 5px;
font-size: 1.5em;
font-family: var(--font-regular);
font-size: 1.125em;
}
.search__input__background {
background-color: var(--background-colour-translucent-9);
@ -24,7 +25,7 @@
border: 0;
background-color: transparent;
color: #fff;
padding: 5px 10px;
padding: 4px 12px;
font-size: inherit;
}

Some files were not shown because too many files have changed in this diff Show more