@primestyleai/tryon 5.1.0 → 5.2.1
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 +43 -17
- package/package.json +2 -4
package/dist/react/index.js
CHANGED
|
@@ -4177,7 +4177,14 @@ function MeasurementOverlay({ lines, fitRows, show, imgWidth, imgHeight }) {
|
|
|
4177
4177
|
const width = x2 - x1;
|
|
4178
4178
|
const curveDepth = width * 0.06;
|
|
4179
4179
|
const midX = (x1 + x2) / 2;
|
|
4180
|
-
const fitRow = fitRows.find((r) =>
|
|
4180
|
+
const fitRow = fitRows.find((r) => {
|
|
4181
|
+
const a = r.area.toLowerCase().trim();
|
|
4182
|
+
if (a === key) return true;
|
|
4183
|
+
if (key === "chest" && (a.includes("bust") || a.includes("chest"))) return true;
|
|
4184
|
+
if (key === "waist" && a.includes("waist")) return true;
|
|
4185
|
+
if (key === "hips" && (a.includes("hip") || a === "hips")) return true;
|
|
4186
|
+
return false;
|
|
4187
|
+
});
|
|
4181
4188
|
const color = fitRow ? fitColor(fitRow.fit) : "#2154EF";
|
|
4182
4189
|
const delay = i * 0.35;
|
|
4183
4190
|
const curvePath = `M ${x1} ${cy} Q ${midX} ${cy + curveDepth} ${x2} ${cy}`;
|
|
@@ -4273,6 +4280,7 @@ const cellValFn = (row, colIdx, header) => {
|
|
|
4273
4280
|
return "";
|
|
4274
4281
|
};
|
|
4275
4282
|
const fitLabelFn = (fit, t) => fit === "good" ? t("perfect fit") : fit === "too-tight" ? t("too tight") : fit === "tight" ? t("tight") : fit === "a-bit-tight" ? t("a bit tight") : fit === "too-loose" ? t("too loose") : fit === "loose" ? t("loose") : t("a bit loose");
|
|
4283
|
+
const lengthFitLabelFn = (fit, t) => fit === "good" ? t("perfect fit") : fit === "too-tight" ? t("too short") : fit === "tight" ? t("short") : fit === "a-bit-tight" ? t("a bit short") : fit === "too-loose" ? t("too long") : fit === "loose" ? t("long") : t("a bit long");
|
|
4276
4284
|
const isLengthSection = (name) => /length|lunghezza|longueur|länge|largo/i.test(name);
|
|
4277
4285
|
function findLengthForSection(sectionName, lengthEntries) {
|
|
4278
4286
|
const base = sectionName.toLowerCase().replace(/\s*(size|sizing|—.*|–.*|\(.*?\))\s*/gi, "").trim();
|
|
@@ -4390,19 +4398,19 @@ function SectionDetailView({
|
|
|
4390
4398
|
if (rMin2 > 0 && rMax2 > 0) {
|
|
4391
4399
|
const range2 = rMax2 - rMin2;
|
|
4392
4400
|
const threshold2 = range2 > 0 ? range2 * 0.5 : rMin2 * 0.05 || 3;
|
|
4393
|
-
const tol2 = Math.max((rMax2 || rMin2) *
|
|
4401
|
+
const tol2 = Math.max((rMax2 || rMin2) * 5e-3, 0.25);
|
|
4394
4402
|
if (userNum2 >= rMin2 - tol2 && userNum2 <= rMax2 + tol2) fit2 = "good";
|
|
4395
4403
|
else if (userNum2 < rMin2) {
|
|
4396
4404
|
const diff = rMin2 - userNum2;
|
|
4397
|
-
fit2 = diff > threshold2 * 2 ? "too-
|
|
4405
|
+
fit2 = diff > threshold2 * 2 ? "too-tight" : diff > threshold2 ? "tight" : "a-bit-tight";
|
|
4398
4406
|
} else {
|
|
4399
4407
|
const diff = userNum2 - rMax2;
|
|
4400
|
-
fit2 = diff > threshold2 * 2 ? "too-
|
|
4408
|
+
fit2 = diff > threshold2 * 2 ? "too-loose" : diff > threshold2 ? "loose" : "a-bit-loose";
|
|
4401
4409
|
}
|
|
4402
4410
|
}
|
|
4403
4411
|
}
|
|
4404
4412
|
}
|
|
4405
|
-
return { area: m.measurement + " (" + activeLength + ")", userNum: userNum2, chartLabel: cleanNumFn(chartLabel2), fit: fit2 };
|
|
4413
|
+
return { area: m.measurement + " (" + activeLength + ")", userNum: userNum2, chartLabel: cleanNumFn(chartLabel2), fit: fit2, isLength: true };
|
|
4406
4414
|
}
|
|
4407
4415
|
const userNum = userMeasurements[m.measurement.toLowerCase()] || pNumFn(m.userValue);
|
|
4408
4416
|
let { min: rMin, max: rMax } = pRangeFn(m.chartRange);
|
|
@@ -4418,7 +4426,7 @@ function SectionDetailView({
|
|
|
4418
4426
|
const range = rMax - rMin;
|
|
4419
4427
|
const threshold = range > 0 ? range * 0.5 : rMin * 0.05 || 3;
|
|
4420
4428
|
let fit;
|
|
4421
|
-
const tol = Math.max((rMax || rMin) *
|
|
4429
|
+
const tol = Math.max((rMax || rMin) * 5e-3, 0.25);
|
|
4422
4430
|
if (userNum >= rMin - tol && userNum <= rMax + tol) fit = "good";
|
|
4423
4431
|
else if (userNum < rMin) {
|
|
4424
4432
|
const diff = rMin - userNum;
|
|
@@ -4427,10 +4435,15 @@ function SectionDetailView({
|
|
|
4427
4435
|
const diff = userNum - rMax;
|
|
4428
4436
|
fit = diff > threshold * 2 ? "too-tight" : diff > threshold ? "tight" : "a-bit-tight";
|
|
4429
4437
|
}
|
|
4430
|
-
return { area: m.measurement, userNum, chartLabel: cleanNumFn(chartLabel), fit };
|
|
4438
|
+
return { area: m.measurement, userNum, chartLabel: cleanNumFn(chartLabel), fit, isLength: false };
|
|
4431
4439
|
});
|
|
4432
4440
|
}, [sectionResult, lengthEntry, userMeasurements, displaySize, recSize, chartRangeFor, selectedLength, recLength]);
|
|
4433
4441
|
return /* @__PURE__ */ jsxs("div", { className: "ps-tryon-sec-detail", children: [
|
|
4442
|
+
/* @__PURE__ */ jsx("div", { style: { marginBottom: "0.3vw" }, children: /* @__PURE__ */ jsxs("button", { className: "ps-bp-back-btn", onClick: onBack, type: "button", children: [
|
|
4443
|
+
/* @__PURE__ */ jsx("span", { className: "ps-bp-back-arrow", children: "←" }),
|
|
4444
|
+
" ",
|
|
4445
|
+
t("Back to sections")
|
|
4446
|
+
] }) }),
|
|
4434
4447
|
/* @__PURE__ */ jsxs("div", { className: "ps-tryon-sec-detail-header", children: [
|
|
4435
4448
|
/* @__PURE__ */ jsx("div", { className: "ps-tryon-sec-detail-icon", children: /* @__PURE__ */ jsx(GarmentIcon, { name: sectionName, size: 28 }) }),
|
|
4436
4449
|
/* @__PURE__ */ jsx("span", { className: "ps-tryon-sec-detail-name", children: sectionName })
|
|
@@ -4460,7 +4473,7 @@ function SectionDetailView({
|
|
|
4460
4473
|
unitLbl
|
|
4461
4474
|
] }),
|
|
4462
4475
|
/* @__PURE__ */ jsx("td", { className: "ps-tryon-sr-ft-garment", children: row.chartLabel }),
|
|
4463
|
-
/* @__PURE__ */ jsx("td", { children: /* @__PURE__ */ jsx("span", { className: `ps-tryon-sr-fit-status ps-fit-${row.fit}`, children: fitLabelFn(row.fit, t) }) })
|
|
4476
|
+
/* @__PURE__ */ jsx("td", { children: /* @__PURE__ */ jsx("span", { className: `ps-tryon-sr-fit-status ps-fit-${row.fit}`, children: row.isLength ? lengthFitLabelFn(row.fit, t) : fitLabelFn(row.fit, t) }) })
|
|
4464
4477
|
] }, i)) })
|
|
4465
4478
|
] }),
|
|
4466
4479
|
allSizes.length > 1 && (() => {
|
|
@@ -4633,15 +4646,21 @@ function SizeResultView({
|
|
|
4633
4646
|
const allSectionEntries = useMemo(() => {
|
|
4634
4647
|
if (!isMultiSection || !sizeGuide?.sections) return [];
|
|
4635
4648
|
return Object.entries(sizeGuide.sections).map(([name, section]) => {
|
|
4636
|
-
const secResult =
|
|
4637
|
-
|
|
4638
|
-
|
|
4639
|
-
|
|
4640
|
-
|
|
4641
|
-
const
|
|
4642
|
-
|
|
4643
|
-
|
|
4644
|
-
|
|
4649
|
+
const secResult = (() => {
|
|
4650
|
+
const fromSections = sizingResult?.sections?.[name];
|
|
4651
|
+
if (fromSections?.matchDetails?.length) return fromSections;
|
|
4652
|
+
if (sizingResult?.matchDetails?.length) {
|
|
4653
|
+
const secHeaderKeys = new Set(section.requiredFields.map((f) => f.key.toLowerCase()));
|
|
4654
|
+
const secHeaderLabels = new Set(section.headers.map((h) => h.toLowerCase().replace(/\s*\(.*?\)\s*/g, "").trim()));
|
|
4655
|
+
const relevantDetails = sizingResult.matchDetails.filter((m) => {
|
|
4656
|
+
const mLower = m.measurement.toLowerCase();
|
|
4657
|
+
return secHeaderKeys.has(mLower) || secHeaderLabels.has(mLower);
|
|
4658
|
+
});
|
|
4659
|
+
if (relevantDetails.length) {
|
|
4660
|
+
return { recommendedSize: fromSections?.recommendedSize || sizingResult.recommendedSize, matchDetails: relevantDetails };
|
|
4661
|
+
}
|
|
4662
|
+
}
|
|
4663
|
+
return fromSections || { recommendedSize: sizingResult?.recommendedSize || "", matchDetails: [] };
|
|
4645
4664
|
})();
|
|
4646
4665
|
const userMeasurements = {};
|
|
4647
4666
|
if (sizingResult?.matchDetails) {
|
|
@@ -5059,6 +5078,13 @@ function SizeResultView({
|
|
|
5059
5078
|
/* @__PURE__ */ jsx("br", {}),
|
|
5060
5079
|
t("Don't apply filters or edits")
|
|
5061
5080
|
] })
|
|
5081
|
+
] }),
|
|
5082
|
+
/* @__PURE__ */ jsxs("div", { style: { background: "rgba(59,130,246,0.08)", border: "1px solid rgba(59,130,246,0.2)", borderRadius: "0.5vw", padding: "0.5vw 0.8vw" }, children: [
|
|
5083
|
+
/* @__PURE__ */ jsxs("div", { style: { display: "flex", alignItems: "center", gap: "0.3vw", marginBottom: "0.2vw" }, children: [
|
|
5084
|
+
/* @__PURE__ */ jsx(SparkleIcon, { size: 12 }),
|
|
5085
|
+
/* @__PURE__ */ jsx("span", { style: { color: "var(--ps-accent)", fontSize: "0.65vw", fontWeight: 700 }, children: t("Pro Tip") })
|
|
5086
|
+
] }),
|
|
5087
|
+
/* @__PURE__ */ jsx("div", { style: { fontSize: "0.55vw", color: "var(--ps-text-secondary)", lineHeight: 1.7 }, children: t("Our AI works best with front-facing, full-body photos in fitted clothing. Better photos = more accurate virtual try-on!") })
|
|
5062
5088
|
] })
|
|
5063
5089
|
] })
|
|
5064
5090
|
] }),
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@primestyleai/tryon",
|
|
3
|
-
"version": "5.1
|
|
3
|
+
"version": "5.2.1",
|
|
4
4
|
"description": "PrimeStyle Virtual Try-On SDK — React component & Web Component",
|
|
5
5
|
"type": "module",
|
|
6
6
|
"main": "dist/primestyle-tryon.js",
|
|
@@ -57,7 +57,5 @@
|
|
|
57
57
|
"typescript": "^5.5.0",
|
|
58
58
|
"vite": "^5.4.0"
|
|
59
59
|
},
|
|
60
|
-
"dependencies": {
|
|
61
|
-
"@primestyleai/tryon": "^4.3.2"
|
|
62
|
-
}
|
|
60
|
+
"dependencies": {}
|
|
63
61
|
}
|