Linted & Formatted project
This commit is contained in:
parent
322378904c
commit
fc9a0df38d
|
|
@ -38,7 +38,8 @@
|
|||
"predeploy": "npm run dist",
|
||||
"deploy": "gh-pages -d dist",
|
||||
"lint": "eslint src --ext .ts",
|
||||
"lint:fix": "eslint src --ext .ts --fix"
|
||||
"lint:fix": "eslint src --ext .ts --fix",
|
||||
"format": "prettier --write ./src/**/*.ts"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@rollup/plugin-typescript": "^11.1.2",
|
||||
|
|
|
|||
|
|
@ -54,15 +54,15 @@ export class Editor {
|
|||
}
|
||||
case "Enter": {
|
||||
if (!this.root.selection.selectedCell) return;
|
||||
|
||||
|
||||
this.root.events.dispatch({
|
||||
type: EventTypes.CELL_CHANGE,
|
||||
cell: this.root.getCell(this.root.selection.selectedCell),
|
||||
values: {
|
||||
value: this.element.value,
|
||||
displayValue: this.element.value,
|
||||
}
|
||||
})
|
||||
},
|
||||
});
|
||||
|
||||
this.hide();
|
||||
}
|
||||
|
|
|
|||
|
|
@ -43,7 +43,7 @@ export class Scroller {
|
|||
}
|
||||
|
||||
public setSelectingMode(mode: boolean) {
|
||||
this.isSelecting = mode
|
||||
this.isSelecting = mode;
|
||||
}
|
||||
|
||||
private handleMouseMove = (event: MouseEvent) => {
|
||||
|
|
@ -51,37 +51,42 @@ export class Scroller {
|
|||
const { offsetX, offsetY } = event;
|
||||
const lastSelectedCell = this.root.getCellByCoords(offsetX, offsetY);
|
||||
|
||||
let isRangeChanged = false
|
||||
let isRangeChanged = false;
|
||||
|
||||
if (this.root.selection.selectedRange) {
|
||||
isRangeChanged = !checkEqualCellSelections(this.root.selection.selectedRange.to, lastSelectedCell)
|
||||
isRangeChanged = !checkEqualCellSelections(
|
||||
this.root.selection.selectedRange.to,
|
||||
lastSelectedCell,
|
||||
);
|
||||
|
||||
if (isRangeChanged) {
|
||||
this.root.selection.selectedRange.to = lastSelectedCell;
|
||||
this.root.events.dispatch({
|
||||
type: EventTypes.SELECTION_CHANGE,
|
||||
selection: this.root.selection,
|
||||
enableCallback: true
|
||||
})
|
||||
enableCallback: true,
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
};
|
||||
|
||||
private handleMouseUp = () => {
|
||||
this.isSelecting = false;
|
||||
const newSelection = {...this.root.selection}
|
||||
const newSelection = { ...this.root.selection };
|
||||
|
||||
if (this.root.selection.selectedRange) {
|
||||
if (
|
||||
checkEqualCellSelections(this.root.selection.selectedRange.from, this.root.selection.selectedRange.to)
|
||||
checkEqualCellSelections(
|
||||
this.root.selection.selectedRange.from,
|
||||
this.root.selection.selectedRange.to,
|
||||
)
|
||||
) {
|
||||
newSelection.selectedRange = null;
|
||||
this.root.events.dispatch({
|
||||
type: EventTypes.SELECTION_CHANGE,
|
||||
selection: newSelection,
|
||||
enableCallback: false
|
||||
})
|
||||
enableCallback: false,
|
||||
});
|
||||
}
|
||||
}
|
||||
|
||||
|
|
@ -118,7 +123,7 @@ export class Scroller {
|
|||
if (
|
||||
this.root.selection.selectedCell &&
|
||||
this.root.selection.selectedCell.column <
|
||||
this.root.config.columns.length - 1
|
||||
this.root.config.columns.length - 1
|
||||
) {
|
||||
this.root.selection.selectedCell.column += 1;
|
||||
// this.root.renderSheet();
|
||||
|
|
@ -139,7 +144,7 @@ export class Scroller {
|
|||
if (
|
||||
this.root.selection.selectedCell &&
|
||||
this.root.selection.selectedCell.row <
|
||||
this.root.config.rows.length - 1
|
||||
this.root.config.rows.length - 1
|
||||
) {
|
||||
this.root.selection.selectedCell.row += 1;
|
||||
// this.root.renderSheet();
|
||||
|
|
@ -150,8 +155,8 @@ export class Scroller {
|
|||
this.root.events.dispatch({
|
||||
type: EventTypes.SELECTION_CHANGE,
|
||||
selection: this.root.selection,
|
||||
enableCallback: true
|
||||
})
|
||||
enableCallback: true,
|
||||
});
|
||||
}
|
||||
|
||||
//* Start typings
|
||||
|
|
@ -183,8 +188,8 @@ export class Scroller {
|
|||
this.root.events.dispatch({
|
||||
type: EventTypes.CELL_CLICK,
|
||||
event,
|
||||
scroller: this
|
||||
})
|
||||
scroller: this,
|
||||
});
|
||||
};
|
||||
|
||||
private handleScroll = () => {
|
||||
|
|
|
|||
|
|
@ -2,19 +2,18 @@ import Spreadsheet, { SpreadsheetConstructorProperties } from "./main";
|
|||
|
||||
const options: SpreadsheetConstructorProperties = {
|
||||
onCellClick: (event, cell) => {
|
||||
console.log('Cell click', event, cell)
|
||||
console.log("Cell click", event, cell);
|
||||
},
|
||||
onSelectionChange: (selection) => {
|
||||
console.log("Changed selection: ", selection)
|
||||
console.log("Changed selection: ", selection);
|
||||
},
|
||||
onCellChange(cell) {
|
||||
console.log("Cell changed: ", cell)
|
||||
console.log("Cell changed: ", cell);
|
||||
},
|
||||
}
|
||||
};
|
||||
|
||||
const sheet = new Spreadsheet("#spreadsheet", options);
|
||||
|
||||
|
||||
function saveDataToLS() {
|
||||
const serializableData = sheet.serializeData();
|
||||
localStorage.setItem("sheet", JSON.stringify(serializableData));
|
||||
|
|
|
|||
27
src/main.ts
27
src/main.ts
|
|
@ -10,7 +10,13 @@ import {
|
|||
Position,
|
||||
SerializableCell,
|
||||
} from "./modules/cell";
|
||||
import { CellChangeEvent, CellClickEvent, Config, SelectionChangeEvent, ViewProperties } from "./modules/config";
|
||||
import {
|
||||
CellChangeEvent,
|
||||
CellClickEvent,
|
||||
Config,
|
||||
SelectionChangeEvent,
|
||||
ViewProperties,
|
||||
} from "./modules/config";
|
||||
import { RangeSelectionType, Selection } from "./modules/selection";
|
||||
import { Styles } from "./modules/styles";
|
||||
import { Viewport } from "./modules/viewport";
|
||||
|
|
@ -37,9 +43,9 @@ import { Events } from "./modules/events";
|
|||
|
||||
export interface SpreadsheetConstructorProperties {
|
||||
view?: ViewProperties;
|
||||
onCellClick?: CellClickEvent | null
|
||||
onSelectionChange?: SelectionChangeEvent | null
|
||||
onCellChange?: CellChangeEvent | null
|
||||
onCellClick?: CellClickEvent | null;
|
||||
onSelectionChange?: SelectionChangeEvent | null;
|
||||
onCellChange?: CellChangeEvent | null;
|
||||
}
|
||||
|
||||
export const CSS_PREFIX = "modern_sc_";
|
||||
|
|
@ -58,7 +64,7 @@ export default class Spreadsheet {
|
|||
public viewport: Viewport;
|
||||
public selection: Selection;
|
||||
public cache: Cache;
|
||||
public events: Events
|
||||
public events: Events;
|
||||
|
||||
constructor(
|
||||
target: string | HTMLElement,
|
||||
|
|
@ -75,9 +81,9 @@ export default class Spreadsheet {
|
|||
|
||||
this.config = new Config(config);
|
||||
|
||||
this.config.onCellClick = props?.onCellClick ?? null
|
||||
this.config.onSelectonChange = props?.onSelectionChange ?? null
|
||||
this.config.onCellChange = props?.onCellChange ?? null
|
||||
this.config.onCellClick = props?.onCellClick ?? null;
|
||||
this.config.onSelectonChange = props?.onSelectionChange ?? null;
|
||||
this.config.onCellChange = props?.onCellChange ?? null;
|
||||
|
||||
this.rowsBar = new RowsBar(this);
|
||||
this.columnsBar = new ColumnsBar(this);
|
||||
|
|
@ -92,8 +98,7 @@ export default class Spreadsheet {
|
|||
this.scroller.getViewportBoundlingRect(),
|
||||
);
|
||||
this.selection = new Selection();
|
||||
this.events = new Events(this)
|
||||
|
||||
this.events = new Events(this);
|
||||
|
||||
this.data = data;
|
||||
this.styles = new Styles();
|
||||
|
|
@ -376,7 +381,7 @@ export default class Spreadsheet {
|
|||
view,
|
||||
rows,
|
||||
columns,
|
||||
onCellClick: null
|
||||
onCellClick: null,
|
||||
});
|
||||
|
||||
return config;
|
||||
|
|
|
|||
|
|
@ -7,9 +7,9 @@ export interface ViewProperties {
|
|||
width: number;
|
||||
height: number;
|
||||
}
|
||||
export type CellClickEvent = (event: MouseEvent, cell: Cell) => void
|
||||
export type SelectionChangeEvent = (selection: Selection) => void
|
||||
export type CellChangeEvent = (cell: Cell) => void
|
||||
export type CellClickEvent = (event: MouseEvent, cell: Cell) => void;
|
||||
export type SelectionChangeEvent = (selection: Selection) => void;
|
||||
export type CellChangeEvent = (cell: Cell) => void;
|
||||
|
||||
export type ConfigProperties = {
|
||||
/** Please, end it with '_' symbol.
|
||||
|
|
@ -21,9 +21,9 @@ export type ConfigProperties = {
|
|||
rows: Row[];
|
||||
columns: Column[];
|
||||
view: ViewProperties;
|
||||
onCellClick?: CellClickEvent | null
|
||||
onSelectionChange?: SelectionChangeEvent | null
|
||||
onCellChange?: CellChangeEvent | null
|
||||
onCellClick?: CellClickEvent | null;
|
||||
onSelectionChange?: SelectionChangeEvent | null;
|
||||
onCellChange?: CellChangeEvent | null;
|
||||
};
|
||||
|
||||
export type SheetConfigConstructorProps = {
|
||||
|
|
@ -39,17 +39,17 @@ export class Config {
|
|||
height: 600,
|
||||
};
|
||||
|
||||
onCellClick: ((event: MouseEvent, cell: Cell) => void) | null = null
|
||||
onSelectonChange: SelectionChangeEvent | null = null
|
||||
onCellChange: CellChangeEvent | null = null
|
||||
onCellClick: ((event: MouseEvent, cell: Cell) => void) | null = null;
|
||||
onSelectonChange: SelectionChangeEvent | null = null;
|
||||
onCellChange: CellChangeEvent | null = null;
|
||||
|
||||
constructor(props: ConfigProperties) {
|
||||
this.columns = props.columns;
|
||||
this.rows = props.rows;
|
||||
this.view = props.view;
|
||||
|
||||
this.onCellClick = props.onCellClick ?? null
|
||||
this.onSelectonChange = props.onSelectionChange ?? null
|
||||
this.onCellChange = props.onCellChange ?? null
|
||||
this.onCellClick = props.onCellClick ?? null;
|
||||
this.onSelectonChange = props.onSelectionChange ?? null;
|
||||
this.onCellChange = props.onCellChange ?? null;
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -2,106 +2,111 @@ import { Scroller } from "../components/scroller";
|
|||
import Spreadsheet, { Cell, CellConstructorProps, Selection } from "../main";
|
||||
|
||||
export enum EventTypes {
|
||||
CELL_CLICK = "CELL_CLICK",
|
||||
SELECTION_CHANGE = "CHANGE_SELECTION",
|
||||
CELL_CHANGE = "CELL_CHANGE"
|
||||
CELL_CLICK = "CELL_CLICK",
|
||||
SELECTION_CHANGE = "CHANGE_SELECTION",
|
||||
CELL_CHANGE = "CELL_CHANGE",
|
||||
}
|
||||
|
||||
export type CellClickEvent = {
|
||||
type: EventTypes.CELL_CLICK
|
||||
event: MouseEvent
|
||||
scroller: Scroller
|
||||
}
|
||||
type: EventTypes.CELL_CLICK;
|
||||
event: MouseEvent;
|
||||
scroller: Scroller;
|
||||
};
|
||||
|
||||
export type ChangeSelectionEvent = {
|
||||
type: EventTypes.SELECTION_CHANGE,
|
||||
selection: Selection
|
||||
enableCallback?: boolean
|
||||
}
|
||||
type: EventTypes.SELECTION_CHANGE;
|
||||
selection: Selection;
|
||||
enableCallback?: boolean;
|
||||
};
|
||||
|
||||
export type ChangeCellEvent = {
|
||||
type: EventTypes.CELL_CHANGE,
|
||||
cell: Cell,
|
||||
values: Partial<Omit<CellConstructorProps, "position">>
|
||||
}
|
||||
type: EventTypes.CELL_CHANGE;
|
||||
cell: Cell;
|
||||
values: Partial<Omit<CellConstructorProps, "position">>;
|
||||
};
|
||||
|
||||
export type ActionTypes = CellClickEvent | ChangeSelectionEvent | ChangeCellEvent
|
||||
export type ActionTypes =
|
||||
| CellClickEvent
|
||||
| ChangeSelectionEvent
|
||||
| ChangeCellEvent;
|
||||
|
||||
export class Events {
|
||||
root: Spreadsheet;
|
||||
|
||||
root: Spreadsheet
|
||||
constructor(root: Spreadsheet) {
|
||||
this.root = root;
|
||||
}
|
||||
|
||||
constructor(root: Spreadsheet) {
|
||||
this.root = root
|
||||
dispatch(action: ActionTypes) {
|
||||
switch (action.type) {
|
||||
case EventTypes.CELL_CLICK: {
|
||||
const { event, scroller } = action;
|
||||
//
|
||||
//* Here may be side effects
|
||||
//
|
||||
this.cellClick(event, scroller);
|
||||
break;
|
||||
}
|
||||
|
||||
case EventTypes.SELECTION_CHANGE: {
|
||||
const { selection, enableCallback } = action;
|
||||
//
|
||||
//* Here may be side effects
|
||||
//
|
||||
this.changeSelection(selection, enableCallback);
|
||||
break;
|
||||
}
|
||||
|
||||
case EventTypes.CELL_CHANGE: {
|
||||
const { cell, values } = action;
|
||||
//
|
||||
//* Here may be side effects
|
||||
//
|
||||
this.changeCellValues(cell, values);
|
||||
break;
|
||||
}
|
||||
|
||||
default: {
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
dispatch(action: ActionTypes) {
|
||||
switch (action.type) {
|
||||
case EventTypes.CELL_CLICK: {
|
||||
const { event, scroller } = action
|
||||
//
|
||||
//* Here may be side effects
|
||||
//
|
||||
this.cellClick(event, scroller)
|
||||
break;
|
||||
}
|
||||
private cellClick = (event: MouseEvent, scroller: Scroller) => {
|
||||
if (event.button !== 0) return; // Left mouse button
|
||||
const { offsetX, offsetY } = event;
|
||||
const clickedCell = this.root.getCellByCoords(offsetX, offsetY);
|
||||
const cell = this.root.getCell(clickedCell);
|
||||
|
||||
case EventTypes.SELECTION_CHANGE: {
|
||||
const { selection, enableCallback } = action
|
||||
//
|
||||
//* Here may be side effects
|
||||
//
|
||||
this.changeSelection(selection, enableCallback)
|
||||
break;
|
||||
}
|
||||
const selection = new Selection();
|
||||
selection.selectedCell = clickedCell;
|
||||
selection.selectedRange = {
|
||||
from: clickedCell,
|
||||
to: clickedCell,
|
||||
};
|
||||
|
||||
case EventTypes.CELL_CHANGE: {
|
||||
const { cell, values } = action
|
||||
//
|
||||
//* Here may be side effects
|
||||
//
|
||||
this.changeCellValues(cell, values)
|
||||
break;
|
||||
}
|
||||
scroller.setSelectingMode(true);
|
||||
|
||||
default: {
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
this.changeSelection(selection, true);
|
||||
|
||||
private cellClick = (event: MouseEvent, scroller: Scroller) => {
|
||||
if (event.button !== 0) return; // Left mouse button
|
||||
const { offsetX, offsetY } = event;
|
||||
const clickedCell = this.root.getCellByCoords(offsetX, offsetY);
|
||||
const cell = this.root.getCell(clickedCell)
|
||||
this.root.config.onCellClick?.(event, cell);
|
||||
};
|
||||
|
||||
const selection = new Selection()
|
||||
selection.selectedCell = clickedCell
|
||||
selection.selectedRange = {
|
||||
from: clickedCell,
|
||||
to: clickedCell,
|
||||
};
|
||||
private changeSelection = (selection: Selection, enableCallback = false) => {
|
||||
this.root.selection = selection;
|
||||
|
||||
scroller.setSelectingMode(true);
|
||||
if (enableCallback) this.root.config.onSelectonChange?.(selection);
|
||||
this.root.renderSheet();
|
||||
this.root.renderColumnsBar();
|
||||
this.root.renderRowsBar();
|
||||
};
|
||||
|
||||
this.changeSelection(selection, true)
|
||||
private changeCellValues(
|
||||
cell: Cell,
|
||||
values: Partial<Omit<CellConstructorProps, "position">>,
|
||||
) {
|
||||
this.root.changeCellValues(cell.position, values);
|
||||
|
||||
this.root.config.onCellClick?.(event, cell)
|
||||
}
|
||||
|
||||
private changeSelection = (selection: Selection, enableCallback = false) => {
|
||||
this.root.selection = selection
|
||||
|
||||
if (enableCallback) this.root.config.onSelectonChange?.(selection)
|
||||
this.root.renderSheet();
|
||||
this.root.renderColumnsBar();
|
||||
this.root.renderRowsBar();
|
||||
}
|
||||
|
||||
private changeCellValues(cell: Cell, values: Partial<Omit<CellConstructorProps, "position">>) {
|
||||
this.root.changeCellValues(cell.position, values)
|
||||
|
||||
this.root.config.onCellChange?.(cell)
|
||||
}
|
||||
}
|
||||
this.root.config.onCellChange?.(cell);
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -1,12 +1,20 @@
|
|||
import { BaseSelectionType, RangeSelectionType } from "../main";
|
||||
|
||||
export function checkEqualRanges(range1: RangeSelectionType, range2: RangeSelectionType) {
|
||||
const equalRows = range1.from.row === range2.to.row
|
||||
const equalColumns = range1.from.column === range2.to.column
|
||||
export function checkEqualRanges(
|
||||
range1: RangeSelectionType,
|
||||
range2: RangeSelectionType,
|
||||
) {
|
||||
const equalRows = range1.from.row === range2.to.row;
|
||||
const equalColumns = range1.from.column === range2.to.column;
|
||||
|
||||
return equalRows && equalColumns
|
||||
return equalRows && equalColumns;
|
||||
}
|
||||
|
||||
export function checkEqualCellSelections(selection1: BaseSelectionType, selection2: BaseSelectionType) {
|
||||
return selection1.column === selection2.column && selection1.row === selection2.row
|
||||
}
|
||||
export function checkEqualCellSelections(
|
||||
selection1: BaseSelectionType,
|
||||
selection2: BaseSelectionType,
|
||||
) {
|
||||
return (
|
||||
selection1.column === selection2.column && selection1.row === selection2.row
|
||||
);
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in New Issue