diff --git a/package.json b/package.json
index 6efe614..ea1eb2c 100644
--- a/package.json
+++ b/package.json
@@ -8,15 +8,11 @@
"build": "svelte-kit build",
"preview": "svelte-kit preview",
"lint": "prettier --check . && eslint --ignore-path .gitignore .",
- "format": "prettier --write .",
- "storybook": "storybook-server",
- "vitebook:dev": "vitebook dev",
- "vitebook:build": "vitebook build",
- "vitebook:preview": "vitebook preview"
+ "format": "prettier --write ."
},
"devDependencies": {
"@sveltejs/adapter-static": "^1.0.0-next.28",
- "@sveltejs/kit": "^1.0.0-next.288",
+ "@sveltejs/kit": "^1.10.0",
"@sveltejs/vite-plugin-svelte": "^1.0.0-next.38",
"@testing-library/svelte": "^3.1.1",
"@testing-library/user-event": "^13.5.0",
@@ -26,18 +22,13 @@
"prettier": "~2.5.1",
"prettier-plugin-svelte": "^2.6.0",
"showdown": "^2.0.3",
- "standard-version": "^9.3.2",
- "storybook-builder-vite": "0.1.21",
- "svelte": "^3.46.4",
+ "svelte": "^3.55.1",
"typescript": "^4.9.5",
"vitest": "^0.9.3",
"vitest-svelte-kit": "^0.0.6"
},
"dependencies": {
"@reduxjs/toolkit": "^1.9.3",
- "@storybook/addon-essentials": "^6.4.19",
- "@storybook/addon-svelte-csf": "^1.1.0",
- "@storybook/svelte": "^6.4.21",
"@sveltejs/adapter-node": "^1.0.0-next.0",
"@yanick/updeep-remeda": "^2.1.0",
"chota": "^0.8.0",
@@ -46,13 +37,11 @@
"redux": "^4.1.2",
"remeda": "^1.1.0",
"reselect": "^4.1.5",
- "rollup-plugin-analyzer": "^4.0.0",
"svelte-chota": "^1.8.6",
"svelte-knobby": "^0.3.4",
"svelte-moveable": "^0.20.0",
"ts-action": "^11.0.0",
- "updux": "link:/home/yanick/work/javascript/updux-js/",
- "webpack": "5"
+ "vite": "^4.1.4"
},
"prettier": {
"svelteSortOrder": "options-markup-scripts-styles",
diff --git a/src/app.html b/src/app.html
index 245305c..c7c366d 100644
--- a/src/app.html
+++ b/src/app.html
@@ -1,12 +1,12 @@
-
-
-
-
- %svelte.head%
-
-
- %svelte.body%
-
+
+
+
+
+ %sveltekit.head%
+
+
+ %sveltekit.body%
+
diff --git a/src/lib/components/ShipEdit/Carrier/Squadron.svelte b/src/lib/components/ShipEdit/Carrier/Squadron.svelte
index 4b17645..388ee55 100644
--- a/src/lib/components/ShipEdit/Carrier/Squadron.svelte
+++ b/src/lib/components/ShipEdit/Carrier/Squadron.svelte
@@ -14,23 +14,22 @@
import Section from "$lib/components/Section/index.svelte";
import Field from "$lib/components/Field/index.svelte";
import ShipItem from "$lib/components/ShipItem/index.svelte";
- import { squadronTypes } from "$lib/shipDux/carrier.js";
+ import { squadronTypes } from "$lib/shipDux/carrier";
const types = squadronTypes.map(({ type }) => type);
export let id = 1;
export let type = types[0].type;
- export let reqs= {};
+ export let reqs = {};
export let { dispatch } = getContext("ship");
- $: console.log(type)
-$: dispatch.setSquadronType({type, id});
-
+ $: console.log(type);
+ $: dispatch.setSquadronType({ type, id });
diff --git a/src/lib/components/ShipEdit/Weaponry/AddWeapon.svelte b/src/lib/components/ShipEdit/Weaponry/AddWeapon.svelte
index e72af04..fac5724 100644
--- a/src/lib/components/ShipEdit/Weaponry/AddWeapon.svelte
+++ b/src/lib/components/ShipEdit/Weaponry/AddWeapon.svelte
@@ -1,18 +1,18 @@
-
+
diff --git a/src/lib/shipDux/carrier.ts b/src/lib/shipDux/carrier.ts
index d4592f3..04048f1 100644
--- a/src/lib/shipDux/carrier.ts
+++ b/src/lib/shipDux/carrier.ts
@@ -2,78 +2,78 @@ import { PayloadAction, createSlice } from "@reduxjs/toolkit";
import { reqs, Reqs } from "./reqs";
type Squadron = {
- type: string;
- reqs: Reqs;
+ type: string;
+ reqs: Reqs;
};
const initialState = {
- bays: 0,
- squadrons: [] as Squadron[],
- reqs,
+ bays: 0,
+ squadrons: [] as Squadron[],
+ reqs,
};
-export const carrierSlice = createSlice({
- name: "carrier",
- initialState,
- reducers: {
- setCarrierBays: (state, action: PayloadAction) => {
- state.bays = action.payload;
- state.reqs = calcBaysReqs(action.payload);
- state.squadrons = adjustSquadrons(action.payload)(state.squadrons);
- },
- setSquadronType: (
- state,
- action: PayloadAction<{ type: string; id: number }>
- ) => {
- state.squadrons[action.payload.id - 1] = {
- type: action.payload.type,
- reqs: squadronReqs(action.payload.type),
- };
- },
+export const { actions, reducer } = createSlice({
+ name: "carrier",
+ initialState,
+ reducers: {
+ setCarrierBays: (state, action: PayloadAction) => {
+ state.bays = action.payload;
+ state.reqs = calcBaysReqs(action.payload);
+ state.squadrons = adjustSquadrons(action.payload)(state.squadrons);
},
+ setSquadronType: (
+ state,
+ action: PayloadAction<{ type: string; id: number }>
+ ) => {
+ state.squadrons[action.payload.id - 1] = {
+ type: action.payload.type,
+ reqs: squadronReqs(action.payload.type),
+ };
+ },
+ },
});
export const squadronTypes = [
- { type: "standard", cost: 3 },
- { type: "fast", cost: 4 },
- { type: "heavy", cost: 5 },
- { type: "interceptor", cost: 3 },
- { type: "attack", cost: 4 },
- { type: "long range", cost: 4 },
- { type: "torpedo", cost: 6 },
+ { type: "standard", cost: 3 },
+ { type: "fast", cost: 4 },
+ { type: "heavy", cost: 5 },
+ { type: "interceptor", cost: 3 },
+ { type: "attack", cost: 4 },
+ { type: "long range", cost: 4 },
+ { type: "torpedo", cost: 6 },
];
function squadronReqs(type: string) {
- return {
- mass: 6,
- cost: 6 * squadronTypes.find((s) => s.type === type)?.cost,
- };
+ return {
+ mass: 6,
+ cost: 6 * squadronTypes.find((s) => s.type === type)?.cost,
+ };
}
const adjustSquadrons = (bays) => (squadrons) => {
- if (squadrons.length > bays) {
- squadrons = squadrons.slice(0, bays);
- }
+ if (squadrons.length > bays) {
+ squadrons = squadrons.slice(0, bays);
+ }
- if (squadrons.length < bays) {
- squadrons = [
- ...squadrons,
- ..._.times(bays - squadrons.length, () => ({
- type: squadronTypes[0].type,
- reqs: {
- cost: 6 * squadronTypes[0].cost,
- mass: 6,
- },
- })),
- ];
- }
+ if (squadrons.length < bays) {
+ squadrons = [
+ ...squadrons,
+ ..._.times(bays - squadrons.length, () => ({
+ type: squadronTypes[0].type,
+ reqs: {
+ cost: 6 * squadronTypes[0].cost,
+ mass: 6,
+ },
+ })),
+ ];
+ }
- return squadrons;
+ return squadrons;
};
function calcBaysReqs(bays) {
- return {
- mass: 9 * bays,
- cost: 18 * bays,
- };
+ return {
+ mass: 9 * bays,
+ cost: 18 * bays,
+ };
}
diff --git a/src/lib/shipDux/index.test.ts b/src/lib/shipDux/index.test.ts
new file mode 100644
index 0000000..7dc3bc4
--- /dev/null
+++ b/src/lib/shipDux/index.test.ts
@@ -0,0 +1,10 @@
+import { createStore } from "./index.js";
+
+test("basic, initial store", () => {
+ const store = createStore();
+
+ const state = store.getState();
+
+ expect(state).toHaveProperty("propulsion.drive.reqs.mass", 0);
+ expect(state).toHaveProperty("structure.cargo.space", 0);
+});
diff --git a/src/lib/shipDux/index.ts b/src/lib/shipDux/index.ts
index dfd4852..448d316 100644
--- a/src/lib/shipDux/index.ts
+++ b/src/lib/shipDux/index.ts
@@ -1,3 +1,37 @@
+import { combineReducers, configureStore, createSlice } from "@reduxjs/toolkit";
+import R from "remeda";
+
+import * as propulsion from "./propulsion";
+import * as structure from "./structure";
+import * as weaponry from "./weaponry/index.js";
+import * as carrier from "./carrier";
+
+const shipSlice = createSlice({
+ name: "ship",
+ initialState: {},
+ reducers: {},
+ extraReducers(builder) {
+ builder.addMatcher(
+ () => true,
+ combineReducers({
+ propulsion: propulsion.reducer,
+ structure: structure.reducer,
+ weaponry: weaponry.reducer,
+ carrier: carrier.reducer,
+ })
+ );
+ },
+});
+
+export function createStore() {
+ return configureStore({
+ reducer: shipSlice.reducer,
+ });
+}
+
+export const actions = shipSlice.actions;
+
+/**
import * as propulsion from "./propulsion/index.js";
import * as identification from "./identification.js";
import { calculateDriveReqs } from "./propulsion/drive.js";
@@ -5,7 +39,27 @@ import { ftlReqsReaction } from "./propulsion/ftl.js";
import * as structure from "./structure/index.js";
import * as carrier from "./carrier.js";
import * as weaponry from "./weaponry/index.js";
+import * as shipReqs from "./shipReqs.js";
import { screensReqsReaction } from "./structure/screens.js";
+import { createSlice } from "@reduxjs/toolkit";
+
+
+const initialState = {
+ propulsion: propulsion.initialState,
+ identification: identification.initialState,
+ structure: structure.initialState,
+ carrier: carrier.initialState,
+ weaponry: weaponry.initialState,
+ shipReqs: shipReqs.initialState,
+}
+
+const shipSlice = createSlice({
+ name: "ship",
+ ),
+});
+
+
+
const dux = new Updux({
subduxes: {
@@ -39,9 +93,6 @@ dux.setMutation("resetShip", () => () => dux.initial);
dux.setMutation("resetLayout", () => resetUITransform);
-dux.setMutation("setShipMass", (mass) => u({ reqs: { mass } }));
-dux.setMutation("setShipReqs", (reqs) => u({ reqs }));
-
dux.setMutation("setUITransform", ({ system, systemId, translate }) => {
const transform = translate
? `translate(${translate[0]}px,${translate[1]}px)`
@@ -104,3 +155,4 @@ dux.addReaction((store) => (state) => {
});
export default dux;
+*/
diff --git a/src/lib/shipDux/propulsion/drive.ts b/src/lib/shipDux/propulsion/drive.ts
index ffbd3f0..3f9ddc7 100644
--- a/src/lib/shipDux/propulsion/drive.ts
+++ b/src/lib/shipDux/propulsion/drive.ts
@@ -2,28 +2,28 @@ import { PayloadAction, createSlice } from "@reduxjs/toolkit";
import { reqs, Reqs } from "../reqs";
type DriveProps = {
- rating: number;
- advanced: boolean;
+ rating: number;
+ advanced: boolean;
};
-const initialState: DriveProps & { reqs: Reqs } = {
- rating: 0,
- advanced: false,
- reqs,
+export const initialState: DriveProps & { reqs: Reqs } = {
+ rating: 0,
+ advanced: false,
+ reqs,
};
const driveSlice = createSlice({
- initialState,
- name: "drive",
- reducers: {
- setDrive: (state, action: PayloadAction) => {
- state.rating = action.payload.rating;
- state.advanced = action.payload.advanced;
- },
- setDriveReqs: (state, action: PayloadAction) => {
- state.reqs = action.payload;
- },
+ initialState,
+ name: "drive",
+ reducers: {
+ setDrive: (state, action: PayloadAction) => {
+ state.rating = action.payload.rating;
+ state.advanced = action.payload.advanced;
},
+ setDriveReqs: (state, action: PayloadAction) => {
+ state.reqs = action.payload;
+ },
+ },
});
export const { actions, reducer } = driveSlice;
diff --git a/src/lib/shipDux/propulsion/ftl.ts b/src/lib/shipDux/propulsion/ftl.ts
index 8d08f77..b138bfe 100644
--- a/src/lib/shipDux/propulsion/ftl.ts
+++ b/src/lib/shipDux/propulsion/ftl.ts
@@ -8,40 +8,40 @@ import { reqs, Reqs } from "../reqs.js";
export const ftlTypes = ["none", "standard", "advanced"] as const;
type FtlType = typeof ftlTypes[number];
-const initialState = {
- reqs,
- type: "none" as FtlType,
+export const initialState = {
+ reqs,
+ type: "none" as FtlType,
};
const ftl = createSlice({
- name: "ftl",
- initialState,
- reducers: {
- setFtl: (state, { payload }: PayloadAction) => {
- state.type = payload;
- },
- setFtlReqs: (state, action: PayloadAction) => {
- state.reqs = action.payload;
- },
+ name: "ftl",
+ initialState,
+ reducers: {
+ setFtl: (state, { payload }: PayloadAction) => {
+ state.type = payload;
},
+ setFtlReqs: (state, action: PayloadAction) => {
+ state.reqs = action.payload;
+ },
+ },
});
export function calcFtlReqs(type: FtlType, shipMass: number): Reqs {
- if (type === "none") return { cost: 0, mass: 0 };
+ if (type === "none") return { cost: 0, mass: 0 };
- const mass = Math.ceil(shipMass / 10);
+ const mass = Math.ceil(shipMass / 10);
- return {
- mass,
- cost: mass * (type === "advanced" ? 3 : 2),
- };
+ return {
+ mass,
+ cost: mass * (type === "advanced" ? 3 : 2),
+ };
}
export const { actions, reducer } = ftl;
// needs to be at the top level
export const ftlReqsReaction = (store) =>
- createSelector(
- [(ship) => ship.propulsion.ftl.type, (ship) => ship.reqs.mass],
- (type, shipMass) => store.dispatch.setFtlReqs(calcFtlReqs(type, shipMass))
- );
+ createSelector(
+ [(ship) => ship.propulsion.ftl.type, (ship) => ship.reqs.mass],
+ (type, shipMass) => store.dispatch.setFtlReqs(calcFtlReqs(type, shipMass))
+ );
diff --git a/src/lib/shipDux/propulsion/index.ts b/src/lib/shipDux/propulsion/index.ts
index 78142d0..8c409d5 100644
--- a/src/lib/shipDux/propulsion/index.ts
+++ b/src/lib/shipDux/propulsion/index.ts
@@ -6,3 +6,8 @@ export const reducer = combineReducers({
drive: drive.reducer,
ftl: ftl.reducer,
});
+
+export const initialState = {
+ drive: drive.initialState,
+ ftl: ftl.initialState,
+};
diff --git a/src/lib/shipDux/ship.test.ts b/src/lib/shipDux/ship.test.ts
new file mode 100644
index 0000000..9c37cf9
--- /dev/null
+++ b/src/lib/shipDux/ship.test.ts
@@ -0,0 +1 @@
+import
diff --git a/src/lib/shipDux/shipReqs.ts b/src/lib/shipDux/shipReqs.ts
new file mode 100644
index 0000000..d3566ec
--- /dev/null
+++ b/src/lib/shipDux/shipReqs.ts
@@ -0,0 +1,24 @@
+import { createSlice } from "@reduxjs/toolkit";
+import { reqs } from "./reqs";
+
+const initialState = {
+ usedMass: 0,
+ mass: 10,
+ cost: 0,
+};
+
+const shipReqs = createSlice({
+ name: "shipReqs",
+ initialState,
+ reducers: {
+ setShipMass(state, action) {
+ state.mass = action.payload;
+ },
+ setShipReqs(state, action) {
+ return {
+ ...state,
+ ...action.payload,
+ };
+ },
+ },
+});
diff --git a/src/lib/shipDux/structure/armor.ts b/src/lib/shipDux/structure/armor.ts
index bc95567..a219ee7 100644
--- a/src/lib/shipDux/structure/armor.ts
+++ b/src/lib/shipDux/structure/armor.ts
@@ -4,32 +4,34 @@ import { Reqs, reqs } from "../reqs";
type Layer = number;
const initialState = {
- reqs,
- layers: [] as Layer[],
+ reqs,
+ layers: [] as Layer[],
};
const armor = createSlice({
- name: "armor",
- initialState,
- reducers: {
- setArmorRating: (state, action) => {
- state.layers[action.payload.layer - 1] = action.payload.rating;
- state.reqs = calcArmorReqs(state.layers);
- },
- setArmorLayers: (state, action: PayloadAction) => {
- while (state.layers.length > action.payload) state.layers.pop();
- while (state.layers.length < action.payload) state.layers.push(0);
- state.reqs = calcArmorReqs(state.layers);
- },
+ name: "armor",
+ initialState,
+ reducers: {
+ setArmorRating: (state, action) => {
+ state.layers[action.payload.layer - 1] = action.payload.rating;
+ state.reqs = calcArmorReqs(state.layers);
},
+ setArmorLayers: (state, action: PayloadAction) => {
+ while (state.layers.length > action.payload) state.layers.pop();
+ while (state.layers.length < action.payload) state.layers.push(0);
+ state.reqs = calcArmorReqs(state.layers);
+ },
+ },
});
-function calcArmorReqs(layers: Layer[]): Reqs {
- const mass = 2 * layers.reduce((a, b) => a + b, 0);
- const cost = 2 * layers.map((v, k) => v * (k + 1)).reduce((a, b) => a + b, 0);
+export const { actions, reducer } = armor;
- return {
- mass,
- cost,
- };
+function calcArmorReqs(layers: Layer[]): Reqs {
+ const mass = 2 * layers.reduce((a, b) => a + b, 0);
+ const cost = 2 * layers.map((v, k) => v * (k + 1)).reduce((a, b) => a + b, 0);
+
+ return {
+ mass,
+ cost,
+ };
}
diff --git a/src/lib/shipDux/structure/hull.ts b/src/lib/shipDux/structure/hull.ts
index 0da4623..92af84d 100644
--- a/src/lib/shipDux/structure/hull.ts
+++ b/src/lib/shipDux/structure/hull.ts
@@ -2,33 +2,32 @@ import { createSlice, PayloadAction } from "@reduxjs/toolkit";
import { reqs } from "../reqs";
const initialState = {
- rating: 0,
- min: 0,
- max: 0,
- reqs,
+ rating: 0,
+ min: 0,
+ max: 0,
+ reqs,
};
const hull = createSlice({
- name: "hull",
- initialState,
- reducers: {
- setHull: (state, action: PayloadAction) => {
- state.rating = action.payload;
- state.reqs = {
- mass: action.payload,
- cost: 2 * action.payload,
- }
- },
- setShipMass: (state, action: PayloadAction) => {
- const mass = action.payload;
- let { rating } = state;
- if (rating > mass) state.rating = mass;
- state.min = Math.ceil(mass / 10);
- if (state.rating < state.min) state.rating = state.min;
- state.max = mass;
- };
+ name: "hull",
+ initialState,
+ reducers: {
+ setHull: (state, action: PayloadAction) => {
+ state.rating = action.payload;
+ state.reqs = {
+ mass: action.payload,
+ cost: 2 * action.payload,
+ };
},
-},
+ setShipMass: (state, action: PayloadAction) => {
+ const mass = action.payload;
+ let { rating } = state;
+ if (rating > mass) state.rating = mass;
+ state.min = Math.ceil(mass / 10);
+ if (state.rating < state.min) state.rating = state.min;
+ state.max = mass;
+ },
+ },
});
export const { actions, reducer } = hull;
diff --git a/src/lib/shipDux/structure/index.ts b/src/lib/shipDux/structure/index.ts
index c775f89..ec5a663 100644
--- a/src/lib/shipDux/structure/index.ts
+++ b/src/lib/shipDux/structure/index.ts
@@ -2,20 +2,20 @@ import { combineReducers } from "redux";
import * as R from "remeda";
import * as hull from "./hull.js";
-import * as screens from "./screens.js";
+import * as screens from "./screen.js";
import * as cargo from "./cargo.js";
import * as armor from "./armor.js";
import * as streamlining from "./streamlining.js";
export const reducer = combineReducers(
- R.mapValues(
- {
- hull,
- screens,
- cargo,
- armor,
- streamlining,
- },
- R.prop("reducer")
- )
+ R.mapValues(
+ {
+ hull,
+ screens,
+ cargo,
+ armor,
+ streamlining,
+ },
+ R.prop("reducer")
+ )
);
diff --git a/src/lib/store/ship.js b/src/lib/store/ship.js
index 1fd3c0c..daab0da 100644
--- a/src/lib/store/ship.js
+++ b/src/lib/store/ship.js
@@ -1,40 +1,40 @@
-import { browser, dev } from "$app/env";
+import { browser, dev } from "$app/environment";
import { readable, get, derived } from "svelte/store";
import { compose, applyMiddleware } from "redux";
-import shipDux from "../shipDux/index.js";
+import shipDux from "../shipDux/index";
import { initial } from "lodash";
let composeEnhancers = compose;
if (dev && browser && window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__) {
- composeEnhancers = window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__;
+ composeEnhancers = window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__;
}
export default (initialState = undefined) => {
- if (browser) {
- const i = localStorage.getItem("ship");
+ if (browser) {
+ const i = localStorage.getItem("ship");
- if (i) initialState = JSON.parse(localStorage.getItem("ship"));
- }
+ if (i) initialState = JSON.parse(localStorage.getItem("ship"));
+ }
- const duxStore = shipDux.createStore(initialState, (mw) =>
- composeEnhancers(applyMiddleware(mw))
- );
+ const duxStore = shipDux.createStore(initialState, (mw) =>
+ composeEnhancers(applyMiddleware(mw))
+ );
- let previous;
- const state = readable(duxStore.getState(), (set) => {
- duxStore.subscribe(() => {
- if (previous === duxStore.getState()) return;
- previous = duxStore.getState();
- set(previous);
- if (browser) localStorage.setItem("ship", JSON.stringify(previous));
+ let previous;
+ const state = readable(duxStore.getState(), (set) => {
+ duxStore.subscribe(() => {
+ if (previous === duxStore.getState()) return;
+ previous = duxStore.getState();
+ set(previous);
+ if (browser) localStorage.setItem("ship", JSON.stringify(previous));
+ });
});
- });
- return {
- dispatch: duxStore.dispatch,
- state,
- shipMass: derived(state, (state) => state.reqs.mass),
- };
+ return {
+ dispatch: duxStore.dispatch,
+ state,
+ shipMass: derived(state, (state) => state.reqs.mass),
+ };
};
diff --git a/src/routes/index.svelte b/src/routes/+page.svelte
similarity index 86%
rename from src/routes/index.svelte
rename to src/routes/+page.svelte
index df71d56..8c3d41a 100644
--- a/src/routes/index.svelte
+++ b/src/routes/+page.svelte
@@ -3,7 +3,7 @@