Skip to content

Commit 9810b9e

Browse files
Cyperghostdtdesign
andauthored
Migrate StyleAction functions to Command/API-Endpoints (#6429)
* Migrate the function to change the style to a command * API endpoint to get style chooser and change style * Minor improvements --------- Co-authored-by: Alexander Ebert <ebert@woltlab.com>
1 parent d1b6005 commit 9810b9e

12 files changed

Lines changed: 302 additions & 103 deletions

File tree

Lines changed: 17 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
/**
2+
* Change the style of the current user.
3+
*
4+
* @author Olaf Braun
5+
* @copyright 2001-2025 WoltLab GmbH
6+
* @license GNU Lesser General Public License <http://opensource.org/licenses/lgpl-license.php>
7+
* @since 6.3
8+
*/
9+
10+
import { prepareRequest } from "WoltLabSuite/Core/Ajax/Backend";
11+
import { fromInfallibleApiRequest } from "../Result";
12+
13+
export function changeStyle(styleId: number): Promise<[]> {
14+
return fromInfallibleApiRequest(() => {
15+
return prepareRequest(`${window.WSC_RPC_API_URL}core/styles/${styleId}/change`).post().fetchAsJson();
16+
});
17+
}
Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,21 @@
1+
/**
2+
* Change the style of the current user.
3+
*
4+
* @author Olaf Braun
5+
* @copyright 2001-2025 WoltLab GmbH
6+
* @license GNU Lesser General Public License <http://opensource.org/licenses/lgpl-license.php>
7+
* @since 6.3
8+
*/
9+
10+
import { prepareRequest } from "WoltLabSuite/Core/Ajax/Backend";
11+
import { fromInfallibleApiRequest } from "../Result";
12+
13+
type Response = {
14+
template: string;
15+
};
16+
17+
export function getStyleChooser(): Promise<Response> {
18+
return fromInfallibleApiRequest(() => {
19+
return prepareRequest(`${window.WSC_RPC_API_URL}core/styles/chooser`).get().fetchAsJson();
20+
});
21+
}

ts/WoltLabSuite/Core/Controller/Style/Changer.ts

Lines changed: 27 additions & 42 deletions
Original file line numberDiff line numberDiff line change
@@ -7,70 +7,55 @@
77
* @woltlabExcludeBundle all
88
*/
99

10-
import * as Ajax from "../../Ajax";
11-
import * as Language from "../../Language";
12-
import UiDialog from "../../Ui/Dialog";
13-
import { DialogCallbackSetup } from "../../Ui/Dialog/Data";
10+
import { getPhrase } from "../../Language";
11+
import { changeStyle } from "WoltLabSuite/Core/Api/Styles/ChangeStyle";
12+
import { dialogFactory } from "WoltLabSuite/Core/Component/Dialog";
13+
import { promiseMutex } from "WoltLabSuite/Core/Helper/PromiseMutex";
14+
import { getStyleChooser } from "WoltLabSuite/Core/Api/Styles/GetStyleChooser";
1415

1516
class ControllerStyleChanger {
1617
/**
1718
* Adds the style changer to the bottom navigation.
1819
*/
1920
constructor() {
2021
document.querySelectorAll(".jsButtonStyleChanger").forEach((link: HTMLAnchorElement) => {
21-
link.addEventListener("click", (ev) => this.showDialog(ev));
22+
link.addEventListener(
23+
"click",
24+
promiseMutex((ev) => this.showDialog(ev)),
25+
);
2226
});
2327
}
2428

2529
/**
2630
* Loads and displays the style change dialog.
2731
*/
28-
showDialog(event: MouseEvent): void {
32+
async showDialog(event: MouseEvent): Promise<void> {
2933
event.preventDefault();
3034

31-
UiDialog.open(this);
32-
}
35+
const { template } = await getStyleChooser();
36+
const dialog = dialogFactory().fromHtml(template).withoutControls();
37+
38+
dialog.content.querySelectorAll(".styleList > li").forEach((style: HTMLLIElement) => {
39+
style.classList.add("pointer");
40+
style.addEventListener("click", (event) => {
41+
event.preventDefault();
42+
43+
promiseMutex(() => this.#changeStyle(style));
44+
});
45+
});
3346

34-
_dialogSetup(): ReturnType<DialogCallbackSetup> {
35-
return {
36-
id: "styleChanger",
37-
options: {
38-
disableContentPadding: true,
39-
title: Language.get("wcf.style.changeStyle"),
40-
},
41-
source: {
42-
data: {
43-
actionName: "getStyleChooser",
44-
className: "wcf\\data\\style\\StyleAction",
45-
},
46-
after: (content) => {
47-
content.querySelectorAll(".styleList > li").forEach((style: HTMLLIElement) => {
48-
style.classList.add("pointer");
49-
style.addEventListener("click", (ev) => this.click(ev));
50-
});
51-
},
52-
},
53-
};
47+
dialog.show(getPhrase("wcf.style.changeStyle"));
5448
}
5549

5650
/**
5751
* Changes the style and reloads current page.
5852
*/
59-
private click(event: MouseEvent): void {
60-
event.preventDefault();
53+
async #changeStyle(style: HTMLLIElement): Promise<void> {
54+
const styleId = parseInt(style.dataset.styleId!, 10);
6155

62-
const listElement = event.currentTarget as HTMLLIElement;
56+
await changeStyle(styleId);
6357

64-
Ajax.apiOnce({
65-
data: {
66-
actionName: "changeStyle",
67-
className: "wcf\\data\\style\\StyleAction",
68-
objectIDs: [listElement.dataset.styleId],
69-
},
70-
success: function () {
71-
window.location.reload();
72-
},
73-
});
58+
window.location.reload();
7459
}
7560
}
7661

@@ -89,5 +74,5 @@ export function setup(): void {
8974
* Loads and displays the style change dialog.
9075
*/
9176
export function showDialog(event: MouseEvent): void {
92-
controllerStyleChanger.showDialog(event);
77+
void controllerStyleChanger.showDialog(event);
9378
}

wcfsetup/install/files/js/WoltLabSuite/Core/Api/Styles/ChangeStyle.js

Lines changed: 18 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

wcfsetup/install/files/js/WoltLabSuite/Core/Api/Styles/GetStyleChooser.js

Lines changed: 18 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

wcfsetup/install/files/js/WoltLabSuite/Core/Controller/Style/Changer.js

Lines changed: 18 additions & 42 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

wcfsetup/install/files/lib/bootstrap/com.woltlab.wcf.php

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -169,6 +169,8 @@ static function (\wcf\event\endpoint\ControllerCollecting $event) {
169169
$event->register(new \wcf\system\endpoint\controller\core\styles\DisableStyle());
170170
$event->register(new \wcf\system\endpoint\controller\core\styles\EnableStyle());
171171
$event->register(new \wcf\system\endpoint\controller\core\styles\SetStyleAsDefault());
172+
$event->register(new \wcf\system\endpoint\controller\core\styles\ChangeStyle());
173+
$event->register(new \wcf\system\endpoint\controller\core\styles\GetStyleChooser());
172174
$event->register(new \wcf\system\endpoint\controller\core\users\options\DeleteOption());
173175
$event->register(new \wcf\system\endpoint\controller\core\users\options\DisableOption());
174176
$event->register(new \wcf\system\endpoint\controller\core\users\options\EnableOption());
Lines changed: 61 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,61 @@
1+
<?php
2+
3+
namespace wcf\command\style;
4+
5+
use wcf\data\style\Style;
6+
use wcf\data\user\UserAction;
7+
use wcf\event\style\StyleChanged;
8+
use wcf\system\event\EventHandler;
9+
use wcf\system\style\StyleHandler;
10+
use wcf\system\WCF;
11+
12+
/**
13+
* Change the style for the current user.
14+
*
15+
* @author Olaf Braun
16+
* @copyright 2001-2025 WoltLab GmbH
17+
* @license GNU Lesser General Public License <http://opensource.org/licenses/lgpl-license.php>
18+
* @since 6.3
19+
*/
20+
final class ChangeStyle
21+
{
22+
public function __construct(
23+
private readonly Style $style
24+
) {}
25+
26+
public function __invoke(): void
27+
{
28+
StyleHandler::getInstance()->changeStyle($this->style->styleID);
29+
if (StyleHandler::getInstance()->getStyle()->styleID !== $this->style->styleID) {
30+
// style could not be changed
31+
return;
32+
}
33+
34+
if (WCF::getUser()->userID) {
35+
$this->saveUserStyle($this->style->styleID, (bool)$this->style->isDefault);
36+
} else {
37+
$this->saveGuestStyle($this->style->styleID, (bool)$this->style->isDefault);
38+
}
39+
40+
$event = new StyleChanged($this->style);
41+
EventHandler::getInstance()->fire($event);
42+
}
43+
44+
private function saveUserStyle(int $styleID, bool $isDefaultStyle): void
45+
{
46+
(new UserAction([WCF::getUser()], 'update', [
47+
'data' => [
48+
'styleID' => $isDefaultStyle ? 0 : $styleID,
49+
],
50+
]))->executeAction();
51+
}
52+
53+
private function saveGuestStyle(int $styleID, bool $isDefaultStyle): void
54+
{
55+
if ($isDefaultStyle) {
56+
WCF::getSession()->unregister('styleID');
57+
} else {
58+
WCF::getSession()->register('styleID', $styleID);
59+
}
60+
}
61+
}

0 commit comments

Comments
 (0)