themes registration, starting extensions API

ui-refactor
Valerie 2021-06-19 18:23:44 -04:00
parent 8e38189560
commit b697856c4e
13 changed files with 202 additions and 34 deletions

25
.vscode/tasks.json vendored 100644
View File

@ -0,0 +1,25 @@
{
"version": "2.0.0",
"tasks": [
{
"label": "tsc watch",
"type": "npm",
"script": "compile:watch",
"isBackground": true,
"group": {
"kind": "build",
"isDefault": true
},
"presentation": {
"reveal": "never",
"echo": false,
"focus": false,
"panel": "dedicated"
},
"problemMatcher": {
"base": "$tsc-watch",
"applyTo": "allDocuments"
}
}
]
}

View File

View File

@ -0,0 +1,8 @@
import { registerTheme } from '@theme';
import chalk from 'chalk'
registerTheme("default", {});
registerTheme("high contrast", {
selected: chalk.ansi256(250).inverse
});

33
lib/aliases.mjs 100644
View File

@ -0,0 +1,33 @@
import path from 'path';
const moduleAliases = {
"@theme": "./out/src/ui/Theme.js"
};
const getAliases = () => {
const base = process.cwd();
const aliases = moduleAliases || {};
const absoluteAliases = Object.keys(aliases).reduce((acc, key) =>
aliases[key][0] === '/'
? acc
: { ...acc, [key]: 'file:///' + path.join(base, aliases[key]) },
aliases)
return absoluteAliases;
}
const isAliasInSpecifier = (path, alias) => {
return path.indexOf(alias) === 0
&& (path.length === alias.length || path[alias.length] === '/')
}
const aliases = getAliases();
export const resolve = (specifier, parentModuleURL, defaultResolve) => {
const alias = Object.keys(aliases).find((key) => isAliasInSpecifier(specifier, key));
const newSpecifier = alias === undefined
? specifier
: path.join(aliases[alias], specifier.substr(alias.length));
return defaultResolve(newSpecifier, parentModuleURL);
}

View File

@ -11,22 +11,25 @@
"@types/uuid": "^8.3.0",
"bonjour": "^3.5.0",
"chalk": "^4.1.1",
"deepmerge": "^4.2.2",
"faker": "^5.5.3",
"frigid": "^1.3.8",
"fs-extra": "^10.0.0",
"get-port": "^5.1.1",
"logger": "^0.0.1",
"module-alias": "^2.2.2",
"neo-blessed": "^0.2.0",
"printable-characters": "^1.0.42",
"sisteransi": "^1.0.5",
"typescript": "^4.3.2",
"uuid": "^8.3.2",
"walk-sync": "^3.0.0",
"ws": "^7.4.6",
"yarn": "^1.22.10"
},
"scripts": {
"compile:watch": "tsc --watch",
"start": "node --enable-source-maps out/index.js",
"start": "node --loader ./lib/aliases.mjs --enable-source-maps out/src/index.js",
"dev": "supervisor -w out -n exit -t -k --exec yarn -- start",
"prod": "git fetch && git pull && yarn && tsc && yarn start"
}

View File

@ -7,6 +7,7 @@ import { ChopTreeTask } from './tasks/ChopTreeTask.js';
import { Game } from './Game.js';
import { render } from './ui/UI.js';
import { Memory } from './Memory.js';
import { getTheme } from './ui/Theme.js';
const LABORS = {
CUT_TREE: Symbol('CUT_TREE'),
@ -127,7 +128,7 @@ export class Pawn extends Serializable implements Tickable {
if(this.job) {
return this.job.status;
} else {
return this.awake ? chalk.bold.black('IDLE') : chalk.blue('RESTING')
return this.awake ? getTheme().status.idle('IDLE') : getTheme().status.self('RESTING')
}
}

View File

@ -23,7 +23,19 @@ export function progressbar(completion: number, width: number, style: Progressba
} else if(style === ProgressbarStyle.progress) {
chalkFn = getTheme().progressBar.normal;
}
const chars = [' ', '▏', '▎', '▍', '▌', '▋', '▊', '▉', '█'];
const chars = [
'\u0020',
'\u258f',
'\u258e',
'\u258d',
'\u258c',
'\u258b',
'\u258a',
'\u2589',
'\u2588'
];
let str = '';
for(let i = 0; i < width; i ++) {
const remainder = Math.floor(Math.min(Math.max(0, (completion * width) - i), 1) * 8);

View File

@ -58,7 +58,7 @@ export default class Time extends Serializable implements Renderable {
render() {
const sym = (this.hour >= 6 && this.hour < 20) ?
chalk.ansi256(226).bgAnsi256(27)(' ') :
chalk.ansi256(226).bgAnsi256(27)(' ') :
chalk.ansi256(254).bgAnsi256(17)(' ☾ ')
return `${sym} ${
@ -74,8 +74,6 @@ export default class Time extends Serializable implements Renderable {
this.normalizedYear
}`)
}`;
// return '☾' || '☼';
}
toString() {

View File

@ -1,15 +1,30 @@
import { Game } from './Game.js';
import { render } from './ui/UI.js';
import { ensureDirSync } from 'fs-extra';
import { parse } from 'path';
import { lstatSync } from 'fs';
import { parse, resolve } from 'path';
import walkSync from 'walk-sync';
import { fileURLToPath } from 'url';
const saveFile = process.argv[2] || 'data/world01.json';
ensureDirSync(parse(saveFile).dir);
// TODO move render logic into game, so that the ui doesnt exist until the game does...
// maybe, i mean, an argument could be made for not that, because the game
// isnt necessarily the entire thing, its just one instance of a save file.
// But probably the initial menu screens will be their own thing entirely.
const game = Game.create(saveFile);
render(game);
const extensionsPath = resolve(parse(fileURLToPath(import.meta.url)).dir, '../content');
const extensions = walkSync(extensionsPath)
.map(path => resolve(extensionsPath, path))
.filter(path => lstatSync(path).isFile())
.filter(path => parse(path).ext === '.js')
.map(path => import(path));
Promise.all(extensions).then((extensions) => {
// TODO move render logic into game, so that the ui doesnt exist until the game does...
// maybe, i mean, an argument could be made for not that, because the game
// isnt necessarily the entire thing, its just one instance of a save file.
// But probably the initial menu screens will be their own thing entirely.
const game = Game.create(saveFile);
render(game);
});

View File

@ -6,6 +6,8 @@
// instead of upsampling them to 16m codes.
import chalk from 'chalk';
chalk.level = 2;
import merge from 'deepmerge';
import log from '../log.js';
type StyleFunction = (text: string) => string;
@ -36,11 +38,11 @@ export type Theme = {
status: {
idle: StyleFunction,
self: StyleFunction,
work: StyleFunction
}
}
export const defaultTheme: Theme = {
export const backupTheme: Theme = {
header: chalk.ansi256(255).bold,
subheader: chalk.ansi256(243).bold,
normal: chalk.ansi256(243),
@ -63,27 +65,31 @@ export const defaultTheme: Theme = {
buckets: [.1, .25, .95]
},
normal: chalk.bgAnsi256(235).ansi256(243)
},
status: {
idle: chalk.ansi256(243),
self: chalk.ansi256(45),
work: chalk.ansi256(208)
}
}
const debugStyle = chalk.ansi256(213);
export const debugTheme: Theme = {
header: debugStyle.inverse,
subheader: debugStyle,
normal: debugStyle,
selected: debugStyle.inverse,
hotkey: debugStyle,
tab: {
normal: debugStyle,
selected: debugStyle.inverse,
},
border: {
focused: '#ff88ff',
normal: '#ff00ff'
},
progressBar: defaultTheme.progressBar
export type ThemeName = string;
let currentTheme = backupTheme;
const themes: Map<ThemeName, Theme> = new Map();
export function registerTheme(name: ThemeName, theme: Partial<Theme>) {
log.info('registering theme', name)
themes.set(name, merge(backupTheme, theme));
}
export function setTheme(name: ThemeName): void {
if(!themes.has(name)) return;
currentTheme = themes.get(name);
// TODO reset borders and other weird shit that wont just update on a re-render
}
export function getTheme(): Theme {
return defaultTheme;
return currentTheme;
}

0
test.js 100644
View File

View File

@ -6,9 +6,13 @@
"allowSyntheticDefaultImports": true,
"outDir": "out",
"declaration": true,
"sourceMap": true
"sourceMap": true,
"paths": {
"@theme": ["./src/ui/Theme"]
}
},
"include": [
"src/**/*.ts"
"src/**/*.ts",
"content/**/*.ts"
]
}

View File

@ -18,6 +18,11 @@
version "5.5.6"
resolved "https://registry.yarnpkg.com/@types/faker/-/faker-5.5.6.tgz#039b700a9d8ad9150ecc842bf5e717e2027b6f75"
"@types/minimatch@^3.0.3", "@types/minimatch@^3.0.4":
version "3.0.4"
resolved "https://registry.yarnpkg.com/@types/minimatch/-/minimatch-3.0.4.tgz#f0ec25dbf2f0e4b18647313ac031134ca5b24b21"
integrity sha512-1z8k4wzFnNjVK/tlxvrWuK5WMt6mydWWP7+zvH5eFep4oj+UkrfiJTRtjCeBXNpwaA/FYqqtb4/QS4ianFpIRA==
"@types/node@*":
version "15.12.2"
resolved "https://registry.npmjs.org/@types/node/-/node-15.12.2.tgz"
@ -36,6 +41,11 @@ array-flatten@^2.1.0:
version "2.1.2"
resolved "https://registry.yarnpkg.com/array-flatten/-/array-flatten-2.1.2.tgz#24ef80a28c1a893617e2149b0c6d0d788293b099"
balanced-match@^1.0.0:
version "1.0.2"
resolved "https://registry.yarnpkg.com/balanced-match/-/balanced-match-1.0.2.tgz#e83e3a7e3f300b34cb9d87f615fa0cbf357690ee"
integrity sha512-3oSeUO0TMV67hN1AmbXsK4yaqU7tjiHlbxRDZOpH0KW9+CeX4bRAaX0Anxt0tx2MrpRpWwQaPwIlISEJhYU5Pw==
bonjour@^3.5.0:
version "3.5.0"
resolved "https://registry.yarnpkg.com/bonjour/-/bonjour-3.5.0.tgz#8e890a183d8ee9a2393b3844c691a42bcf7bc9f5"
@ -47,6 +57,14 @@ bonjour@^3.5.0:
multicast-dns "^6.0.1"
multicast-dns-service-types "^1.1.0"
brace-expansion@^1.1.7:
version "1.1.11"
resolved "https://registry.yarnpkg.com/brace-expansion/-/brace-expansion-1.1.11.tgz#3c7fcbf529d87226f3d2f52b966ff5271eb441dd"
integrity sha512-iCuPHDFgrHX7H2vEI/5xpz07zSHB00TpugqhmYtVmMO6518mCuRMoOYFldEBl0g187ufozdaHgWKcYFb61qGiA==
dependencies:
balanced-match "^1.0.0"
concat-map "0.0.1"
buffer-indexof@^1.0.0:
version "1.1.1"
resolved "https://registry.yarnpkg.com/buffer-indexof/-/buffer-indexof-1.1.1.tgz#52fabcc6a606d1a00302802648ef68f639da268c"
@ -75,6 +93,11 @@ color-name@~1.1.4:
version "1.1.4"
resolved "https://registry.npmjs.org/color-name/-/color-name-1.1.4.tgz"
concat-map@0.0.1:
version "0.0.1"
resolved "https://registry.yarnpkg.com/concat-map/-/concat-map-0.0.1.tgz#d8a96bd77fd68df7793a73036a3ba0d5405d477b"
integrity sha1-2Klr13/Wjfd5OnMDajug1UBdR3s=
deep-equal@^1.0.1:
version "1.1.1"
resolved "https://registry.yarnpkg.com/deep-equal/-/deep-equal-1.1.1.tgz#b5c98c942ceffaf7cb051e24e1434a25a2e6076a"
@ -86,6 +109,11 @@ deep-equal@^1.0.1:
object-keys "^1.1.1"
regexp.prototype.flags "^1.2.0"
deepmerge@^4.2.2:
version "4.2.2"
resolved "https://registry.yarnpkg.com/deepmerge/-/deepmerge-4.2.2.tgz#44d2ea3679b8f4d4ffba33f03d865fc1e7bf4955"
integrity sha512-FJ3UgI4gIl+PHZm53knsuSFpE+nESMr7M4v9QcgB7S63Kj/6WqMiFQJpBBYz1Pt+66bZpP3Q7Lye0Oo9MPKEdg==
define-properties@^1.1.3:
version "1.1.3"
resolved "https://registry.yarnpkg.com/define-properties/-/define-properties-1.1.3.tgz#cf88da6cbee26fe6db7094f61d870cbd84cee9f1"
@ -109,6 +137,11 @@ dns-txt@^2.0.2:
dependencies:
buffer-indexof "^1.0.0"
ensure-posix-path@^1.1.0:
version "1.1.1"
resolved "https://registry.yarnpkg.com/ensure-posix-path/-/ensure-posix-path-1.1.1.tgz#3c62bdb19fa4681544289edb2b382adc029179ce"
integrity sha512-VWU0/zXzVbeJNXvME/5EmLuEj2TauvoaTz6aFYK1Z92JCBlDlZ3Gu0tuGR42kpW1754ywTs+QB0g5TP0oj9Zaw==
faker@^5.5.3:
version "5.5.3"
resolved "https://registry.npmjs.org/faker/-/faker-5.5.3.tgz"
@ -196,6 +229,26 @@ logger@^0.0.1:
version "0.0.1"
resolved "https://registry.yarnpkg.com/logger/-/logger-0.0.1.tgz#cb08171f8a6f6f674b8499dadf50bed4befb72c4"
matcher-collection@^2.0.1:
version "2.0.1"
resolved "https://registry.yarnpkg.com/matcher-collection/-/matcher-collection-2.0.1.tgz#90be1a4cf58d6f2949864f65bb3b0f3e41303b29"
integrity sha512-daE62nS2ZQsDg9raM0IlZzLmI2u+7ZapXBwdoeBUKAYERPDDIc0qNqA8E0Rp2D+gspKR7BgIFP52GeujaGXWeQ==
dependencies:
"@types/minimatch" "^3.0.3"
minimatch "^3.0.2"
minimatch@^3.0.2, minimatch@^3.0.4:
version "3.0.4"
resolved "https://registry.yarnpkg.com/minimatch/-/minimatch-3.0.4.tgz#5166e286457f03306064be5497e8dbb0c3d32083"
integrity sha512-yJHVQEhyqPLUTgt9B83PXu6W3rx4MvvHvSUvToogpwoGDOUQ+yDrR0HRot+yOCdCO7u4hX3pWft6kWBBcqh0UA==
dependencies:
brace-expansion "^1.1.7"
module-alias@^2.2.2:
version "2.2.2"
resolved "https://registry.yarnpkg.com/module-alias/-/module-alias-2.2.2.tgz#151cdcecc24e25739ff0aa6e51e1c5716974c0e0"
integrity sha512-A/78XjoX2EmNvppVWEhM2oGk3x4lLxnkEA4jTbaK97QKSDjkIoOsKQlfylt/d3kKKi596Qy3NP5XrXJ6fZIC9Q==
multicast-dns-service-types@^1.1.0:
version "1.1.0"
resolved "https://registry.yarnpkg.com/multicast-dns-service-types/-/multicast-dns-service-types-1.1.0.tgz#899f11d9686e5e05cb91b35d5f0e63b773cfc901"
@ -265,6 +318,16 @@ uuid@^8.3.2:
version "8.3.2"
resolved "https://registry.yarnpkg.com/uuid/-/uuid-8.3.2.tgz#80d5b5ced271bb9af6c445f21a1a04c606cefbe2"
walk-sync@^3.0.0:
version "3.0.0"
resolved "https://registry.yarnpkg.com/walk-sync/-/walk-sync-3.0.0.tgz#67f882925021e20569a1edd560b8da31da8d171c"
integrity sha512-41TvKmDGVpm2iuH7o+DAOt06yyu/cSHpX3uzAwetzASvlNtVddgIjXIb2DfB/Wa20B1Jo86+1Dv1CraSU7hWdw==
dependencies:
"@types/minimatch" "^3.0.4"
ensure-posix-path "^1.1.0"
matcher-collection "^2.0.1"
minimatch "^3.0.4"
ws@^7.4.6:
version "7.4.6"
resolved "https://registry.yarnpkg.com/ws/-/ws-7.4.6.tgz#5654ca8ecdeee47c33a9a4bf6d28e2be2980377c"