@jlunamena/design-system 1.0.0 → 1.0.2
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/dist/index.d.mts +1 -0
- package/dist/index.d.ts +1 -0
- package/dist/index.js +12 -7
- package/dist/index.mjs +12 -7
- package/dist/index.native.js +231 -0
- package/dist/index.native.mjs +224 -0
- package/package.json +14 -2
package/dist/index.d.mts
CHANGED
|
@@ -122,6 +122,7 @@ type BodyDiagramProps = {
|
|
|
122
122
|
overlayStyle?: BodyDiagramOverlayStyle;
|
|
123
123
|
intensityByMuscle?: Record<string, BodyDiagramIntensity>;
|
|
124
124
|
};
|
|
125
|
+
|
|
125
126
|
declare const BodyDiagram: ({ view, svgMarkupByView, baseImageByView, selectedMuscles, onSelectedChange, debugForceVisible, interactionMode, palette, overlayStyle, intensityByMuscle, }: BodyDiagramProps) => react_jsx_runtime.JSX.Element;
|
|
126
127
|
|
|
127
128
|
export { BodyDiagram, type BodyDiagramIntensity, type BodyDiagramOverlayStyle, type BodyDiagramPalette, type BodyDiagramProps, type BodyDiagramView, type Colors, type Radius, type Shadows, type Spacing, type Typography, colors, radius, shadows, spacing, typography };
|
package/dist/index.d.ts
CHANGED
|
@@ -122,6 +122,7 @@ type BodyDiagramProps = {
|
|
|
122
122
|
overlayStyle?: BodyDiagramOverlayStyle;
|
|
123
123
|
intensityByMuscle?: Record<string, BodyDiagramIntensity>;
|
|
124
124
|
};
|
|
125
|
+
|
|
125
126
|
declare const BodyDiagram: ({ view, svgMarkupByView, baseImageByView, selectedMuscles, onSelectedChange, debugForceVisible, interactionMode, palette, overlayStyle, intensityByMuscle, }: BodyDiagramProps) => react_jsx_runtime.JSX.Element;
|
|
126
127
|
|
|
127
128
|
export { BodyDiagram, type BodyDiagramIntensity, type BodyDiagramOverlayStyle, type BodyDiagramPalette, type BodyDiagramProps, type BodyDiagramView, type Colors, type Radius, type Shadows, type Spacing, type Typography, colors, radius, shadows, spacing, typography };
|
package/dist/index.js
CHANGED
|
@@ -166,6 +166,17 @@ var resolveBodyDiagramMuscleState = (input) => {
|
|
|
166
166
|
isDebugForced
|
|
167
167
|
};
|
|
168
168
|
};
|
|
169
|
+
|
|
170
|
+
// src/components/body-diagram/toggleMuscle.ts
|
|
171
|
+
var toggleMuscle = (selectedMuscles, key) => {
|
|
172
|
+
const next = new Set(selectedMuscles);
|
|
173
|
+
if (next.has(key)) {
|
|
174
|
+
next.delete(key);
|
|
175
|
+
} else {
|
|
176
|
+
next.add(key);
|
|
177
|
+
}
|
|
178
|
+
return Array.from(next);
|
|
179
|
+
};
|
|
169
180
|
var BodyDiagram = ({
|
|
170
181
|
view,
|
|
171
182
|
svgMarkupByView,
|
|
@@ -188,13 +199,7 @@ var BodyDiagram = ({
|
|
|
188
199
|
const element = target.closest("[data-muscle-key]");
|
|
189
200
|
const key = element?.getAttribute("data-muscle-key");
|
|
190
201
|
if (!key) return;
|
|
191
|
-
|
|
192
|
-
if (next.has(key)) {
|
|
193
|
-
next.delete(key);
|
|
194
|
-
} else {
|
|
195
|
-
next.add(key);
|
|
196
|
-
}
|
|
197
|
-
onSelectedChange(Array.from(next));
|
|
202
|
+
onSelectedChange(toggleMuscle(selectedMuscles, key));
|
|
198
203
|
},
|
|
199
204
|
[interactionMode, onSelectedChange, selectedMuscles]
|
|
200
205
|
);
|
package/dist/index.mjs
CHANGED
|
@@ -164,6 +164,17 @@ var resolveBodyDiagramMuscleState = (input) => {
|
|
|
164
164
|
isDebugForced
|
|
165
165
|
};
|
|
166
166
|
};
|
|
167
|
+
|
|
168
|
+
// src/components/body-diagram/toggleMuscle.ts
|
|
169
|
+
var toggleMuscle = (selectedMuscles, key) => {
|
|
170
|
+
const next = new Set(selectedMuscles);
|
|
171
|
+
if (next.has(key)) {
|
|
172
|
+
next.delete(key);
|
|
173
|
+
} else {
|
|
174
|
+
next.add(key);
|
|
175
|
+
}
|
|
176
|
+
return Array.from(next);
|
|
177
|
+
};
|
|
167
178
|
var BodyDiagram = ({
|
|
168
179
|
view,
|
|
169
180
|
svgMarkupByView,
|
|
@@ -186,13 +197,7 @@ var BodyDiagram = ({
|
|
|
186
197
|
const element = target.closest("[data-muscle-key]");
|
|
187
198
|
const key = element?.getAttribute("data-muscle-key");
|
|
188
199
|
if (!key) return;
|
|
189
|
-
|
|
190
|
-
if (next.has(key)) {
|
|
191
|
-
next.delete(key);
|
|
192
|
-
} else {
|
|
193
|
-
next.add(key);
|
|
194
|
-
}
|
|
195
|
-
onSelectedChange(Array.from(next));
|
|
200
|
+
onSelectedChange(toggleMuscle(selectedMuscles, key));
|
|
196
201
|
},
|
|
197
202
|
[interactionMode, onSelectedChange, selectedMuscles]
|
|
198
203
|
);
|
|
@@ -0,0 +1,231 @@
|
|
|
1
|
+
'use strict';
|
|
2
|
+
|
|
3
|
+
var react = require('react');
|
|
4
|
+
var reactNative = require('react-native');
|
|
5
|
+
var reactNativeSvg = require('react-native-svg');
|
|
6
|
+
var jsxRuntime = require('react/jsx-runtime');
|
|
7
|
+
|
|
8
|
+
// src/tokens/colors.ts
|
|
9
|
+
var colors = {
|
|
10
|
+
primary: "#FDC026",
|
|
11
|
+
accent: "#6AABDE",
|
|
12
|
+
bodyDiagram: {
|
|
13
|
+
muscleFill: "#FFBF00",
|
|
14
|
+
muscleStroke: "#FF0090",
|
|
15
|
+
muscleStrokeWidth: 2,
|
|
16
|
+
muscleOpacity: 1
|
|
17
|
+
},
|
|
18
|
+
background: {
|
|
19
|
+
default: "#161C26",
|
|
20
|
+
muted: "#1C2434",
|
|
21
|
+
highlight: "#383040",
|
|
22
|
+
depth: "#08080A"
|
|
23
|
+
},
|
|
24
|
+
text: {
|
|
25
|
+
primary: "#E8E8E8",
|
|
26
|
+
secondary: "#9B9B9B"
|
|
27
|
+
}
|
|
28
|
+
};
|
|
29
|
+
|
|
30
|
+
// src/tokens/spacing.ts
|
|
31
|
+
var spacing = {
|
|
32
|
+
big: 32,
|
|
33
|
+
default: 24,
|
|
34
|
+
small: 12,
|
|
35
|
+
textHorizontal: 4,
|
|
36
|
+
textVertical: 0
|
|
37
|
+
};
|
|
38
|
+
|
|
39
|
+
// src/tokens/radius.ts
|
|
40
|
+
var radius = {
|
|
41
|
+
button: 4,
|
|
42
|
+
card: 8,
|
|
43
|
+
input: 4,
|
|
44
|
+
full: 9999
|
|
45
|
+
};
|
|
46
|
+
|
|
47
|
+
// src/tokens/typography.ts
|
|
48
|
+
var typography = {
|
|
49
|
+
size: {
|
|
50
|
+
xs: 11,
|
|
51
|
+
sm: 13,
|
|
52
|
+
base: 15,
|
|
53
|
+
md: 17,
|
|
54
|
+
lg: 20,
|
|
55
|
+
xl: 24,
|
|
56
|
+
"2xl": 30,
|
|
57
|
+
"3xl": 36
|
|
58
|
+
},
|
|
59
|
+
weight: {
|
|
60
|
+
regular: "400",
|
|
61
|
+
medium: "500",
|
|
62
|
+
semibold: "600",
|
|
63
|
+
bold: "700"
|
|
64
|
+
},
|
|
65
|
+
lineHeight: {
|
|
66
|
+
tight: 1.2,
|
|
67
|
+
normal: 1.5,
|
|
68
|
+
relaxed: 1.75
|
|
69
|
+
}
|
|
70
|
+
};
|
|
71
|
+
|
|
72
|
+
// src/tokens/shadows.ts
|
|
73
|
+
var shadows = {
|
|
74
|
+
sm: {
|
|
75
|
+
shadowColor: colors.background.depth,
|
|
76
|
+
shadowOffset: { width: 0, height: 1 },
|
|
77
|
+
shadowOpacity: 0.4,
|
|
78
|
+
shadowRadius: 2,
|
|
79
|
+
elevation: 2
|
|
80
|
+
},
|
|
81
|
+
md: {
|
|
82
|
+
shadowColor: colors.background.depth,
|
|
83
|
+
shadowOffset: { width: 0, height: 4 },
|
|
84
|
+
shadowOpacity: 0.5,
|
|
85
|
+
shadowRadius: 8,
|
|
86
|
+
elevation: 4
|
|
87
|
+
},
|
|
88
|
+
lg: {
|
|
89
|
+
shadowColor: colors.background.depth,
|
|
90
|
+
shadowOffset: { width: 0, height: 8 },
|
|
91
|
+
shadowOpacity: 0.6,
|
|
92
|
+
shadowRadius: 16,
|
|
93
|
+
elevation: 8
|
|
94
|
+
}
|
|
95
|
+
};
|
|
96
|
+
|
|
97
|
+
// src/utils/bodyDiagramState.ts
|
|
98
|
+
var DEFAULT_LEVEL_OPACITY = {
|
|
99
|
+
off: 0,
|
|
100
|
+
low: 0.2,
|
|
101
|
+
medium: 0.5,
|
|
102
|
+
high: 0.9
|
|
103
|
+
};
|
|
104
|
+
var DEFAULT_DEBUG_STYLE = {
|
|
105
|
+
fill: "red",
|
|
106
|
+
stroke: "yellow",
|
|
107
|
+
strokeWidth: 4,
|
|
108
|
+
opacity: 1
|
|
109
|
+
};
|
|
110
|
+
var DEFAULT_PALETTE = {
|
|
111
|
+
muscleFill: colors.bodyDiagram.muscleFill,
|
|
112
|
+
muscleStroke: colors.bodyDiagram.muscleStroke,
|
|
113
|
+
muscleStrokeWidth: colors.bodyDiagram.muscleStrokeWidth,
|
|
114
|
+
muscleOpacity: colors.bodyDiagram.muscleOpacity
|
|
115
|
+
};
|
|
116
|
+
var LEVELS = ["off", "low", "medium", "high"];
|
|
117
|
+
var resolveBodyDiagramTheme = (input = {}) => {
|
|
118
|
+
const palette = { ...DEFAULT_PALETTE, ...input.palette };
|
|
119
|
+
const opacityByLevel = { ...DEFAULT_LEVEL_OPACITY, ...input.levelOpacity };
|
|
120
|
+
const baseOpacity = palette.muscleOpacity ?? 1;
|
|
121
|
+
const levels = LEVELS.reduce(
|
|
122
|
+
(acc, level) => {
|
|
123
|
+
acc[level] = {
|
|
124
|
+
fill: palette.muscleFill ?? "",
|
|
125
|
+
stroke: palette.muscleStroke,
|
|
126
|
+
strokeWidth: palette.muscleStrokeWidth,
|
|
127
|
+
opacity: baseOpacity * (opacityByLevel[level] ?? 1)
|
|
128
|
+
};
|
|
129
|
+
return acc;
|
|
130
|
+
},
|
|
131
|
+
{
|
|
132
|
+
off: { fill: "", opacity: 0 },
|
|
133
|
+
low: { fill: "", opacity: 0 },
|
|
134
|
+
medium: { fill: "", opacity: 0 },
|
|
135
|
+
high: { fill: "", opacity: 0 }
|
|
136
|
+
}
|
|
137
|
+
);
|
|
138
|
+
return {
|
|
139
|
+
levels,
|
|
140
|
+
debug: input.debugStyle ?? DEFAULT_DEBUG_STYLE
|
|
141
|
+
};
|
|
142
|
+
};
|
|
143
|
+
var resolveBodyDiagramMuscleState = (input) => {
|
|
144
|
+
const { muscleKey, selectedMuscles, intensityByMuscle, debugForceVisible } = input;
|
|
145
|
+
const explicitLevel = intensityByMuscle?.[muscleKey];
|
|
146
|
+
let level = "off";
|
|
147
|
+
let source = "defaultOff";
|
|
148
|
+
if (explicitLevel) {
|
|
149
|
+
level = explicitLevel;
|
|
150
|
+
source = "explicit";
|
|
151
|
+
} else if (selectedMuscles.includes(muscleKey)) {
|
|
152
|
+
level = "high";
|
|
153
|
+
source = "selectedFallback";
|
|
154
|
+
}
|
|
155
|
+
const theme = input.theme ?? resolveBodyDiagramTheme({ palette: input.palette });
|
|
156
|
+
const isDebugForced = Boolean(debugForceVisible);
|
|
157
|
+
const style = isDebugForced ? theme.debug ?? DEFAULT_DEBUG_STYLE : theme.levels[level];
|
|
158
|
+
const shouldRender = isDebugForced ? true : level !== "off";
|
|
159
|
+
const interactionMode = input.interactionMode ?? "auto";
|
|
160
|
+
const interactive = interactionMode === "readonly" ? false : interactionMode === "editable" ? true : level !== "off";
|
|
161
|
+
return {
|
|
162
|
+
key: muscleKey,
|
|
163
|
+
level,
|
|
164
|
+
interactive,
|
|
165
|
+
style,
|
|
166
|
+
source,
|
|
167
|
+
shouldRender,
|
|
168
|
+
isDebugForced
|
|
169
|
+
};
|
|
170
|
+
};
|
|
171
|
+
var styleMarkup = (markup, params) => {
|
|
172
|
+
const { selectedMuscles, intensityByMuscle, palette, debugForceVisible, interactionMode } = params;
|
|
173
|
+
const theme = resolveBodyDiagramTheme({ palette });
|
|
174
|
+
return markup.replace(/<(\w+)([^>]*?\bdata-muscle-key="([^"]+)"[^>]*?)>/g, (match, tag, attrs, key) => {
|
|
175
|
+
const resolved = resolveBodyDiagramMuscleState({
|
|
176
|
+
muscleKey: key,
|
|
177
|
+
selectedMuscles,
|
|
178
|
+
intensityByMuscle,
|
|
179
|
+
palette,
|
|
180
|
+
debugForceVisible,
|
|
181
|
+
theme,
|
|
182
|
+
interactionMode
|
|
183
|
+
});
|
|
184
|
+
const isOff = resolved.level === "off";
|
|
185
|
+
const fill = isOff && !resolved.isDebugForced ? "rgba(0,0,0,0)" : resolved.style.fill || void 0;
|
|
186
|
+
const parts = [];
|
|
187
|
+
if (fill) parts.push(`fill="${fill}"`);
|
|
188
|
+
if (resolved.style.stroke) parts.push(`stroke="${resolved.style.stroke}"`);
|
|
189
|
+
if (resolved.style.strokeWidth != null) parts.push(`stroke-width="${resolved.style.strokeWidth}"`);
|
|
190
|
+
parts.push(`opacity="${resolved.style.opacity}"`);
|
|
191
|
+
return `<${tag}${attrs} ${parts.join(" ")}>`;
|
|
192
|
+
});
|
|
193
|
+
};
|
|
194
|
+
var BodyDiagram = ({
|
|
195
|
+
view,
|
|
196
|
+
svgMarkupByView,
|
|
197
|
+
selectedMuscles,
|
|
198
|
+
onSelectedChange,
|
|
199
|
+
debugForceVisible = false,
|
|
200
|
+
interactionMode = "auto",
|
|
201
|
+
palette,
|
|
202
|
+
intensityByMuscle
|
|
203
|
+
}) => {
|
|
204
|
+
const svgMarkup = svgMarkupByView[view] || "";
|
|
205
|
+
const xml = react.useMemo(
|
|
206
|
+
() => styleMarkup(svgMarkup, {
|
|
207
|
+
selectedMuscles,
|
|
208
|
+
intensityByMuscle,
|
|
209
|
+
palette,
|
|
210
|
+
debugForceVisible,
|
|
211
|
+
interactionMode
|
|
212
|
+
}),
|
|
213
|
+
[svgMarkup, selectedMuscles, intensityByMuscle, palette, debugForceVisible, interactionMode]
|
|
214
|
+
);
|
|
215
|
+
return /* @__PURE__ */ jsxRuntime.jsx(reactNative.View, { style: styles.container, children: /* @__PURE__ */ jsxRuntime.jsx(reactNativeSvg.SvgXml, { xml, width: "100%", height: "100%", preserveAspectRatio: "xMidYMid meet" }) });
|
|
216
|
+
};
|
|
217
|
+
var styles = reactNative.StyleSheet.create({
|
|
218
|
+
container: {
|
|
219
|
+
flex: 1,
|
|
220
|
+
width: "100%",
|
|
221
|
+
height: "100%",
|
|
222
|
+
overflow: "hidden"
|
|
223
|
+
}
|
|
224
|
+
});
|
|
225
|
+
|
|
226
|
+
exports.BodyDiagram = BodyDiagram;
|
|
227
|
+
exports.colors = colors;
|
|
228
|
+
exports.radius = radius;
|
|
229
|
+
exports.shadows = shadows;
|
|
230
|
+
exports.spacing = spacing;
|
|
231
|
+
exports.typography = typography;
|
|
@@ -0,0 +1,224 @@
|
|
|
1
|
+
import { useMemo } from 'react';
|
|
2
|
+
import { StyleSheet, View } from 'react-native';
|
|
3
|
+
import { SvgXml } from 'react-native-svg';
|
|
4
|
+
import { jsx } from 'react/jsx-runtime';
|
|
5
|
+
|
|
6
|
+
// src/tokens/colors.ts
|
|
7
|
+
var colors = {
|
|
8
|
+
primary: "#FDC026",
|
|
9
|
+
accent: "#6AABDE",
|
|
10
|
+
bodyDiagram: {
|
|
11
|
+
muscleFill: "#FFBF00",
|
|
12
|
+
muscleStroke: "#FF0090",
|
|
13
|
+
muscleStrokeWidth: 2,
|
|
14
|
+
muscleOpacity: 1
|
|
15
|
+
},
|
|
16
|
+
background: {
|
|
17
|
+
default: "#161C26",
|
|
18
|
+
muted: "#1C2434",
|
|
19
|
+
highlight: "#383040",
|
|
20
|
+
depth: "#08080A"
|
|
21
|
+
},
|
|
22
|
+
text: {
|
|
23
|
+
primary: "#E8E8E8",
|
|
24
|
+
secondary: "#9B9B9B"
|
|
25
|
+
}
|
|
26
|
+
};
|
|
27
|
+
|
|
28
|
+
// src/tokens/spacing.ts
|
|
29
|
+
var spacing = {
|
|
30
|
+
big: 32,
|
|
31
|
+
default: 24,
|
|
32
|
+
small: 12,
|
|
33
|
+
textHorizontal: 4,
|
|
34
|
+
textVertical: 0
|
|
35
|
+
};
|
|
36
|
+
|
|
37
|
+
// src/tokens/radius.ts
|
|
38
|
+
var radius = {
|
|
39
|
+
button: 4,
|
|
40
|
+
card: 8,
|
|
41
|
+
input: 4,
|
|
42
|
+
full: 9999
|
|
43
|
+
};
|
|
44
|
+
|
|
45
|
+
// src/tokens/typography.ts
|
|
46
|
+
var typography = {
|
|
47
|
+
size: {
|
|
48
|
+
xs: 11,
|
|
49
|
+
sm: 13,
|
|
50
|
+
base: 15,
|
|
51
|
+
md: 17,
|
|
52
|
+
lg: 20,
|
|
53
|
+
xl: 24,
|
|
54
|
+
"2xl": 30,
|
|
55
|
+
"3xl": 36
|
|
56
|
+
},
|
|
57
|
+
weight: {
|
|
58
|
+
regular: "400",
|
|
59
|
+
medium: "500",
|
|
60
|
+
semibold: "600",
|
|
61
|
+
bold: "700"
|
|
62
|
+
},
|
|
63
|
+
lineHeight: {
|
|
64
|
+
tight: 1.2,
|
|
65
|
+
normal: 1.5,
|
|
66
|
+
relaxed: 1.75
|
|
67
|
+
}
|
|
68
|
+
};
|
|
69
|
+
|
|
70
|
+
// src/tokens/shadows.ts
|
|
71
|
+
var shadows = {
|
|
72
|
+
sm: {
|
|
73
|
+
shadowColor: colors.background.depth,
|
|
74
|
+
shadowOffset: { width: 0, height: 1 },
|
|
75
|
+
shadowOpacity: 0.4,
|
|
76
|
+
shadowRadius: 2,
|
|
77
|
+
elevation: 2
|
|
78
|
+
},
|
|
79
|
+
md: {
|
|
80
|
+
shadowColor: colors.background.depth,
|
|
81
|
+
shadowOffset: { width: 0, height: 4 },
|
|
82
|
+
shadowOpacity: 0.5,
|
|
83
|
+
shadowRadius: 8,
|
|
84
|
+
elevation: 4
|
|
85
|
+
},
|
|
86
|
+
lg: {
|
|
87
|
+
shadowColor: colors.background.depth,
|
|
88
|
+
shadowOffset: { width: 0, height: 8 },
|
|
89
|
+
shadowOpacity: 0.6,
|
|
90
|
+
shadowRadius: 16,
|
|
91
|
+
elevation: 8
|
|
92
|
+
}
|
|
93
|
+
};
|
|
94
|
+
|
|
95
|
+
// src/utils/bodyDiagramState.ts
|
|
96
|
+
var DEFAULT_LEVEL_OPACITY = {
|
|
97
|
+
off: 0,
|
|
98
|
+
low: 0.2,
|
|
99
|
+
medium: 0.5,
|
|
100
|
+
high: 0.9
|
|
101
|
+
};
|
|
102
|
+
var DEFAULT_DEBUG_STYLE = {
|
|
103
|
+
fill: "red",
|
|
104
|
+
stroke: "yellow",
|
|
105
|
+
strokeWidth: 4,
|
|
106
|
+
opacity: 1
|
|
107
|
+
};
|
|
108
|
+
var DEFAULT_PALETTE = {
|
|
109
|
+
muscleFill: colors.bodyDiagram.muscleFill,
|
|
110
|
+
muscleStroke: colors.bodyDiagram.muscleStroke,
|
|
111
|
+
muscleStrokeWidth: colors.bodyDiagram.muscleStrokeWidth,
|
|
112
|
+
muscleOpacity: colors.bodyDiagram.muscleOpacity
|
|
113
|
+
};
|
|
114
|
+
var LEVELS = ["off", "low", "medium", "high"];
|
|
115
|
+
var resolveBodyDiagramTheme = (input = {}) => {
|
|
116
|
+
const palette = { ...DEFAULT_PALETTE, ...input.palette };
|
|
117
|
+
const opacityByLevel = { ...DEFAULT_LEVEL_OPACITY, ...input.levelOpacity };
|
|
118
|
+
const baseOpacity = palette.muscleOpacity ?? 1;
|
|
119
|
+
const levels = LEVELS.reduce(
|
|
120
|
+
(acc, level) => {
|
|
121
|
+
acc[level] = {
|
|
122
|
+
fill: palette.muscleFill ?? "",
|
|
123
|
+
stroke: palette.muscleStroke,
|
|
124
|
+
strokeWidth: palette.muscleStrokeWidth,
|
|
125
|
+
opacity: baseOpacity * (opacityByLevel[level] ?? 1)
|
|
126
|
+
};
|
|
127
|
+
return acc;
|
|
128
|
+
},
|
|
129
|
+
{
|
|
130
|
+
off: { fill: "", opacity: 0 },
|
|
131
|
+
low: { fill: "", opacity: 0 },
|
|
132
|
+
medium: { fill: "", opacity: 0 },
|
|
133
|
+
high: { fill: "", opacity: 0 }
|
|
134
|
+
}
|
|
135
|
+
);
|
|
136
|
+
return {
|
|
137
|
+
levels,
|
|
138
|
+
debug: input.debugStyle ?? DEFAULT_DEBUG_STYLE
|
|
139
|
+
};
|
|
140
|
+
};
|
|
141
|
+
var resolveBodyDiagramMuscleState = (input) => {
|
|
142
|
+
const { muscleKey, selectedMuscles, intensityByMuscle, debugForceVisible } = input;
|
|
143
|
+
const explicitLevel = intensityByMuscle?.[muscleKey];
|
|
144
|
+
let level = "off";
|
|
145
|
+
let source = "defaultOff";
|
|
146
|
+
if (explicitLevel) {
|
|
147
|
+
level = explicitLevel;
|
|
148
|
+
source = "explicit";
|
|
149
|
+
} else if (selectedMuscles.includes(muscleKey)) {
|
|
150
|
+
level = "high";
|
|
151
|
+
source = "selectedFallback";
|
|
152
|
+
}
|
|
153
|
+
const theme = input.theme ?? resolveBodyDiagramTheme({ palette: input.palette });
|
|
154
|
+
const isDebugForced = Boolean(debugForceVisible);
|
|
155
|
+
const style = isDebugForced ? theme.debug ?? DEFAULT_DEBUG_STYLE : theme.levels[level];
|
|
156
|
+
const shouldRender = isDebugForced ? true : level !== "off";
|
|
157
|
+
const interactionMode = input.interactionMode ?? "auto";
|
|
158
|
+
const interactive = interactionMode === "readonly" ? false : interactionMode === "editable" ? true : level !== "off";
|
|
159
|
+
return {
|
|
160
|
+
key: muscleKey,
|
|
161
|
+
level,
|
|
162
|
+
interactive,
|
|
163
|
+
style,
|
|
164
|
+
source,
|
|
165
|
+
shouldRender,
|
|
166
|
+
isDebugForced
|
|
167
|
+
};
|
|
168
|
+
};
|
|
169
|
+
var styleMarkup = (markup, params) => {
|
|
170
|
+
const { selectedMuscles, intensityByMuscle, palette, debugForceVisible, interactionMode } = params;
|
|
171
|
+
const theme = resolveBodyDiagramTheme({ palette });
|
|
172
|
+
return markup.replace(/<(\w+)([^>]*?\bdata-muscle-key="([^"]+)"[^>]*?)>/g, (match, tag, attrs, key) => {
|
|
173
|
+
const resolved = resolveBodyDiagramMuscleState({
|
|
174
|
+
muscleKey: key,
|
|
175
|
+
selectedMuscles,
|
|
176
|
+
intensityByMuscle,
|
|
177
|
+
palette,
|
|
178
|
+
debugForceVisible,
|
|
179
|
+
theme,
|
|
180
|
+
interactionMode
|
|
181
|
+
});
|
|
182
|
+
const isOff = resolved.level === "off";
|
|
183
|
+
const fill = isOff && !resolved.isDebugForced ? "rgba(0,0,0,0)" : resolved.style.fill || void 0;
|
|
184
|
+
const parts = [];
|
|
185
|
+
if (fill) parts.push(`fill="${fill}"`);
|
|
186
|
+
if (resolved.style.stroke) parts.push(`stroke="${resolved.style.stroke}"`);
|
|
187
|
+
if (resolved.style.strokeWidth != null) parts.push(`stroke-width="${resolved.style.strokeWidth}"`);
|
|
188
|
+
parts.push(`opacity="${resolved.style.opacity}"`);
|
|
189
|
+
return `<${tag}${attrs} ${parts.join(" ")}>`;
|
|
190
|
+
});
|
|
191
|
+
};
|
|
192
|
+
var BodyDiagram = ({
|
|
193
|
+
view,
|
|
194
|
+
svgMarkupByView,
|
|
195
|
+
selectedMuscles,
|
|
196
|
+
onSelectedChange,
|
|
197
|
+
debugForceVisible = false,
|
|
198
|
+
interactionMode = "auto",
|
|
199
|
+
palette,
|
|
200
|
+
intensityByMuscle
|
|
201
|
+
}) => {
|
|
202
|
+
const svgMarkup = svgMarkupByView[view] || "";
|
|
203
|
+
const xml = useMemo(
|
|
204
|
+
() => styleMarkup(svgMarkup, {
|
|
205
|
+
selectedMuscles,
|
|
206
|
+
intensityByMuscle,
|
|
207
|
+
palette,
|
|
208
|
+
debugForceVisible,
|
|
209
|
+
interactionMode
|
|
210
|
+
}),
|
|
211
|
+
[svgMarkup, selectedMuscles, intensityByMuscle, palette, debugForceVisible, interactionMode]
|
|
212
|
+
);
|
|
213
|
+
return /* @__PURE__ */ jsx(View, { style: styles.container, children: /* @__PURE__ */ jsx(SvgXml, { xml, width: "100%", height: "100%", preserveAspectRatio: "xMidYMid meet" }) });
|
|
214
|
+
};
|
|
215
|
+
var styles = StyleSheet.create({
|
|
216
|
+
container: {
|
|
217
|
+
flex: 1,
|
|
218
|
+
width: "100%",
|
|
219
|
+
height: "100%",
|
|
220
|
+
overflow: "hidden"
|
|
221
|
+
}
|
|
222
|
+
});
|
|
223
|
+
|
|
224
|
+
export { BodyDiagram, colors, radius, shadows, spacing, typography };
|
package/package.json
CHANGED
|
@@ -1,12 +1,14 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@jlunamena/design-system",
|
|
3
|
-
"version": "1.0.
|
|
3
|
+
"version": "1.0.2",
|
|
4
4
|
"description": "PT Design System",
|
|
5
5
|
"main": "dist/index.js",
|
|
6
|
+
"react-native": "dist/index.native.js",
|
|
6
7
|
"module": "dist/index.mjs",
|
|
7
8
|
"types": "dist/index.d.ts",
|
|
8
9
|
"exports": {
|
|
9
10
|
".": {
|
|
11
|
+
"react-native": "./dist/index.native.js",
|
|
10
12
|
"types": "./dist/index.d.ts",
|
|
11
13
|
"import": "./dist/index.mjs",
|
|
12
14
|
"require": "./dist/index.js"
|
|
@@ -23,7 +25,17 @@
|
|
|
23
25
|
"generate:exports": "node scripts/generate-exports.mjs"
|
|
24
26
|
},
|
|
25
27
|
"peerDependencies": {
|
|
26
|
-
"react": ">=18.0.0"
|
|
28
|
+
"react": ">=18.0.0",
|
|
29
|
+
"react-native": "*",
|
|
30
|
+
"react-native-svg": "*"
|
|
31
|
+
},
|
|
32
|
+
"peerDependenciesMeta": {
|
|
33
|
+
"react-native": {
|
|
34
|
+
"optional": true
|
|
35
|
+
},
|
|
36
|
+
"react-native-svg": {
|
|
37
|
+
"optional": true
|
|
38
|
+
}
|
|
27
39
|
},
|
|
28
40
|
"devDependencies": {
|
|
29
41
|
"@storybook/addon-essentials": "^8.6.0",
|