@revikornmann/muka-ui 0.15.0 → 0.17.0
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/build/manifest.json +10 -0
- package/dist/cjs/components/BottomBar/BottomBar.css +19 -4
- package/dist/cjs/components/ChatComposer/ChatComposer.js +12 -4
- package/dist/cjs/components/ChatComposer/ChatComposer.js.map +1 -1
- package/dist/cjs/components/ChatMessage/ChatMessage.css +7 -1
- package/dist/cjs/components/ChatMessage/ChatMessage.js.map +1 -1
- package/dist/cjs/components/ChatMessageList/ChatMessageList.css +1 -1
- package/dist/cjs/components/Combobox/Combobox.css +59 -1
- package/dist/cjs/components/Combobox/Combobox.js +22 -3
- package/dist/cjs/components/Combobox/Combobox.js.map +1 -1
- package/dist/cjs/components/EmojiPicker/EmojiPicker.css +19 -0
- package/dist/cjs/components/EmojiPicker/EmojiPicker.js +54 -0
- package/dist/cjs/components/EmojiPicker/EmojiPicker.js.map +1 -0
- package/dist/cjs/components/EmojiPicker/index.js +12 -0
- package/dist/cjs/components/EmojiPicker/index.js.map +1 -0
- package/dist/cjs/components/PhotoDraftStrip/PhotoDraftStrip.css +27 -0
- package/dist/cjs/components/PhotoDraftStrip/PhotoDraftStrip.js +36 -0
- package/dist/cjs/components/PhotoDraftStrip/PhotoDraftStrip.js.map +1 -0
- package/dist/cjs/components/PhotoDraftStrip/index.js +11 -0
- package/dist/cjs/components/PhotoDraftStrip/index.js.map +1 -0
- package/dist/cjs/components/RecordingBar/RecordingBar.css +47 -0
- package/dist/cjs/components/RecordingBar/RecordingBar.js +22 -0
- package/dist/cjs/components/RecordingBar/RecordingBar.js.map +1 -0
- package/dist/cjs/components/RecordingBar/index.js +11 -0
- package/dist/cjs/components/RecordingBar/index.js.map +1 -0
- package/dist/cjs/components/SearchInput/SearchInput.js +7 -2
- package/dist/cjs/components/SearchInput/SearchInput.js.map +1 -1
- package/dist/cjs/components/TextLink/TextLink.css +79 -0
- package/dist/cjs/components/TextLink/TextLink.js +28 -0
- package/dist/cjs/components/TextLink/TextLink.js.map +1 -0
- package/dist/cjs/components/TextLink/index.js +11 -0
- package/dist/cjs/components/TextLink/index.js.map +1 -0
- package/dist/cjs/components/VoiceMessage/VoiceMessage.css +29 -0
- package/dist/cjs/components/VoiceMessage/VoiceMessage.js +85 -0
- package/dist/cjs/components/VoiceMessage/VoiceMessage.js.map +1 -0
- package/dist/cjs/components/VoiceMessage/index.js +11 -0
- package/dist/cjs/components/VoiceMessage/index.js.map +1 -0
- package/dist/cjs/components/VoiceRecorder/audio.js +61 -0
- package/dist/cjs/components/VoiceRecorder/audio.js.map +1 -0
- package/dist/cjs/components/VoiceRecorder/index.js +16 -0
- package/dist/cjs/components/VoiceRecorder/index.js.map +1 -0
- package/dist/cjs/components/VoiceRecorder/useVoiceRecorder.js +213 -0
- package/dist/cjs/components/VoiceRecorder/useVoiceRecorder.js.map +1 -0
- package/dist/cjs/components/Waveform/Waveform.css +23 -0
- package/dist/cjs/components/Waveform/Waveform.js +36 -0
- package/dist/cjs/components/Waveform/Waveform.js.map +1 -0
- package/dist/cjs/components/Waveform/index.js +11 -0
- package/dist/cjs/components/Waveform/index.js.map +1 -0
- package/dist/cjs/components/index.js +20 -1
- package/dist/cjs/components/index.js.map +1 -1
- package/dist/esm/components/BottomBar/BottomBar.css +19 -4
- package/dist/esm/components/ChatComposer/ChatComposer.js +12 -4
- package/dist/esm/components/ChatComposer/ChatComposer.js.map +1 -1
- package/dist/esm/components/ChatMessage/ChatMessage.css +7 -1
- package/dist/esm/components/ChatMessage/ChatMessage.js.map +1 -1
- package/dist/esm/components/ChatMessageList/ChatMessageList.css +1 -1
- package/dist/esm/components/Combobox/Combobox.css +59 -1
- package/dist/esm/components/Combobox/Combobox.js +23 -4
- package/dist/esm/components/Combobox/Combobox.js.map +1 -1
- package/dist/esm/components/EmojiPicker/EmojiPicker.css +19 -0
- package/dist/esm/components/EmojiPicker/EmojiPicker.js +50 -0
- package/dist/esm/components/EmojiPicker/EmojiPicker.js.map +1 -0
- package/dist/esm/components/EmojiPicker/index.js +3 -0
- package/dist/esm/components/EmojiPicker/index.js.map +1 -0
- package/dist/esm/components/PhotoDraftStrip/PhotoDraftStrip.css +27 -0
- package/dist/esm/components/PhotoDraftStrip/PhotoDraftStrip.js +32 -0
- package/dist/esm/components/PhotoDraftStrip/PhotoDraftStrip.js.map +1 -0
- package/dist/esm/components/PhotoDraftStrip/index.js +3 -0
- package/dist/esm/components/PhotoDraftStrip/index.js.map +1 -0
- package/dist/esm/components/RecordingBar/RecordingBar.css +47 -0
- package/dist/esm/components/RecordingBar/RecordingBar.js +18 -0
- package/dist/esm/components/RecordingBar/RecordingBar.js.map +1 -0
- package/dist/esm/components/RecordingBar/index.js +3 -0
- package/dist/esm/components/RecordingBar/index.js.map +1 -0
- package/dist/esm/components/SearchInput/SearchInput.js +7 -2
- package/dist/esm/components/SearchInput/SearchInput.js.map +1 -1
- package/dist/esm/components/TextLink/TextLink.css +79 -0
- package/dist/esm/components/TextLink/TextLink.js +24 -0
- package/dist/esm/components/TextLink/TextLink.js.map +1 -0
- package/dist/esm/components/TextLink/index.js +3 -0
- package/dist/esm/components/TextLink/index.js.map +1 -0
- package/dist/esm/components/VoiceMessage/VoiceMessage.css +29 -0
- package/dist/esm/components/VoiceMessage/VoiceMessage.js +81 -0
- package/dist/esm/components/VoiceMessage/VoiceMessage.js.map +1 -0
- package/dist/esm/components/VoiceMessage/index.js +3 -0
- package/dist/esm/components/VoiceMessage/index.js.map +1 -0
- package/dist/esm/components/VoiceRecorder/audio.js +55 -0
- package/dist/esm/components/VoiceRecorder/audio.js.map +1 -0
- package/dist/esm/components/VoiceRecorder/index.js +4 -0
- package/dist/esm/components/VoiceRecorder/index.js.map +1 -0
- package/dist/esm/components/VoiceRecorder/useVoiceRecorder.js +210 -0
- package/dist/esm/components/VoiceRecorder/useVoiceRecorder.js.map +1 -0
- package/dist/esm/components/Waveform/Waveform.css +23 -0
- package/dist/esm/components/Waveform/Waveform.js +32 -0
- package/dist/esm/components/Waveform/Waveform.js.map +1 -0
- package/dist/esm/components/Waveform/index.js +3 -0
- package/dist/esm/components/Waveform/index.js.map +1 -0
- package/dist/esm/components/index.js +7 -0
- package/dist/esm/components/index.js.map +1 -1
- package/dist/styles/components/BottomBar.css +19 -4
- package/dist/styles/components/ChatMessage.css +7 -1
- package/dist/styles/components/ChatMessageList.css +1 -1
- package/dist/styles/components/Combobox.css +59 -1
- package/dist/styles/components/EmojiPicker.css +19 -0
- package/dist/styles/components/PhotoDraftStrip.css +27 -0
- package/dist/styles/components/RecordingBar.css +47 -0
- package/dist/styles/components/TextLink.css +79 -0
- package/dist/styles/components/VoiceMessage.css +29 -0
- package/dist/styles/components/Waveform.css +23 -0
- package/dist/styles/index.css +373 -50
- package/dist/styles/muka-dark.css +373 -50
- package/dist/styles/muka-light.css +373 -50
- package/dist/styles/tokens-bouwplan-dark.css +4 -2
- package/dist/styles/tokens-bouwplan-light.css +4 -2
- package/dist/styles/tokens-fscl-dark.css +4 -2
- package/dist/styles/tokens-fscl-light.css +4 -2
- package/dist/styles/tokens-grip-dark.css +4 -2
- package/dist/styles/tokens-grip-light.css +4 -2
- package/dist/styles/tokens-muka-dark.css +4 -2
- package/dist/styles/tokens-muka-light.css +4 -2
- package/dist/styles/tokens-wireframe-dark.css +4 -2
- package/dist/styles/tokens-wireframe-light.css +4 -2
- package/dist/styles/wireframe-dark.css +373 -50
- package/dist/styles/wireframe-light.css +373 -50
- package/dist/types/components/ChatComposer/ChatComposer.d.ts +7 -0
- package/dist/types/components/ChatComposer/ChatComposer.d.ts.map +1 -1
- package/dist/types/components/ChatMessage/ChatMessage.d.ts +4 -1
- package/dist/types/components/ChatMessage/ChatMessage.d.ts.map +1 -1
- package/dist/types/components/Combobox/Combobox.d.ts +7 -0
- package/dist/types/components/Combobox/Combobox.d.ts.map +1 -1
- package/dist/types/components/EmojiPicker/EmojiPicker.d.ts +28 -0
- package/dist/types/components/EmojiPicker/EmojiPicker.d.ts.map +1 -0
- package/dist/types/components/EmojiPicker/index.d.ts +3 -0
- package/dist/types/components/EmojiPicker/index.d.ts.map +1 -0
- package/dist/types/components/PhotoDraftStrip/PhotoDraftStrip.d.ts +51 -0
- package/dist/types/components/PhotoDraftStrip/PhotoDraftStrip.d.ts.map +1 -0
- package/dist/types/components/PhotoDraftStrip/index.d.ts +3 -0
- package/dist/types/components/PhotoDraftStrip/index.d.ts.map +1 -0
- package/dist/types/components/RecordingBar/RecordingBar.d.ts +22 -0
- package/dist/types/components/RecordingBar/RecordingBar.d.ts.map +1 -0
- package/dist/types/components/RecordingBar/index.d.ts +3 -0
- package/dist/types/components/RecordingBar/index.d.ts.map +1 -0
- package/dist/types/components/SearchInput/SearchInput.d.ts.map +1 -1
- package/dist/types/components/TextLink/TextLink.d.ts +30 -0
- package/dist/types/components/TextLink/TextLink.d.ts.map +1 -0
- package/dist/types/components/TextLink/index.d.ts +3 -0
- package/dist/types/components/TextLink/index.d.ts.map +1 -0
- package/dist/types/components/VoiceMessage/VoiceMessage.d.ts +34 -0
- package/dist/types/components/VoiceMessage/VoiceMessage.d.ts.map +1 -0
- package/dist/types/components/VoiceMessage/index.d.ts +3 -0
- package/dist/types/components/VoiceMessage/index.d.ts.map +1 -0
- package/dist/types/components/VoiceRecorder/audio.d.ts +20 -0
- package/dist/types/components/VoiceRecorder/audio.d.ts.map +1 -0
- package/dist/types/components/VoiceRecorder/index.d.ts +4 -0
- package/dist/types/components/VoiceRecorder/index.d.ts.map +1 -0
- package/dist/types/components/VoiceRecorder/useVoiceRecorder.d.ts +48 -0
- package/dist/types/components/VoiceRecorder/useVoiceRecorder.d.ts.map +1 -0
- package/dist/types/components/Waveform/Waveform.d.ts +31 -0
- package/dist/types/components/Waveform/Waveform.d.ts.map +1 -0
- package/dist/types/components/Waveform/index.d.ts +3 -0
- package/dist/types/components/Waveform/index.d.ts.map +1 -0
- package/dist/types/components/index.d.ts +7 -0
- package/dist/types/components/index.d.ts.map +1 -1
- package/package.json +2 -1
- package/tokens/t4-components/bottombar.json +2 -1
- package/tokens/t4-components/chat.json +15 -0
- package/tokens/t4-components/chatbubble.json +7 -1
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
/* RecordingBar Component Styles */
|
|
2
|
+
|
|
3
|
+
.muka-recording-bar {
|
|
4
|
+
display: flex;
|
|
5
|
+
align-items: center;
|
|
6
|
+
gap: var(--spacing-3);
|
|
7
|
+
width: 100%;
|
|
8
|
+
min-width: 0;
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
.muka-recording-bar__dot {
|
|
12
|
+
flex: 0 0 auto;
|
|
13
|
+
width: 0.625rem;
|
|
14
|
+
height: 0.625rem;
|
|
15
|
+
border-radius: var(--radius-full, 9999px);
|
|
16
|
+
background: var(--alert-color-error-accent, var(--color-text-default-default));
|
|
17
|
+
animation: muka-recording-bar-pulse 1s ease-in-out infinite;
|
|
18
|
+
}
|
|
19
|
+
|
|
20
|
+
.muka-recording-bar__time {
|
|
21
|
+
flex: 0 0 auto;
|
|
22
|
+
font-size: var(--text-label-sm-fontSize, 0.75rem);
|
|
23
|
+
line-height: var(--text-label-sm-lineHeight, 1);
|
|
24
|
+
font-variant-numeric: tabular-nums;
|
|
25
|
+
color: var(--color-text-default-default);
|
|
26
|
+
}
|
|
27
|
+
|
|
28
|
+
.muka-recording-bar__wave {
|
|
29
|
+
flex: 1 1 auto;
|
|
30
|
+
min-width: 0;
|
|
31
|
+
}
|
|
32
|
+
|
|
33
|
+
@keyframes muka-recording-bar-pulse {
|
|
34
|
+
0%,
|
|
35
|
+
100% {
|
|
36
|
+
opacity: 1;
|
|
37
|
+
}
|
|
38
|
+
50% {
|
|
39
|
+
opacity: 0.3;
|
|
40
|
+
}
|
|
41
|
+
}
|
|
42
|
+
|
|
43
|
+
@media (prefers-reduced-motion: reduce) {
|
|
44
|
+
.muka-recording-bar__dot {
|
|
45
|
+
animation: none;
|
|
46
|
+
}
|
|
47
|
+
}
|
|
@@ -0,0 +1,22 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
'use client';
|
|
3
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
4
|
+
exports.RecordingBar = void 0;
|
|
5
|
+
const jsx_runtime_1 = require("react/jsx-runtime");
|
|
6
|
+
const Waveform_1 = require("../Waveform");
|
|
7
|
+
const VoiceRecorder_1 = require("../VoiceRecorder");
|
|
8
|
+
require("./RecordingBar.css");
|
|
9
|
+
/**
|
|
10
|
+
* RecordingBar — drop-in content for `ChatComposer.recordingSlot` while a voice
|
|
11
|
+
* note is being recorded. A pulsing record dot, an elapsed timer, and the live
|
|
12
|
+
* `Waveform`. Muka delegates this slot to the app, but ships this default so
|
|
13
|
+
* consumers don't rebuild it. Feed it straight from `useVoiceRecorder`
|
|
14
|
+
* (`elapsedMs`, `livePeaks`). Tokens only; the label comes via props.
|
|
15
|
+
*/
|
|
16
|
+
const RecordingBar = ({ elapsedMs, livePeaks, recordingLabel = 'Recording', className = '', }) => {
|
|
17
|
+
const classes = ['muka-recording-bar', className].filter(Boolean).join(' ');
|
|
18
|
+
return ((0, jsx_runtime_1.jsxs)("div", { className: classes, role: "status", "aria-label": recordingLabel, children: [(0, jsx_runtime_1.jsx)("span", { className: "muka-recording-bar__dot", "aria-hidden": "true" }), (0, jsx_runtime_1.jsx)("span", { className: "muka-recording-bar__time", children: (0, VoiceRecorder_1.formatClock)(elapsedMs / 1000) }), (0, jsx_runtime_1.jsx)("div", { className: "muka-recording-bar__wave", children: (0, jsx_runtime_1.jsx)(Waveform_1.Waveform, { peaks: livePeaks, progress: 1 }) })] }));
|
|
19
|
+
};
|
|
20
|
+
exports.RecordingBar = RecordingBar;
|
|
21
|
+
exports.default = exports.RecordingBar;
|
|
22
|
+
//# sourceMappingURL=RecordingBar.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"RecordingBar.js","sourceRoot":"","sources":["../../../../components/RecordingBar/RecordingBar.tsx"],"names":[],"mappings":";AAAA,YAAY,CAAC;;;;AAGb,0CAAuC;AACvC,oDAA+C;AAC/C,8BAA4B;AAgB5B;;;;;;GAMG;AACI,MAAM,YAAY,GAAgC,CAAC,EACxD,SAAS,EACT,SAAS,EACT,cAAc,GAAG,WAAW,EAC5B,SAAS,GAAG,EAAE,GACf,EAAE,EAAE;IACH,MAAM,OAAO,GAAG,CAAC,oBAAoB,EAAE,SAAS,CAAC,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;IAE5E,OAAO,CACL,iCAAK,SAAS,EAAE,OAAO,EAAE,IAAI,EAAC,QAAQ,gBAAa,cAAc,aAC/D,iCAAM,SAAS,EAAC,yBAAyB,iBAAa,MAAM,GAAG,EAC/D,iCAAM,SAAS,EAAC,0BAA0B,YAAE,IAAA,2BAAW,EAAC,SAAS,GAAG,IAAI,CAAC,GAAQ,EACjF,gCAAK,SAAS,EAAC,0BAA0B,YACvC,uBAAC,mBAAQ,IAAC,KAAK,EAAE,SAAS,EAAE,QAAQ,EAAE,CAAC,GAAI,GACvC,IACF,CACP,CAAC;AACJ,CAAC,CAAC;AAjBW,QAAA,YAAY,gBAiBvB;AAEF,kBAAe,oBAAY,CAAC"}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
exports.default = exports.RecordingBar = void 0;
|
|
7
|
+
var RecordingBar_1 = require("./RecordingBar");
|
|
8
|
+
Object.defineProperty(exports, "RecordingBar", { enumerable: true, get: function () { return RecordingBar_1.RecordingBar; } });
|
|
9
|
+
var RecordingBar_2 = require("./RecordingBar");
|
|
10
|
+
Object.defineProperty(exports, "default", { enumerable: true, get: function () { return __importDefault(RecordingBar_2).default; } });
|
|
11
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../components/RecordingBar/index.ts"],"names":[],"mappings":";;;;;;AAAA,+CAAsE;AAA7D,4GAAA,YAAY,OAAA;AACrB,+CAAyC;AAAhC,wHAAA,OAAO,OAAA"}
|
|
@@ -66,10 +66,15 @@ autoComplete = 'off', autoCorrect = 'off', spellCheck = false, onKeyDown, onFocu
|
|
|
66
66
|
}, onBlur: (e) => {
|
|
67
67
|
setFocused(false);
|
|
68
68
|
onBlur?.(e);
|
|
69
|
-
}, onKeyDown: handleKeyDown, placeholder: placeholder, disabled: disabled,
|
|
69
|
+
}, onKeyDown: handleKeyDown, placeholder: placeholder, disabled: disabled,
|
|
70
|
+
// Not an unconditional autofocus: this forwards the consumer's own
|
|
71
|
+
// opt-in `autoFocus` prop, which defaults to false. The caller
|
|
72
|
+
// decides, exactly as with a native <input>.
|
|
73
|
+
// eslint-disable-next-line jsx-a11y/no-autofocus
|
|
74
|
+
autoFocus: autoFocus, "aria-label": ariaLabel || placeholder,
|
|
70
75
|
// The browser-supplied clear icon is hidden in CSS via the
|
|
71
76
|
// `-webkit-search-cancel-button` pseudo-element — we render our own.
|
|
72
|
-
autoComplete: autoComplete, autoCorrect: autoCorrect, spellCheck: spellCheck }), loading && ((0, jsx_runtime_1.jsx)("span", { className: "muka-search-input__trailing", children: (0, jsx_runtime_1.jsx)(Spinner_1.Spinner, { size: "sm", variant: "subtle" }) })), showClear && ((0, jsx_runtime_1.jsx)("button", { type: "button", className: "muka-search-input__clear", onClick: handleClear, "aria-label": "Clear search",
|
|
77
|
+
autoComplete: autoComplete, autoCorrect: autoCorrect, spellCheck: spellCheck }), loading && ((0, jsx_runtime_1.jsx)("span", { className: "muka-search-input__trailing", children: (0, jsx_runtime_1.jsx)(Spinner_1.Spinner, { size: "sm", variant: "subtle" }) })), showClear && ((0, jsx_runtime_1.jsx)("button", { type: "button", className: "muka-search-input__clear", onClick: handleClear, "aria-label": "Clear search", children: (0, jsx_runtime_1.jsx)(Icon_1.Icon, { name: "close", variant: "line", size: "sm" }) }))] }), showCancel && ((0, jsx_runtime_1.jsx)("button", { type: "button", className: "muka-search-input__cancel", onClick: handleCancel, children: cancelLabel }))] }));
|
|
73
78
|
});
|
|
74
79
|
exports.SearchInput.displayName = 'SearchInput';
|
|
75
80
|
exports.default = exports.SearchInput;
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"SearchInput.js","sourceRoot":"","sources":["../../../../components/SearchInput/SearchInput.tsx"],"names":[],"mappings":"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
|
|
1
|
+
{"version":3,"file":"SearchInput.js","sourceRoot":"","sources":["../../../../components/SearchInput/SearchInput.tsx"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,79 @@
|
|
|
1
|
+
/* TextLink Component Styles - Using Muka Design Tokens */
|
|
2
|
+
|
|
3
|
+
.muka-text-link {
|
|
4
|
+
display: inline;
|
|
5
|
+
cursor: pointer;
|
|
6
|
+
text-decoration: underline;
|
|
7
|
+
/* Nudge the rule clear of descenders; the Figma underline sits off baseline. */
|
|
8
|
+
text-underline-offset: 0.2em;
|
|
9
|
+
text-decoration-thickness: from-font;
|
|
10
|
+
/* Rounds the focus ring's corners; the link itself has no visible box. */
|
|
11
|
+
border-radius: var(--border-radius-sm);
|
|
12
|
+
transition: color var(--motion-duration-micro, 0.15s) var(--motion-easing-enter, ease);
|
|
13
|
+
}
|
|
14
|
+
|
|
15
|
+
/* ─── Sizes ───────────────────────────────────────────────
|
|
16
|
+
Mirrors the body text scale so a link matches the copy it sits in. */
|
|
17
|
+
.muka-text-link--sm {
|
|
18
|
+
font-family: var(--text-body-sm-regular-fontFamily);
|
|
19
|
+
font-weight: var(--text-body-sm-regular-fontWeight);
|
|
20
|
+
font-size: var(--text-body-sm-regular-fontSize);
|
|
21
|
+
line-height: var(--text-body-sm-regular-lineHeight);
|
|
22
|
+
}
|
|
23
|
+
|
|
24
|
+
.muka-text-link--base {
|
|
25
|
+
font-family: var(--text-body-base-regular-fontFamily);
|
|
26
|
+
font-weight: var(--text-body-base-regular-fontWeight);
|
|
27
|
+
font-size: var(--text-body-base-regular-fontSize);
|
|
28
|
+
line-height: var(--text-body-base-regular-lineHeight);
|
|
29
|
+
}
|
|
30
|
+
|
|
31
|
+
.muka-text-link--lg {
|
|
32
|
+
font-family: var(--text-body-lg-regular-fontFamily);
|
|
33
|
+
font-weight: var(--text-body-lg-regular-fontWeight);
|
|
34
|
+
font-size: var(--text-body-lg-regular-fontSize);
|
|
35
|
+
line-height: var(--text-body-lg-regular-lineHeight);
|
|
36
|
+
}
|
|
37
|
+
|
|
38
|
+
/* ─── Variant: default (accent) ───────────────────────────
|
|
39
|
+
Visited repeats the default colour on purpose: the design treats visited and
|
|
40
|
+
default the same, and pinning it stops the browser's purple from showing. */
|
|
41
|
+
.muka-text-link--default,
|
|
42
|
+
.muka-text-link--default:visited {
|
|
43
|
+
color: var(--color-text-action-default);
|
|
44
|
+
}
|
|
45
|
+
|
|
46
|
+
.muka-text-link--default:hover,
|
|
47
|
+
.muka-text-link--default:focus-visible {
|
|
48
|
+
color: var(--color-text-action-hover);
|
|
49
|
+
}
|
|
50
|
+
|
|
51
|
+
.muka-text-link--default:active {
|
|
52
|
+
color: var(--color-text-action-pressed);
|
|
53
|
+
}
|
|
54
|
+
|
|
55
|
+
/* ─── Variant: subtle (neutral) ───────────────────────────
|
|
56
|
+
Hover, focus and pressed all darken to the default text colour. */
|
|
57
|
+
.muka-text-link--subtle,
|
|
58
|
+
.muka-text-link--subtle:visited {
|
|
59
|
+
color: var(--color-text-subtle-default);
|
|
60
|
+
}
|
|
61
|
+
|
|
62
|
+
.muka-text-link--subtle:hover,
|
|
63
|
+
.muka-text-link--subtle:focus-visible,
|
|
64
|
+
.muka-text-link--subtle:active {
|
|
65
|
+
color: var(--color-text-default-default);
|
|
66
|
+
}
|
|
67
|
+
|
|
68
|
+
/* ─── Focus ───────────────────────────────────────────────
|
|
69
|
+
Same ring as every other focusable Muka component. */
|
|
70
|
+
.muka-text-link:focus-visible {
|
|
71
|
+
outline: 2px solid var(--color-border-focus);
|
|
72
|
+
outline-offset: 2px;
|
|
73
|
+
}
|
|
74
|
+
|
|
75
|
+
@media (prefers-reduced-motion: reduce) {
|
|
76
|
+
.muka-text-link {
|
|
77
|
+
transition: none;
|
|
78
|
+
}
|
|
79
|
+
}
|
|
@@ -0,0 +1,28 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
+
exports.TextLink = void 0;
|
|
4
|
+
const jsx_runtime_1 = require("react/jsx-runtime");
|
|
5
|
+
require("./TextLink.css");
|
|
6
|
+
/**
|
|
7
|
+
* TextLink Component
|
|
8
|
+
*
|
|
9
|
+
* An underlined inline text link. Renders a native `<a>`, so `href`, `target`,
|
|
10
|
+
* `rel`, `download` and the rest of the anchor attributes pass straight through.
|
|
11
|
+
*
|
|
12
|
+
* Variants: default (accent), subtle (neutral)
|
|
13
|
+
* Sizes: sm, base, lg
|
|
14
|
+
* States: hover, focus-visible, pressed. Visited is pinned to the default colour
|
|
15
|
+
* so the browser's purple never leaks in.
|
|
16
|
+
*/
|
|
17
|
+
const TextLink = ({ children, variant = 'default', size = 'base', className = '', ...props }) => {
|
|
18
|
+
const linkClasses = [
|
|
19
|
+
'muka-text-link',
|
|
20
|
+
`muka-text-link--${variant}`,
|
|
21
|
+
`muka-text-link--${size}`,
|
|
22
|
+
className,
|
|
23
|
+
].filter(Boolean).join(' ');
|
|
24
|
+
return ((0, jsx_runtime_1.jsx)("a", { className: linkClasses, ...props, children: children }));
|
|
25
|
+
};
|
|
26
|
+
exports.TextLink = TextLink;
|
|
27
|
+
exports.default = exports.TextLink;
|
|
28
|
+
//# sourceMappingURL=TextLink.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"TextLink.js","sourceRoot":"","sources":["../../../../components/TextLink/TextLink.tsx"],"names":[],"mappings":";;;;AACA,0BAAwB;AAoBxB;;;;;;;;;;GAUG;AACI,MAAM,QAAQ,GAA4B,CAAC,EAChD,QAAQ,EACR,OAAO,GAAG,SAAS,EACnB,IAAI,GAAG,MAAM,EACb,SAAS,GAAG,EAAE,EACd,GAAG,KAAK,EACT,EAAE,EAAE;IACH,MAAM,WAAW,GAAG;QAClB,gBAAgB;QAChB,mBAAmB,OAAO,EAAE;QAC5B,mBAAmB,IAAI,EAAE;QACzB,SAAS;KACV,CAAC,MAAM,CAAC,OAAO,CAAC,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC;IAE5B,OAAO,CACL,8BAAG,SAAS,EAAE,WAAW,KAAM,KAAK,YACjC,QAAQ,GACP,CACL,CAAC;AACJ,CAAC,CAAC;AAnBW,QAAA,QAAQ,YAmBnB;AAEF,kBAAe,gBAAQ,CAAC"}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
exports.default = exports.TextLink = void 0;
|
|
7
|
+
var TextLink_1 = require("./TextLink");
|
|
8
|
+
Object.defineProperty(exports, "TextLink", { enumerable: true, get: function () { return TextLink_1.TextLink; } });
|
|
9
|
+
var TextLink_2 = require("./TextLink");
|
|
10
|
+
Object.defineProperty(exports, "default", { enumerable: true, get: function () { return __importDefault(TextLink_2).default; } });
|
|
11
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../components/TextLink/index.ts"],"names":[],"mappings":";;;;;;AAAA,uCAA0D;AAAjD,oGAAA,QAAQ,OAAA;AACjB,uCAAqC;AAA5B,oHAAA,OAAO,OAAA"}
|
|
@@ -0,0 +1,29 @@
|
|
|
1
|
+
/* VoiceMessage Component Styles */
|
|
2
|
+
|
|
3
|
+
.muka-voice-message {
|
|
4
|
+
display: flex;
|
|
5
|
+
align-items: center;
|
|
6
|
+
gap: var(--spacing-3);
|
|
7
|
+
width: 100%;
|
|
8
|
+
min-width: min(16rem, 60vw);
|
|
9
|
+
}
|
|
10
|
+
|
|
11
|
+
.muka-voice-message__wave {
|
|
12
|
+
flex: 1 1 auto;
|
|
13
|
+
min-width: 0;
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
.muka-voice-message__time {
|
|
17
|
+
flex: 0 0 auto;
|
|
18
|
+
white-space: nowrap;
|
|
19
|
+
font-size: var(--text-label-sm-fontSize, 0.75rem);
|
|
20
|
+
line-height: var(--text-label-sm-lineHeight, 1);
|
|
21
|
+
font-variant-numeric: tabular-nums;
|
|
22
|
+
color: var(--color-text-subtle-default);
|
|
23
|
+
}
|
|
24
|
+
|
|
25
|
+
/* On the tinted own bubble the surface is the action color, so the timer flips
|
|
26
|
+
* to the inverse text token for contrast. */
|
|
27
|
+
.muka-voice-message--own .muka-voice-message__time {
|
|
28
|
+
color: var(--color-text-default-inverse);
|
|
29
|
+
}
|
|
@@ -0,0 +1,85 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
'use client';
|
|
3
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
4
|
+
exports.VoiceMessage = void 0;
|
|
5
|
+
const jsx_runtime_1 = require("react/jsx-runtime");
|
|
6
|
+
const react_1 = require("react");
|
|
7
|
+
const Button_1 = require("../Button");
|
|
8
|
+
const Icon_1 = require("../Icon");
|
|
9
|
+
const Waveform_1 = require("../Waveform");
|
|
10
|
+
const VoiceRecorder_1 = require("../VoiceRecorder");
|
|
11
|
+
require("./VoiceMessage.css");
|
|
12
|
+
/**
|
|
13
|
+
* VoiceMessage — inline play/pause player for a sent voice note.
|
|
14
|
+
*
|
|
15
|
+
* Composes a Muka `Button` with the shared token-based `Waveform`; the media
|
|
16
|
+
* stays with the app (`src` is whatever URL it hands over — Muka never fetches
|
|
17
|
+
* or signs it). Play/pause only: there is no transcription/speech-to-text.
|
|
18
|
+
*/
|
|
19
|
+
const VoiceMessage = ({ src, durationSec, peaks, variant, playLabel = 'Play voice message', pauseLabel = 'Pause voice message', unavailableLabel = 'Voice message unavailable', className = '', }) => {
|
|
20
|
+
const audioRef = (0, react_1.useRef)(null);
|
|
21
|
+
const [playing, setPlaying] = (0, react_1.useState)(false);
|
|
22
|
+
const [currentSec, setCurrentSec] = (0, react_1.useState)(0);
|
|
23
|
+
const [totalSec, setTotalSec] = (0, react_1.useState)(durationSec);
|
|
24
|
+
(0, react_1.useEffect)(() => {
|
|
25
|
+
const audio = audioRef.current;
|
|
26
|
+
if (!audio)
|
|
27
|
+
return;
|
|
28
|
+
const onTime = () => setCurrentSec(audio.currentTime);
|
|
29
|
+
const onLoaded = () => {
|
|
30
|
+
if (Number.isFinite(audio.duration) && audio.duration > 0) {
|
|
31
|
+
setTotalSec(audio.duration);
|
|
32
|
+
}
|
|
33
|
+
};
|
|
34
|
+
const onEnded = () => {
|
|
35
|
+
setPlaying(false);
|
|
36
|
+
setCurrentSec(0);
|
|
37
|
+
};
|
|
38
|
+
audio.addEventListener('timeupdate', onTime);
|
|
39
|
+
audio.addEventListener('loadedmetadata', onLoaded);
|
|
40
|
+
audio.addEventListener('ended', onEnded);
|
|
41
|
+
return () => {
|
|
42
|
+
audio.removeEventListener('timeupdate', onTime);
|
|
43
|
+
audio.removeEventListener('loadedmetadata', onLoaded);
|
|
44
|
+
audio.removeEventListener('ended', onEnded);
|
|
45
|
+
};
|
|
46
|
+
}, [src]);
|
|
47
|
+
const toggle = () => {
|
|
48
|
+
const audio = audioRef.current;
|
|
49
|
+
if (!audio)
|
|
50
|
+
return;
|
|
51
|
+
if (playing) {
|
|
52
|
+
audio.pause();
|
|
53
|
+
setPlaying(false);
|
|
54
|
+
}
|
|
55
|
+
else {
|
|
56
|
+
void audio
|
|
57
|
+
.play()
|
|
58
|
+
.then(() => setPlaying(true))
|
|
59
|
+
.catch(() => setPlaying(false));
|
|
60
|
+
}
|
|
61
|
+
};
|
|
62
|
+
const effectiveTotal = totalSec || durationSec;
|
|
63
|
+
const progress = effectiveTotal > 0 ? Math.min(1, currentSec / effectiveTotal) : 0;
|
|
64
|
+
const remaining = playing || currentSec > 0 ? effectiveTotal - currentSec : effectiveTotal;
|
|
65
|
+
// On own (tinted) bubbles the surface is the action color, so the played bars
|
|
66
|
+
// use the inverse text token for contrast; elsewhere the action color reads
|
|
67
|
+
// well against the light card.
|
|
68
|
+
const activeColor = variant === 'own'
|
|
69
|
+
? 'var(--color-text-default-inverse)'
|
|
70
|
+
: 'var(--color-action-default)';
|
|
71
|
+
const inactiveColor = variant === 'own'
|
|
72
|
+
? 'var(--color-black-alpha-3, rgba(0, 0, 0, 0.25))'
|
|
73
|
+
: 'var(--color-border-contrast)';
|
|
74
|
+
const classes = [
|
|
75
|
+
'muka-voice-message',
|
|
76
|
+
`muka-voice-message--${variant}`,
|
|
77
|
+
className,
|
|
78
|
+
]
|
|
79
|
+
.filter(Boolean)
|
|
80
|
+
.join(' ');
|
|
81
|
+
return ((0, jsx_runtime_1.jsxs)("div", { className: classes, children: [(0, jsx_runtime_1.jsx)(Button_1.Button, { variant: variant === 'own' ? 'secondary' : 'primary', size: "md", iconOnly: true, "aria-label": playing ? pauseLabel : playLabel, onClick: toggle, disabled: !src, children: (0, jsx_runtime_1.jsx)(Icon_1.Icon, { name: playing ? 'pause' : 'play', variant: "fill", size: "sm" }) }), (0, jsx_runtime_1.jsx)("div", { className: "muka-voice-message__wave", children: (0, jsx_runtime_1.jsx)(Waveform_1.Waveform, { peaks: peaks, progress: progress, activeColor: activeColor, inactiveColor: inactiveColor, "aria-label": src ? undefined : unavailableLabel }) }), (0, jsx_runtime_1.jsx)("span", { className: "muka-voice-message__time", children: (0, VoiceRecorder_1.formatClock)(remaining) }), src && (0, jsx_runtime_1.jsx)("audio", { ref: audioRef, src: src, preload: "metadata" })] }));
|
|
82
|
+
};
|
|
83
|
+
exports.VoiceMessage = VoiceMessage;
|
|
84
|
+
exports.default = exports.VoiceMessage;
|
|
85
|
+
//# sourceMappingURL=VoiceMessage.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"VoiceMessage.js","sourceRoot":"","sources":["../../../../components/VoiceMessage/VoiceMessage.tsx"],"names":[],"mappings":"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"}
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
exports.default = exports.VoiceMessage = void 0;
|
|
7
|
+
var VoiceMessage_1 = require("./VoiceMessage");
|
|
8
|
+
Object.defineProperty(exports, "VoiceMessage", { enumerable: true, get: function () { return VoiceMessage_1.VoiceMessage; } });
|
|
9
|
+
var VoiceMessage_2 = require("./VoiceMessage");
|
|
10
|
+
Object.defineProperty(exports, "default", { enumerable: true, get: function () { return __importDefault(VoiceMessage_2).default; } });
|
|
11
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../components/VoiceMessage/index.ts"],"names":[],"mappings":";;;;;;AAAA,+CAIwB;AAHtB,4GAAA,YAAY,OAAA;AAId,+CAAyC;AAAhC,wHAAA,OAAO,OAAA"}
|
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
'use client';
|
|
3
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
4
|
+
exports.VOICE_PEAK_COUNT = void 0;
|
|
5
|
+
exports.downsamplePeaks = downsamplePeaks;
|
|
6
|
+
exports.formatClock = formatClock;
|
|
7
|
+
exports.isVoiceRecordingSupported = isVoiceRecordingSupported;
|
|
8
|
+
/**
|
|
9
|
+
* Audio helpers shared by the voice-recording hook and the players.
|
|
10
|
+
*
|
|
11
|
+
* Pure, DOM-light utilities: peak downsampling for a compact persisted waveform
|
|
12
|
+
* and a clock formatter for the recorder timer / player countdown. No upload,
|
|
13
|
+
* no network, no speech-to-text.
|
|
14
|
+
*/
|
|
15
|
+
/** Default number of persisted waveform bars. Apps may override per clip. */
|
|
16
|
+
exports.VOICE_PEAK_COUNT = 48;
|
|
17
|
+
/**
|
|
18
|
+
* Downsample a stream of amplitude samples (each already 0..1) into exactly
|
|
19
|
+
* `count` normalized peaks by taking the max of each bucket, then scaling so the
|
|
20
|
+
* loudest bar reaches 1. Pure — unit-testable independently of the DOM.
|
|
21
|
+
*/
|
|
22
|
+
function downsamplePeaks(samples, count = exports.VOICE_PEAK_COUNT) {
|
|
23
|
+
if (samples.length === 0 || count <= 0)
|
|
24
|
+
return [];
|
|
25
|
+
const buckets = new Array(count).fill(0);
|
|
26
|
+
const size = samples.length / count;
|
|
27
|
+
for (let i = 0; i < count; i += 1) {
|
|
28
|
+
const start = Math.floor(i * size);
|
|
29
|
+
const end = Math.min(samples.length, Math.max(start + 1, Math.floor((i + 1) * size)));
|
|
30
|
+
let peak = 0;
|
|
31
|
+
for (let j = start; j < end; j += 1) {
|
|
32
|
+
const v = Math.abs(samples[j]);
|
|
33
|
+
if (v > peak)
|
|
34
|
+
peak = v;
|
|
35
|
+
}
|
|
36
|
+
buckets[i] = peak;
|
|
37
|
+
}
|
|
38
|
+
const max = buckets.reduce((m, v) => (v > m ? v : m), 0);
|
|
39
|
+
if (max <= 0)
|
|
40
|
+
return buckets;
|
|
41
|
+
return buckets.map((v) => Math.min(1, v / max));
|
|
42
|
+
}
|
|
43
|
+
/** Format a number of seconds as `m:ss` for the recorder timer / player. */
|
|
44
|
+
function formatClock(totalSeconds) {
|
|
45
|
+
const safe = Number.isFinite(totalSeconds) && totalSeconds > 0
|
|
46
|
+
? Math.floor(totalSeconds)
|
|
47
|
+
: 0;
|
|
48
|
+
const minutes = Math.floor(safe / 60);
|
|
49
|
+
const seconds = safe % 60;
|
|
50
|
+
const paddedSeconds = seconds < 10 ? `0${seconds}` : `${seconds}`;
|
|
51
|
+
return `${minutes}:${paddedSeconds}`;
|
|
52
|
+
}
|
|
53
|
+
/** True when this browser can record audio at all (SSR-safe). */
|
|
54
|
+
function isVoiceRecordingSupported() {
|
|
55
|
+
return (typeof window !== 'undefined' &&
|
|
56
|
+
typeof navigator !== 'undefined' &&
|
|
57
|
+
!!navigator.mediaDevices &&
|
|
58
|
+
typeof navigator.mediaDevices.getUserMedia === 'function' &&
|
|
59
|
+
typeof MediaRecorder !== 'undefined');
|
|
60
|
+
}
|
|
61
|
+
//# sourceMappingURL=audio.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"audio.js","sourceRoot":"","sources":["../../../../components/VoiceRecorder/audio.ts"],"names":[],"mappings":";AAAA,YAAY,CAAC;;;AAkBb,0CAuBC;AAGD,kCASC;AAGD,8DAQC;AA9DD;;;;;;GAMG;AAEH,6EAA6E;AAChE,QAAA,gBAAgB,GAAG,EAAE,CAAC;AAEnC;;;;GAIG;AACH,SAAgB,eAAe,CAC7B,OAAiB,EACjB,QAAgB,wBAAgB;IAEhC,IAAI,OAAO,CAAC,MAAM,KAAK,CAAC,IAAI,KAAK,IAAI,CAAC;QAAE,OAAO,EAAE,CAAC;IAClD,MAAM,OAAO,GAAa,IAAI,KAAK,CAAC,KAAK,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC;IACnD,MAAM,IAAI,GAAG,OAAO,CAAC,MAAM,GAAG,KAAK,CAAC;IACpC,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,KAAK,EAAE,CAAC,IAAI,CAAC,EAAE,CAAC;QAClC,MAAM,KAAK,GAAG,IAAI,CAAC,KAAK,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC;QACnC,MAAM,GAAG,GAAG,IAAI,CAAC,GAAG,CAClB,OAAO,CAAC,MAAM,EACd,IAAI,CAAC,GAAG,CAAC,KAAK,GAAG,CAAC,EAAE,IAAI,CAAC,KAAK,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,GAAG,IAAI,CAAC,CAAC,CAChD,CAAC;QACF,IAAI,IAAI,GAAG,CAAC,CAAC;QACb,KAAK,IAAI,CAAC,GAAG,KAAK,EAAE,CAAC,GAAG,GAAG,EAAE,CAAC,IAAI,CAAC,EAAE,CAAC;YACpC,MAAM,CAAC,GAAG,IAAI,CAAC,GAAG,CAAC,OAAO,CAAC,CAAC,CAAC,CAAC,CAAC;YAC/B,IAAI,CAAC,GAAG,IAAI;gBAAE,IAAI,GAAG,CAAC,CAAC;QACzB,CAAC;QACD,OAAO,CAAC,CAAC,CAAC,GAAG,IAAI,CAAC;IACpB,CAAC;IACD,MAAM,GAAG,GAAG,OAAO,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;IACzD,IAAI,GAAG,IAAI,CAAC;QAAE,OAAO,OAAO,CAAC;IAC7B,OAAO,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,IAAI,CAAC,GAAG,CAAC,CAAC,EAAE,CAAC,GAAG,GAAG,CAAC,CAAC,CAAC;AAClD,CAAC;AAED,4EAA4E;AAC5E,SAAgB,WAAW,CAAC,YAAoB;IAC9C,MAAM,IAAI,GACR,MAAM,CAAC,QAAQ,CAAC,YAAY,CAAC,IAAI,YAAY,GAAG,CAAC;QAC/C,CAAC,CAAC,IAAI,CAAC,KAAK,CAAC,YAAY,CAAC;QAC1B,CAAC,CAAC,CAAC,CAAC;IACR,MAAM,OAAO,GAAG,IAAI,CAAC,KAAK,CAAC,IAAI,GAAG,EAAE,CAAC,CAAC;IACtC,MAAM,OAAO,GAAG,IAAI,GAAG,EAAE,CAAC;IAC1B,MAAM,aAAa,GAAG,OAAO,GAAG,EAAE,CAAC,CAAC,CAAC,IAAI,OAAO,EAAE,CAAC,CAAC,CAAC,GAAG,OAAO,EAAE,CAAC;IAClE,OAAO,GAAG,OAAO,IAAI,aAAa,EAAE,CAAC;AACvC,CAAC;AAED,iEAAiE;AACjE,SAAgB,yBAAyB;IACvC,OAAO,CACL,OAAO,MAAM,KAAK,WAAW;QAC7B,OAAO,SAAS,KAAK,WAAW;QAChC,CAAC,CAAC,SAAS,CAAC,YAAY;QACxB,OAAO,SAAS,CAAC,YAAY,CAAC,YAAY,KAAK,UAAU;QACzD,OAAO,aAAa,KAAK,WAAW,CACrC,CAAC;AACJ,CAAC"}
|
|
@@ -0,0 +1,16 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
var __importDefault = (this && this.__importDefault) || function (mod) {
|
|
3
|
+
return (mod && mod.__esModule) ? mod : { "default": mod };
|
|
4
|
+
};
|
|
5
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
6
|
+
exports.default = exports.VOICE_PEAK_COUNT = exports.isVoiceRecordingSupported = exports.formatClock = exports.downsamplePeaks = exports.useVoiceRecorder = void 0;
|
|
7
|
+
var useVoiceRecorder_1 = require("./useVoiceRecorder");
|
|
8
|
+
Object.defineProperty(exports, "useVoiceRecorder", { enumerable: true, get: function () { return useVoiceRecorder_1.useVoiceRecorder; } });
|
|
9
|
+
var audio_1 = require("./audio");
|
|
10
|
+
Object.defineProperty(exports, "downsamplePeaks", { enumerable: true, get: function () { return audio_1.downsamplePeaks; } });
|
|
11
|
+
Object.defineProperty(exports, "formatClock", { enumerable: true, get: function () { return audio_1.formatClock; } });
|
|
12
|
+
Object.defineProperty(exports, "isVoiceRecordingSupported", { enumerable: true, get: function () { return audio_1.isVoiceRecordingSupported; } });
|
|
13
|
+
Object.defineProperty(exports, "VOICE_PEAK_COUNT", { enumerable: true, get: function () { return audio_1.VOICE_PEAK_COUNT; } });
|
|
14
|
+
var useVoiceRecorder_2 = require("./useVoiceRecorder");
|
|
15
|
+
Object.defineProperty(exports, "default", { enumerable: true, get: function () { return __importDefault(useVoiceRecorder_2).default; } });
|
|
16
|
+
//# sourceMappingURL=index.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"index.js","sourceRoot":"","sources":["../../../../components/VoiceRecorder/index.ts"],"names":[],"mappings":";;;;;;AAAA,uDAK4B;AAJ1B,oHAAA,gBAAgB,OAAA;AAKlB,iCAKiB;AAJf,wGAAA,eAAe,OAAA;AACf,oGAAA,WAAW,OAAA;AACX,kHAAA,yBAAyB,OAAA;AACzB,yGAAA,gBAAgB,OAAA;AAElB,uDAA6C;AAApC,4HAAA,OAAO,OAAA"}
|