@mideind/netskrafl-react 1.0.0-beta.6 → 1.0.0-beta.8

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (69) hide show
  1. package/README.md +1 -1
  2. package/dist/cjs/css/netskrafl.css +1508 -215
  3. package/dist/cjs/index.js +9018 -7764
  4. package/dist/cjs/index.js.map +1 -1
  5. package/dist/esm/css/netskrafl.css +1508 -215
  6. package/dist/esm/index.js +9017 -7764
  7. package/dist/esm/index.js.map +1 -1
  8. package/dist/types.d.ts +4 -1
  9. package/package.json +13 -2
  10. package/.eslintignore +0 -8
  11. package/.eslintrc.json +0 -13
  12. package/rollup.config.js +0 -67
  13. package/src/components/index.ts +0 -2
  14. package/src/components/netskrafl/Netskrafl.stories.tsx +0 -66
  15. package/src/components/netskrafl/Netskrafl.tsx +0 -155
  16. package/src/components/netskrafl/Netskrafl.types.ts +0 -7
  17. package/src/components/netskrafl/index.ts +0 -2
  18. package/src/css/fonts.css +0 -4
  19. package/src/css/glyphs.css +0 -223
  20. package/src/css/main.css +0 -4
  21. package/src/css/skrafl-explo.css +0 -6636
  22. package/src/fonts/glyphicons-regular.eot +0 -0
  23. package/src/fonts/glyphicons-regular.ttf +0 -0
  24. package/src/fonts/glyphicons-regular.woff +0 -0
  25. package/src/index.ts +0 -4
  26. package/src/messages/messages.json +0 -1576
  27. package/src/mithril/actions.ts +0 -319
  28. package/src/mithril/bag.ts +0 -65
  29. package/src/mithril/bestdisplay.ts +0 -74
  30. package/src/mithril/blankdialog.ts +0 -94
  31. package/src/mithril/board.ts +0 -339
  32. package/src/mithril/buttons.ts +0 -303
  33. package/src/mithril/challengedialog.ts +0 -186
  34. package/src/mithril/channel.ts +0 -162
  35. package/src/mithril/chat.ts +0 -228
  36. package/src/mithril/components.ts +0 -496
  37. package/src/mithril/dragdrop.ts +0 -219
  38. package/src/mithril/elopage.ts +0 -202
  39. package/src/mithril/friend.ts +0 -227
  40. package/src/mithril/game.ts +0 -1378
  41. package/src/mithril/gameview.ts +0 -111
  42. package/src/mithril/globalstate.ts +0 -33
  43. package/src/mithril/i18n.ts +0 -187
  44. package/src/mithril/localstorage.ts +0 -133
  45. package/src/mithril/login.ts +0 -122
  46. package/src/mithril/logo.ts +0 -323
  47. package/src/mithril/main.ts +0 -755
  48. package/src/mithril/mithril.ts +0 -29
  49. package/src/mithril/model.ts +0 -855
  50. package/src/mithril/movelistitem.ts +0 -226
  51. package/src/mithril/page.ts +0 -856
  52. package/src/mithril/playername.ts +0 -91
  53. package/src/mithril/promodialog.ts +0 -82
  54. package/src/mithril/recentlist.ts +0 -148
  55. package/src/mithril/request.ts +0 -52
  56. package/src/mithril/review.ts +0 -634
  57. package/src/mithril/rightcolumn.ts +0 -398
  58. package/src/mithril/searchbutton.ts +0 -118
  59. package/src/mithril/statsdisplay.ts +0 -109
  60. package/src/mithril/tabs.ts +0 -169
  61. package/src/mithril/tile.ts +0 -145
  62. package/src/mithril/twoletter.ts +0 -76
  63. package/src/mithril/types.ts +0 -384
  64. package/src/mithril/userinfodialog.ts +0 -171
  65. package/src/mithril/util.ts +0 -304
  66. package/src/mithril/wait.ts +0 -246
  67. package/src/mithril/wordcheck.ts +0 -102
  68. package/tsconfig.json +0 -28
  69. package/vite.config.ts +0 -12
@@ -1,169 +0,0 @@
1
- /*
2
- Tabs.ts
3
-
4
- Utility functions to set up tabbed views
5
-
6
- Copyright (C) 2024 Miðeind ehf.
7
- Author: Vilhjalmur Thorsteinsson
8
-
9
- The Creative Commons Attribution-NonCommercial 4.0
10
- International Public License (CC-BY-NC 4.0) applies to this software.
11
- For further information, see https://github.com/mideind/Netskrafl
12
-
13
- */
14
-
15
- import { IView } from "./types";
16
- import { m } from "./mithril";
17
- import { getUrlVars } from "./util";
18
-
19
- const ROUTE_PREFIX = "/page#!";
20
- const ROUTE_PREFIX_LEN = ROUTE_PREFIX.length;
21
-
22
- export type TabVnode = m.VnodeDOM<
23
- Record<string, any>,
24
- {
25
- selected: number;
26
- lis: HTMLElement[];
27
- ids: string[];
28
- }
29
- >;
30
-
31
- export function makeTabs(view: IView, id: string, createFunc: ((vnode: TabVnode) => void) | undefined, wireHrefs: boolean, vnode: TabVnode) {
32
- // When the tabs are displayed for the first time, wire'em up
33
- let tabdiv = document.getElementById(id);
34
- if (!tabdiv)
35
- return;
36
- // Add bunch of jQueryUI compatible classes
37
- tabdiv.setAttribute("class", "ui-tabs ui-widget ui-widget-content ui-corner-all");
38
- const tabul = document.querySelector("#" + id + " > ul");
39
- if (tabul) {
40
- tabul.setAttribute("class", "ui-tabs-nav ui-helper-reset ui-helper-clearfix ui-widget-header ui-corner-all");
41
- tabul.setAttribute("role", "tablist");
42
- }
43
- let tablist = document.querySelectorAll("#" + id + " > ul > li > a") as NodeListOf<HTMLElement>;
44
- let tabitems = document.querySelectorAll("#" + id + " > ul > li") as NodeListOf<HTMLElement>;
45
- let ids: string[] = [];
46
- let lis: HTMLElement[] = []; // The <li> elements
47
- // Iterate over the <a> elements inside the <li> elements inside the <ul>
48
- for (let i = 0; i < tablist.length; i++) {
49
- const href = tablist[i].getAttribute("href");
50
- if (!href) continue;
51
- ids.push(href.slice(1));
52
- // Decorate the <a> elements
53
- tablist[i].onclick = (ev) => { selectTab(vnode, i); ev.preventDefault(); };
54
- tablist[i].removeAttribute("href");
55
- tablist[i].setAttribute("class", "ui-tabs-anchor sp"); // Single-page marker
56
- tablist[i].setAttribute("role", "presentation");
57
- // Also decorate the <li> elements
58
- lis.push(tabitems[i]);
59
- tabitems[i].setAttribute("class", "ui-state-default ui-corner-top");
60
- tabitems[i].setAttribute("role", "tab");
61
- tabitems[i].onmouseover = (ev) => {
62
- (ev.currentTarget as HTMLElement).classList.toggle("ui-state-hover", true);
63
- };
64
- tabitems[i].onmouseout = (ev) => {
65
- (ev.currentTarget as HTMLElement).classList.toggle("ui-state-hover", false);
66
- };
67
- // Find the tab's content <div>
68
- const tabcontent = document.getElementById(ids[i]);
69
- // Decorate it
70
- if (tabcontent) {
71
- tabcontent.setAttribute("class", "ui-tabs-panel ui-widget-content ui-corner-bottom");
72
- tabcontent.setAttribute("role", "tabpanel");
73
- }
74
- }
75
- // Save the list of tab identifiers
76
- vnode.state.ids = ids;
77
- // Save the list of <li> elements
78
- vnode.state.lis = lis;
79
- // Select the first tab by default
80
- vnode.state.selected = 0;
81
- if (wireHrefs) {
82
- // Wire all hrefs that point to single-page URLs
83
- const model = view.model;
84
- const clickURL = (ev: Event, href: string) => {
85
- let uri = href.slice(ROUTE_PREFIX_LEN); // Cut the /page#!/ prefix off the route
86
- let qix = uri.indexOf("?");
87
- let route = (qix >= 0) ? uri.slice(0, qix) : uri;
88
- let qparams = uri.slice(route.length + 1);
89
- let params = qparams.length ? getUrlVars(qparams) : {};
90
- m.route.set(route, params);
91
- if (window.history)
92
- window.history.pushState({}, "", href); // Enable the back button
93
- ev.preventDefault();
94
- };
95
- const clickUserPrefs = (ev: Event) => {
96
- if (model?.state?.userId)
97
- // Don't show the userprefs if no user logged in
98
- view.pushDialog("userprefs");
99
- ev.preventDefault();
100
- };
101
- const clickTwoLetter = (ev: Event) => {
102
- selectTab(vnode, 2); // Select tab number 2
103
- ev.preventDefault();
104
- };
105
- const clickNewBag = (ev: Event) => {
106
- selectTab(vnode, 3); // Select tab number 3
107
- ev.preventDefault();
108
- };
109
- let anchors = tabdiv.querySelectorAll("a");
110
- for (let i = 0; i < anchors.length; i++) {
111
- let a = anchors[i];
112
- let href = a.getAttribute("href");
113
- if (href && href.slice(0, ROUTE_PREFIX_LEN) == ROUTE_PREFIX) {
114
- // Single-page URL: wire it up (as if it had had an m.route.Link on it)
115
- a.onclick = (ev) => clickURL(ev, href);
116
- }
117
- else
118
- if (href && href === "$$userprefs$$") {
119
- // Special marker indicating that this link invokes
120
- // a user preference dialog
121
- a.onclick = clickUserPrefs;
122
- }
123
- else
124
- if (href && href === "$$twoletter$$") {
125
- // Special marker indicating that this link invokes
126
- // the two-letter word list or the opponents tab
127
- a.onclick = clickTwoLetter;
128
- }
129
- else
130
- if (href && href === "$$newbag$$") {
131
- // Special marker indicating that this link invokes
132
- // the explanation of the new bag
133
- a.onclick = clickNewBag;
134
- }
135
- }
136
- }
137
- // If a createFunc was specified, run it now
138
- if (createFunc)
139
- createFunc(vnode);
140
- // Finally, make the default tab visible and hide the others
141
- updateTabVisibility(vnode);
142
- }
143
-
144
- function updateTabVisibility(vnode: TabVnode) {
145
- // Shows the tab that is currently selected,
146
- // i.e. the one whose index is in vnode.state.selected
147
- const selected: number = vnode.state.selected;
148
- const lis = vnode.state.lis;
149
- vnode.state.ids.map((id: string, i: number) => {
150
- document.getElementById(id)?.setAttribute("style", "display: " +
151
- (i == selected ? "block" : "none"));
152
- lis[i].classList.toggle("ui-tabs-active", i === selected);
153
- lis[i].classList.toggle("ui-state-active", i === selected);
154
- }
155
- );
156
- }
157
-
158
- export function selectTab(vnode: TabVnode, i: number) {
159
- // Selects the tab with the given index under the tab control vnode
160
- vnode.state.selected = i;
161
- updateTabVisibility(vnode);
162
- }
163
-
164
- export function updateSelection(vnode: TabVnode) {
165
- // Select a tab according to the ?tab= query parameter in the current route
166
- var tab = m.route.param("tab");
167
- if (tab !== undefined)
168
- selectTab(vnode, parseInt(tab) || 0);
169
- }
@@ -1,145 +0,0 @@
1
- /*
2
-
3
- Tile.ts
4
-
5
- Tile component
6
-
7
- Copyright (C) 2025 Miðeind ehf.
8
- Author: Vilhjalmur Thorsteinsson
9
-
10
- The Creative Commons Attribution-NonCommercial 4.0
11
- International Public License (CC-BY-NC 4.0) applies to this software.
12
- For further information, see https://github.com/mideind/Netskrafl
13
-
14
- */
15
-
16
- import { EXTRA_WIDE_LETTERS, IView, WIDE_LETTERS } from "./types";
17
- import { VnodeAttrs, ComponentFunc, m, MithrilMouseEvent, MithrilTouchEvent } from "./mithril";
18
- import { nbsp } from "./util";
19
- import { startDrag } from "./dragdrop";
20
-
21
- interface IAttributes {
22
- view: IView;
23
- coord: string;
24
- opponent: boolean;
25
- }
26
-
27
- export const Tile: ComponentFunc<IAttributes> = (initialVnode) => {
28
- // Display a tile on the board or in the rack
29
- const { view, coord } = initialVnode.attrs;
30
- const model = view.model;
31
-
32
- const dragHandler = (ev: MithrilMouseEvent | MithrilTouchEvent) => {
33
- // Start a drag-and-drop process, for mouse or touch interaction
34
- startDrag(ev, (_, target) => {
35
- // Drop handler
36
- const game = model.game;
37
- if (!game) return;
38
- const id = target.id;
39
- if (!id) return;
40
- let targetCoord: string = "";
41
- if (id === "board-background") {
42
- // Drop on the background: transfer back to the rack
43
- targetCoord = "R1";
44
- } else if (id.startsWith("sq_")) {
45
- // Drop on a board square
46
- targetCoord = id.slice(3);
47
- }
48
- if (targetCoord) {
49
- try {
50
- game.attemptMove(coord, targetCoord);
51
- view.updateScale();
52
- // Make sure that Mithril draws the updated state
53
- m.redraw();
54
- } catch (e) {
55
- // Something went wrong: display a console error
56
- console.error(e);
57
- }
58
- }
59
- });
60
- ev.redraw = false;
61
- return false;
62
- };
63
-
64
- return {
65
- view: (vnode) => {
66
- const { opponent } = vnode.attrs;
67
- const game = model.game;
68
- if (!game) return undefined;
69
- const isRackTile = coord[0] === 'R';
70
- // A single tile, on the board or in the rack
71
- const t = game.tiles[coord];
72
- let classes = [".tile"];
73
- let attrs: VnodeAttrs = {};
74
- if (t.tile === '?')
75
- classes.push("blanktile");
76
- if (EXTRA_WIDE_LETTERS.includes(t.letter))
77
- // Extra wide letter: handle specially
78
- classes.push("extra-wide");
79
- else if (WIDE_LETTERS.includes(t.letter))
80
- // Wide letter: handle specially
81
- classes.push("wide");
82
- if (isRackTile || t.draggable) {
83
- // Rack tile, or at least a draggable one
84
- classes.push(opponent ? "freshtile" : "racktile");
85
- if (isRackTile && game.showingDialog === "exchange") {
86
- // Rack tile, and we're showing the exchange dialog
87
- if (t.xchg)
88
- // Chosen as an exchange tile
89
- classes.push("xchgsel");
90
- // Exchange dialog is live: add a click handler for the
91
- // exchange state
92
- attrs.onclick = (ev: Event) => {
93
- // Toggle the exchange status of this tile
94
- t.xchg = !t.xchg;
95
- ev.preventDefault();
96
- };
97
- }
98
- } else if (t.freshtile) {
99
- // A fresh tile on the board that has
100
- // just been played by the opponent
101
- classes.push("freshtile");
102
- }
103
- if (t.index) {
104
- // Make fresh or highlighted tiles appear sequentally by animation
105
- const ANIMATION_STEP = 150; // Milliseconds
106
- const delay = (t.index * ANIMATION_STEP).toString() + "ms";
107
- attrs.style = `animation-delay: ${delay}`;
108
- }
109
- if (coord === game.selectedSq)
110
- // Currently selected square
111
- classes.push("sel"); // Blinks red
112
- if (t.highlight !== undefined) {
113
- // highlight0 is the local player color
114
- // highlight1 is the remote player color
115
- classes.push("highlight" + t.highlight);
116
- /*
117
- if (t.player == parseInt(t.highlight))
118
- // This tile was originally laid down by the other player
119
- classes.push("dim");
120
- */
121
- }
122
- if (game.showingDialog === null && !game.over) {
123
- if (t.draggable) {
124
- attrs.onmousedown = dragHandler;
125
- attrs.ontouchstart = dragHandler;
126
- /*
127
- attrs.onclick = (ev: MouseEvent) => {
128
- // When clicking a tile, make it selected (blinking)
129
- if (coord === game.selectedSq)
130
- // Clicking again: deselect
131
- game.selectedSq = null;
132
- else
133
- game.selectedSq = coord;
134
- ev.stopPropagation();
135
- return false;
136
- };
137
- */
138
- }
139
- }
140
- return m(classes.join("."), attrs,
141
- [t.letter === " " ? nbsp() : t.letter, m(".letterscore", t.score)]
142
- );
143
- }
144
- };
145
- }
@@ -1,76 +0,0 @@
1
- /*
2
-
3
- Twoletter.ts
4
-
5
- Two Letter Word display component
6
-
7
- Copyright (C) 2024 Miðeind ehf.
8
- Author: Vilhjalmur Thorsteinsson
9
-
10
- The Creative Commons Attribution-NonCommercial 4.0
11
- International Public License (CC-BY-NC 4.0) applies to this software.
12
- For further information, see https://github.com/mideind/Netskrafl
13
-
14
- */
15
-
16
- import { IView } from "./types";
17
- import { Vnode, ComponentFunc, m, VnodeChildren } from "./mithril";
18
- import { ts } from "./i18n";
19
-
20
- interface IAttributes {
21
- view: IView;
22
- }
23
-
24
- export const TwoLetter: ComponentFunc<IAttributes> = (initialVnode) => {
25
-
26
- // The two-letter-word list tab
27
- const view = initialVnode.attrs.view;
28
- const model = view.model;
29
- let page = 0;
30
-
31
- function renderWord(bold: boolean, w: string): Vnode {
32
- // For the first two-letter word in each group,
33
- // render the former letter in bold
34
- if (!bold)
35
- return m(".twoletter-word", w);
36
- if (page == 0)
37
- return m(".twoletter-word", [m("b", w[0]), w[1]]);
38
- else
39
- return m(".twoletter-word", [w[0], m("b", w[1])]);
40
- }
41
-
42
- return {
43
- view: () => {
44
- if (!model.game) return;
45
- const game = model.game;
46
- const twoLetters = game.twoLetterWords();
47
- const twoLetterWords = twoLetters[page];
48
- const twoLetterList: VnodeChildren = [];
49
- for (const tw of twoLetterWords) {
50
- const twl = tw[1];
51
- const sublist: VnodeChildren = [];
52
- for (let j = 0; j < twl.length; j++)
53
- sublist.push(renderWord(j == 0, twl[j]));
54
- twoLetterList.push(
55
- m(".twoletter-group", sublist)
56
- );
57
- }
58
- return m(".twoletter",
59
- {
60
- // Switch between pages when clicked
61
- onclick: () => { page = 1 - page; },
62
- style: "z-index: 6" // Appear on top of board on mobile
63
- },
64
- // Show the requested page
65
- m(".twoletter-area" + (game.showClock() ? ".with-clock" : ""),
66
- {
67
- title: page == 0 ?
68
- ts("Smelltu til að raða eftir seinni staf") :
69
- ts("Smelltu til að raða eftir fyrri staf")
70
- },
71
- twoLetterList
72
- )
73
- );
74
- }
75
- };
76
- };