Convert all class methods and function declarations to camel case
This commit is contained in:
parent
7552e539c5
commit
9e7da12bf5
|
@ -1,5 +1,5 @@
|
|||
import { CpuEvent, CpuEventHandler, UiCpuSignal, UiCpuSignalHandler, UiEvent, UiEventHandler } from "./events";
|
||||
import { byte_array_to_js_source, format_hex } from "./etc";
|
||||
import { byteArrayToJsSource, formatHex } from "./etc";
|
||||
import { Instruction, ISA } from "./instructionSet";
|
||||
import { m256, u2, u3, u8 } from "./num";
|
||||
import { DEFAULT_VRAM_BANK } from "./constants";
|
||||
|
@ -40,7 +40,7 @@ export class Computer {
|
|||
pos: this.program_counter,
|
||||
code: current_byte,
|
||||
});
|
||||
console.log(`Invalid instruction: ${format_hex(current_byte)}`);
|
||||
console.log(`Invalid instruction: ${formatHex(current_byte)}`);
|
||||
this.step_forward();
|
||||
this.events.dispatch(CpuEvent.Cycle);
|
||||
return;
|
||||
|
@ -174,22 +174,22 @@ export class Computer {
|
|||
this.vram_bank = 3;
|
||||
}
|
||||
|
||||
init_events(ui: UiCpuSignalHandler): void {
|
||||
initEvents(ui: UiCpuSignalHandler): void {
|
||||
ui.listen(UiCpuSignal.RequestCpuCycle, (cycle_count) => {
|
||||
for (let i = 0; i < cycle_count; i++) this.cycle();
|
||||
});
|
||||
ui.listen(UiCpuSignal.RequestMemoryChange, ({ address, bank, value }) => this.setMemory(address, value, bank));
|
||||
ui.listen(UiCpuSignal.RequestRegisterChange, ({ register_no, value }) => this.setRegister(register_no, value));
|
||||
ui.listen(UiCpuSignal.RequestMemoryDump, (callback) => callback(this.dump_memory()));
|
||||
ui.listen(UiCpuSignal.RequestMemoryDump, (callback) => callback(this.dumpMemory()));
|
||||
ui.listen(UiCpuSignal.RequestCpuReset, () => this.reset());
|
||||
ui.listen(UiCpuSignal.RequestProgramCounterChange, ({ address }) => {
|
||||
this.setProgramCounter(address);
|
||||
});
|
||||
}
|
||||
|
||||
load_memory(program: Array<u8>): void {
|
||||
loadMemory(program: Array<u8>): void {
|
||||
// TODO allow loading into other banks
|
||||
console.log(byte_array_to_js_source(program));
|
||||
console.log(byteArrayToJsSource(program));
|
||||
const max_loop: u8 = Math.min(255, program.length) as u8;
|
||||
for (let i: u8 = 0; i < 256; i++) {
|
||||
// Don't fire event if no change is made
|
||||
|
@ -201,7 +201,7 @@ export class Computer {
|
|||
this.program_counter = 0;
|
||||
}
|
||||
|
||||
dump_memory(): [Uint8Array, Uint8Array, Uint8Array, Uint8Array] {
|
||||
dumpMemory(): [Uint8Array, Uint8Array, Uint8Array, Uint8Array] {
|
||||
return this.banks;
|
||||
}
|
||||
|
||||
|
|
|
@ -14,16 +14,16 @@ import { u8 } from "./num";
|
|||
*/
|
||||
export const $ = (id: string): HTMLElement => document.getElementById(id) as HTMLElement;
|
||||
|
||||
export const format_hex = (n: u8): string => n.toString(16).toUpperCase().padStart(2, "0");
|
||||
export const formatHex = (n: u8): string => n.toString(16).toUpperCase().padStart(2, "0");
|
||||
|
||||
/**
|
||||
* Converts array of bytes to a JavaScript syntax array of hexadecimal literals
|
||||
* @param bytes
|
||||
*/
|
||||
export const byte_array_to_js_source = (bytes: Array<u8>): string => {
|
||||
export const byteArrayToJsSource = (bytes: Array<u8>): string => {
|
||||
let str = "[";
|
||||
for (const b of bytes) {
|
||||
str += `0x${format_hex(b)},`;
|
||||
str += `0x${formatHex(b)},`;
|
||||
}
|
||||
str += "]";
|
||||
return str;
|
||||
|
@ -33,7 +33,7 @@ export type NonEmptyArray<T> = T[] & { 0: T };
|
|||
|
||||
export const SVG_NS = "http://www.w3.org/2000/svg";
|
||||
|
||||
export function in_range(check: number, start: number, end: number): boolean {
|
||||
export function inRange(check: number, start: number, end: number): boolean {
|
||||
if (check >= start && check <= end) return true;
|
||||
return false;
|
||||
}
|
||||
|
|
10
src/index.ts
10
src/index.ts
|
@ -6,7 +6,7 @@
|
|||
import { Computer } from "./computer";
|
||||
import { $ } from "./etc";
|
||||
import { ISA } from "./instructionSet";
|
||||
import { generate_isa } from "./isaGenerator";
|
||||
import { generateIsa } from "./isaGenerator";
|
||||
import { UI } from "./ui";
|
||||
import { u8 } from "./num";
|
||||
|
||||
|
@ -41,13 +41,13 @@ function main(): void {
|
|||
const computer = new Computer();
|
||||
|
||||
const ui = new UI();
|
||||
ui.init_events(computer.events);
|
||||
computer.load_memory(program);
|
||||
computer.init_events(ui.cpu_signaler);
|
||||
ui.initEvents(computer.events);
|
||||
computer.loadMemory(program);
|
||||
computer.initEvents(ui.cpu_signaler);
|
||||
window.comp = computer;
|
||||
window.ui = ui;
|
||||
|
||||
$("ISA").textContent = generate_isa(ISA);
|
||||
$("ISA").textContent = generateIsa(ISA);
|
||||
|
||||
let fire = false;
|
||||
window.firehose = (): void => {
|
||||
|
|
|
@ -4,7 +4,7 @@
|
|||
* @license GPL-3.0
|
||||
*/
|
||||
import { CpuEvent, CpuEventHandler } from "./events";
|
||||
import { format_hex, in_range } from "./etc";
|
||||
import { formatHex, inRange } from "./etc";
|
||||
import { isU2, isU3, m256, u2, u3, u8 } from "./num";
|
||||
|
||||
export enum ParamType {
|
||||
|
@ -86,7 +86,7 @@ export class InstructionSet {
|
|||
|
||||
insertInstruction(hexCode: u8, instruction: Instruction): void {
|
||||
if (this.instructions.has(hexCode)) {
|
||||
throw new Error(`Instruction "${format_hex(hexCode)}" already exists`);
|
||||
throw new Error(`Instruction "${formatHex(hexCode)}" already exists`);
|
||||
}
|
||||
this.instructions.set(hexCode, instruction);
|
||||
}
|
||||
|
@ -94,7 +94,7 @@ export class InstructionSet {
|
|||
addCategory(c: InstrCategory): void {
|
||||
// Check for overlap with existing ranges
|
||||
for (const r of this.category_ranges) {
|
||||
if (in_range(c.start, r.start, r.end) || in_range(c.end, r.start, r.end)) {
|
||||
if (inRange(c.start, r.start, r.end) || inRange(c.end, r.start, r.end)) {
|
||||
throw new Error(`Range of ${c.start}...${c.end} is already registered`);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -3,48 +3,11 @@
|
|||
* @copyright Alexander Bass 2024
|
||||
* @license GPL-3.0
|
||||
*/
|
||||
import { format_hex, in_range } from "./etc";
|
||||
import { formatHex, inRange } from "./etc";
|
||||
import { InstrCategory, Instruction, InstructionSet, ParameterType, ParamType } from "./instructionSet";
|
||||
import { u8 } from "./num";
|
||||
|
||||
export function generate_isa(iset: InstructionSet): string {
|
||||
const instructions: Array<[u8, Instruction]> = [];
|
||||
|
||||
for (const kv of iset.instructions.entries()) instructions.push(kv);
|
||||
|
||||
let output_string = "INSTRUCTIONS\n";
|
||||
|
||||
const max_instr_name_len = instructions.map((i) => i[1].name.length).reduce((acc, p) => Math.max(p, acc), 0);
|
||||
instructions.sort((a, b) => a[0] - b[0]);
|
||||
|
||||
let current_category: InstrCategory | null = null;
|
||||
|
||||
for (const instruction of instructions) {
|
||||
const cat = iset.category_ranges.find((i) => in_range(instruction[0], i.start, i.end));
|
||||
if (cat === undefined) {
|
||||
throw new Error("Instruction found which is not part of category");
|
||||
}
|
||||
if (current_category !== cat) {
|
||||
output_string += `-- ${cat.name.toUpperCase()} --\n`;
|
||||
current_category = cat;
|
||||
}
|
||||
const hex_code = format_hex(instruction[0]);
|
||||
|
||||
const short_description = instruction[1].name.padEnd(max_instr_name_len, " ");
|
||||
const parameters = parameter_description(instruction[1].params);
|
||||
const description = instruction[1].desc;
|
||||
output_string += `0x${hex_code}: ${short_description}`;
|
||||
if (parameters.length !== 0) {
|
||||
output_string += ` -${parameters}- `;
|
||||
} else {
|
||||
output_string += " - ";
|
||||
}
|
||||
output_string += `${description}\n`;
|
||||
}
|
||||
return output_string;
|
||||
}
|
||||
|
||||
function parameter_description(params: Array<ParameterType>): string {
|
||||
function parameterDescription(params: Array<ParameterType>): string {
|
||||
let str = "";
|
||||
if (params.length !== 0) {
|
||||
str += " ";
|
||||
|
@ -57,3 +20,40 @@ function parameter_description(params: Array<ParameterType>): string {
|
|||
}
|
||||
return str;
|
||||
}
|
||||
|
||||
export function generateIsa(iset: InstructionSet): string {
|
||||
const instructions: Array<[u8, Instruction]> = [];
|
||||
|
||||
for (const kv of iset.instructions.entries()) instructions.push(kv);
|
||||
|
||||
let output_string = "INSTRUCTIONS\n";
|
||||
|
||||
const max_instr_name_len = instructions.map((i) => i[1].name.length).reduce((acc, p) => Math.max(p, acc), 0);
|
||||
instructions.sort((a, b) => a[0] - b[0]);
|
||||
|
||||
let current_category: InstrCategory | null = null;
|
||||
|
||||
for (const instruction of instructions) {
|
||||
const cat = iset.category_ranges.find((i) => inRange(instruction[0], i.start, i.end));
|
||||
if (cat === undefined) {
|
||||
throw new Error("Instruction found which is not part of category");
|
||||
}
|
||||
if (current_category !== cat) {
|
||||
output_string += `-- ${cat.name.toUpperCase()} --\n`;
|
||||
current_category = cat;
|
||||
}
|
||||
const hex_code = formatHex(instruction[0]);
|
||||
|
||||
const short_description = instruction[1].name.padEnd(max_instr_name_len, " ");
|
||||
const parameters = parameterDescription(instruction[1].params);
|
||||
const description = instruction[1].desc;
|
||||
output_string += `0x${hex_code}: ${short_description}`;
|
||||
if (parameters.length !== 0) {
|
||||
output_string += ` -${parameters}- `;
|
||||
} else {
|
||||
output_string += " - ";
|
||||
}
|
||||
output_string += `${description}\n`;
|
||||
}
|
||||
return output_string;
|
||||
}
|
||||
|
|
|
@ -46,12 +46,12 @@ export class UI {
|
|||
this.components.push(component);
|
||||
}
|
||||
|
||||
init_events(cpu_events: CpuEventHandler): void {
|
||||
initEvents(cpu_events: CpuEventHandler): void {
|
||||
cpu_events.listen(CpuEvent.Reset, () => {
|
||||
this.reset();
|
||||
});
|
||||
|
||||
for (const c of this.components) if (c.init_cpu_events) c.init_cpu_events(cpu_events);
|
||||
for (const c of this.components) if (c.initCpuEvents) c.initCpuEvents(cpu_events);
|
||||
}
|
||||
|
||||
reset(): void {
|
||||
|
|
|
@ -3,7 +3,7 @@
|
|||
* @copyright Alexander Bass 2024
|
||||
* @license GPL-3.0
|
||||
*/
|
||||
import { NonEmptyArray, el, format_hex } from "../etc";
|
||||
import { NonEmptyArray, el, formatHex } from "../etc";
|
||||
import { u8 } from "../num";
|
||||
import EditorContext from "./editableHex";
|
||||
|
||||
|
@ -39,41 +39,41 @@ export default class CelledViewer {
|
|||
|
||||
reset(): void {
|
||||
for (let i = 0; i < this.height * this.width; i++) {
|
||||
this.set_cell_value(i as u8, 0);
|
||||
this.setCellValue(i as u8, 0);
|
||||
this.cells[i].el.className = "";
|
||||
}
|
||||
}
|
||||
add_cell_class(address: u8, ...css_class: NonEmptyArray<string>): void {
|
||||
addCellClass(address: u8, ...css_class: NonEmptyArray<string>): void {
|
||||
for (const str of css_class) {
|
||||
this.cells[address].el.classList.add(str);
|
||||
}
|
||||
}
|
||||
|
||||
remove_cell_class(address: u8, ...css_class: NonEmptyArray<string>): void {
|
||||
removeCellClass(address: u8, ...css_class: NonEmptyArray<string>): void {
|
||||
for (const str of css_class) {
|
||||
this.cells[address].el.classList.remove(str);
|
||||
}
|
||||
}
|
||||
|
||||
remove_all_cell_class(css_class: string): void {
|
||||
removeAllCellClass(css_class: string): void {
|
||||
for (const cell of this.cells) {
|
||||
cell.el.classList.remove(css_class);
|
||||
}
|
||||
}
|
||||
|
||||
clear_all_classes(): void {
|
||||
clearAllClasses(): void {
|
||||
for (const cell of this.cells) {
|
||||
cell.el.className = "";
|
||||
}
|
||||
}
|
||||
|
||||
add_cell_class_exclusive(address: u8, css_class: string): void {
|
||||
this.remove_all_cell_class(css_class);
|
||||
this.add_cell_class(address, css_class);
|
||||
addCellClassExclusive(address: u8, css_class: string): void {
|
||||
this.removeAllCellClass(css_class);
|
||||
this.addCellClass(address, css_class);
|
||||
}
|
||||
|
||||
set_cell_value(address: u8, value: u8): void {
|
||||
const str = format_hex(value);
|
||||
setCellValue(address: u8, value: u8): void {
|
||||
const str = formatHex(value);
|
||||
const a = str[0];
|
||||
const b = str[1];
|
||||
this.cells[address].el.textContent = "";
|
||||
|
|
|
@ -53,7 +53,7 @@ export default class frequencyIndicator implements UiComponent {
|
|||
this.last_value = 0;
|
||||
this.start();
|
||||
}
|
||||
init_cpu_events(c: CpuEventHandler): void {
|
||||
initCpuEvents(c: CpuEventHandler): void {
|
||||
c.listen(CpuEvent.Cycle, () => {
|
||||
this.count += 1;
|
||||
});
|
||||
|
|
|
@ -6,7 +6,7 @@ import { el } from "../../etc";
|
|||
import CelledViewer from "../celledViewer";
|
||||
|
||||
/** Only to be run once */
|
||||
function create_banks(
|
||||
function createBanks(
|
||||
element: HTMLElement,
|
||||
edit_callback: (address: u8, bank: u2, value: u8) => void
|
||||
): [CelledViewer, CelledViewer, CelledViewer, CelledViewer] {
|
||||
|
@ -39,50 +39,50 @@ export default class MemoryView implements UiComponent {
|
|||
this.events = events;
|
||||
this.cpu_signals = cpu_signals;
|
||||
|
||||
this.banks = create_banks(element, (address, bank, value) => {
|
||||
this.banks = createBanks(element, (address, bank, value) => {
|
||||
cpu_signals.dispatch(UiCpuSignal.RequestMemoryChange, { address, bank, value });
|
||||
});
|
||||
for (const bank of this.banks) {
|
||||
this.events.listen(UiEvent.EditOn, () => {
|
||||
bank.editor.enable();
|
||||
bank.clear_all_classes();
|
||||
bank.clearAllClasses();
|
||||
});
|
||||
this.events.listen(UiEvent.EditOff, () => {
|
||||
bank.editor.disable();
|
||||
bank.clear_all_classes();
|
||||
bank.clearAllClasses();
|
||||
});
|
||||
}
|
||||
this.events.listen(UiEvent.ChangeViewBank, ({ bank }) => this.set_bank(bank));
|
||||
this.events.listen(UiEvent.ChangeViewBank, ({ bank }) => this.setBank(bank));
|
||||
}
|
||||
|
||||
get program(): CelledViewer {
|
||||
return this.banks[0];
|
||||
}
|
||||
|
||||
set_bank(bank: u2): void {
|
||||
setBank(bank: u2): void {
|
||||
for (const bank of this.banks) bank.container.classList.remove("selected");
|
||||
this.banks[bank].container.classList.add("selected");
|
||||
}
|
||||
|
||||
set_program_counter(position: u8): void {
|
||||
this.program.remove_cell_class(this.program_counter, "program_counter");
|
||||
this.program.add_cell_class(position, "program_counter");
|
||||
setProgramCounter(position: u8): void {
|
||||
this.program.removeCellClass(this.program_counter, "program_counter");
|
||||
this.program.addCellClass(position, "program_counter");
|
||||
this.program_counter = position;
|
||||
}
|
||||
|
||||
reset(): void {
|
||||
for (const viewer of this.banks) viewer.reset();
|
||||
this.last_accessed_cell = null;
|
||||
this.set_program_counter(0);
|
||||
this.setProgramCounter(0);
|
||||
}
|
||||
|
||||
init_cpu_events(c: CpuEventHandler): void {
|
||||
initCpuEvents(c: CpuEventHandler): void {
|
||||
c.listen(CpuEvent.MemoryAccessed, ({ address, bank, value }) => {
|
||||
if (this.last_accessed_cell?.address !== address || this.last_accessed_cell?.bank !== bank) {
|
||||
if (this.last_accessed_cell !== null) {
|
||||
this.banks[this.last_accessed_cell.bank].remove_cell_class(this.last_accessed_cell.address, "last_access");
|
||||
this.banks[this.last_accessed_cell.bank].removeCellClass(this.last_accessed_cell.address, "last_access");
|
||||
}
|
||||
this.banks[bank].add_cell_class(address, "last_access");
|
||||
this.banks[bank].addCellClass(address, "last_access");
|
||||
this.last_accessed_cell = { address, bank };
|
||||
}
|
||||
});
|
||||
|
@ -90,15 +90,15 @@ export default class MemoryView implements UiComponent {
|
|||
if (bank !== 0) {
|
||||
return;
|
||||
}
|
||||
this.banks[bank].set_cell_value(address, value);
|
||||
this.banks[bank].setCellValue(address, value);
|
||||
});
|
||||
c.listen(CpuEvent.ProgramCounterChanged, ({ counter }) => {
|
||||
this.set_program_counter(counter);
|
||||
this.setProgramCounter(counter);
|
||||
});
|
||||
c.listen(CpuEvent.ParameterParsed, ({ param, code, pos }) => {
|
||||
this.program.add_cell_class(pos, "instruction_argument");
|
||||
this.program.addCellClass(pos, "instruction_argument");
|
||||
const t = param.type;
|
||||
this.program.remove_cell_class(pos, "constant", "register", "memory", "instruction", "invalid");
|
||||
this.program.removeCellClass(pos, "constant", "register", "memory", "instruction", "invalid");
|
||||
let name: string = "";
|
||||
if (t === ParamType.Const) {
|
||||
name = "constant";
|
||||
|
@ -109,18 +109,18 @@ export default class MemoryView implements UiComponent {
|
|||
} else {
|
||||
throw new Error("unreachable");
|
||||
}
|
||||
this.program.add_cell_class(pos, name);
|
||||
this.program.addCellClass(pos, name);
|
||||
});
|
||||
c.listen(CpuEvent.InstructionParsed, ({ instr, code, pos }) => {
|
||||
this.program.remove_all_cell_class("instruction_argument");
|
||||
this.program.remove_all_cell_class("current_instruction");
|
||||
this.program.remove_cell_class(pos, "constant", "register", "memory", "invalid");
|
||||
this.program.add_cell_class(pos, "current_instruction");
|
||||
this.program.add_cell_class(pos, "instruction");
|
||||
this.program.removeAllCellClass("instruction_argument");
|
||||
this.program.removeAllCellClass("current_instruction");
|
||||
this.program.removeCellClass(pos, "constant", "register", "memory", "invalid");
|
||||
this.program.addCellClass(pos, "current_instruction");
|
||||
this.program.addCellClass(pos, "instruction");
|
||||
});
|
||||
c.listen(CpuEvent.InvalidParsed, ({ code, pos }) => {
|
||||
this.program.remove_cell_class(pos, "constant", "register", "memory", "instruction");
|
||||
this.program.add_cell_class(pos, "invalid");
|
||||
this.program.removeCellClass(pos, "constant", "register", "memory", "instruction");
|
||||
this.program.addCellClass(pos, "invalid");
|
||||
});
|
||||
}
|
||||
}
|
||||
|
|
|
@ -24,8 +24,8 @@ export default class RegisterView extends CelledViewer implements UiComponent {
|
|||
});
|
||||
}
|
||||
|
||||
init_cpu_events(c: CpuEventHandler): void {
|
||||
c.listen(CpuEvent.RegisterChanged, ({ register_no, value }) => this.set_cell_value(register_no, value));
|
||||
initCpuEvents(c: CpuEventHandler): void {
|
||||
c.listen(CpuEvent.RegisterChanged, ({ register_no, value }) => this.setCellValue(register_no, value));
|
||||
c.listen(CpuEvent.Reset, () => this.reset());
|
||||
}
|
||||
}
|
||||
|
|
|
@ -13,14 +13,14 @@ export default class ResetButtons implements UiComponent {
|
|||
const reset_button = el("button").cl("nostyle").tx("R").fin();
|
||||
const trash_button = el("button").cl("nostyle").tx("T").fin();
|
||||
|
||||
reset_button.addEventListener("click", () => this.reset_clicked());
|
||||
trash_button.addEventListener("click", () => this.trash_clicked());
|
||||
reset_button.addEventListener("click", () => this.resetClicked());
|
||||
trash_button.addEventListener("click", () => this.trashClicked());
|
||||
this.container.append(reset_button, trash_button);
|
||||
}
|
||||
|
||||
reset_clicked(): void {}
|
||||
resetClicked(): void {}
|
||||
|
||||
trash_clicked(): void {
|
||||
trashClicked(): void {
|
||||
this.cpu_signals.dispatch(UiCpuSignal.RequestCpuReset);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -29,7 +29,7 @@ export default class SaveLoad implements UiComponent {
|
|||
this.download();
|
||||
});
|
||||
this.binary_upload.addEventListener("change", (e) => {
|
||||
this.upload_changed(e);
|
||||
this.uploadChanged(e);
|
||||
});
|
||||
}
|
||||
|
||||
|
@ -52,7 +52,7 @@ export default class SaveLoad implements UiComponent {
|
|||
});
|
||||
}
|
||||
|
||||
private upload_changed(e: Event): void {
|
||||
private uploadChanged(e: Event): void {
|
||||
const t = e.target;
|
||||
if (t === null) return;
|
||||
|
||||
|
|
|
@ -20,9 +20,9 @@ export default interface UiComponent {
|
|||
cpu_signals?: UiCpuSignalHandler;
|
||||
/** Completely reset the state of the component */
|
||||
reset?: () => void;
|
||||
soft_reset?: () => void;
|
||||
softReset?: () => void;
|
||||
/** Allows listening CPUEvents*/
|
||||
init_cpu_events?: (c: CpuEventHandler) => void;
|
||||
initCpuEvents?: (c: CpuEventHandler) => void;
|
||||
}
|
||||
|
||||
export interface UiComponentConstructor {
|
||||
|
|
|
@ -32,7 +32,7 @@ export default abstract class WindowBox {
|
|||
title_bar_text_box.textContent = title;
|
||||
|
||||
this.collapse_button = el("button").id("collapse_button").cl("nostyle").fin();
|
||||
this.collapse_button.addEventListener("click", () => this.toggle_collapse());
|
||||
this.collapse_button.addEventListener("click", () => this.toggleCollapse());
|
||||
|
||||
this.title_bar.appendChild(title_bar_text_box);
|
||||
this.title_bar.appendChild(this.collapse_button);
|
||||
|
@ -48,20 +48,20 @@ export default abstract class WindowBox {
|
|||
this.resize.addEventListener("mousedown", (e) => {
|
||||
if (this.resize_func) window.addEventListener("mousemove", this.resize_func);
|
||||
});
|
||||
window.addEventListener("mouseup", () => this.remove_resize_listeners());
|
||||
window.addEventListener("mouseleave", () => this.remove_resize_listeners());
|
||||
window.addEventListener("mouseup", () => this.removeResizeListeners());
|
||||
window.addEventListener("mouseleave", () => this.removeResizeListeners());
|
||||
}
|
||||
}
|
||||
|
||||
collapse(): void {
|
||||
this.container.classList.add("collapsed");
|
||||
this.remove_resize_listeners();
|
||||
this.removeResizeListeners();
|
||||
if (this.resize) this.resize.style.visibility = "hidden";
|
||||
this.set_height(this.title_bar.offsetHeight - BORDER_STROKE);
|
||||
this.setHeight(this.title_bar.offsetHeight - BORDER_STROKE);
|
||||
this.collapsed = true;
|
||||
}
|
||||
|
||||
correct_height_value(height: number): number {
|
||||
correctHeightValue(height: number): number {
|
||||
if (this.fit_content) {
|
||||
let height_sum = 0;
|
||||
for (const c of this.container.children) {
|
||||
|
@ -73,7 +73,7 @@ export default abstract class WindowBox {
|
|||
return height;
|
||||
}
|
||||
|
||||
toggle_collapse(): void {
|
||||
toggleCollapse(): void {
|
||||
if (this.collapsed) {
|
||||
this.uncollapse();
|
||||
} else {
|
||||
|
@ -81,27 +81,27 @@ export default abstract class WindowBox {
|
|||
}
|
||||
}
|
||||
|
||||
set_height(height: number): void {
|
||||
setHeight(height: number): void {
|
||||
this.container.style.height = `${height + 2 * BORDER_STROKE}px`;
|
||||
}
|
||||
|
||||
uncollapse(): void {
|
||||
this.container.classList.remove("collapsed");
|
||||
if (this.resize) this.resize.style.visibility = "unset";
|
||||
const new_height = this.correct_height_value(this.title_bar.offsetHeight + 200);
|
||||
this.set_height(new_height);
|
||||
const new_height = this.correctHeightValue(this.title_bar.offsetHeight + 200);
|
||||
this.setHeight(new_height);
|
||||
|
||||
this.collapsed = false;
|
||||
}
|
||||
|
||||
remove_resize_listeners(): void {
|
||||
removeResizeListeners(): void {
|
||||
if (this.resize_func) window.removeEventListener("mousemove", this.resize_func);
|
||||
}
|
||||
|
||||
resize_move(e: MouseEvent): void {
|
||||
if (this.collapsed) {
|
||||
this.uncollapse();
|
||||
this.remove_resize_listeners();
|
||||
this.removeResizeListeners();
|
||||
return;
|
||||
}
|
||||
const distance_to_title = e.clientY - this.container.offsetTop - this.title_bar.offsetHeight + window.scrollY + 5;
|
||||
|
@ -109,6 +109,6 @@ export default abstract class WindowBox {
|
|||
this.collapse();
|
||||
return;
|
||||
}
|
||||
this.set_height(e.clientY - this.container.offsetTop + window.scrollY);
|
||||
this.setHeight(e.clientY - this.container.offsetTop + window.scrollY);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -14,7 +14,7 @@ export default class BankVisualizer extends WindowBox implements UiComponent {
|
|||
this.vram_banks = [...element.querySelectorAll("#vram_bank>polyline")] as Array<SVGPolylineElement>;
|
||||
}
|
||||
|
||||
init_cpu_events(c: CpuEventHandler): void {
|
||||
initCpuEvents(c: CpuEventHandler): void {
|
||||
c.listen(CpuEvent.SetVramBank, ({ bank }) => {
|
||||
for (const bank_path of this.vram_banks) bank_path.setAttribute("stroke", "gray");
|
||||
this.vram_banks[bank].setAttribute("stroke", "yellow");
|
||||
|
|
|
@ -1,4 +1,4 @@
|
|||
import { el, format_hex } from "../../etc";
|
||||
import { el, formatHex } from "../../etc";
|
||||
import { CpuEvent, CpuEventHandler, UiCpuSignalHandler, UiEventHandler } from "../../events";
|
||||
import { Instruction, ParamType, ParameterType } from "../../instructionSet";
|
||||
import { u8 } from "../../num";
|
||||
|
@ -13,12 +13,12 @@ export default class InstructionExplainer extends WindowBox implements UiCompone
|
|||
this.cpu_signals = cpu_signals;
|
||||
this.events = events;
|
||||
}
|
||||
add_instruction(instr: Instruction, pos: u8, byte: u8): void {
|
||||
addInstruction(instr: Instruction, pos: u8, byte: u8): void {
|
||||
this.reset();
|
||||
this.add_box(format_hex(byte), instr.name, "instruction");
|
||||
this.addBox(formatHex(byte), instr.name, "instruction");
|
||||
}
|
||||
|
||||
private add_box(box_icon_text: string, name: string, css_class: string): void {
|
||||
private addBox(box_icon_text: string, name: string, css_class: string): void {
|
||||
const instr_box = el("div").id("expl_box").fin();
|
||||
const instr_icon = el("span")
|
||||
.id("expl_icon")
|
||||
|
@ -32,7 +32,7 @@ export default class InstructionExplainer extends WindowBox implements UiCompone
|
|||
this.container.appendChild(instr_box);
|
||||
}
|
||||
|
||||
add_parameter(param: ParameterType, pos: u8, byte: u8): void {
|
||||
addParameter(param: ParameterType, pos: u8, byte: u8): void {
|
||||
const t = param.type;
|
||||
let name;
|
||||
if (t === ParamType.Const) {
|
||||
|
@ -44,23 +44,23 @@ export default class InstructionExplainer extends WindowBox implements UiCompone
|
|||
} else {
|
||||
throw new Error("unreachable");
|
||||
}
|
||||
this.add_box(format_hex(byte), param.desc, name);
|
||||
this.addBox(formatHex(byte), param.desc, name);
|
||||
}
|
||||
|
||||
add_invalid(pos: u8, byte: u8): void {
|
||||
addInvalid(pos: u8, byte: u8): void {
|
||||
this.reset();
|
||||
this.add_box(format_hex(byte), "Invalid Instruction", "invalid");
|
||||
this.addBox(formatHex(byte), "Invalid Instruction", "invalid");
|
||||
}
|
||||
|
||||
init_cpu_events(c: CpuEventHandler): void {
|
||||
initCpuEvents(c: CpuEventHandler): void {
|
||||
c.listen(CpuEvent.ParameterParsed, ({ param, code, pos }) => {
|
||||
this.add_parameter(param, pos, code);
|
||||
this.addParameter(param, pos, code);
|
||||
});
|
||||
c.listen(CpuEvent.InstructionParsed, ({ instr, code, pos }) => {
|
||||
this.add_instruction(instr, pos, code);
|
||||
this.addInstruction(instr, pos, code);
|
||||
});
|
||||
c.listen(CpuEvent.InvalidParsed, ({ code, pos }) => {
|
||||
this.add_invalid(pos, code);
|
||||
this.addInvalid(pos, code);
|
||||
});
|
||||
}
|
||||
|
||||
|
|
|
@ -15,7 +15,7 @@ export default class Printout extends WindowBox implements UiComponent {
|
|||
this.container.appendChild(this.text_box);
|
||||
}
|
||||
|
||||
init_cpu_events(c: CpuEventHandler): void {
|
||||
initCpuEvents(c: CpuEventHandler): void {
|
||||
c.listen(CpuEvent.Print, (c) => {
|
||||
this.text_box.textContent += c;
|
||||
});
|
||||
|
|
|
@ -46,7 +46,7 @@ export default class Screen extends WindowBox implements UiComponent {
|
|||
}
|
||||
}
|
||||
|
||||
init_cpu_events(c: CpuEventHandler): void {
|
||||
initCpuEvents(c: CpuEventHandler): void {
|
||||
c.listen(CpuEvent.MemoryChanged, ({ address, bank, value }) => {
|
||||
if (bank !== 1) return;
|
||||
|
||||
|
|
Loading…
Reference in a new issue