@omnimedia/omnitool 1.1.0-55 → 1.1.0-56
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.
- package/package.json +1 -1
- package/s/demo/demo.bundle.ts +5 -3
- package/s/demo/routines/waveform-test.ts +30 -5
- package/s/index.html.ts +1 -2
- package/s/timeline/parts/waveform/parts/collect.ts +72 -0
- package/s/timeline/parts/waveform/parts/render.ts +45 -0
- package/s/timeline/parts/waveform/parts/types.ts +24 -0
- package/s/timeline/parts/waveform/waveform.ts +152 -0
- package/s/timeline/parts/waveform.ts +0 -61
- package/x/demo/demo.bundle.js +2 -0
- package/x/demo/demo.bundle.js.map +1 -1
- package/x/demo/demo.bundle.min.js +11 -84
- package/x/demo/demo.bundle.min.js.map +4 -4
- package/x/demo/routines/waveform-test.js +24 -4
- package/x/demo/routines/waveform-test.js.map +1 -1
- package/x/index.html +3 -3
- package/x/index.html.js +1 -1
- package/x/timeline/parts/waveform/parts/collect.d.ts +11 -0
- package/x/timeline/parts/waveform/parts/collect.js +56 -0
- package/x/timeline/parts/waveform/parts/collect.js.map +1 -0
- package/x/timeline/parts/waveform/parts/render.d.ts +5 -0
- package/x/timeline/parts/waveform/parts/render.js +29 -0
- package/x/timeline/parts/waveform/parts/render.js.map +1 -0
- package/x/timeline/parts/waveform/parts/types.d.ts +21 -0
- package/x/timeline/parts/waveform/parts/types.js +2 -0
- package/x/timeline/parts/waveform/parts/types.js.map +1 -0
- package/x/timeline/parts/waveform/waveform.d.ts +17 -0
- package/x/timeline/parts/waveform/waveform.js +125 -0
- package/x/timeline/parts/waveform/waveform.js.map +1 -0
- package/x/timeline/parts/waveform.d.ts +1 -9
- package/x/timeline/parts/waveform.js +1 -48
- package/x/timeline/parts/waveform.js.map +1 -1
package/package.json
CHANGED
package/s/demo/demo.bundle.ts
CHANGED
|
@@ -26,8 +26,11 @@ let exportState: {timeline: TimelineFile; omni: Omni} | null = null
|
|
|
26
26
|
}
|
|
27
27
|
|
|
28
28
|
const setProgress = (card: HTMLElement, state: "idle" | "running" | "done") => {
|
|
29
|
-
const progress = card.querySelector(".progress") as HTMLProgressElement
|
|
30
|
-
const status = card.querySelector(".status") as HTMLSpanElement
|
|
29
|
+
const progress = card.querySelector(".progress") as HTMLProgressElement | null
|
|
30
|
+
const status = card.querySelector(".status") as HTMLSpanElement | null
|
|
31
|
+
|
|
32
|
+
if (!progress || !status)
|
|
33
|
+
return
|
|
31
34
|
|
|
32
35
|
if (state === "running") {
|
|
33
36
|
progress.removeAttribute("value")
|
|
@@ -124,4 +127,3 @@ exportButton.addEventListener("click", async () => {
|
|
|
124
127
|
await exportState.omni.render(exportState.timeline)
|
|
125
128
|
setProgress(exportCard, "done")
|
|
126
129
|
})
|
|
127
|
-
|
|
@@ -1,14 +1,39 @@
|
|
|
1
|
+
|
|
1
2
|
import {Driver} from "../../driver/driver.js"
|
|
2
|
-
import {Waveform} from "../../timeline/parts/waveform.js"
|
|
3
|
+
import {Waveform} from "../../timeline/parts/waveform/waveform.js"
|
|
3
4
|
|
|
4
5
|
export async function waveformTest(driver: Driver, source: File, root: HTMLElement) {
|
|
5
|
-
const container = root.querySelector(".waveform-canvas") as
|
|
6
|
+
const container = root.querySelector(".waveform-canvas") as HTMLDivElement
|
|
6
7
|
const widthSlider = root.querySelector(".width") as HTMLInputElement
|
|
8
|
+
|
|
7
9
|
container.replaceChildren()
|
|
8
|
-
|
|
10
|
+
container.style.position = "relative"
|
|
11
|
+
container.style.height = "96px"
|
|
12
|
+
container.style.overflow = "hidden"
|
|
13
|
+
|
|
14
|
+
const waveform = await Waveform.init(driver, source, {
|
|
15
|
+
tileHeight: 96,
|
|
16
|
+
onChange: () => renderTiles()
|
|
17
|
+
})
|
|
9
18
|
|
|
10
|
-
|
|
19
|
+
const renderTiles = () => {
|
|
11
20
|
const width = +widthSlider.value
|
|
12
|
-
|
|
21
|
+
const zoom = pixelsPerSecond(width, waveform.duration)
|
|
22
|
+
waveform.zoom = zoom
|
|
23
|
+
container.style.width = `${width}px`
|
|
24
|
+
container.replaceChildren(...[...waveform.getTiles().values()].map(tile => {
|
|
25
|
+
tile.canvas.style.position = "absolute"
|
|
26
|
+
tile.canvas.style.top = "0"
|
|
27
|
+
tile.canvas.style.left = `${tile.startTime * pixelsPerSecond(width, waveform.duration)}px`
|
|
28
|
+
tile.canvas.style.height = "100%"
|
|
29
|
+
return tile.canvas
|
|
30
|
+
}))
|
|
13
31
|
}
|
|
32
|
+
|
|
33
|
+
widthSlider.oninput = renderTiles
|
|
34
|
+
waveform.range = [0, waveform.duration]
|
|
35
|
+
}
|
|
36
|
+
|
|
37
|
+
function pixelsPerSecond(width: number, duration: number) {
|
|
38
|
+
return duration > 0 ? width / duration : 0
|
|
14
39
|
}
|
package/s/index.html.ts
CHANGED
|
@@ -85,7 +85,7 @@ export default ssg.page(import.meta.url, async orb => ({
|
|
|
85
85
|
</div>
|
|
86
86
|
<div class="waveform-controls">
|
|
87
87
|
<label>width</label>
|
|
88
|
-
<input class="width" type="range" min="100" max="1000000" value="1000" />
|
|
88
|
+
<input class="width" type="range" min="100" max="1000000" value="1000" step="100" />
|
|
89
89
|
</div>
|
|
90
90
|
<div class="waveform-canvas"></div>
|
|
91
91
|
</article>
|
|
@@ -134,4 +134,3 @@ export default ssg.page(import.meta.url, async orb => ({
|
|
|
134
134
|
</section>
|
|
135
135
|
`,
|
|
136
136
|
}))
|
|
137
|
-
|
|
@@ -0,0 +1,72 @@
|
|
|
1
|
+
|
|
2
|
+
import {Driver} from "../../../../driver/driver.js"
|
|
3
|
+
import {DecoderSource} from "../../../../driver/fns/schematic.js"
|
|
4
|
+
|
|
5
|
+
export const PEAK_LEVELS = [2048, 1024, 512, 256, 128, 64, 32] as const
|
|
6
|
+
|
|
7
|
+
export async function collectPeakLevels(driver: Driver, source: DecoderSource) {
|
|
8
|
+
const duration = (await driver.getAudioDuration(source)) ?? 0
|
|
9
|
+
const readable = driver.decodeAudio({source}).readable
|
|
10
|
+
const finestSamplesPerPeak = PEAK_LEVELS[PEAK_LEVELS.length - 1]
|
|
11
|
+
const finestPeaks: number[] = []
|
|
12
|
+
|
|
13
|
+
let currentMax = 0
|
|
14
|
+
let sampleCount = 0
|
|
15
|
+
let sampleRate = 0
|
|
16
|
+
|
|
17
|
+
for await (const audioData of readable) {
|
|
18
|
+
sampleRate ||= audioData.sampleRate
|
|
19
|
+
|
|
20
|
+
const frames = audioData.numberOfFrames
|
|
21
|
+
const plane = new Float32Array(frames)
|
|
22
|
+
audioData.copyTo(plane, {planeIndex: 0})
|
|
23
|
+
|
|
24
|
+
for (let i = 0; i < plane.length; i++) {
|
|
25
|
+
const amplitude = Math.abs(plane[i]!)
|
|
26
|
+
if (amplitude > currentMax) currentMax = amplitude
|
|
27
|
+
|
|
28
|
+
sampleCount++
|
|
29
|
+
if (sampleCount >= finestSamplesPerPeak) {
|
|
30
|
+
finestPeaks.push(currentMax)
|
|
31
|
+
currentMax = 0
|
|
32
|
+
sampleCount = 0
|
|
33
|
+
}
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
audioData.close()
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
if (sampleCount > 0) finestPeaks.push(currentMax)
|
|
40
|
+
|
|
41
|
+
const base = new Float32Array(finestPeaks)
|
|
42
|
+
const levels = PEAK_LEVELS.map(samplesPerPeak => {
|
|
43
|
+
const factor = Math.max(1, Math.round(samplesPerPeak / finestSamplesPerPeak))
|
|
44
|
+
const peaks = factor === 1 ? base : downsampleMax(base, factor)
|
|
45
|
+
return {
|
|
46
|
+
samplesPerPeak,
|
|
47
|
+
peaks,
|
|
48
|
+
peaksPerSecond: sampleRate > 0 ? sampleRate / samplesPerPeak : 0,
|
|
49
|
+
}
|
|
50
|
+
})
|
|
51
|
+
|
|
52
|
+
return {duration, levels}
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
function downsampleMax(peaks: Float32Array, factor: number) {
|
|
56
|
+
const downsampled = new Float32Array(Math.ceil(peaks.length / factor))
|
|
57
|
+
|
|
58
|
+
for (let i = 0; i < downsampled.length; i++) {
|
|
59
|
+
let maxPeak = 0
|
|
60
|
+
const start = i * factor
|
|
61
|
+
const end = Math.min(start + factor, peaks.length)
|
|
62
|
+
|
|
63
|
+
for (let j = start; j < end; j++) {
|
|
64
|
+
if (peaks[j]! > maxPeak) maxPeak = peaks[j]!
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
downsampled[i] = maxPeak
|
|
68
|
+
}
|
|
69
|
+
|
|
70
|
+
return downsampled
|
|
71
|
+
}
|
|
72
|
+
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
|
|
2
|
+
export function renderTile(
|
|
3
|
+
peaks: Float32Array,
|
|
4
|
+
opts: {
|
|
5
|
+
width: number
|
|
6
|
+
height: number
|
|
7
|
+
color: string
|
|
8
|
+
}
|
|
9
|
+
) {
|
|
10
|
+
const dpr = typeof window !== "undefined" ? window.devicePixelRatio || 1 : 1
|
|
11
|
+
const canvas = document.createElement("canvas")
|
|
12
|
+
canvas.width = opts.width * dpr
|
|
13
|
+
canvas.height = opts.height * dpr
|
|
14
|
+
canvas.style.width = `${opts.width}px`
|
|
15
|
+
canvas.style.height = `${opts.height}px`
|
|
16
|
+
|
|
17
|
+
const ctx = canvas.getContext("2d")
|
|
18
|
+
if (!ctx) return canvas
|
|
19
|
+
|
|
20
|
+
ctx.scale(dpr, dpr)
|
|
21
|
+
ctx.fillStyle = opts.color
|
|
22
|
+
|
|
23
|
+
const centerY = opts.height / 2
|
|
24
|
+
const columns = Math.max(1, opts.width)
|
|
25
|
+
const peaksPerPixel = peaks.length / columns
|
|
26
|
+
|
|
27
|
+
for (let px = 0; px < columns; px++) {
|
|
28
|
+
const startIndex = Math.floor(px * peaksPerPixel)
|
|
29
|
+
const endIndex = Math.max(
|
|
30
|
+
startIndex + 1,
|
|
31
|
+
Math.floor((px + 1) * peaksPerPixel)
|
|
32
|
+
)
|
|
33
|
+
|
|
34
|
+
let maxPeak = 0
|
|
35
|
+
for (let i = startIndex; i < endIndex && i < peaks.length; i++) {
|
|
36
|
+
if (peaks[i]! > maxPeak) maxPeak = peaks[i]!
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
const barHeight = maxPeak * opts.height
|
|
40
|
+
ctx.fillRect(px, centerY - barHeight / 2, 1, barHeight)
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
return canvas
|
|
44
|
+
}
|
|
45
|
+
|
|
@@ -0,0 +1,24 @@
|
|
|
1
|
+
export interface WaveformTileData {
|
|
2
|
+
startTime: number
|
|
3
|
+
endTime: number
|
|
4
|
+
peaks: Float32Array
|
|
5
|
+
canvas: HTMLCanvasElement
|
|
6
|
+
}
|
|
7
|
+
|
|
8
|
+
export interface WaveformOptions {
|
|
9
|
+
tileSize?: number
|
|
10
|
+
zoom?: number
|
|
11
|
+
tileWidth?: number
|
|
12
|
+
tileHeight?: number
|
|
13
|
+
preloadMargin?: number
|
|
14
|
+
color?: string
|
|
15
|
+
onChange?: (tiles: WaveformTileData[]) => void
|
|
16
|
+
}
|
|
17
|
+
|
|
18
|
+
export type WaveformTimeRange = [start: number, end: number]
|
|
19
|
+
|
|
20
|
+
export type WaveformPeakLevel = {
|
|
21
|
+
samplesPerPeak: number
|
|
22
|
+
peaks: Float32Array
|
|
23
|
+
peaksPerSecond: number
|
|
24
|
+
}
|
|
@@ -0,0 +1,152 @@
|
|
|
1
|
+
|
|
2
|
+
import {renderTile} from "./parts/render.js"
|
|
3
|
+
import {Driver} from "../../../driver/driver.js"
|
|
4
|
+
import {collectPeakLevels} from "./parts/collect.js"
|
|
5
|
+
import {DecoderSource} from "../../../driver/fns/schematic.js"
|
|
6
|
+
import {WaveformOptions, WaveformPeakLevel, WaveformTileData, WaveformTimeRange} from "./parts/types.js"
|
|
7
|
+
|
|
8
|
+
const MAX_TILE_WIDTH = 4096
|
|
9
|
+
|
|
10
|
+
export class Waveform {
|
|
11
|
+
#tiles = new Map<number, WaveformTileData>()
|
|
12
|
+
#activeRange: WaveformTimeRange = [0, 0]
|
|
13
|
+
|
|
14
|
+
#zoom
|
|
15
|
+
#levels
|
|
16
|
+
#onChange
|
|
17
|
+
#updateQueued = false
|
|
18
|
+
|
|
19
|
+
readonly color
|
|
20
|
+
readonly duration
|
|
21
|
+
readonly tileSize
|
|
22
|
+
readonly tileHeight
|
|
23
|
+
readonly preloadMargin
|
|
24
|
+
|
|
25
|
+
private constructor(levels: WaveformPeakLevel[], duration: number, options: WaveformOptions) {
|
|
26
|
+
this.#levels = levels
|
|
27
|
+
this.duration = duration
|
|
28
|
+
this.tileSize = options.tileSize ?? 1
|
|
29
|
+
this.#zoom = options.zoom ?? ((options.tileWidth ?? 256) / this.tileSize)
|
|
30
|
+
this.tileHeight = options.tileHeight ?? 96
|
|
31
|
+
this.preloadMargin = options.preloadMargin ?? 2
|
|
32
|
+
this.color = options.color ?? "rgb(3, 148, 129)"
|
|
33
|
+
this.#onChange = options.onChange
|
|
34
|
+
}
|
|
35
|
+
|
|
36
|
+
static async init(driver: Driver, source: DecoderSource, options: WaveformOptions = {}) {
|
|
37
|
+
const {duration, levels} = await collectPeakLevels(driver, source)
|
|
38
|
+
return new Waveform(levels, duration, options)
|
|
39
|
+
}
|
|
40
|
+
|
|
41
|
+
set zoom(value: number) {
|
|
42
|
+
const next = Math.max(1, value)
|
|
43
|
+
if (next === this.#zoom)
|
|
44
|
+
return
|
|
45
|
+
|
|
46
|
+
this.#zoom = next
|
|
47
|
+
this.#tiles.clear()
|
|
48
|
+
this.#queueUpdate()
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
get zoom() {
|
|
52
|
+
return this.#zoom
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
#computeActiveRange([start, end]: WaveformTimeRange, margin = 1): WaveformTimeRange {
|
|
56
|
+
const visibleSize = end - start
|
|
57
|
+
return [
|
|
58
|
+
Math.max(0, start - visibleSize * margin),
|
|
59
|
+
Math.min(this.duration, end + visibleSize * margin),
|
|
60
|
+
]
|
|
61
|
+
}
|
|
62
|
+
|
|
63
|
+
set range(visibleRange: WaveformTimeRange) {
|
|
64
|
+
const [visibleStart, visibleEnd] = visibleRange
|
|
65
|
+
const visibleSize = visibleEnd - visibleStart
|
|
66
|
+
const [activeStart, activeEnd] = this.#activeRange
|
|
67
|
+
|
|
68
|
+
const leftTrigger = activeStart + visibleSize
|
|
69
|
+
const rightTrigger = activeEnd - visibleSize
|
|
70
|
+
|
|
71
|
+
if (visibleStart >= leftTrigger && visibleEnd <= rightTrigger) return
|
|
72
|
+
|
|
73
|
+
this.#activeRange = this.#computeActiveRange(visibleRange, this.preloadMargin)
|
|
74
|
+
this.#queueUpdate()
|
|
75
|
+
}
|
|
76
|
+
|
|
77
|
+
#queueUpdate() {
|
|
78
|
+
if (this.#updateQueued) return
|
|
79
|
+
this.#updateQueued = true
|
|
80
|
+
|
|
81
|
+
queueMicrotask(() => {
|
|
82
|
+
this.#updateQueued = false
|
|
83
|
+
this.#generateTiles()
|
|
84
|
+
})
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
#generateTiles() {
|
|
88
|
+
const [rangeStart, rangeEnd] = this.#activeRange
|
|
89
|
+
const neededStarts = new Set<number>()
|
|
90
|
+
const level = this.#levelForZoom()
|
|
91
|
+
|
|
92
|
+
const firstStart = Math.max(0, Math.floor(rangeStart / this.tileSize) * this.tileSize)
|
|
93
|
+
const lastStart = Math.min(this.duration, rangeEnd)
|
|
94
|
+
|
|
95
|
+
for (let startTime = firstStart; startTime <= lastStart; startTime += this.tileSize) {
|
|
96
|
+
neededStarts.add(startTime)
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
for (const startTime of neededStarts) {
|
|
100
|
+
if (!this.#tiles.has(startTime)) {
|
|
101
|
+
const endTime = Math.min(startTime + this.tileSize, this.duration)
|
|
102
|
+
this.#tiles.set(startTime, this.#buildTileData(startTime, endTime, level))
|
|
103
|
+
}
|
|
104
|
+
}
|
|
105
|
+
|
|
106
|
+
for (const startTime of this.#tiles.keys()) {
|
|
107
|
+
if (!neededStarts.has(startTime)) this.#tiles.delete(startTime)
|
|
108
|
+
}
|
|
109
|
+
|
|
110
|
+
this.#emit()
|
|
111
|
+
}
|
|
112
|
+
|
|
113
|
+
#buildTileData(startTime: number, endTime: number, level: WaveformPeakLevel): WaveformTileData {
|
|
114
|
+
const peaks = this.#slicePeaks(level, startTime, endTime)
|
|
115
|
+
return {
|
|
116
|
+
startTime,
|
|
117
|
+
endTime,
|
|
118
|
+
peaks,
|
|
119
|
+
canvas: renderTile(peaks, {
|
|
120
|
+
width: this.#tilePixelWidth(startTime, endTime),
|
|
121
|
+
height: this.tileHeight,
|
|
122
|
+
color: this.color,
|
|
123
|
+
}),
|
|
124
|
+
}
|
|
125
|
+
}
|
|
126
|
+
|
|
127
|
+
#levelForZoom() {
|
|
128
|
+
return this.#levels.find(level => level.peaksPerSecond >= this.#zoom)
|
|
129
|
+
?? this.#levels[this.#levels.length - 1]!
|
|
130
|
+
}
|
|
131
|
+
|
|
132
|
+
#slicePeaks(level: WaveformPeakLevel, startTime: number, endTime: number) {
|
|
133
|
+
if (!level.peaksPerSecond) return new Float32Array()
|
|
134
|
+
const from = Math.max(0, Math.floor(startTime * level.peaksPerSecond))
|
|
135
|
+
const to = Math.max(from + 1, Math.min(level.peaks.length, Math.ceil(endTime * level.peaksPerSecond)))
|
|
136
|
+
return level.peaks.slice(from, to)
|
|
137
|
+
}
|
|
138
|
+
|
|
139
|
+
#tilePixelWidth(startTime: number, endTime: number) {
|
|
140
|
+
return Math.min(MAX_TILE_WIDTH, Math.max(1, Math.ceil((endTime - startTime) * this.#zoom)))
|
|
141
|
+
}
|
|
142
|
+
|
|
143
|
+
#emit() {
|
|
144
|
+
if (!this.#onChange) return
|
|
145
|
+
this.#onChange([...this.#tiles.values()].sort((a, b) => a.startTime - b.startTime))
|
|
146
|
+
}
|
|
147
|
+
|
|
148
|
+
getTiles() {
|
|
149
|
+
return this.#tiles
|
|
150
|
+
}
|
|
151
|
+
}
|
|
152
|
+
|
|
@@ -1,61 +0,0 @@
|
|
|
1
|
-
import WaveSurfer from "wavesurfer.js"
|
|
2
|
-
|
|
3
|
-
import {Driver} from "../../driver/driver.js"
|
|
4
|
-
import {DecoderSource} from "../../driver/fns/schematic.js"
|
|
5
|
-
|
|
6
|
-
export class Waveform {
|
|
7
|
-
wavesurfer: WaveSurfer
|
|
8
|
-
|
|
9
|
-
constructor(peaks: number[], container: HTMLElement, duration: number) {
|
|
10
|
-
this.wavesurfer = WaveSurfer.create({
|
|
11
|
-
container,
|
|
12
|
-
waveColor: 'rgb(200, 0, 200)',
|
|
13
|
-
progressColor: 'rgb(100, 0, 100)',
|
|
14
|
-
barWidth: 10,
|
|
15
|
-
barRadius: 10,
|
|
16
|
-
barGap: 2,
|
|
17
|
-
peaks: [peaks],
|
|
18
|
-
duration
|
|
19
|
-
})
|
|
20
|
-
}
|
|
21
|
-
|
|
22
|
-
static async init(driver: Driver, source: DecoderSource, container: HTMLElement) {
|
|
23
|
-
const reader = driver.decodeAudio({source}).readable.getReader()
|
|
24
|
-
|
|
25
|
-
const peaks: number[] = []
|
|
26
|
-
let buffer: number[] = []
|
|
27
|
-
const samplesPerPeak = 1024
|
|
28
|
-
const duration = await driver.getAudioDuration(source)
|
|
29
|
-
|
|
30
|
-
while (true) {
|
|
31
|
-
const {done, value: audioData} = await reader.read()
|
|
32
|
-
if (done) break
|
|
33
|
-
|
|
34
|
-
const frames = audioData.numberOfFrames
|
|
35
|
-
const plane = new Float32Array(frames)
|
|
36
|
-
audioData.copyTo(plane, {planeIndex: 0}) // Use left channel only
|
|
37
|
-
|
|
38
|
-
for (let i = 0; i < plane.length; i++) {
|
|
39
|
-
buffer.push(plane[i])
|
|
40
|
-
if (buffer.length >= samplesPerPeak) {
|
|
41
|
-
const chunk = buffer.splice(0, samplesPerPeak)
|
|
42
|
-
const min = Math.min(...chunk)
|
|
43
|
-
const max = Math.max(...chunk)
|
|
44
|
-
peaks.push(min, max)
|
|
45
|
-
}
|
|
46
|
-
}
|
|
47
|
-
|
|
48
|
-
audioData.close()
|
|
49
|
-
}
|
|
50
|
-
|
|
51
|
-
return new Waveform(peaks, container, duration ?? 0)
|
|
52
|
-
}
|
|
53
|
-
|
|
54
|
-
// set zoom(value: number) {
|
|
55
|
-
// this.wavesurfer.zoom(value)
|
|
56
|
-
// }
|
|
57
|
-
|
|
58
|
-
set width(value: number) {
|
|
59
|
-
this.wavesurfer.setOptions({width: value})
|
|
60
|
-
}
|
|
61
|
-
}
|
package/x/demo/demo.bundle.js
CHANGED
|
@@ -23,6 +23,8 @@ let exportState = null;
|
|
|
23
23
|
const setProgress = (card, state) => {
|
|
24
24
|
const progress = card.querySelector(".progress");
|
|
25
25
|
const status = card.querySelector(".status");
|
|
26
|
+
if (!progress || !status)
|
|
27
|
+
return;
|
|
26
28
|
if (state === "running") {
|
|
27
29
|
progress.removeAttribute("value");
|
|
28
30
|
status.textContent = "running";
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"demo.bundle.js","sourceRoot":"","sources":["../../s/demo/demo.bundle.ts"],"names":[],"mappings":"AACA,OAAO,EAAC,MAAM,EAAC,MAAM,qBAAqB,CAAA;AAE1C,OAAO,EAAC,YAAY,EAAC,MAAM,6BAA6B,CAAA;AACxD,OAAO,EAAC,YAAY,EAAC,MAAM,6BAA6B,CAAA;AACxD,OAAO,EAAC,kBAAkB,EAAE,MAAM,8BAA8B,CAAA;AAChE,OAAO,EAAC,aAAa,EAAC,MAAM,8BAA8B,CAAA;AAC1D,OAAO,EAAC,kBAAkB,EAAC,MAAM,8BAA8B,CAAA;AAE/D,MAAM,MAAM,GAAG,MAAM,MAAM,CAAC,KAAK,CAAC,EAAC,SAAS,EAAE,IAAI,GAAG,CAAC,uCAAuC,EAAE,MAAM,CAAC,IAAI,CAAC,GAAG,CAAC,EAAC,CAAC,CAAA;AAEjH,MAAM,aAAa,GAAG,QAAQ,CAAC,aAAa,CAAC,yBAAyB,CAAgB,CAAA;AACtF,MAAM,aAAa,GAAG,QAAQ,CAAC,aAAa,CAAC,yBAAyB,CAAgB,CAAA;AACtF,MAAM,YAAY,GAAG,QAAQ,CAAC,aAAa,CAAC,wBAAwB,CAAgB,CAAA;AACpF,MAAM,YAAY,GAAG,QAAQ,CAAC,aAAa,CAAC,wBAAwB,CAAgB,CAAA;AACpF,MAAM,UAAU,GAAG,QAAQ,CAAC,aAAa,CAAC,sBAAsB,CAAgB,CAAA;AAChF,MAAM,YAAY,GAAG,UAAU,CAAC,aAAa,CAAC,wBAAwB,CAAsB,CAAA;AAE5F,IAAI,WAAW,GAAgD,IAAI,CAAA;AAEnE,mBAAmB;AACnB,CAAC;IACA,MAAM,MAAM,CAAC,MAAM,CAAC,IAAI,CAAC,KAAK,EAAE,CAAA;IAChC,IAAI,MAAM,CAAC,OAAO,CAAC,KAAK,KAAK,CAAC;QAAE,OAAO,CAAC,GAAG,CAAC,gBAAgB,CAAC,CAAA;;QACxD,OAAO,CAAC,KAAK,CAAC,gCAAgC,CAAC,CAAA;AACrD,CAAC;AAED,MAAM,WAAW,GAAG,CAAC,IAAiB,EAAE,KAAkC,EAAE,EAAE;IAC7E,MAAM,QAAQ,GAAG,IAAI,CAAC,aAAa,CAAC,WAAW,
|
|
1
|
+
{"version":3,"file":"demo.bundle.js","sourceRoot":"","sources":["../../s/demo/demo.bundle.ts"],"names":[],"mappings":"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"}
|