solid-pianoroll 0.0.9 → 0.0.11

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (33) hide show
  1. package/dist/cjs/index.js +458 -456
  2. package/dist/cjs/index.js.map +1 -1
  3. package/dist/esm/index.js +460 -458
  4. package/dist/esm/index.js.map +1 -1
  5. package/dist/source/PianoRoll.jsx +53 -27
  6. package/dist/source/PianoRollContext.jsx +3 -42
  7. package/dist/source/PianoRollGrid.jsx +18 -33
  8. package/dist/source/PianoRollKeys.jsx +10 -6
  9. package/dist/source/PianoRollNotes.jsx +91 -46
  10. package/dist/source/usePianoRoll.js +6 -3
  11. package/dist/source/viewport/HorizontalZoomControl.jsx +9 -0
  12. package/dist/source/viewport/ScrollContainer.jsx +87 -0
  13. package/dist/source/viewport/ScrollZoomViewPort.jsx +19 -0
  14. package/dist/source/viewport/VerticalZoomControl.jsx +12 -0
  15. package/dist/source/viewport/createViewPortDimension.js +39 -0
  16. package/dist/types/PianoRoll.d.ts +1 -1
  17. package/dist/types/PianoRollContext.d.ts +2 -22
  18. package/dist/types/PianoRollNotes.d.ts +1 -1
  19. package/dist/types/usePianoRoll.d.ts +1 -0
  20. package/dist/types/viewport/HorizontalZoomControl.d.ts +3 -0
  21. package/dist/types/viewport/ScrollContainer.d.ts +5 -0
  22. package/dist/types/viewport/ScrollZoomViewPort.d.ts +23 -0
  23. package/dist/types/viewport/VerticalZoomControl.d.ts +3 -0
  24. package/dist/types/viewport/createViewPortDimension.d.ts +31 -0
  25. package/package.json +7 -1
  26. package/dist/source/HorizontalZoomControl.jsx +0 -9
  27. package/dist/source/ScrollContainer.jsx +0 -138
  28. package/dist/source/VerticalZoomControl.jsx +0 -12
  29. package/dist/source/useViewPortScaler.js +0 -44
  30. package/dist/types/HorizontalZoomControl.d.ts +0 -2
  31. package/dist/types/ScrollContainer.d.ts +0 -5
  32. package/dist/types/VerticalZoomControl.d.ts +0 -2
  33. package/dist/types/useViewPortScaler.d.ts +0 -20
@@ -1,138 +0,0 @@
1
- import { createEffect, createMemo, createSignal } from "solid-js";
2
- import { usePianoRollContext } from "./PianoRollContext";
3
- const ScrollContainer = (props) => {
4
- let scrollContentRef;
5
- const context = usePianoRollContext();
6
- const gridDivisorTicks = createMemo(() => (context.ppq * 4) / context.gridDivision);
7
- const forwardEventToNote = (event) => {
8
- const x = "clientX" in event ? event.clientX : event.touches[0]?.clientX ?? 0;
9
- const y = "clientY" in event ? event.clientY : event.touches[0]?.clientY ?? 0;
10
- const elementUnderMouse = [...(context.notesContainer?.querySelectorAll?.("div") ?? [])].find((element) => {
11
- const rect = element.getBoundingClientRect();
12
- return (x >= rect.left &&
13
- rect.left + rect.width > x &&
14
- y >= rect.top &&
15
- rect.top + rect.height > y);
16
- });
17
- if (elementUnderMouse) {
18
- return elementUnderMouse.dispatchEvent(new MouseEvent(event.type, event));
19
- }
20
- };
21
- const handleScroll = (event) => {
22
- event.preventDefault();
23
- if (didUpdateScroll) {
24
- didUpdateScroll = false;
25
- return;
26
- }
27
- const maxVerticalPosition = context.verticalViewPort.getMaxPosition();
28
- const maxPosition = context.horizontalViewPort.getMaxPosition();
29
- const { width, height } = context.clientRect;
30
- const { scrollTop, scrollLeft, scrollWidth, scrollHeight } = event.currentTarget;
31
- const scrollTopAmount = scrollTop / (scrollHeight - height);
32
- const scrollLeftAmount = scrollLeft / (scrollWidth - width);
33
- context.onVerticalPositionChange?.(maxVerticalPosition * scrollTopAmount);
34
- context.onPositionChange?.(maxPosition * scrollLeftAmount);
35
- };
36
- let didUpdateScroll = false;
37
- createEffect(() => {
38
- const maxVerticalPosition = context.verticalViewPort.getMaxPosition();
39
- const maxPosition = context.horizontalViewPort.getMaxPosition();
40
- const scrollTopAmount = maxVerticalPosition > 0 ? context.verticalPosition / maxVerticalPosition : 0;
41
- const scrollLeftAmount = maxPosition > 0 ? context.position / maxPosition : 0;
42
- const { height, width } = context.clientRect;
43
- if (!scrollContentRef?.parentElement)
44
- return;
45
- const scrollDivHeight = context.verticalViewPort.getScrollSize();
46
- const scrollTop = scrollTopAmount * (scrollDivHeight - height);
47
- const scrollDivWidth = context.horizontalViewPort.getScrollSize();
48
- const scrollLeft = scrollLeftAmount * (scrollDivWidth - width);
49
- didUpdateScroll = true;
50
- scrollContentRef.style.height = `${scrollDivHeight}px`;
51
- scrollContentRef.style.width = `${scrollDivWidth}px`;
52
- scrollContentRef.parentElement.scrollTo({
53
- left: scrollLeft,
54
- top: scrollTop,
55
- });
56
- });
57
- const insertOrUpdateNote = (event) => {
58
- const position = context.horizontalViewPort.getPosition(event.clientX);
59
- const midi = 127 - Math.floor(context.verticalViewPort.getPosition(event.clientY));
60
- const eventPositionTicks = Math.floor(position / gridDivisorTicks()) * gridDivisorTicks();
61
- const velocity = 127;
62
- const existingNote = newNote();
63
- const ticks = existingNote?.ticks ?? eventPositionTicks;
64
- const durationTicks = existingNote?.ticks
65
- ? eventPositionTicks - existingNote?.ticks
66
- : gridDivisorTicks();
67
- const note = { midi, ticks, durationTicks, velocity };
68
- if (existingNote) {
69
- context.onNoteChange?.(newNoteIndex(), note);
70
- return newNoteIndex();
71
- }
72
- else {
73
- return context.onInsertNote?.(note) ?? -1;
74
- }
75
- };
76
- const [newNoteIndex, setNewNoteIndex] = createSignal(-1);
77
- const newNote = createMemo(() => context.notes[newNoteIndex()]);
78
- const [isMouseDown, setIsMouseDown] = createSignal(false);
79
- return (<div ref={props.ref} class="PianoRoll-Vertical-Scroller" style={{
80
- flex: 1,
81
- ...(context.noteDragMode && {
82
- cursor: context.noteDragMode === "trimStart"
83
- ? "w-resize"
84
- : context.noteDragMode === "trimEnd"
85
- ? "e-resize"
86
- : "pointer",
87
- }),
88
- "z-index": 4,
89
- overflow: "scroll",
90
- "pointer-events": "auto",
91
- }} onScroll={handleScroll} onMouseDown={(event) => {
92
- if (forwardEventToNote(event))
93
- return;
94
- setIsMouseDown(true);
95
- }} onMouseMove={(event) => {
96
- event.preventDefault();
97
- if (forwardEventToNote(event))
98
- return;
99
- if (context.isDragging)
100
- return;
101
- if (!isMouseDown()) {
102
- context.onNoteDragModeChange(undefined);
103
- return;
104
- }
105
- const index = insertOrUpdateNote(event);
106
- setNewNoteIndex(index);
107
- }} onDblClick={(event) => {
108
- if (newNote())
109
- return;
110
- if (context.isDragging)
111
- return;
112
- if (forwardEventToNote(event))
113
- return;
114
- insertOrUpdateNote(event);
115
- }} onClick={(event) => {
116
- if (newNote()) {
117
- setNewNoteIndex(-1);
118
- return;
119
- }
120
- if (forwardEventToNote(event))
121
- return;
122
- if (!event.altKey)
123
- return;
124
- insertOrUpdateNote(event);
125
- }} onMouseUp={(event) => {
126
- setIsMouseDown(false);
127
- if (newNote())
128
- return;
129
- if (forwardEventToNote(event))
130
- return;
131
- if (!event.altKey)
132
- return;
133
- insertOrUpdateNote(event);
134
- }} onTouchStart={forwardEventToNote} onTouchMove={forwardEventToNote} onTouchEnd={forwardEventToNote} onTouchCancel={forwardEventToNote} onDragStart={forwardEventToNote} onDrag={forwardEventToNote} onDragEnd={forwardEventToNote}>
135
- <div ref={scrollContentRef}></div>
136
- </div>);
137
- };
138
- export default ScrollContainer;
@@ -1,12 +0,0 @@
1
- import { usePianoRollContext } from "./PianoRollContext";
2
- const VerticalZoomControl = () => {
3
- const context = usePianoRollContext();
4
- return (<input value={context.verticalZoom} onInput={(event) => context.onVerticalZoomChange?.(event.currentTarget.valueAsNumber)} type="range" min="1" max="11" step={0.01} {...{ orient: "vertical" }} style={{
5
- width: "16px",
6
- ...{
7
- "writing-mode": "bt-lr" /* IE */,
8
- "-webkit-appearance": "slider-vertical" /* WebKit */,
9
- },
10
- }}/>);
11
- };
12
- export default VerticalZoomControl;
@@ -1,44 +0,0 @@
1
- import { createMemo } from "solid-js";
2
- export default function useViewPortScaler(getState) {
3
- const state = createMemo(() => getState());
4
- function getScaledValue(position) {
5
- const virtualSize = state().viewPortSize * state().zoom;
6
- return (position / state().virtualRange) * virtualSize;
7
- }
8
- function getCoordinates(position) {
9
- return getScaledValue(position) - getScaledValue(state().virtualPosition);
10
- }
11
- function getVisibleRange() {
12
- return state().virtualRange / state().zoom;
13
- }
14
- function getPosition(offset) {
15
- const percentX = (offset - state().viewPortOffset) / state().viewPortSize;
16
- const position = state().virtualPosition + percentX * getVisibleRange();
17
- return position;
18
- }
19
- function getMaxPosition() {
20
- return state().virtualRange - state().virtualRange / state().zoom;
21
- }
22
- function getScrollSize() {
23
- return clamp(state().zoom * state().viewPortSize, state().viewPortSize, 100000);
24
- }
25
- function getVirtualDimensions(position, length) {
26
- const virtualLeft = getCoordinates(position);
27
- const virtualWidth = getScaledValue(length);
28
- const offset = clamp(virtualLeft, 0, state().viewPortSize);
29
- const size = clamp(virtualWidth - (offset - virtualLeft), 0, state().viewPortSize - offset);
30
- return { offset, size };
31
- }
32
- return {
33
- getScaledValue,
34
- getCoordinates,
35
- getPosition,
36
- getVirtualDimensions,
37
- getVisibleRange,
38
- getMaxPosition,
39
- getScrollSize,
40
- };
41
- }
42
- export const clamp = (value, min, max) => {
43
- return Math.max(min, Math.min(max, value));
44
- };
@@ -1,2 +0,0 @@
1
- declare const HorizontalZoomControl: () => import("solid-js").JSX.Element;
2
- export default HorizontalZoomControl;
@@ -1,5 +0,0 @@
1
- import { Ref } from "solid-js";
2
- declare const ScrollContainer: (props: {
3
- ref: Ref<HTMLDivElement>;
4
- }) => import("solid-js").JSX.Element;
5
- export default ScrollContainer;
@@ -1,2 +0,0 @@
1
- declare const VerticalZoomControl: () => import("solid-js").JSX.Element;
2
- export default VerticalZoomControl;
@@ -1,20 +0,0 @@
1
- export type ViewPortScaler = ReturnType<typeof useViewPortScaler>;
2
- export default function useViewPortScaler(getState: () => {
3
- virtualPosition: number;
4
- virtualRange: number;
5
- viewPortOffset: number;
6
- viewPortSize: number;
7
- zoom: number;
8
- }): {
9
- getScaledValue: (position: number) => number;
10
- getCoordinates: (position: number) => number;
11
- getPosition: (offset: number) => number;
12
- getVirtualDimensions: (position: number, length: number) => {
13
- offset: number;
14
- size: number;
15
- };
16
- getVisibleRange: () => number;
17
- getMaxPosition: () => number;
18
- getScrollSize: () => number;
19
- };
20
- export declare const clamp: (value: number, min: number, max: number) => number;