@primestyleai/tryon 2.0.1 → 2.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/react/index.js +92 -60
- package/package.json +1 -1
package/dist/react/index.js
CHANGED
|
@@ -60,6 +60,22 @@ function lbsToKg(lbs) {
|
|
|
60
60
|
function ftInToCm(ft, inch) {
|
|
61
61
|
return +(ft * 30.48 + inch * 2.54).toFixed(1);
|
|
62
62
|
}
|
|
63
|
+
function SvgIcon({ d, size = 18, strokeWidth = 2 }) {
|
|
64
|
+
return /* @__PURE__ */ jsx(
|
|
65
|
+
"svg",
|
|
66
|
+
{
|
|
67
|
+
width: size,
|
|
68
|
+
height: size,
|
|
69
|
+
viewBox: "0 0 24 24",
|
|
70
|
+
fill: "none",
|
|
71
|
+
stroke: "currentColor",
|
|
72
|
+
strokeWidth,
|
|
73
|
+
strokeLinecap: "round",
|
|
74
|
+
strokeLinejoin: "round",
|
|
75
|
+
children: /* @__PURE__ */ jsx("path", { d })
|
|
76
|
+
}
|
|
77
|
+
);
|
|
78
|
+
}
|
|
63
79
|
function CameraIcon({ size = 18 }) {
|
|
64
80
|
return /* @__PURE__ */ jsxs("svg", { width: size, height: size, viewBox: "0 0 24 24", fill: "none", stroke: "currentColor", strokeWidth: 2, strokeLinecap: "round", strokeLinejoin: "round", children: [
|
|
65
81
|
/* @__PURE__ */ jsx("path", { d: "M23 19a2 2 0 0 1-2 2H3a2 2 0 0 1-2-2V8a2 2 0 0 1 2-2h4l2-3h6l2 3h4a2 2 0 0 1 2 2z" }),
|
|
@@ -160,7 +176,9 @@ function PrimeStyleTryon({
|
|
|
160
176
|
const [resultImageUrl, setResultImageUrl] = useState(null);
|
|
161
177
|
const [errorMessage, setErrorMessage] = useState(null);
|
|
162
178
|
const [dragOver, setDragOver] = useState(false);
|
|
163
|
-
const
|
|
179
|
+
const countdownRef = useRef(25);
|
|
180
|
+
const countdownElRef = useRef(null);
|
|
181
|
+
const countdownCircleRef = useRef(null);
|
|
164
182
|
const [sizingMethod, setSizingMethod] = useState(null);
|
|
165
183
|
const [sizingResult, setSizingResult] = useState(null);
|
|
166
184
|
const [sizeGuide, setSizeGuide] = useState(null);
|
|
@@ -199,15 +217,12 @@ function PrimeStyleTryon({
|
|
|
199
217
|
}, [apiUrl]);
|
|
200
218
|
useEffect(() => {
|
|
201
219
|
if (view === "processing") {
|
|
202
|
-
|
|
220
|
+
countdownRef.current = 25;
|
|
203
221
|
const interval = setInterval(() => {
|
|
204
|
-
|
|
205
|
-
|
|
206
|
-
|
|
207
|
-
|
|
208
|
-
}
|
|
209
|
-
return p - 1;
|
|
210
|
-
});
|
|
222
|
+
countdownRef.current -= 1;
|
|
223
|
+
if (countdownElRef.current) countdownElRef.current.textContent = String(Math.max(countdownRef.current, 0));
|
|
224
|
+
if (countdownCircleRef.current) countdownCircleRef.current.style.strokeDashoffset = `${Math.max(countdownRef.current, 0) / 25 * 326.73}`;
|
|
225
|
+
if (countdownRef.current <= 0) clearInterval(interval);
|
|
211
226
|
}, 1e3);
|
|
212
227
|
return () => clearInterval(interval);
|
|
213
228
|
}
|
|
@@ -709,23 +724,33 @@ function PrimeStyleTryon({
|
|
|
709
724
|
setView("sizing-form");
|
|
710
725
|
}, children: [
|
|
711
726
|
/* @__PURE__ */ jsx("div", { className: "ps-tryon-choice-icon", children: /* @__PURE__ */ jsx(RulerIcon, { size: 24 }) }),
|
|
712
|
-
/* @__PURE__ */
|
|
713
|
-
|
|
714
|
-
|
|
727
|
+
/* @__PURE__ */ jsxs("div", { className: "ps-tryon-choice-info", children: [
|
|
728
|
+
/* @__PURE__ */ jsx("div", { className: "ps-tryon-choice-title", children: "Enter my measurements" }),
|
|
729
|
+
/* @__PURE__ */ jsx("div", { className: "ps-tryon-choice-desc", children: "Chest, waist, hips, shoes & more" })
|
|
730
|
+
] }),
|
|
731
|
+
/* @__PURE__ */ jsx("span", { className: "ps-tryon-choice-badge", children: "Best accuracy" })
|
|
715
732
|
] }),
|
|
716
733
|
/* @__PURE__ */ jsxs("button", { className: "ps-tryon-choice-card", onClick: () => {
|
|
717
734
|
setSizingMethod("quick");
|
|
718
735
|
setView("sizing-form");
|
|
719
736
|
}, children: [
|
|
720
737
|
/* @__PURE__ */ jsx("div", { className: "ps-tryon-choice-icon", children: /* @__PURE__ */ jsx(SparkleIcon, { size: 24 }) }),
|
|
721
|
-
/* @__PURE__ */
|
|
722
|
-
|
|
738
|
+
/* @__PURE__ */ jsxs("div", { className: "ps-tryon-choice-info", children: [
|
|
739
|
+
/* @__PURE__ */ jsx("div", { className: "ps-tryon-choice-title", children: "Just height & weight" }),
|
|
740
|
+
/* @__PURE__ */ jsx("div", { className: "ps-tryon-choice-desc", children: "Quick estimate in seconds" })
|
|
741
|
+
] })
|
|
742
|
+
] }),
|
|
743
|
+
/* @__PURE__ */ jsxs("button", { className: "ps-tryon-choice-card", onClick: () => {
|
|
744
|
+
setSizingMethod(null);
|
|
745
|
+
handleSubmit();
|
|
746
|
+
}, children: [
|
|
747
|
+
/* @__PURE__ */ jsx("div", { className: "ps-tryon-choice-icon", children: /* @__PURE__ */ jsx(SvgIcon, { d: "M13 5H1M13 9H1M13 13H1M5 17l4 4 8-8", size: 24, strokeWidth: 1.5 }) }),
|
|
748
|
+
/* @__PURE__ */ jsxs("div", { className: "ps-tryon-choice-info", children: [
|
|
749
|
+
/* @__PURE__ */ jsx("div", { className: "ps-tryon-choice-title", children: "Skip sizing" }),
|
|
750
|
+
/* @__PURE__ */ jsx("div", { className: "ps-tryon-choice-desc", children: "Just show me the try-on" })
|
|
751
|
+
] })
|
|
723
752
|
] })
|
|
724
|
-
] })
|
|
725
|
-
/* @__PURE__ */ jsx("button", { className: "ps-tryon-skip-btn", onClick: () => {
|
|
726
|
-
setSizingMethod(null);
|
|
727
|
-
handleSubmit();
|
|
728
|
-
}, children: "Skip sizing — just try it on" })
|
|
753
|
+
] })
|
|
729
754
|
] });
|
|
730
755
|
}
|
|
731
756
|
function SizingFormView() {
|
|
@@ -744,17 +769,19 @@ function PrimeStyleTryon({
|
|
|
744
769
|
] }),
|
|
745
770
|
/* @__PURE__ */ jsxs("div", { className: "ps-tryon-input-row", children: [
|
|
746
771
|
/* @__PURE__ */ jsx("label", { children: "Height" }),
|
|
747
|
-
/* @__PURE__ */
|
|
772
|
+
heightUnit === "ft" ? /* @__PURE__ */ jsxs("div", { className: "ps-tryon-height-ft", children: [
|
|
773
|
+
/* @__PURE__ */ jsx("input", { type: "number", placeholder: "5", value: formData.heightFeet || "", onChange: (e) => updateField("heightFeet", e.target.value) }),
|
|
774
|
+
/* @__PURE__ */ jsx("span", { children: "ft" }),
|
|
775
|
+
/* @__PURE__ */ jsx("input", { type: "number", placeholder: "4", value: formData.heightInches || "", onChange: (e) => updateField("heightInches", e.target.value) }),
|
|
776
|
+
/* @__PURE__ */ jsx("span", { children: "in" })
|
|
777
|
+
] }) : /* @__PURE__ */ jsx("input", { type: "number", placeholder: "e.g. 175", value: formData.height || "", onChange: (e) => updateField("height", e.target.value) }),
|
|
778
|
+
/* @__PURE__ */ jsx(UnitToggle, { options: [{ label: "cm", value: "cm" }, { label: "ft", value: "ft" }], value: heightUnit, onChange: setHeightUnit })
|
|
748
779
|
] }),
|
|
749
|
-
heightUnit === "ft" ? /* @__PURE__ */ jsxs("div", { className: "ps-tryon-input-row ps-tryon-dual-input", children: [
|
|
750
|
-
/* @__PURE__ */ jsx("input", { type: "number", placeholder: "ft", value: formData.heightFeet || "", onChange: (e) => updateField("heightFeet", e.target.value) }),
|
|
751
|
-
/* @__PURE__ */ jsx("input", { type: "number", placeholder: "in", value: formData.heightInches || "", onChange: (e) => updateField("heightInches", e.target.value) })
|
|
752
|
-
] }) : /* @__PURE__ */ jsx(InputRow, { label: "", fieldKey: "height", placeholder: "e.g. 175", type: "number", unit: "cm" }),
|
|
753
780
|
/* @__PURE__ */ jsxs("div", { className: "ps-tryon-input-row", children: [
|
|
754
781
|
/* @__PURE__ */ jsx("label", { children: "Weight" }),
|
|
782
|
+
/* @__PURE__ */ jsx("input", { type: "number", placeholder: weightUnit === "lbs" ? "e.g. 170" : "e.g. 75", value: formData.weight || "", onChange: (e) => updateField("weight", e.target.value) }),
|
|
755
783
|
/* @__PURE__ */ jsx(UnitToggle, { options: [{ label: "kg", value: "kg" }, { label: "lbs", value: "lbs" }], value: weightUnit, onChange: setWeightUnit })
|
|
756
784
|
] }),
|
|
757
|
-
/* @__PURE__ */ jsx(InputRow, { label: "", fieldKey: "weight", placeholder: weightUnit === "lbs" ? "e.g. 170" : "e.g. 75", type: "number", unit: weightUnit }),
|
|
758
785
|
sizingMethod === "exact" && /* @__PURE__ */ jsxs(Fragment, { children: [
|
|
759
786
|
/* @__PURE__ */ jsxs("div", { className: "ps-tryon-input-row", children: [
|
|
760
787
|
/* @__PURE__ */ jsx("label", { children: "Measurements" }),
|
|
@@ -799,15 +826,15 @@ function PrimeStyleTryon({
|
|
|
799
826
|
}
|
|
800
827
|
function ProcessingView() {
|
|
801
828
|
return /* @__PURE__ */ jsxs("div", { className: "ps-tryon-processing", children: [
|
|
802
|
-
|
|
829
|
+
/* @__PURE__ */ jsxs("div", { className: "ps-tryon-countdown-ring", children: [
|
|
803
830
|
/* @__PURE__ */ jsxs("svg", { viewBox: "0 0 120 120", children: [
|
|
804
831
|
/* @__PURE__ */ jsx("circle", { className: "ps-tryon-countdown-track", cx: "60", cy: "60", r: "52" }),
|
|
805
|
-
/* @__PURE__ */ jsx("circle", { className: "ps-tryon-countdown-progress", cx: "60", cy: "60", r: "52", style: { strokeDashoffset: `${
|
|
832
|
+
/* @__PURE__ */ jsx("circle", { ref: countdownCircleRef, className: "ps-tryon-countdown-progress", cx: "60", cy: "60", r: "52", style: { strokeDashoffset: `${25 / 25 * 326.73}` } })
|
|
806
833
|
] }),
|
|
807
|
-
/* @__PURE__ */ jsx("span", { className: "ps-tryon-countdown-number", children:
|
|
808
|
-
] })
|
|
809
|
-
/* @__PURE__ */ jsx("p", { className: cx("ps-tryon-processing-text", cn.processingText), children:
|
|
810
|
-
/* @__PURE__ */ jsx("p", { className: cx("ps-tryon-processing-sub", cn.processingSubText), children:
|
|
834
|
+
/* @__PURE__ */ jsx("span", { ref: countdownElRef, className: "ps-tryon-countdown-number", children: "25" })
|
|
835
|
+
] }),
|
|
836
|
+
/* @__PURE__ */ jsx("p", { className: cx("ps-tryon-processing-text", cn.processingText), children: "Generating your try-on..." }),
|
|
837
|
+
/* @__PURE__ */ jsx("p", { className: cx("ps-tryon-processing-sub", cn.processingSubText), children: "This usually takes 15-25 seconds" })
|
|
811
838
|
] });
|
|
812
839
|
}
|
|
813
840
|
function ResultView() {
|
|
@@ -851,14 +878,17 @@ function PrimeStyleTryon({
|
|
|
851
878
|
/* @__PURE__ */ jsx("button", { onClick: handleRetry, className: cx("ps-tryon-btn-retry", cn.retryButton), children: "Try Another" })
|
|
852
879
|
] }),
|
|
853
880
|
sizingMethod && !profileSaved && /* @__PURE__ */ jsxs("div", { className: "ps-tryon-save-prompt", children: [
|
|
854
|
-
/* @__PURE__ */ jsx("
|
|
855
|
-
/* @__PURE__ */
|
|
856
|
-
|
|
857
|
-
|
|
881
|
+
/* @__PURE__ */ jsx("div", { className: "ps-tryon-save-label", children: "Save your measurements for next time" }),
|
|
882
|
+
/* @__PURE__ */ jsxs("div", { className: "ps-tryon-save-row", children: [
|
|
883
|
+
/* @__PURE__ */ jsx("input", { type: "text", placeholder: "Name this profile (e.g. John, Sarah)", value: profileName, onChange: (e) => setProfileName(e.target.value) }),
|
|
884
|
+
/* @__PURE__ */ jsx("button", { onClick: () => {
|
|
885
|
+
if (profileName.trim()) saveProfile(profileName.trim());
|
|
886
|
+
}, children: "Save" })
|
|
887
|
+
] })
|
|
858
888
|
] }),
|
|
859
889
|
profileSaved && /* @__PURE__ */ jsxs("div", { className: "ps-tryon-save-done", children: [
|
|
860
890
|
/* @__PURE__ */ jsx(CheckIcon, {}),
|
|
861
|
-
"
|
|
891
|
+
" Measurements saved to profile"
|
|
862
892
|
] })
|
|
863
893
|
] })
|
|
864
894
|
] });
|
|
@@ -1168,28 +1198,25 @@ const STYLES = `
|
|
|
1168
1198
|
|
|
1169
1199
|
/* Sizing choice */
|
|
1170
1200
|
.ps-tryon-sizing-choice { text-align: center; }
|
|
1171
|
-
.ps-tryon-section-title { font-size: 16px; font-weight: 600; color: #fff; margin: 0 0
|
|
1172
|
-
.ps-tryon-choice-cards { display: flex; flex-direction: column; gap:
|
|
1201
|
+
.ps-tryon-section-title { font-size: 16px; font-weight: 600; color: #fff; margin: 0 0 16px; }
|
|
1202
|
+
.ps-tryon-choice-cards { display: flex; flex-direction: column; gap: 10px; }
|
|
1173
1203
|
.ps-tryon-choice-card {
|
|
1174
|
-
|
|
1204
|
+
display: flex; align-items: center; gap: 14px; padding: 16px;
|
|
1205
|
+
border: 1.5px solid #333; border-radius: 12px;
|
|
1175
1206
|
background: #1a1b1a; cursor: pointer; transition: all 0.25s; text-align: left;
|
|
1176
|
-
|
|
1207
|
+
width: 100%; font-family: inherit; position: relative; overflow: hidden;
|
|
1177
1208
|
}
|
|
1178
|
-
.ps-tryon-choice-card:hover { border-color: #bb945c; box-shadow: 0
|
|
1179
|
-
.ps-tryon-choice-
|
|
1209
|
+
.ps-tryon-choice-card:hover { border-color: #bb945c; transform: translateY(-1px); box-shadow: 0 6px 20px rgba(187,148,92,0.08); }
|
|
1210
|
+
.ps-tryon-choice-card:hover::before { content: ''; position: absolute; left: 0; top: 0; bottom: 0; width: 3px; background: #bb945c; }
|
|
1211
|
+
.ps-tryon-choice-icon { color: #bb945c; flex-shrink: 0; }
|
|
1180
1212
|
.ps-tryon-choice-icon svg { stroke: currentColor; fill: none; }
|
|
1181
|
-
.ps-tryon-choice-
|
|
1182
|
-
.ps-tryon-choice-
|
|
1213
|
+
.ps-tryon-choice-info { flex: 1; min-width: 0; }
|
|
1214
|
+
.ps-tryon-choice-title { font-size: 14px; font-weight: 600; color: #fff; }
|
|
1215
|
+
.ps-tryon-choice-desc { font-size: 12px; color: #999; margin-top: 2px; }
|
|
1183
1216
|
.ps-tryon-choice-badge {
|
|
1184
|
-
|
|
1185
|
-
background: rgba(187,148,92,0.12); color: #bb945c; font-size:
|
|
1186
|
-
}
|
|
1187
|
-
.ps-tryon-skip-btn {
|
|
1188
|
-
margin-top: 16px; padding: 10px; background: none; border: 1px solid #333;
|
|
1189
|
-
border-radius: 10px; color: #999; font-size: 13px; cursor: pointer; transition: all 0.2s;
|
|
1190
|
-
width: 100%; font-family: inherit;
|
|
1217
|
+
padding: 3px 10px; border-radius: 20px; flex-shrink: 0;
|
|
1218
|
+
background: rgba(187,148,92,0.12); color: #bb945c; font-size: 10px; font-weight: 600;
|
|
1191
1219
|
}
|
|
1192
|
-
.ps-tryon-skip-btn:hover { border-color: #666; color: #ccc; }
|
|
1193
1220
|
|
|
1194
1221
|
/* Sizing form */
|
|
1195
1222
|
.ps-tryon-sizing-form { display: flex; flex-direction: column; gap: 12px; }
|
|
@@ -1204,8 +1231,11 @@ const STYLES = `
|
|
|
1204
1231
|
.ps-tryon-input-row input::-webkit-inner-spin-button { -webkit-appearance: none; margin: 0; }
|
|
1205
1232
|
.ps-tryon-input-row input:focus { border-color: #bb945c; }
|
|
1206
1233
|
.ps-tryon-input-unit { font-size: 12px; color: #666; flex-shrink: 0; }
|
|
1207
|
-
.ps-tryon-
|
|
1208
|
-
.ps-tryon-
|
|
1234
|
+
.ps-tryon-height-ft { display: flex; align-items: center; gap: 6px; flex: 1; }
|
|
1235
|
+
.ps-tryon-height-ft input { width: 60px; padding: 10px 10px; border: 1.5px solid #333; border-radius: 10px; background: #1a1b1a; color: #fff; font-size: 14px; font-family: inherit; outline: none; text-align: center; -moz-appearance: textfield; }
|
|
1236
|
+
.ps-tryon-height-ft input::-webkit-outer-spin-button, .ps-tryon-height-ft input::-webkit-inner-spin-button { -webkit-appearance: none; margin: 0; }
|
|
1237
|
+
.ps-tryon-height-ft input:focus { border-color: #bb945c; }
|
|
1238
|
+
.ps-tryon-height-ft span { font-size: 12px; color: #666; }
|
|
1209
1239
|
.ps-tryon-country-select {
|
|
1210
1240
|
flex: 1; padding: 10px 36px 10px 14px; border: 1.5px solid #333; border-radius: 10px;
|
|
1211
1241
|
background: #1a1b1a; color: #fff; font-size: 13px; font-family: inherit;
|
|
@@ -1280,17 +1310,19 @@ const STYLES = `
|
|
|
1280
1310
|
.ps-fit-good { color: #4ade80; } .ps-fit-tight { color: #f59e0b; } .ps-fit-loose { color: #60a5fa; }
|
|
1281
1311
|
|
|
1282
1312
|
/* Save profile prompt */
|
|
1283
|
-
.ps-tryon-save-prompt {
|
|
1284
|
-
.ps-tryon-save-
|
|
1313
|
+
.ps-tryon-save-prompt { margin-top: 14px; padding: 14px; border: 1px solid #333; border-radius: 12px; background: #1a1b1a; }
|
|
1314
|
+
.ps-tryon-save-label { font-size: 12px; color: #999; margin-bottom: 10px; }
|
|
1315
|
+
.ps-tryon-save-row { display: flex; gap: 8px; }
|
|
1316
|
+
.ps-tryon-save-row input {
|
|
1285
1317
|
flex: 1; padding: 10px 14px; border: 1.5px solid #333; border-radius: 10px;
|
|
1286
|
-
background: #
|
|
1318
|
+
background: #111211; color: #fff; font-size: 13px; font-family: inherit; outline: none;
|
|
1287
1319
|
}
|
|
1288
|
-
.ps-tryon-save-
|
|
1289
|
-
.ps-tryon-save-
|
|
1320
|
+
.ps-tryon-save-row input:focus { border-color: #bb945c; }
|
|
1321
|
+
.ps-tryon-save-row button {
|
|
1290
1322
|
padding: 10px 20px; background: #bb945c; color: #111; border: none; border-radius: 10px;
|
|
1291
1323
|
font-size: 13px; font-weight: 600; cursor: pointer; transition: opacity 0.2s; font-family: inherit;
|
|
1292
1324
|
}
|
|
1293
|
-
.ps-tryon-save-
|
|
1325
|
+
.ps-tryon-save-row button:hover { opacity: 0.9; }
|
|
1294
1326
|
.ps-tryon-save-done { font-size: 12px; color: #4ade80; margin-top: 10px; display: flex; align-items: center; gap: 6px; justify-content: center; }
|
|
1295
1327
|
.ps-tryon-save-done svg { stroke: currentColor; }
|
|
1296
1328
|
|