mirror of
https://github.com/bitcoinresearchkit/brk.git
synced 2026-04-24 22:59:58 -07:00
410 lines
9.4 KiB
JavaScript
410 lines
9.4 KiB
JavaScript
/**
|
|
* @import {Options} from './options';
|
|
*/
|
|
|
|
/**
|
|
* @param {Object} args
|
|
* @param {Colors} args.colors
|
|
* @param {Consts} args.consts
|
|
* @param {LightweightCharts} args.lightweightCharts
|
|
* @param {Accessor<ChartOption>} args.selected
|
|
* @param {Signals} args.signals
|
|
* @param {Utilities} args.utils
|
|
* @param {Options} args.options
|
|
* @param {Datasets} args.datasets
|
|
* @param {WebSockets} args.webSockets
|
|
* @param {Elements} args.elements
|
|
* @param {Ids} args.ids
|
|
* @param {Accessor<boolean>} args.dark
|
|
*/
|
|
export function init({
|
|
colors,
|
|
consts,
|
|
dark,
|
|
datasets,
|
|
elements,
|
|
ids,
|
|
lightweightCharts,
|
|
options,
|
|
selected,
|
|
signals,
|
|
utils,
|
|
webSockets,
|
|
}) {
|
|
const simulationElement = elements.simulation;
|
|
|
|
const parametersElement = window.document.createElement("div");
|
|
simulationElement.append(parametersElement);
|
|
const resultsElement = window.document.createElement("div");
|
|
simulationElement.append(resultsElement);
|
|
|
|
const storagePrefix = "save-in-bitcoin";
|
|
const settings = {
|
|
initial: signals.createSignal(/** @type {number | null} */ (1000), {
|
|
save: {
|
|
...utils.serde.number,
|
|
id: `${storagePrefix}-initial-amount`,
|
|
param: "initial-amount",
|
|
},
|
|
}),
|
|
later: signals.createSignal(/** @type {number | null} */ (0), {
|
|
save: {
|
|
...utils.serde.number,
|
|
id: `${storagePrefix}-later-amount`,
|
|
param: "later-amount",
|
|
},
|
|
}),
|
|
recurrent: {
|
|
amount: signals.createSignal(/** @type {number | null} */ (100), {
|
|
save: {
|
|
...utils.serde.number,
|
|
id: `${storagePrefix}-recurrent-amount`,
|
|
param: "recurrent-amount",
|
|
},
|
|
}),
|
|
},
|
|
};
|
|
|
|
const initialGroup = createParameterGroup({
|
|
title: "Initial",
|
|
description:
|
|
"The initial amount of dollars you're willing to eventually save in Bitcoin.",
|
|
});
|
|
parametersElement.append(initialGroup);
|
|
|
|
initialGroup.append(
|
|
createInputField({
|
|
name: "Directly converted",
|
|
input: createInputDollar({
|
|
id: "simulation-dollars-initial",
|
|
title: "Initial amount of dollars converted",
|
|
signal: settings.initial,
|
|
}),
|
|
}),
|
|
);
|
|
|
|
initialGroup.append(
|
|
createInputField({
|
|
name: "Converted over time",
|
|
input: createInputDollar({
|
|
id: "simulation-dollars-later",
|
|
title: "Dollars to spread over time",
|
|
signal: settings.later,
|
|
}),
|
|
}),
|
|
);
|
|
|
|
parametersElement.append(createHrElement());
|
|
|
|
const recurrentGroup = createParameterGroup({
|
|
title: "Recurrent",
|
|
description:
|
|
"The recurrent amount of dollars you're willing to eventually save in Bitcoin.",
|
|
});
|
|
parametersElement.append(recurrentGroup);
|
|
|
|
recurrentGroup.append(
|
|
createInputField({
|
|
name: "Amount",
|
|
input: createInputDollar({
|
|
id: "simulation-dollars-recurrent",
|
|
title: "Recurrent dollar amount",
|
|
signal: settings.recurrent.amount,
|
|
}),
|
|
}),
|
|
);
|
|
|
|
const frequencyUL = appendUl({ parent: recurrentGroup });
|
|
|
|
[{ name: "Daily" }, { name: "Weekly" }, { name: "Monthly" }].forEach(
|
|
({ name }) => {
|
|
const li = appendLi({ name, parent: frequencyUL });
|
|
},
|
|
);
|
|
|
|
const frequencyChoiceUL = appendUl({ parent: recurrentGroup });
|
|
|
|
[
|
|
"Monday",
|
|
"Tuesday",
|
|
"Wednesday",
|
|
"Thursday",
|
|
"Friday",
|
|
"Saturday",
|
|
"Sunday",
|
|
].forEach((name) => {
|
|
const li = appendLi({ name, parent: frequencyChoiceUL });
|
|
});
|
|
|
|
parametersElement.append(createHrElement());
|
|
|
|
const today = signals.createSignal(utils.date.todayUTC());
|
|
setInterval(() => {
|
|
today.set(utils.date.todayUTC());
|
|
}, consts.FIVE_SECONDS_IN_MS);
|
|
|
|
const intervalGroup = createParameterGroup({
|
|
title: "Interval",
|
|
description: "wkfpweokf",
|
|
});
|
|
parametersElement.append(intervalGroup);
|
|
|
|
/**
|
|
* @param {Object} args
|
|
* @param {HTMLElement} args.parent
|
|
*/
|
|
function appendDiv({ parent }) {
|
|
const div = window.document.createElement("div");
|
|
parent.append(div);
|
|
return div;
|
|
}
|
|
|
|
function createInputDateField() {
|
|
const div = appendDiv({ parent: intervalGroup });
|
|
|
|
appendInputDate({
|
|
id: "",
|
|
title: "",
|
|
value: "2021-04-15",
|
|
parent: div,
|
|
signals,
|
|
today,
|
|
});
|
|
|
|
appendButton({
|
|
onClick: () => {},
|
|
text: "Reset",
|
|
title: "",
|
|
parent: div,
|
|
});
|
|
|
|
return div;
|
|
}
|
|
|
|
createInputDateField();
|
|
createInputDateField();
|
|
|
|
parametersElement.append(createHrElement());
|
|
|
|
const feesGroup = createParameterGroup({
|
|
title: "Fees",
|
|
description:
|
|
"The amount of fees (in %) from where you'll be exchanging your currency",
|
|
});
|
|
parametersElement.append(feesGroup);
|
|
|
|
createInputNumber({
|
|
id: "",
|
|
title: "",
|
|
value: 0.25,
|
|
parent: feesGroup,
|
|
min: 0,
|
|
max: 10,
|
|
});
|
|
|
|
parametersElement.append(createHrElement());
|
|
|
|
const strategyGroup = createParameterGroup({
|
|
title: "Strategy",
|
|
description: "The strategy used to convert your fiat into Bitcoin",
|
|
});
|
|
parametersElement.append(strategyGroup);
|
|
|
|
const ulStrategies = appendUl({ parent: strategyGroup });
|
|
|
|
["All in", "Weighted Local", "Weighted Cycle"].forEach((strategy) => {
|
|
appendLi({
|
|
name: strategy,
|
|
parent: ulStrategies,
|
|
});
|
|
});
|
|
|
|
//
|
|
// On the side
|
|
// Value in Bitcoin
|
|
// Value in Dollars + total converted
|
|
//
|
|
// Value min estimated value in 4 years
|
|
//
|
|
}
|
|
|
|
/**
|
|
* @param {Object} args
|
|
* @param {HTMLInputElement} args.input
|
|
* @param {string} args.name
|
|
*/
|
|
function createInputField({ name, input }) {
|
|
const div = window.document.createElement("div");
|
|
|
|
const label = window.document.createElement("label");
|
|
div.append(label);
|
|
// @ts-ignore
|
|
label.for = input.id;
|
|
label.innerHTML = name;
|
|
|
|
div.append(input);
|
|
|
|
return div;
|
|
}
|
|
|
|
/**
|
|
* @param {Object} args
|
|
* @param {string} args.title
|
|
* @param {string} args.description
|
|
*/
|
|
function createParameterGroup({ title, description }) {
|
|
const div = window.document.createElement("div");
|
|
|
|
const wrapper = window.document.createElement("div");
|
|
div.append(wrapper);
|
|
|
|
const titleElement = window.document.createElement("h4");
|
|
titleElement.innerHTML = title;
|
|
wrapper.append(titleElement);
|
|
|
|
const descriptionElement = window.document.createElement("small");
|
|
descriptionElement.innerHTML = description;
|
|
wrapper.append(descriptionElement);
|
|
|
|
return div;
|
|
}
|
|
|
|
function createHrElement() {
|
|
return window.document.createElement("hr");
|
|
}
|
|
|
|
/**
|
|
*@param {Object} args
|
|
*@param {string} args.id
|
|
*@param {string} args.title
|
|
*@param {number} args.value
|
|
*@param {HTMLElement} args.parent
|
|
*@param {number} args.min
|
|
*@param {number} args.max
|
|
*/
|
|
function createInputNumber({ id, title, value, parent, min, max }) {
|
|
const input = window.document.createElement("input");
|
|
input.id = id;
|
|
input.title = title;
|
|
input.type = "number";
|
|
input.value = String(value);
|
|
input.min = String(min);
|
|
input.max = String(max);
|
|
parent.append(input);
|
|
return input;
|
|
}
|
|
|
|
/**
|
|
* @param {Object} args
|
|
* @param {string} args.id
|
|
* @param {string} args.title
|
|
* @param {Signal<number | null>} args.signal
|
|
*/
|
|
function createInputDollar({ id, title, signal }) {
|
|
const input = window.document.createElement("input");
|
|
input.id = id;
|
|
input.type = "number";
|
|
input.placeholder = "US Dollars";
|
|
input.min = "0";
|
|
input.title = title;
|
|
|
|
const value = signal();
|
|
input.value = value !== null ? String(value) : "";
|
|
|
|
input.addEventListener("input", () => {
|
|
const value = input.value;
|
|
signal.set(value ? Number(value) : null);
|
|
});
|
|
|
|
return input;
|
|
}
|
|
|
|
/**
|
|
* @param {Object} args
|
|
* @param {string} args.id
|
|
* @param {string} args.title
|
|
* @param {Signal<number | null>} args.signal
|
|
*/
|
|
function createInputRangePercentage({ id, title, signal }) {
|
|
const input = window.document.createElement("input");
|
|
input.id = id;
|
|
input.title = title;
|
|
input.type = "range";
|
|
input.min = "0";
|
|
input.max = "100";
|
|
|
|
const value = signal();
|
|
input.value = value !== null ? String(value) : "";
|
|
|
|
input.addEventListener("input", () => {
|
|
const value = input.value;
|
|
signal.set(value ? Number(value) : null);
|
|
});
|
|
|
|
return input;
|
|
}
|
|
|
|
/**
|
|
* @param {Object} args
|
|
* @param {HTMLElement} args.parent
|
|
*/
|
|
function appendUl({ parent }) {
|
|
const ul = window.document.createElement("ul");
|
|
parent.append(ul);
|
|
return ul;
|
|
}
|
|
|
|
/**
|
|
* @param {Object} args
|
|
* @param {string} args.name
|
|
* @param {HTMLUListElement} args.parent
|
|
*/
|
|
function appendLi({ name, parent }) {
|
|
const li = window.document.createElement("li");
|
|
li.innerHTML = name;
|
|
parent.append(li);
|
|
return li;
|
|
}
|
|
|
|
/**
|
|
*@param {Object} args
|
|
*@param {string} args.id
|
|
*@param {string} args.title
|
|
*@param {string} args.value
|
|
*@param {HTMLElement} args.parent
|
|
*@param {Accessor<Date>} args.today
|
|
*@param {Signals} args.signals
|
|
*/
|
|
function appendInputDate({ id, title, value, parent, today, signals }) {
|
|
const input = window.document.createElement("input");
|
|
input.id = id;
|
|
input.title = title;
|
|
input.type = "date";
|
|
input.value = value;
|
|
|
|
input.min = "2011-01-01";
|
|
|
|
signals.createEffect(() => {
|
|
input.max = today().toJSON().split("T")[0];
|
|
});
|
|
|
|
parent.append(input);
|
|
return input;
|
|
}
|
|
|
|
/**
|
|
*@param {Object} args
|
|
*@param {string} args.title
|
|
*@param {string} args.text
|
|
*@param {HTMLElement} args.parent
|
|
*@param {VoidFunction} args.onClick
|
|
*/
|
|
function appendButton({ title, text, onClick, parent }) {
|
|
const button = window.document.createElement("button");
|
|
button.title = title;
|
|
button.innerHTML = text;
|
|
button.addEventListener("click", onClick);
|
|
parent.append(button);
|
|
return button;
|
|
}
|