Skip to content

Commit 73ac0cc

Browse files
committed
okay we are good, some reorganization and time to fix codes and etc
1 parent 466879a commit 73ac0cc

File tree

6 files changed

+230
-217
lines changed

6 files changed

+230
-217
lines changed

src/ts/VMhandlers.ts

Lines changed: 171 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,21 +1,43 @@
1-
import { VM } from "./main";
1+
export let VM: CollabVMClient | null = null;
22
import CollabVMClient from "./protocol/CollabVMClient";
33
import { Format } from './format.js';
4+
import { elements } from "./main";
5+
import { TheI18n } from "./i18n/i18n";
6+
import TurnStatus from './protocol/TurnStatus.js';
7+
import * as kblayout from './keyboard/layout.js';
8+
import { User, chatMessage } from './protocol/User.js';
9+
import VoteStatus from './protocol/VoteStatus.js';
10+
import * as Config from "../../config.json";
411

512
let expectedClose: boolean = false;
613

7-
async function openVM(vm: typeof VM): Promise<void> {
14+
15+
let turnInterval: number | undefined = undefined;
16+
let voteInterval: number | undefined = undefined;
17+
18+
const enableOSK = (enable: boolean) => {
19+
const theme = `simple-keyboard hg-theme-default cvmDark ${enable ? '' : 'cvmDisabled'} hg-layout-default`;
20+
[kblayout.keyboard, kblayout.keyboardControlPad, kblayout.keyboardArrows, kblayout.keyboardNumPad, kblayout.keyboardNumPadEnd].forEach((part) => {
21+
part.setOptions({
22+
theme: theme
23+
});
24+
});
25+
26+
if (enable) kblayout.updateOSKStyle();
27+
};
28+
29+
export async function openVM(elements:any, vm: typeof VM): Promise<void> {
830
// If there's an active VM it must be closed before opening another
931
if (VM !== null) return;
1032
expectedClose = false;
11-
// Set hash*
33+
// Set hash
1234
//@ts-ignore
1335
location.hash = vm.id;
1436
// Create the client
37+
//@ts-ignore
1538
VM = new CollabVMClient(vm.url);
1639

1740
// Register event listeners
18-
1941
VM!.on('chat', (username, message) => chatMessage(username, message));
2042
VM!.on('adduser', (user) => addUser(user));
2143
VM!.on('flag', () => flag());
@@ -63,17 +85,21 @@ async function openVM(vm: typeof VM): Promise<void> {
6385
await VM!.WaitForOpen();
6486

6587
// Connect to node
88+
//@ts-ignore
6689
chatMessage('', `<b>${vm.id}</b><hr>`);
6790
let username = Config.Auth.Enabled ? (auth!.account?.username ?? null) : localStorage.getItem('username');
91+
//@ts-ignore
6892
let connected = await VM.connect(vm.id, username);
93+
//@ts-ignore
6994
elements.adminInputVMID.value = vm.id;
95+
//@ts-ignore
7096
w.VMName = vm.id;
7197
if (!connected) {
72-
// just give up
7398
closeVM();
7499
throw new Error('Failed to connect to node');
75100
}
76101
// Set the title
102+
//@ts-ignore
77103
document.title = Format('{0} - {1}', vm.id, TheI18n.GetString(I18nStringKey.kGeneric_CollabVM));
78104
// Append canvas
79105
elements.vmDisplay.appendChild(VM!.canvas);
@@ -83,7 +109,7 @@ async function openVM(vm: typeof VM): Promise<void> {
83109
return;
84110
}
85111

86-
function closeVM() {
112+
export function closeVM() {
87113
if (VM === null) return;
88114
expectedClose = true;
89115
// Close the VM
@@ -131,3 +157,142 @@ function closeVM() {
131157
elements.accountDropdownMenuLink.style.display = "none";
132158
}
133159
}
160+
161+
function addUser(user: User) {
162+
let olduser = users.find((u) => u.user === user);
163+
if (olduser !== undefined) elements.userlist.removeChild(olduser.element);
164+
let tr = document.createElement('tr');
165+
tr.setAttribute('data-cvm-turn', '-1');
166+
let td = document.createElement('td');
167+
let flagSpan = document.createElement('span');
168+
let usernameSpan = document.createElement('span');
169+
flagSpan.classList.add("userlist-flag");
170+
usernameSpan.classList.add("userlist-username");
171+
td.appendChild(flagSpan);
172+
if (user.countryCode !== null) {
173+
flagSpan.innerHTML = getFlagEmoji(user.countryCode);
174+
flagSpan.title = TheI18n.getCountryName(user.countryCode);
175+
};
176+
td.appendChild(usernameSpan);
177+
usernameSpan.innerText = user.username;
178+
switch (user.rank) {
179+
case Rank.Admin:
180+
tr.classList.add('user-admin');
181+
break;
182+
case Rank.Moderator:
183+
tr.classList.add('user-moderator');
184+
break;
185+
case Rank.Registered:
186+
tr.classList.add('user-registered');
187+
break;
188+
case Rank.Unregistered:
189+
tr.classList.add('user-unregistered');
190+
break;
191+
}
192+
if (user.username === w.username) tr.classList.add('user-current');
193+
tr.appendChild(td);
194+
let u = { user: user, element: tr, usernameElement: usernameSpan, flagElement: flagSpan };
195+
if (rank === Rank.Admin || rank === Rank.Moderator) userModOptions(u);
196+
elements.userlist.appendChild(tr);
197+
if (olduser !== undefined) olduser.element = tr;
198+
else users.push(u);
199+
elements.onlineusercount.innerHTML = VM!.getUsers().length.toString();
200+
}
201+
202+
function remUser(user: User) {
203+
let olduser = users.findIndex((u) => u.user === user);
204+
if (olduser !== undefined) elements.userlist.removeChild(users[olduser].element);
205+
elements.onlineusercount.innerHTML = VM!.getUsers().length.toString();
206+
users.splice(olduser, 1);
207+
}
208+
209+
function flag() {
210+
for (let user of users.filter(u => u.user.countryCode !== null)) {
211+
user.flagElement.innerHTML = getFlagEmoji(user.user.countryCode!);
212+
user.flagElement.title = TheI18n.getCountryName(user.user.countryCode!);
213+
}
214+
}
215+
216+
function userRenamed(oldname: string, newname: string, selfrename: boolean) {
217+
let user = users.find((u) => u.user.username === newname);
218+
if (user) {
219+
user.usernameElement.innerHTML = newname;
220+
}
221+
if (selfrename) {
222+
w.username = newname;
223+
elements.username.innerText = newname;
224+
localStorage.setItem('username', newname);
225+
}
226+
}
227+
228+
function turnUpdate(status: TurnStatus) {
229+
// Clear all turn data
230+
turn = -1;
231+
VM!.canvas.classList.remove('focused', 'waiting');
232+
clearInterval(turnInterval);
233+
turnTimer = 0;
234+
for (const user of users) {
235+
user.element.classList.remove('user-turn', 'user-waiting');
236+
user.element.setAttribute('data-cvm-turn', '-1');
237+
}
238+
elements.turnBtnText.innerHTML = TheI18n.GetString(I18nStringKey.kVMButtons_TakeTurn);
239+
enableOSK(false);
240+
241+
if (status.user !== null) {
242+
let el = users.find((u) => u.user === status.user)!.element;
243+
el!.classList.add('user-turn');
244+
el!.setAttribute('data-cvm-turn', '0');
245+
}
246+
for (const user of status.queue) {
247+
let el = users.find((u) => u.user === user)!.element;
248+
el!.classList.add('user-waiting');
249+
el.setAttribute('data-cvm-turn', status.queue.indexOf(user).toString(10));
250+
}
251+
if (status.user?.username === w.username) {
252+
turn = 0;
253+
turnTimer = status.turnTime! / 1000;
254+
elements.turnBtnText.innerHTML = TheI18n.GetString(I18nStringKey.kVMButtons_EndTurn);
255+
VM!.canvas.classList.add('focused');
256+
enableOSK(true);
257+
}
258+
if (status.queue.some((u) => u.username === w.username)) {
259+
turn = status.queue.findIndex((u) => u.username === w.username) + 1;
260+
turnTimer = status.queueTime! / 1000;
261+
elements.turnBtnText.innerHTML = TheI18n.GetString(I18nStringKey.kVMButtons_EndTurn);
262+
VM!.canvas.classList.add('waiting');
263+
}
264+
if (turn === -1) elements.turnstatus.innerText = '';
265+
else {
266+
//@ts-ignore
267+
turnInterval = setInterval(() => turnIntervalCb(), 1000);
268+
setTurnStatus();
269+
}
270+
sortUserList();
271+
}
272+
273+
function voteUpdate(status: VoteStatus) {
274+
clearInterval(voteInterval);
275+
elements.voteResetPanel.style.display = 'block';
276+
elements.voteYesLabel.innerText = status.yesVotes.toString();
277+
elements.voteNoLabel.innerText = status.noVotes.toString();
278+
voteTimer = Math.floor(status.timeToEnd / 1000);
279+
//@ts-ignore
280+
voteInterval = setInterval(() => updateVoteEndTime(), 1000);
281+
updateVoteEndTime();
282+
}
283+
284+
function updateVoteEndTime() {
285+
voteTimer--;
286+
elements.voteTimeText.innerText = TheI18n.GetString(I18nStringKey.kVM_VoteForResetTimer, voteTimer);
287+
if (voteTimer === 0) clearInterval(voteInterval);
288+
}
289+
290+
function voteEnd() {
291+
clearInterval(voteInterval);
292+
elements.voteResetPanel.style.display = 'none';
293+
}
294+
295+
function turnIntervalCb() {
296+
turnTimer--;
297+
setTurnStatus();
298+
}
File renamed without changes.

src/ts/i18n.ts renamed to src/ts/i18n/i18n.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,7 @@
1-
import { StringLike } from './StringLike';
2-
import { Format } from './format';
1+
import { StringLike } from '../StringLike';
2+
import { Format } from '../format';
33
import { Emitter, Unsubscribe, createNanoEvents } from 'nanoevents';
4-
import Config from '../../config.json';
4+
import Config from '../../../config.json';
55

66
/// All string keys.
77
export enum I18nStringKey {

0 commit comments

Comments
 (0)