@sage-rsc/talking-head-react 1.2.1 → 1.2.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.js CHANGED
@@ -1,5 +1,5 @@
1
- import { jsxs as Pe, jsx as pe } from "react/jsx-runtime";
2
- import { forwardRef as Me, useRef as V, useState as de, useEffect as me, useCallback as O, useImperativeHandle as Fe, useLayoutEffect as Xe } from "react";
1
+ import { jsxs as Pe, jsx as me } from "react/jsx-runtime";
2
+ import { forwardRef as Me, useRef as O, useState as ce, useEffect as de, useCallback as B, useImperativeHandle as Fe, useLayoutEffect as Xe } from "react";
3
3
  import * as f from "three";
4
4
  import { OrbitControls as Ye } from "three/addons/controls/OrbitControls.js";
5
5
  import { GLTFLoader as je } from "three/addons/loaders/GLTFLoader.js";
@@ -7,12 +7,12 @@ import { DRACOLoader as Qe } from "three/addons/loaders/DRACOLoader.js";
7
7
  import { FBXLoader as De } from "three/addons/loaders/FBXLoader.js";
8
8
  import { RoomEnvironment as qe } from "three/addons/environments/RoomEnvironment.js";
9
9
  import _e from "three/addons/libs/stats.module.js";
10
- let m, le, ue;
11
- const w = [0, 0, 0, 0], M = new f.Vector3(), ze = new f.Vector3(), ae = new f.Vector3(), Ce = new f.Vector3();
10
+ let m, re, ue;
11
+ const w = [0, 0, 0, 0], T = new f.Vector3(), ze = new f.Vector3(), ie = new f.Vector3(), Ce = new f.Vector3();
12
12
  new f.Plane();
13
13
  new f.Ray();
14
14
  new f.Euler();
15
- const re = new f.Quaternion(), Oe = new f.Quaternion(), fe = new f.Matrix4(), xe = new f.Matrix4();
15
+ const oe = new f.Quaternion(), Oe = new f.Quaternion(), fe = new f.Matrix4(), xe = new f.Matrix4();
16
16
  new f.Vector3();
17
17
  const He = new f.Vector3(0, 0, 1), Ke = new f.Vector3(1, 0, 0), Je = new f.Vector3(0, 1, 0), $e = new f.Vector3(0, 0, 1);
18
18
  class et {
@@ -321,7 +321,7 @@ class et {
321
321
  /// Bone's parent object
322
322
  vBasis: r.position.clone(),
323
323
  // Original local position
324
- vWorld: r.parent.getWorldPosition(M).clone(),
324
+ vWorld: r.parent.getWorldPosition(T).clone(),
325
325
  // World position, parent
326
326
  qBasis: r.parent.quaternion.clone(),
327
327
  // Original quaternion, parent
@@ -338,7 +338,7 @@ class et {
338
338
  ea: [0, 0, 0, 0]
339
339
  // External acceleration [m/s^2]
340
340
  };
341
- u.boneParent.matrixWorld.decompose(M, re, ae), M.copy(He).applyQuaternion(re).setY(0).normalize(), re.premultiply(Oe.setFromUnitVectors(He, M).invert()).normalize(), u.qWorldInverseYaw = re.clone().normalize(), this.data.push(u), this.dict[h] = u;
341
+ u.boneParent.matrixWorld.decompose(T, oe, ie), T.copy(He).applyQuaternion(oe).setY(0).normalize(), oe.premultiply(Oe.setFromUnitVectors(He, T).invert()).normalize(), u.qWorldInverseYaw = oe.clone().normalize(), this.data.push(u), this.dict[h] = u;
342
342
  try {
343
343
  this.setValue(h, "type", s.type), this.setValue(h, "stiffness", s.stiffness), this.setValue(h, "damping", s.damping), this.setValue(h, "external", s.external), this.setValue(h, "limits", s.limits), this.setValue(h, "excludes", s.excludes), this.setValue(h, "deltaLocal", s.deltaLocal), this.setValue(h, "deltaWorld", s.deltaWorld), this.setValue(h, "pivot", s.pivot), this.setValue(h, "helper", s.helper);
344
344
  } catch (a) {
@@ -356,22 +356,22 @@ class et {
356
356
  for (this.timerMs += t, t > 1e3 && (this.timerMs = 0), t /= 1e3, e = 0, i = this.objectsUpdate.length; e < i; e++)
357
357
  o = this.objectsUpdate[e], o.updateMatrix(), o.parent === null ? o.matrixWorld.copy(o.matrix) : o.matrixWorld.multiplyMatrices(o.parent.matrixWorld, o.matrix), o.matrixWorldNeedsUpdate = !1;
358
358
  for (e = 0, i = this.data.length; e < i; e++) {
359
- if (o = this.data[e], M.copy(o.vWorld), fe.copy(o.boneParent.matrixWorld), xe.copy(fe).invert(), o.vWorld.setFromMatrixPosition(fe), M.applyMatrix4(xe), M.length() > 0.5 && (console.info("Info: Unrealistic jump of " + M.length().toFixed(2) + " meters."), M.setLength(0.5)), M.applyQuaternion(o.bone.quaternion), w[0] = M.x, w[1] = M.y, w[2] = -M.z, w[3] = M.length() / 3, o.children)
359
+ if (o = this.data[e], T.copy(o.vWorld), fe.copy(o.boneParent.matrixWorld), xe.copy(fe).invert(), o.vWorld.setFromMatrixPosition(fe), T.applyMatrix4(xe), T.length() > 0.5 && (console.info("Info: Unrealistic jump of " + T.length().toFixed(2) + " meters."), T.setLength(0.5)), T.applyQuaternion(o.bone.quaternion), w[0] = T.x, w[1] = T.y, w[2] = -T.z, w[3] = T.length() / 3, o.children)
360
360
  for (n = 0, s = o.children.length; n < s; n++)
361
361
  m = o.children[n], w[0] -= m.v[0] * t / 3, w[1] -= m.v[1] * t / 3, w[2] += m.v[2] * t / 3, w[3] -= m.v[3] * t / 3;
362
- if (m = this.opt.sensitivityFactor, w[0] *= o.ext * m, w[1] *= o.ext * m, w[2] *= o.ext * m, w[3] *= o.ext * m, o.isX && (m = w[0] / t, o.ea[0] = (m - o.ev[0]) / t, o.ev[0] = m, o.a[0] = -o.k[0] * o.p[0] - o.c[0] * o.v[0] - o.ea[0], o.p[0] += o.v[0] * t + o.a[0] * t * t / 2 + w[0], m = o.v[0] + o.a[0] * t / 2, m = -o.k[0] * o.p[0] - o.c[0] * m - o.ea[0], o.v[0] = o.v[0] + (m + o.a[0]) * t / 2), o.isY && (m = w[1] / t, o.ea[1] = (m - o.ev[1]) / t, o.ev[1] = m, o.a[1] = -o.k[1] * o.p[1] - o.c[1] * o.v[1] - o.ea[1], o.p[1] += o.v[1] * t + o.a[1] * t * t / 2 + w[1], m = o.v[1] + o.a[1] * t / 2, m = -o.k[1] * o.p[1] - o.c[1] * m - o.ea[1], o.v[1] = o.v[1] + (m + o.a[1]) * t / 2), o.isZ && (m = w[2] / t, o.ea[2] = (m - o.ev[2]) / t, o.ev[2] = m, o.a[2] = -o.k[2] * o.p[2] - o.c[2] * o.v[2] - o.ea[2], o.p[2] += o.v[2] * t + o.a[2] * t * t / 2 + w[2], m = o.v[2] + o.a[2] * t / 2, m = -o.k[2] * o.p[2] - o.c[2] * m - o.ea[2], o.v[2] = o.v[2] + (m + o.a[2]) * t / 2), o.isT && (m = w[3] / t, o.ea[3] = (m - o.ev[3]) / t, o.ev[3] = m, o.a[3] = -o.k[3] * o.p[3] - o.c[3] * o.v[3] - o.ea[3], o.p[3] += o.v[3] * t + o.a[3] * t * t / 2 + w[3], m = o.v[3] + o.a[3] * t / 2, m = -o.k[3] * o.p[3] - o.c[3] * m - o.ea[3], o.v[3] = o.v[3] + (m + o.a[3]) * t / 2), this.timerMs < this.opt.warmupMs && (o.v[0] *= 1e-4, o.p[0] *= 1e-4, o.v[1] *= 1e-4, o.p[1] *= 1e-4, o.v[2] *= 1e-4, o.p[2] *= 1e-4, o.v[3] *= 1e-4, o.p[3] *= 1e-4), w[0] = o.p[0], w[1] = o.p[1], w[2] = o.p[2], w[3] = o.p[3], m = this.opt.movementFactor, w[0] *= m, w[1] *= m, w[2] *= m, w[3] *= m, o.dl && (m = o.dl, w[0] += m[0], w[1] += m[1], w[2] += m[2]), o.dw && (m = o.dw, M.set(
362
+ if (m = this.opt.sensitivityFactor, w[0] *= o.ext * m, w[1] *= o.ext * m, w[2] *= o.ext * m, w[3] *= o.ext * m, o.isX && (m = w[0] / t, o.ea[0] = (m - o.ev[0]) / t, o.ev[0] = m, o.a[0] = -o.k[0] * o.p[0] - o.c[0] * o.v[0] - o.ea[0], o.p[0] += o.v[0] * t + o.a[0] * t * t / 2 + w[0], m = o.v[0] + o.a[0] * t / 2, m = -o.k[0] * o.p[0] - o.c[0] * m - o.ea[0], o.v[0] = o.v[0] + (m + o.a[0]) * t / 2), o.isY && (m = w[1] / t, o.ea[1] = (m - o.ev[1]) / t, o.ev[1] = m, o.a[1] = -o.k[1] * o.p[1] - o.c[1] * o.v[1] - o.ea[1], o.p[1] += o.v[1] * t + o.a[1] * t * t / 2 + w[1], m = o.v[1] + o.a[1] * t / 2, m = -o.k[1] * o.p[1] - o.c[1] * m - o.ea[1], o.v[1] = o.v[1] + (m + o.a[1]) * t / 2), o.isZ && (m = w[2] / t, o.ea[2] = (m - o.ev[2]) / t, o.ev[2] = m, o.a[2] = -o.k[2] * o.p[2] - o.c[2] * o.v[2] - o.ea[2], o.p[2] += o.v[2] * t + o.a[2] * t * t / 2 + w[2], m = o.v[2] + o.a[2] * t / 2, m = -o.k[2] * o.p[2] - o.c[2] * m - o.ea[2], o.v[2] = o.v[2] + (m + o.a[2]) * t / 2), o.isT && (m = w[3] / t, o.ea[3] = (m - o.ev[3]) / t, o.ev[3] = m, o.a[3] = -o.k[3] * o.p[3] - o.c[3] * o.v[3] - o.ea[3], o.p[3] += o.v[3] * t + o.a[3] * t * t / 2 + w[3], m = o.v[3] + o.a[3] * t / 2, m = -o.k[3] * o.p[3] - o.c[3] * m - o.ea[3], o.v[3] = o.v[3] + (m + o.a[3]) * t / 2), this.timerMs < this.opt.warmupMs && (o.v[0] *= 1e-4, o.p[0] *= 1e-4, o.v[1] *= 1e-4, o.p[1] *= 1e-4, o.v[2] *= 1e-4, o.p[2] *= 1e-4, o.v[3] *= 1e-4, o.p[3] *= 1e-4), w[0] = o.p[0], w[1] = o.p[1], w[2] = o.p[2], w[3] = o.p[3], m = this.opt.movementFactor, w[0] *= m, w[1] *= m, w[2] *= m, w[3] *= m, o.dl && (m = o.dl, w[0] += m[0], w[1] += m[1], w[2] += m[2]), o.dw && (m = o.dw, T.set(
363
363
  o.vBasis.x + w[0],
364
364
  o.vBasis.y + w[1],
365
365
  o.vBasis.z + w[2]
366
- ), M.applyMatrix4(fe), M.x += m[0], M.y += m[1], M.z += m[2], M.applyMatrix4(xe), w[0] += M.x - o.vBasis.x, w[1] += M.y - o.vBasis.y, w[2] += M.z - o.vBasis.z), o.limits && this.opt.isLimits && (m = o.limits, m[0] && (m[0][0] !== null && w[0] < m[0][0] && (w[0] = m[0][0]), m[0][1] !== null && w[0] > m[0][1] && (w[0] = m[0][1])), m[1] && (m[1][0] !== null && w[1] < m[1][0] && (w[1] = m[1][0]), m[1][1] !== null && w[1] > m[1][1] && (w[1] = m[1][1])), m[2] && (m[2][0] !== null && w[2] < m[2][0] && (w[2] = m[2][0]), m[2][1] !== null && w[2] > m[2][1] && (w[2] = m[2][1])), m[3] && (m[3][0] !== null && w[3] < m[3][0] && (w[3] = m[3][0]), m[3][1] !== null && w[3] > m[3][1] && (w[3] = m[3][1]))), o.isPoint)
366
+ ), T.applyMatrix4(fe), T.x += m[0], T.y += m[1], T.z += m[2], T.applyMatrix4(xe), w[0] += T.x - o.vBasis.x, w[1] += T.y - o.vBasis.y, w[2] += T.z - o.vBasis.z), o.limits && this.opt.isLimits && (m = o.limits, m[0] && (m[0][0] !== null && w[0] < m[0][0] && (w[0] = m[0][0]), m[0][1] !== null && w[0] > m[0][1] && (w[0] = m[0][1])), m[1] && (m[1][0] !== null && w[1] < m[1][0] && (w[1] = m[1][0]), m[1][1] !== null && w[1] > m[1][1] && (w[1] = m[1][1])), m[2] && (m[2][0] !== null && w[2] < m[2][0] && (w[2] = m[2][0]), m[2][1] !== null && w[2] > m[2][1] && (w[2] = m[2][1])), m[3] && (m[3][0] !== null && w[3] < m[3][0] && (w[3] = m[3][0]), m[3][1] !== null && w[3] > m[3][1] && (w[3] = m[3][1]))), o.isPoint)
367
367
  o.bone.position.set(
368
368
  o.vBasis.x + w[0],
369
369
  o.vBasis.y + w[1],
370
370
  o.vBasis.z - w[2]
371
371
  );
372
- else if (o.boneParent.quaternion.copy(o.qBasis), o.pivot && this.opt.isPivots && (o.boneParent.updateWorldMatrix(!1, !1), o.boneParent.matrixWorld.decompose(M, re, ae), M.copy(He).applyQuaternion(re).setY(0).normalize(), re.premultiply(Oe.setFromUnitVectors(He, M).invert()).normalize(), o.boneParent.quaternion.multiply(re.invert()), o.boneParent.quaternion.multiply(o.qWorldInverseYaw)), o.isZ && (m = Math.atan(w[0] / o.l), re.setFromAxisAngle($e, -m), o.boneParent.quaternion.multiply(re)), o.isY && (m = o.l / 3, m = m * Math.tanh(w[1] / m), o.bone.position.setLength(o.l + m)), o.isX && (m = Math.atan(w[2] / o.l), re.setFromAxisAngle(Ke, -m), o.boneParent.quaternion.multiply(re)), o.isT && (m = 1.5 * Math.tanh(w[3] * 1.5), re.setFromAxisAngle(Je, -m), o.boneParent.quaternion.multiply(re)), o.boneParent.updateWorldMatrix(!1, !0), o.excludes && this.opt.isExcludes)
372
+ else if (o.boneParent.quaternion.copy(o.qBasis), o.pivot && this.opt.isPivots && (o.boneParent.updateWorldMatrix(!1, !1), o.boneParent.matrixWorld.decompose(T, oe, ie), T.copy(He).applyQuaternion(oe).setY(0).normalize(), oe.premultiply(Oe.setFromUnitVectors(He, T).invert()).normalize(), o.boneParent.quaternion.multiply(oe.invert()), o.boneParent.quaternion.multiply(o.qWorldInverseYaw)), o.isZ && (m = Math.atan(w[0] / o.l), oe.setFromAxisAngle($e, -m), o.boneParent.quaternion.multiply(oe)), o.isY && (m = o.l / 3, m = m * Math.tanh(w[1] / m), o.bone.position.setLength(o.l + m)), o.isX && (m = Math.atan(w[2] / o.l), oe.setFromAxisAngle(Ke, -m), o.boneParent.quaternion.multiply(oe)), o.isT && (m = 1.5 * Math.tanh(w[3] * 1.5), oe.setFromAxisAngle(Je, -m), o.boneParent.quaternion.multiply(oe)), o.boneParent.updateWorldMatrix(!1, !0), o.excludes && this.opt.isExcludes)
373
373
  for (n = 0, s = o.excludes.length; n < s; n++)
374
- m = o.excludes[n], ae.set(0, 0, 0), m.deltaLocal && (ae.x += m.deltaLocal[0], ae.y += m.deltaLocal[1], ae.z += m.deltaLocal[2]), ae.applyMatrix4(m.bone.matrixWorld), xe.copy(o.boneParent.matrixWorld).invert(), ae.applyMatrix4(xe), M.copy(o.bone.position), !(M.distanceToSquared(ae) >= m.radiusSq) && (ue = M.length(), le = ae.length(), !(le > m.radius + ue) && (le < Math.abs(m.radius - ue) || (le = (le * le + ue * ue - m.radiusSq) / (2 * le), ae.normalize(), Ce.copy(ae).multiplyScalar(le), le = Math.sqrt(ue * ue - le * le), M.subVectors(M, Ce).projectOnPlane(ae).normalize().multiplyScalar(le), ze.subVectors(o.vBasis, Ce).projectOnPlane(ae).normalize(), ue = ze.dot(M), ue < 0 && (ue = Math.sqrt(le * le - ue * ue), ze.multiplyScalar(ue), M.add(ze)), M.add(Ce).normalize(), ae.copy(o.bone.position).normalize(), re.setFromUnitVectors(ae, M), o.boneParent.quaternion.premultiply(re), o.boneParent.updateWorldMatrix(!1, !0))));
374
+ m = o.excludes[n], ie.set(0, 0, 0), m.deltaLocal && (ie.x += m.deltaLocal[0], ie.y += m.deltaLocal[1], ie.z += m.deltaLocal[2]), ie.applyMatrix4(m.bone.matrixWorld), xe.copy(o.boneParent.matrixWorld).invert(), ie.applyMatrix4(xe), T.copy(o.bone.position), !(T.distanceToSquared(ie) >= m.radiusSq) && (ue = T.length(), re = ie.length(), !(re > m.radius + ue) && (re < Math.abs(m.radius - ue) || (re = (re * re + ue * ue - m.radiusSq) / (2 * re), ie.normalize(), Ce.copy(ie).multiplyScalar(re), re = Math.sqrt(ue * ue - re * re), T.subVectors(T, Ce).projectOnPlane(ie).normalize().multiplyScalar(re), ze.subVectors(o.vBasis, Ce).projectOnPlane(ie).normalize(), ue = ze.dot(T), ue < 0 && (ue = Math.sqrt(re * re - ue * ue), ze.multiplyScalar(ue), T.add(ze)), T.add(Ce).normalize(), ie.copy(o.bone.position).normalize(), oe.setFromUnitVectors(ie, T), o.boneParent.quaternion.premultiply(oe), o.boneParent.updateWorldMatrix(!1, !0))));
375
375
  }
376
376
  this.helpers.isActive && this.updateHelpers();
377
377
  }
@@ -445,14 +445,14 @@ class et {
445
445
  xe.copy(this.armature.matrixWorld).invert();
446
446
  const t = m.object.geometry.getAttribute("position");
447
447
  for (let e = 0, n = m.bones.length; e < n; e++)
448
- fe.multiplyMatrices(xe, m.bones[e].matrixWorld), M.setFromMatrixPosition(fe), t.setXYZ(e, M.x, M.y, M.z);
448
+ fe.multiplyMatrices(xe, m.bones[e].matrixWorld), T.setFromMatrixPosition(fe), t.setXYZ(e, T.x, T.y, T.z);
449
449
  t.needsUpdate = !0, m.object.updateMatrixWorld();
450
450
  }
451
451
  if (m = this.helpers.lines, m.bones.length) {
452
452
  xe.copy(this.armature.matrixWorld).invert();
453
453
  const t = m.object.geometry.getAttribute("position");
454
454
  for (let e = 0, n = 0, i = m.bones.length; e < i; e++, n += 2)
455
- fe.multiplyMatrices(xe, m.bones[e].matrixWorld), M.setFromMatrixPosition(fe), t.setXYZ(n, M.x, M.y, M.z), fe.multiplyMatrices(xe, m.bones[e].parent.matrixWorld), M.setFromMatrixPosition(fe), t.setXYZ(n + 1, M.x, M.y, M.z);
455
+ fe.multiplyMatrices(xe, m.bones[e].matrixWorld), T.setFromMatrixPosition(fe), t.setXYZ(n, T.x, T.y, T.z), fe.multiplyMatrices(xe, m.bones[e].parent.matrixWorld), T.setFromMatrixPosition(fe), t.setXYZ(n + 1, T.x, T.y, T.z);
456
456
  t.needsUpdate = !0, m.object.updateMatrixWorld();
457
457
  }
458
458
  }
@@ -2629,7 +2629,7 @@ const ct = /* @__PURE__ */ Object.freeze(/* @__PURE__ */ Object.defineProperty({
2629
2629
  fr: rt,
2630
2630
  fi: ut,
2631
2631
  lt: ct
2632
- }, K = new f.Quaternion(), Z = new f.Euler(), ve = new f.Vector3(), Re = new f.Vector3(), We = new f.Box3();
2632
+ }, _ = new f.Quaternion(), Z = new f.Euler(), ve = new f.Vector3(), Re = new f.Vector3(), We = new f.Box3();
2633
2633
  new f.Matrix4();
2634
2634
  new f.Matrix4();
2635
2635
  new f.Vector3();
@@ -4400,7 +4400,7 @@ class Be {
4400
4400
  if (e.x === 0 && e.y === 0 && e.z === 0) continue;
4401
4401
  Z.set(e.x, e.y, e.z);
4402
4402
  const n = this.poseAvatar.props[t];
4403
- n.isQuaternion ? (K.setFromEuler(Z), n.multiply(K)) : n.isVector3 && n.add(Z);
4403
+ n.isQuaternion ? (_.setFromEuler(Z), n.multiply(_)) : n.isVector3 && n.add(Z);
4404
4404
  }
4405
4405
  }
4406
4406
  /**
@@ -5193,7 +5193,7 @@ class Be {
5193
5193
  eyeLookOutRight: [null, 0],
5194
5194
  eyeContact: [0]
5195
5195
  }
5196
- })))), e > 2 * this.animFrameDur && (e = 2 * this.animFrameDur), (this.viewName !== "full" || this.isAvatarOnly) && (n = this.mtRandomized[Math.floor(Math.random() * this.mtRandomized.length)], i = this.mtAvatar[n], i.needsUpdate || Object.assign(i, { base: (this.mood.baseline[n] || 0) + (1 + l / 255) * Math.random() / 5, needsUpdate: !0 })), this.updatePoseBase(this.animClock), this.mixer && this.mixer.update(e / 1e3 * this.mixer.timeScale), this.updatePoseDelta(), (this.isSpeaking || this.isListening) && h ? l > this.volumeMax ? (this.volumeHeadBase = 0.05, Math.random() > 0.6 && (this.volumeHeadTarget = -0.05 - Math.random() / 15), this.volumeMax = l) : (this.volumeMax *= 0.92, this.volumeHeadTarget = this.volumeHeadBase - 0.9 * (this.volumeHeadBase - this.volumeHeadTarget)) : (this.volumeHeadTarget = 0, this.volumeMax = 0), n = this.volumeHeadTarget - this.volumeHeadCurrent, i = Math.abs(n), i > 1e-4 && (o = i * (this.volumeHeadEasing(Math.min(1, this.volumeHeadVelocity * e / 1e3 / i) / 2 + 0.5) - 0.5), this.volumeHeadCurrent += Math.sign(n) * Math.min(i, o)), Math.abs(this.volumeHeadCurrent) > 1e-4 && (K.setFromAxisAngle(mt, this.volumeHeadCurrent), this.objectNeck.quaternion.multiply(K)), We.setFromObject(this.armature), this.objectLeftToeBase.getWorldPosition(ve), ve.sub(this.armature.position), this.objectRightToeBase.getWorldPosition(Re), Re.sub(this.armature.position), this.objectHips.position.y -= We.min.y / 2, this.objectHips.position.x -= (ve.x + Re.x) / 4, this.objectHips.position.z -= (ve.z + Re.z) / 2, this.dynamicbones.update(e), this.fbxAnimationLoader && this.fbxAnimationLoader.update(), this.opt.update && this.opt.update(e), this.updateMorphTargets(e), this.isAvatarOnly)
5196
+ })))), e > 2 * this.animFrameDur && (e = 2 * this.animFrameDur), (this.viewName !== "full" || this.isAvatarOnly) && (n = this.mtRandomized[Math.floor(Math.random() * this.mtRandomized.length)], i = this.mtAvatar[n], i.needsUpdate || Object.assign(i, { base: (this.mood.baseline[n] || 0) + (1 + l / 255) * Math.random() / 5, needsUpdate: !0 })), this.updatePoseBase(this.animClock), this.mixer && this.mixer.update(e / 1e3 * this.mixer.timeScale), this.updatePoseDelta(), (this.isSpeaking || this.isListening) && h ? l > this.volumeMax ? (this.volumeHeadBase = 0.05, Math.random() > 0.6 && (this.volumeHeadTarget = -0.05 - Math.random() / 15), this.volumeMax = l) : (this.volumeMax *= 0.92, this.volumeHeadTarget = this.volumeHeadBase - 0.9 * (this.volumeHeadBase - this.volumeHeadTarget)) : (this.volumeHeadTarget = 0, this.volumeMax = 0), n = this.volumeHeadTarget - this.volumeHeadCurrent, i = Math.abs(n), i > 1e-4 && (o = i * (this.volumeHeadEasing(Math.min(1, this.volumeHeadVelocity * e / 1e3 / i) / 2 + 0.5) - 0.5), this.volumeHeadCurrent += Math.sign(n) * Math.min(i, o)), Math.abs(this.volumeHeadCurrent) > 1e-4 && (_.setFromAxisAngle(mt, this.volumeHeadCurrent), this.objectNeck.quaternion.multiply(_)), We.setFromObject(this.armature), this.objectLeftToeBase.getWorldPosition(ve), ve.sub(this.armature.position), this.objectRightToeBase.getWorldPosition(Re), Re.sub(this.armature.position), this.objectHips.position.y -= We.min.y / 2, this.objectHips.position.x -= (ve.x + Re.x) / 4, this.objectHips.position.z -= (ve.z + Re.z) / 2, this.dynamicbones.update(e), this.fbxAnimationLoader && this.fbxAnimationLoader.update(), this.opt.update && this.opt.update(e), this.updateMorphTargets(e), this.isAvatarOnly)
5197
5197
  this.stats && this.stats.end();
5198
5198
  else {
5199
5199
  if (this.cameraClock !== null && this.cameraClock < 1e3) {
@@ -5264,10 +5264,10 @@ class Be {
5264
5264
  let u = "", a = "", d = 0, c = [], g = [];
5265
5265
  const b = Array.from(this.segmenter.segment(t), (x) => x.segment);
5266
5266
  for (let x = 0; x < b.length; x++) {
5267
- const S = x === b.length - 1, G = b[x].match(l);
5267
+ const S = x === b.length - 1, U = b[x].match(l);
5268
5268
  let p = b[x].match(s);
5269
- const B = b[x].match(h), H = b[x].match(o);
5270
- if (p && !S && !B && b[x + 1].match(s) && (p = !1), n && (u += b[x]), G && (!i || i.every((y) => x < y[0] || x > y[1])) && (a += b[x]), (H || p || S) && (a.length && (a = this.lipsyncPreProcessText(a, r), a.length && c.push({
5269
+ const F = b[x].match(h), C = b[x].match(o);
5270
+ if (p && !S && !F && b[x + 1].match(s) && (p = !1), n && (u += b[x]), U && (!i || i.every((y) => x < y[0] || x > y[1])) && (a += b[x]), (C || p || S) && (a.length && (a = this.lipsyncPreProcessText(a, r), a.length && c.push({
5271
5271
  mark: d,
5272
5272
  word: a
5273
5273
  })), u.length && (g.push({
@@ -5300,7 +5300,7 @@ class Be {
5300
5300
  };
5301
5301
  n && (y.onSubtitles = n), c.length && !e.avatarMute && (y.text = c, e.avatarMood && (y.mood = e.avatarMood), e.ttsLang && (y.lang = e.ttsLang), e.ttsVoice && (y.voice = e.ttsVoice), e.ttsRate && (y.rate = e.ttsRate), e.ttsVoice && (y.pitch = e.ttsPitch), e.ttsVolume && (y.volume = e.ttsVolume)), this.speechQueue.push(y), c = [], a = "", d = 0, g = [];
5302
5302
  }
5303
- if (B) {
5303
+ if (F) {
5304
5304
  let y = this.animEmojis[b[x]];
5305
5305
  y && y.link && (y = this.animEmojis[y.link]), y && this.speechQueue.push({ emoji: y });
5306
5306
  }
@@ -5398,10 +5398,10 @@ class Be {
5398
5398
  let b = 0.6 + this.convertRange(g, [0, u], [0, 0.4]);
5399
5399
  if (u = Math.min(u, d.visemes.length * 200), c > 0)
5400
5400
  for (let x = 0; x < d.visemes.length; x++) {
5401
- const S = r + d.times[x] / c * u, G = d.durations[x] / c * u;
5401
+ const S = r + d.times[x] / c * u, U = d.durations[x] / c * u;
5402
5402
  o.push({
5403
5403
  template: { name: "viseme" },
5404
- ts: [S - Math.min(60, 2 * G / 3), S + Math.min(25, G / 2), S + G + Math.min(60, G / 2)],
5404
+ ts: [S - Math.min(60, 2 * U / 3), S + Math.min(25, U / 2), S + U + Math.min(60, U / 2)],
5405
5405
  vs: {
5406
5406
  ["viseme_" + d.visemes[x]]: [null, d.visemes[x] === "PP" || d.visemes[x] === "FF" ? 0.9 : b, 0]
5407
5407
  }
@@ -5483,7 +5483,7 @@ class Be {
5483
5483
  s.lang = o, s.rate = Math.max(0.1, Math.min(10, l)), s.pitch = Math.max(0, Math.min(2, h)), s.volume = Math.max(0, Math.min(1, r));
5484
5484
  const u = speechSynthesis.getVoices(), a = t.voice || this.avatar.ttsVoice || this.opt.ttsVoice;
5485
5485
  if (a && u.length > 0) {
5486
- const p = u.find((B) => B.name.includes(a) || B.lang === o);
5486
+ const p = u.find((F) => F.name.includes(a) || F.lang === o);
5487
5487
  p && (s.voice = p);
5488
5488
  }
5489
5489
  const d = i.length * 100 / s.rate, c = this.audioCtx.createBuffer(1, this.audioCtx.sampleRate * (d / 1e3), this.audioCtx.sampleRate), g = this.avatar.lipsyncLang || this.opt.lipsyncLang || "en", b = this.lipsyncPreProcessText(i, g), x = this.lipsyncWordsToVisemes(b, g);
@@ -5498,19 +5498,19 @@ class Be {
5498
5498
  const S = [];
5499
5499
  if (x && x.visemes && x.visemes.length > 0) {
5500
5500
  const p = x.times[x.visemes.length - 1] + x.durations[x.visemes.length - 1];
5501
- for (let B = 0; B < x.visemes.length; B++) {
5502
- const H = x.visemes[B], y = x.times[B] / p, I = x.durations[B] / p, z = y * d, A = I * d;
5501
+ for (let F = 0; F < x.visemes.length; F++) {
5502
+ const C = x.visemes[F], y = x.times[F] / p, I = x.durations[F] / p, z = y * d, A = I * d;
5503
5503
  S.push({
5504
5504
  template: { name: "viseme" },
5505
5505
  ts: [z - Math.min(60, 2 * A / 3), z + Math.min(25, A / 2), z + A + Math.min(60, A / 2)],
5506
5506
  vs: {
5507
- ["viseme_" + H]: [null, H === "PP" || H === "FF" ? 0.9 : 0.6, 0]
5507
+ ["viseme_" + C]: [null, C === "PP" || C === "FF" ? 0.9 : 0.6, 0]
5508
5508
  }
5509
5509
  });
5510
5510
  }
5511
5511
  }
5512
- const G = [...t.anim, ...S];
5513
- this.audioPlaylist.push({ anim: G, audio: c }), this.onSubtitles = t.onSubtitles || null, this.resetLips(), t.mood && this.setMood(t.mood), this.playAudio(), s.onend = () => {
5512
+ const U = [...t.anim, ...S];
5513
+ this.audioPlaylist.push({ anim: U, audio: c }), this.onSubtitles = t.onSubtitles || null, this.resetLips(), t.mood && this.setMood(t.mood), this.playAudio(), s.onend = () => {
5514
5514
  e();
5515
5515
  }, s.onerror = (p) => {
5516
5516
  console.error("Speech synthesis error:", p.error), n(p.error);
@@ -6159,10 +6159,10 @@ class Be {
6159
6159
  this.lookAt(null, null, t);
6160
6160
  return;
6161
6161
  }
6162
- this.objectLeftEye.updateMatrixWorld(!0), this.objectRightEye.updateMatrixWorld(!0), ve.setFromMatrixPosition(this.objectLeftEye.matrixWorld), Re.setFromMatrixPosition(this.objectRightEye.matrixWorld), ve.add(Re).divideScalar(2), K.copy(this.armature.quaternion), K.multiply(this.poseTarget.props["Hips.quaternion"]), K.multiply(this.poseTarget.props["Spine.quaternion"]), K.multiply(this.poseTarget.props["Spine1.quaternion"]), K.multiply(this.poseTarget.props["Spine2.quaternion"]), K.multiply(this.poseTarget.props["Neck.quaternion"]), K.multiply(this.poseTarget.props["Head.quaternion"]);
6162
+ this.objectLeftEye.updateMatrixWorld(!0), this.objectRightEye.updateMatrixWorld(!0), ve.setFromMatrixPosition(this.objectLeftEye.matrixWorld), Re.setFromMatrixPosition(this.objectRightEye.matrixWorld), ve.add(Re).divideScalar(2), _.copy(this.armature.quaternion), _.multiply(this.poseTarget.props["Hips.quaternion"]), _.multiply(this.poseTarget.props["Spine.quaternion"]), _.multiply(this.poseTarget.props["Spine1.quaternion"]), _.multiply(this.poseTarget.props["Spine2.quaternion"]), _.multiply(this.poseTarget.props["Neck.quaternion"]), _.multiply(this.poseTarget.props["Head.quaternion"]);
6163
6163
  const n = new f.Vector3().subVectors(e, ve).normalize(), i = Math.atan2(n.x, n.z), s = Math.asin(-n.y);
6164
6164
  Z.set(s, i, 0, "YXZ");
6165
- const l = new f.Quaternion().setFromEuler(Z), h = new f.Quaternion().copy(l).multiply(K.clone().invert());
6165
+ const l = new f.Quaternion().setFromEuler(Z), h = new f.Quaternion().copy(l).multiply(_.clone().invert());
6166
6166
  Z.setFromQuaternion(h, "YXZ");
6167
6167
  let r = Z.x / (40 / 24) + 0.2, u = Z.y / (9 / 4), a = Math.min(0.6, Math.max(-0.3, r)), d = Math.min(0.8, Math.max(-0.8, u)), c = (Math.random() - 0.5) / 4, g = (Math.random() - 0.5) / 4;
6168
6168
  if (t) {
@@ -6199,20 +6199,20 @@ class Be {
6199
6199
  const s = new f.Vector3().setFromMatrixPosition(this.objectLeftEye.matrixWorld), o = new f.Vector3().setFromMatrixPosition(this.objectRightEye.matrixWorld), l = new f.Vector3().addVectors(s, o).divideScalar(2);
6200
6200
  l.project(this.camera);
6201
6201
  let h = (l.x + 1) / 2 * i.width + i.left, r = -(l.y - 1) / 2 * i.height + i.top;
6202
- t === null && (t = h), e === null && (e = r), K.copy(this.armature.quaternion), K.multiply(this.poseTarget.props["Hips.quaternion"]), K.multiply(this.poseTarget.props["Spine.quaternion"]), K.multiply(this.poseTarget.props["Spine1.quaternion"]), K.multiply(this.poseTarget.props["Spine2.quaternion"]), K.multiply(this.poseTarget.props["Neck.quaternion"]), K.multiply(this.poseTarget.props["Head.quaternion"]), Z.setFromQuaternion(K);
6202
+ t === null && (t = h), e === null && (e = r), _.copy(this.armature.quaternion), _.multiply(this.poseTarget.props["Hips.quaternion"]), _.multiply(this.poseTarget.props["Spine.quaternion"]), _.multiply(this.poseTarget.props["Spine1.quaternion"]), _.multiply(this.poseTarget.props["Spine2.quaternion"]), _.multiply(this.poseTarget.props["Neck.quaternion"]), _.multiply(this.poseTarget.props["Head.quaternion"]), Z.setFromQuaternion(_);
6203
6203
  let u = Z.x / (40 / 24), a = Z.y / (9 / 4), d = Math.min(0.4, Math.max(-0.4, this.camera.rotation.x)), c = Math.min(0.4, Math.max(-0.4, this.camera.rotation.y)), g = Math.max(window.innerWidth - h, h), b = Math.max(window.innerHeight - r, r), x = this.convertRange(e, [r - b, r + b], [-0.3, 0.6]) - u + d, S = this.convertRange(t, [h - g, h + g], [-0.8, 0.8]) - a + c;
6204
6204
  x = Math.min(0.6, Math.max(-0.3, x)), S = Math.min(0.8, Math.max(-0.8, S));
6205
- let G = (Math.random() - 0.5) / 4, p = (Math.random() - 0.5) / 4;
6205
+ let U = (Math.random() - 0.5) / 4, p = (Math.random() - 0.5) / 4;
6206
6206
  if (n) {
6207
- let B = this.animQueue.findIndex((y) => y.template.name === "lookat");
6208
- B !== -1 && this.animQueue.splice(B, 1);
6209
- const H = {
6207
+ let F = this.animQueue.findIndex((y) => y.template.name === "lookat");
6208
+ F !== -1 && this.animQueue.splice(F, 1);
6209
+ const C = {
6210
6210
  name: "lookat",
6211
6211
  dt: [750, n],
6212
6212
  vs: {
6213
- bodyRotateX: [x + G],
6213
+ bodyRotateX: [x + U],
6214
6214
  bodyRotateY: [S + p],
6215
- eyesRotateX: [-3 * G + 0.1],
6215
+ eyesRotateX: [-3 * U + 0.1],
6216
6216
  eyesRotateY: [-5 * p],
6217
6217
  browInnerUp: [[0, 0.7]],
6218
6218
  mouthLeft: [[0, 0.7]],
@@ -6221,7 +6221,7 @@ class Be {
6221
6221
  headMove: [0]
6222
6222
  }
6223
6223
  };
6224
- this.animQueue.push(this.animFactory(H));
6224
+ this.animQueue.push(this.animFactory(C));
6225
6225
  }
6226
6226
  }
6227
6227
  /**
@@ -6523,8 +6523,8 @@ class Be {
6523
6523
  if (k.toLowerCase() === A)
6524
6524
  return k;
6525
6525
  for (const k of c) {
6526
- const C = k.toLowerCase();
6527
- if ((A.includes("left") && C.includes("left") || A.includes("right") && C.includes("right")) && (A.includes("arm") && C.includes("arm") && !C.includes("fore") || A.includes("forearm") && C.includes("forearm") || A.includes("hand") && C.includes("hand") && !C.includes("index") && !C.includes("thumb") || A.includes("shoulder") && C.includes("shoulder")))
6526
+ const E = k.toLowerCase();
6527
+ if ((A.includes("left") && E.includes("left") || A.includes("right") && E.includes("right")) && (A.includes("arm") && E.includes("arm") && !E.includes("fore") || A.includes("forearm") && E.includes("forearm") || A.includes("hand") && E.includes("hand") && !E.includes("index") && !E.includes("thumb") || A.includes("shoulder") && E.includes("shoulder")))
6528
6528
  return k;
6529
6529
  }
6530
6530
  return null;
@@ -6535,33 +6535,19 @@ class Be {
6535
6535
  }), console.log("=== Ready Player Me Animation Bone Analysis ==="), console.log("FBX bone names:", Array.from(x).sort().join(", ")), console.log("Avatar skeleton bone names:", Array.from(c).sort().join(", "));
6536
6536
  const S = Array.from(x).filter(
6537
6537
  (I) => I.toLowerCase().includes("arm") || I.toLowerCase().includes("hand") || I.toLowerCase().includes("shoulder")
6538
- ), G = Array.from(c).filter(
6538
+ ), U = Array.from(c).filter(
6539
6539
  (I) => I.includes("Arm") || I.includes("Hand") || I.includes("Shoulder")
6540
6540
  );
6541
- console.log("FBX arm/hand/shoulder bones:", S.sort().join(", ")), console.log("Avatar arm/hand/shoulder bones:", G.sort().join(", "));
6542
- const p = [], B = /* @__PURE__ */ new Set();
6541
+ console.log("FBX arm/hand/shoulder bones:", S.sort().join(", ")), console.log("Avatar arm/hand/shoulder bones:", U.sort().join(", "));
6542
+ const p = [], F = /* @__PURE__ */ new Set();
6543
6543
  if (d.tracks.forEach((I) => {
6544
- const A = I.name.replaceAll("mixamorig", "").split("."), Y = A[0], k = A[1], C = b(Y);
6545
- if (C && k) {
6546
- const q = `${C}.${k}`, N = I.clone();
6547
- N.name = q;
6548
- const $ = C.includes("Arm") || C.includes("Hand") || C.includes("Shoulder"), ie = C.includes("Left");
6549
- C.includes("Right");
6550
- const oe = C.includes("ForeArm") || C.includes("Forearm"), he = C.includes("Hand") && !C.includes("Index") && !C.includes("Thumb") && !C.includes("Middle") && !C.includes("Ring") && !C.includes("Pinky");
6551
- if ($ && (k === "quaternion" || k === "rotation") && k === "quaternion" && N.values && N.values.length >= 4) {
6552
- const ee = N.times.length;
6553
- for (let ne = 0; ne < ee; ne++) {
6554
- const D = ne * 4;
6555
- if (D + 3 < N.values.length) {
6556
- let v = N.values[D], R = N.values[D + 1], T = N.values[D + 2], F = N.values[D + 3], P = new f.Quaternion(v, R, T, F);
6557
- ie && (he ? (P.conjugate(), P = new f.Quaternion().setFromAxisAngle(new f.Vector3(0, 1, 0), Math.PI).multiply(P)) : oe && (P = new f.Quaternion().setFromAxisAngle(new f.Vector3(0, 1, 0), Math.PI).multiply(P), P = new f.Quaternion().setFromAxisAngle(new f.Vector3(1, 0, 0), Math.PI / 2).multiply(P))), N.values[D] = P.x, N.values[D + 1] = P.y, N.values[D + 2] = P.z, N.values[D + 3] = P.w;
6558
- }
6559
- }
6560
- }
6561
- p.push(N), Y !== C && g.set(Y, C);
6544
+ const A = I.name.replaceAll("mixamorig", "").split("."), Y = A[0], k = A[1], E = b(Y);
6545
+ if (E && k) {
6546
+ const q = `${E}.${k}`, G = I.clone();
6547
+ G.name = q, p.push(G), Y !== E && g.set(Y, E);
6562
6548
  } else
6563
- B.add(Y), (Y.toLowerCase().includes("arm") || Y.toLowerCase().includes("hand") || Y.toLowerCase().includes("shoulder")) && console.warn(`⚠️ Arm bone "${Y}" could not be mapped to avatar skeleton`);
6564
- }), B.size > 0 && console.warn(`⚠️ ${B.size} bone(s) could not be mapped:`, Array.from(B).sort().join(", ")), p.length > 0) {
6549
+ F.add(Y), (Y.toLowerCase().includes("arm") || Y.toLowerCase().includes("hand") || Y.toLowerCase().includes("shoulder")) && console.warn(`⚠️ Arm bone "${Y}" could not be mapped to avatar skeleton`);
6550
+ }), F.size > 0 && console.warn(`⚠️ ${F.size} bone(s) could not be mapped:`, Array.from(F).sort().join(", ")), p.length > 0) {
6565
6551
  d = new f.AnimationClip(d.name, d.duration, p), console.log(`✓ Created animation with ${p.length} mapped tracks (from ${d.tracks.length} original tracks)`), g.size > 0 && console.log(
6566
6552
  `✓ Mapped ${g.size} bone(s):`,
6567
6553
  Array.from(g.entries()).map(([z, A]) => `${z}→${A}`).join(", ")
@@ -6572,18 +6558,18 @@ class Be {
6572
6558
  I.length > 0 ? console.log(`✓ Arm bones mapped: ${I.join(", ")}`) : console.warn("⚠️ No arm bones were mapped! This may cause arm rigging issues.");
6573
6559
  } else
6574
6560
  console.error("❌ No tracks could be mapped! Animation may not work correctly.");
6575
- const H = {};
6561
+ const C = {};
6576
6562
  d.tracks.forEach((I) => {
6577
6563
  I.name = I.name.replaceAll("mixamorig", "");
6578
6564
  const z = I.name.split(".");
6579
6565
  if (z[1] === "position") {
6580
6566
  for (let A = 0; A < I.values.length; A++)
6581
6567
  I.values[A] = I.values[A] * s;
6582
- H[I.name] = new f.Vector3(I.values[0], I.values[1], I.values[2]);
6583
- } else z[1] === "quaternion" ? H[I.name] = new f.Quaternion(I.values[0], I.values[1], I.values[2], I.values[3]) : z[1] === "rotation" && (H[z[0] + ".quaternion"] = new f.Quaternion().setFromEuler(new f.Euler(I.values[0], I.values[1], I.values[2], "XYZ")).normalize());
6568
+ C[I.name] = new f.Vector3(I.values[0], I.values[1], I.values[2]);
6569
+ } else z[1] === "quaternion" ? C[I.name] = new f.Quaternion(I.values[0], I.values[1], I.values[2], I.values[3]) : z[1] === "rotation" && (C[z[0] + ".quaternion"] = new f.Quaternion().setFromEuler(new f.Euler(I.values[0], I.values[1], I.values[2], "XYZ")).normalize());
6584
6570
  });
6585
- const y = { props: H };
6586
- H["Hips.position"] && (H["Hips.position"].y < 0.5 ? y.lying = !0 : y.standing = !0), this.animClips.push({
6571
+ const y = { props: C };
6572
+ C["Hips.position"] && (C["Hips.position"].y < 0.5 ? y.lying = !0 : y.standing = !0), this.animClips.push({
6587
6573
  url: t + "-" + i,
6588
6574
  clip: d,
6589
6575
  pose: y
@@ -6721,12 +6707,12 @@ class Be {
6721
6707
  const x = t.iterations || 10;
6722
6708
  if (e)
6723
6709
  for (let S = 0; S < x; S++) {
6724
- let G = !1;
6725
- for (let p = 0, B = b.length; p < B; p++) {
6726
- const H = b[p].bone;
6727
- H.matrixWorld.decompose(h, r, u), r.invert(), o.setFromMatrixPosition(g.matrixWorld), l.subVectors(o, h), l.applyQuaternion(r), l.normalize(), s.subVectors(e, h), s.applyQuaternion(r), s.normalize();
6710
+ let U = !1;
6711
+ for (let p = 0, F = b.length; p < F; p++) {
6712
+ const C = b[p].bone;
6713
+ C.matrixWorld.decompose(h, r, u), r.invert(), o.setFromMatrixPosition(g.matrixWorld), l.subVectors(o, h), l.applyQuaternion(r), l.normalize(), s.subVectors(e, h), s.applyQuaternion(r), s.normalize();
6728
6714
  let y = s.dot(l);
6729
- y > 1 ? y = 1 : y < -1 && (y = -1), y = Math.acos(y), !(y < 1e-5) && (b[p].minAngle !== void 0 && y < b[p].minAngle && (y = b[p].minAngle), b[p].maxAngle !== void 0 && y > b[p].maxAngle && (y = b[p].maxAngle), a.crossVectors(l, s), a.normalize(), K.setFromAxisAngle(a, y), H.quaternion.multiply(K), H.rotation.setFromVector3(d.setFromEuler(H.rotation).clamp(new f.Vector3(
6715
+ y > 1 ? y = 1 : y < -1 && (y = -1), y = Math.acos(y), !(y < 1e-5) && (b[p].minAngle !== void 0 && y < b[p].minAngle && (y = b[p].minAngle), b[p].maxAngle !== void 0 && y > b[p].maxAngle && (y = b[p].maxAngle), a.crossVectors(l, s), a.normalize(), _.setFromAxisAngle(a, y), C.quaternion.multiply(_), C.rotation.setFromVector3(d.setFromEuler(C.rotation).clamp(new f.Vector3(
6730
6716
  b[p].minx !== void 0 ? b[p].minx : -1 / 0,
6731
6717
  b[p].miny !== void 0 ? b[p].miny : -1 / 0,
6732
6718
  b[p].minz !== void 0 ? b[p].minz : -1 / 0
@@ -6734,9 +6720,9 @@ class Be {
6734
6720
  b[p].maxx !== void 0 ? b[p].maxx : 1 / 0,
6735
6721
  b[p].maxy !== void 0 ? b[p].maxy : 1 / 0,
6736
6722
  b[p].maxz !== void 0 ? b[p].maxz : 1 / 0
6737
- ))), H.updateMatrixWorld(!0), G = !0);
6723
+ ))), C.updateMatrixWorld(!0), U = !0);
6738
6724
  }
6739
- if (!G) break;
6725
+ if (!U) break;
6740
6726
  }
6741
6727
  i && b.forEach((S) => {
6742
6728
  this.poseTarget.props[S.link + ".quaternion"].copy(S.bone.quaternion), this.poseTarget.props[S.link + ".quaternion"].t = this.animClock, this.poseTarget.props[S.link + ".quaternion"].d = i;
@@ -6829,214 +6815,214 @@ const Ve = Me(({
6829
6815
  style: b = {},
6830
6816
  animations: x = {}
6831
6817
  }, S) => {
6832
- const G = V(null), p = V(null), B = V(r), H = V(null), y = V(null), I = V(!1), z = V({ remainingText: null, originalText: null, options: null }), A = V([]), Y = V(0), [k, C] = de(!0), [q, N] = de(null), [$, ie] = de(!1), [oe, he] = de(!1);
6833
- me(() => {
6834
- I.current = oe;
6835
- }, [oe]), me(() => {
6836
- B.current = r;
6818
+ const U = O(null), p = O(null), F = O(r), C = O(null), y = O(null), I = O(!1), z = O({ remainingText: null, originalText: null, options: null }), A = O([]), Y = O(0), [k, E] = ce(!0), [q, G] = ce(null), [ee, se] = ce(!1), [ae, pe] = ce(!1);
6819
+ de(() => {
6820
+ I.current = ae;
6821
+ }, [ae]), de(() => {
6822
+ F.current = r;
6837
6823
  }, [r]);
6838
- const ee = Ee(), ne = i || ee.service;
6839
- let D;
6840
- ne === "browser" ? D = {
6824
+ const te = Ee(), le = i || te.service;
6825
+ let W;
6826
+ le === "browser" ? W = {
6841
6827
  service: "browser",
6842
6828
  endpoint: "",
6843
6829
  apiKey: null,
6844
6830
  defaultVoice: "Google US English"
6845
- } : ne === "elevenlabs" ? D = {
6831
+ } : le === "elevenlabs" ? W = {
6846
6832
  service: "elevenlabs",
6847
6833
  endpoint: "https://api.elevenlabs.io/v1/text-to-speech",
6848
- apiKey: o || ee.apiKey,
6849
- defaultVoice: s || ee.defaultVoice || Ie.defaultVoice,
6850
- voices: ee.voices || Ie.voices
6851
- } : ne === "deepgram" ? D = {
6834
+ apiKey: o || te.apiKey,
6835
+ defaultVoice: s || te.defaultVoice || Ie.defaultVoice,
6836
+ voices: te.voices || Ie.voices
6837
+ } : le === "deepgram" ? W = {
6852
6838
  service: "deepgram",
6853
6839
  endpoint: "https://api.deepgram.com/v1/speak",
6854
- apiKey: o || ee.apiKey,
6855
- defaultVoice: s || ee.defaultVoice || Te.defaultVoice,
6856
- voices: ee.voices || Te.voices
6857
- } : D = {
6858
- ...ee,
6840
+ apiKey: o || te.apiKey,
6841
+ defaultVoice: s || te.defaultVoice || Te.defaultVoice,
6842
+ voices: te.voices || Te.voices
6843
+ } : W = {
6844
+ ...te,
6859
6845
  // Override API key if provided via props
6860
- apiKey: o !== null ? o : ee.apiKey
6846
+ apiKey: o !== null ? o : te.apiKey
6861
6847
  };
6862
6848
  const v = {
6863
6849
  url: X,
6864
6850
  body: t,
6865
6851
  avatarMood: e,
6866
- ttsLang: ne === "browser" ? "en-US" : n,
6867
- ttsVoice: s || D.defaultVoice,
6852
+ ttsLang: le === "browser" ? "en-US" : n,
6853
+ ttsVoice: s || W.defaultVoice,
6868
6854
  lipsyncLang: "en",
6869
6855
  showFullAvatar: r,
6870
6856
  bodyMovement: l,
6871
6857
  movementIntensity: h
6872
6858
  }, R = {
6873
- ttsEndpoint: D.endpoint,
6874
- ttsApikey: D.apiKey,
6875
- ttsService: ne,
6859
+ ttsEndpoint: W.endpoint,
6860
+ ttsApikey: W.apiKey,
6861
+ ttsService: le,
6876
6862
  lipsyncModules: ["en"],
6877
6863
  cameraView: u
6878
- }, T = O(async () => {
6879
- if (!(!G.current || p.current))
6864
+ }, H = B(async () => {
6865
+ if (!(!U.current || p.current))
6880
6866
  try {
6881
- if (C(!0), N(null), p.current = new Be(G.current, R), p.current.controls && (p.current.controls.enableRotate = !1, p.current.controls.enableZoom = !1, p.current.controls.enablePan = !1, p.current.controls.enableDamping = !1), x && Object.keys(x).length > 0 && (p.current.customAnimations = x), await p.current.showAvatar(v, (W) => {
6882
- if (W.lengthComputable) {
6883
- const te = Math.min(100, Math.round(W.loaded / W.total * 100));
6884
- d(te);
6867
+ if (E(!0), G(null), p.current = new Be(U.current, R), p.current.controls && (p.current.controls.enableRotate = !1, p.current.controls.enableZoom = !1, p.current.controls.enablePan = !1, p.current.controls.enableDamping = !1), x && Object.keys(x).length > 0 && (p.current.customAnimations = x), await p.current.showAvatar(v, (D) => {
6868
+ if (D.lengthComputable) {
6869
+ const $ = Math.min(100, Math.round(D.loaded / D.total * 100));
6870
+ d($);
6885
6871
  }
6886
- }), await new Promise((W) => {
6887
- const te = () => {
6888
- p.current.lipsync && Object.keys(p.current.lipsync).length > 0 ? W() : setTimeout(te, 100);
6872
+ }), await new Promise((D) => {
6873
+ const $ = () => {
6874
+ p.current.lipsync && Object.keys(p.current.lipsync).length > 0 ? D() : setTimeout($, 100);
6889
6875
  };
6890
- te();
6876
+ $();
6891
6877
  }), p.current && p.current.setShowFullAvatar)
6892
6878
  try {
6893
6879
  p.current.setShowFullAvatar(r);
6894
- } catch (W) {
6895
- console.warn("Error setting full body mode on initialization:", W);
6880
+ } catch (D) {
6881
+ console.warn("Error setting full body mode on initialization:", D);
6896
6882
  }
6897
- p.current && p.current.controls && (p.current.controls.enableRotate = !1, p.current.controls.enableZoom = !1, p.current.controls.enablePan = !1, p.current.controls.enableDamping = !1, p.current.controls.update()), C(!1), ie(!0), a(p.current);
6898
- const U = () => {
6883
+ p.current && p.current.controls && (p.current.controls.enableRotate = !1, p.current.controls.enableZoom = !1, p.current.controls.enablePan = !1, p.current.controls.enableDamping = !1, p.current.controls.update()), E(!1), se(!0), a(p.current);
6884
+ const N = () => {
6899
6885
  document.visibilityState === "visible" ? p.current?.start() : p.current?.stop();
6900
6886
  };
6901
- return document.addEventListener("visibilitychange", U), () => {
6902
- document.removeEventListener("visibilitychange", U);
6887
+ return document.addEventListener("visibilitychange", N), () => {
6888
+ document.removeEventListener("visibilitychange", N);
6903
6889
  };
6904
6890
  } catch (L) {
6905
- console.error("Error initializing TalkingHead:", L), N(L.message || "Failed to initialize avatar"), C(!1), c(L);
6891
+ console.error("Error initializing TalkingHead:", L), G(L.message || "Failed to initialize avatar"), E(!1), c(L);
6906
6892
  }
6907
6893
  }, [X, t, e, n, i, s, o, r, l, h, u]);
6908
- me(() => (T(), () => {
6894
+ de(() => (H(), () => {
6909
6895
  p.current && (p.current.stop(), p.current.dispose(), p.current = null);
6910
- }), [T]), me(() => {
6911
- if (!G.current || !p.current) return;
6912
- const L = new ResizeObserver((W) => {
6913
- for (const te of W)
6896
+ }), [H]), de(() => {
6897
+ if (!U.current || !p.current) return;
6898
+ const L = new ResizeObserver((D) => {
6899
+ for (const $ of D)
6914
6900
  p.current && p.current.onResize && p.current.onResize();
6915
6901
  });
6916
- L.observe(G.current);
6917
- const U = () => {
6902
+ L.observe(U.current);
6903
+ const N = () => {
6918
6904
  p.current && p.current.onResize && p.current.onResize();
6919
6905
  };
6920
- return window.addEventListener("resize", U), () => {
6921
- L.disconnect(), window.removeEventListener("resize", U);
6906
+ return window.addEventListener("resize", N), () => {
6907
+ L.disconnect(), window.removeEventListener("resize", N);
6922
6908
  };
6923
- }, [$]);
6924
- const F = O(async () => {
6909
+ }, [ee]);
6910
+ const P = B(async () => {
6925
6911
  if (p.current && p.current.audioCtx)
6926
6912
  try {
6927
6913
  (p.current.audioCtx.state === "suspended" || p.current.audioCtx.state === "interrupted") && (await p.current.audioCtx.resume(), console.log("Audio context resumed"));
6928
6914
  } catch (L) {
6929
6915
  console.warn("Failed to resume audio context:", L);
6930
6916
  }
6931
- }, []), P = O(async (L, U = {}) => {
6932
- if (p.current && $)
6917
+ }, []), V = B(async (L, N = {}) => {
6918
+ if (p.current && ee)
6933
6919
  try {
6934
- y.current && (clearInterval(y.current), y.current = null), H.current = { text: L, options: U }, z.current = { remainingText: null, originalText: null, options: null };
6935
- const W = /[!\.\?\n\p{Extended_Pictographic}]/ug, te = L.split(W).map((Q) => Q.trim()).filter((Q) => Q.length > 0);
6936
- A.current = te, Y.current = 0, he(!1), I.current = !1, await F();
6920
+ y.current && (clearInterval(y.current), y.current = null), C.current = { text: L, options: N }, z.current = { remainingText: null, originalText: null, options: null };
6921
+ const D = /[!\.\?\n\p{Extended_Pictographic}]/ug, $ = L.split(D).map((j) => j.trim()).filter((j) => j.length > 0);
6922
+ A.current = $, Y.current = 0, pe(!1), I.current = !1, await P();
6937
6923
  const ge = {
6938
- ...U,
6939
- lipsyncLang: U.lipsyncLang || v.lipsyncLang || "en"
6924
+ ...N,
6925
+ lipsyncLang: N.lipsyncLang || v.lipsyncLang || "en"
6940
6926
  };
6941
- if (U.onSpeechEnd && p.current) {
6942
- const Q = p.current;
6943
- let ce = null, Se = 0;
6927
+ if (N.onSpeechEnd && p.current) {
6928
+ const j = p.current;
6929
+ let he = null, Se = 0;
6944
6930
  const Le = 1200;
6945
6931
  let be = !1;
6946
- ce = setInterval(() => {
6932
+ he = setInterval(() => {
6947
6933
  if (Se++, I.current)
6948
6934
  return;
6949
6935
  if (Se > Le) {
6950
- if (ce && (clearInterval(ce), ce = null, y.current = null), !be && !I.current) {
6936
+ if (he && (clearInterval(he), he = null, y.current = null), !be && !I.current) {
6951
6937
  be = !0;
6952
6938
  try {
6953
- U.onSpeechEnd();
6939
+ N.onSpeechEnd();
6954
6940
  } catch (Ne) {
6955
6941
  console.error("Error in onSpeechEnd callback (timeout):", Ne);
6956
6942
  }
6957
6943
  }
6958
6944
  return;
6959
6945
  }
6960
- const ye = !Q.speechQueue || Q.speechQueue.length === 0, ke = !Q.audioPlaylist || Q.audioPlaylist.length === 0;
6961
- Q && Q.isSpeaking === !1 && ye && ke && Q.isAudioPlaying === !1 && !be && !I.current && setTimeout(() => {
6962
- if (Q && !I.current && Q.isSpeaking === !1 && (!Q.speechQueue || Q.speechQueue.length === 0) && (!Q.audioPlaylist || Q.audioPlaylist.length === 0) && Q.isAudioPlaying === !1 && !be && !I.current) {
6963
- be = !0, ce && (clearInterval(ce), ce = null, y.current = null);
6946
+ const ye = !j.speechQueue || j.speechQueue.length === 0, ke = !j.audioPlaylist || j.audioPlaylist.length === 0;
6947
+ j && j.isSpeaking === !1 && ye && ke && j.isAudioPlaying === !1 && !be && !I.current && setTimeout(() => {
6948
+ if (j && !I.current && j.isSpeaking === !1 && (!j.speechQueue || j.speechQueue.length === 0) && (!j.audioPlaylist || j.audioPlaylist.length === 0) && j.isAudioPlaying === !1 && !be && !I.current) {
6949
+ be = !0, he && (clearInterval(he), he = null, y.current = null);
6964
6950
  try {
6965
- U.onSpeechEnd();
6951
+ N.onSpeechEnd();
6966
6952
  } catch (Ze) {
6967
6953
  console.error("Error in onSpeechEnd callback:", Ze);
6968
6954
  }
6969
6955
  }
6970
6956
  }, 100);
6971
- }, 100), y.current = ce;
6957
+ }, 100), y.current = he;
6972
6958
  }
6973
6959
  p.current.lipsync && Object.keys(p.current.lipsync).length > 0 ? (p.current.setSlowdownRate && p.current.setSlowdownRate(1.05), p.current.speakText(L, ge)) : setTimeout(async () => {
6974
- await F(), p.current && p.current.lipsync && (p.current.setSlowdownRate && p.current.setSlowdownRate(1.05), p.current.speakText(L, ge));
6960
+ await P(), p.current && p.current.lipsync && (p.current.setSlowdownRate && p.current.setSlowdownRate(1.05), p.current.speakText(L, ge));
6975
6961
  }, 100);
6976
- } catch (W) {
6977
- console.error("Error speaking text:", W), N(W.message || "Failed to speak text");
6962
+ } catch (D) {
6963
+ console.error("Error speaking text:", D), G(D.message || "Failed to speak text");
6978
6964
  }
6979
- }, [$, F, v.lipsyncLang]), _ = O(() => {
6980
- p.current && (p.current.stopSpeaking(), p.current.setSlowdownRate && p.current.setSlowdownRate(1), H.current = null, he(!1));
6981
- }, []), j = O(() => {
6965
+ }, [ee, P, v.lipsyncLang]), J = B(() => {
6966
+ p.current && (p.current.stopSpeaking(), p.current.setSlowdownRate && p.current.setSlowdownRate(1), C.current = null, pe(!1));
6967
+ }, []), Q = B(() => {
6982
6968
  if (p.current && p.current.pauseSpeaking) {
6983
6969
  const L = p.current;
6984
6970
  if (L.isSpeaking || L.audioPlaylist && L.audioPlaylist.length > 0 || L.speechQueue && L.speechQueue.length > 0) {
6985
6971
  y.current && (clearInterval(y.current), y.current = null);
6986
- let W = "";
6987
- if (H.current && A.current.length > 0) {
6988
- const te = A.current.length, ge = L.speechQueue ? L.speechQueue.filter((Le) => Le && Le.text && Array.isArray(Le.text) && Le.text.length > 0).length : 0, Q = L.audioPlaylist && L.audioPlaylist.length > 0, ce = ge + (Q ? 1 : 0), Se = te - ce;
6989
- if (ce > 0 && Se < te && (W = A.current.slice(Se).join(". ").trim(), !W && ge > 0 && L.speechQueue)) {
6972
+ let D = "";
6973
+ if (C.current && A.current.length > 0) {
6974
+ const $ = A.current.length, ge = L.speechQueue ? L.speechQueue.filter((Le) => Le && Le.text && Array.isArray(Le.text) && Le.text.length > 0).length : 0, j = L.audioPlaylist && L.audioPlaylist.length > 0, he = ge + (j ? 1 : 0), Se = $ - he;
6975
+ if (he > 0 && Se < $ && (D = A.current.slice(Se).join(". ").trim(), !D && ge > 0 && L.speechQueue)) {
6990
6976
  const be = L.speechQueue.filter((ye) => ye && ye.text && Array.isArray(ye.text) && ye.text.length > 0).map((ye) => ye.text.map((ke) => ke.word || "").filter((ke) => ke.length > 0).join(" ")).filter((ye) => ye.length > 0).join(" ");
6991
- be && be.trim() && (W = be.trim());
6977
+ be && be.trim() && (D = be.trim());
6992
6978
  }
6993
6979
  }
6994
- H.current && (z.current = {
6995
- remainingText: W || null,
6996
- originalText: H.current.text,
6997
- options: H.current.options
6998
- }), L.speechQueue && (L.speechQueue.length = 0), p.current.pauseSpeaking(), I.current = !0, he(!0);
6980
+ C.current && (z.current = {
6981
+ remainingText: D || null,
6982
+ originalText: C.current.text,
6983
+ options: C.current.options
6984
+ }), L.speechQueue && (L.speechQueue.length = 0), p.current.pauseSpeaking(), I.current = !0, pe(!0);
6999
6985
  }
7000
6986
  }
7001
- }, []), J = O(async () => {
7002
- if (!p.current || !oe)
6987
+ }, []), K = B(async () => {
6988
+ if (!p.current || !ae)
7003
6989
  return;
7004
- let L = "", U = {};
6990
+ let L = "", N = {};
7005
6991
  if (z.current && z.current.remainingText)
7006
- L = z.current.remainingText, U = z.current.options || {}, z.current = { remainingText: null, originalText: null, options: null };
7007
- else if (H.current && H.current.text)
7008
- L = H.current.text, U = H.current.options || {};
6992
+ L = z.current.remainingText, N = z.current.options || {}, z.current = { remainingText: null, originalText: null, options: null };
6993
+ else if (C.current && C.current.text)
6994
+ L = C.current.text, N = C.current.options || {};
7009
6995
  else {
7010
- console.warn("Resume called but no paused speech found"), he(!1), I.current = !1;
6996
+ console.warn("Resume called but no paused speech found"), pe(!1), I.current = !1;
7011
6997
  return;
7012
6998
  }
7013
- he(!1), I.current = !1, await F();
7014
- const W = {
7015
- ...U,
7016
- lipsyncLang: U.lipsyncLang || v.lipsyncLang || "en"
6999
+ pe(!1), I.current = !1, await P();
7000
+ const D = {
7001
+ ...N,
7002
+ lipsyncLang: N.lipsyncLang || v.lipsyncLang || "en"
7017
7003
  };
7018
7004
  try {
7019
- await P(L, W);
7020
- } catch (te) {
7021
- console.error("Error resuming speech:", te), he(!1), I.current = !1;
7005
+ await V(L, D);
7006
+ } catch ($) {
7007
+ console.error("Error resuming speech:", $), pe(!1), I.current = !1;
7022
7008
  }
7023
- }, [F, oe, P, v]), Ae = O((L) => {
7009
+ }, [P, ae, V, v]), Ae = B((L) => {
7024
7010
  p.current && p.current.setMood(L);
7025
- }, []), we = O((L) => {
7011
+ }, []), we = B((L) => {
7026
7012
  p.current && p.current.setSlowdownRate && p.current.setSlowdownRate(L);
7027
- }, []), E = O((L, U = !1) => {
7013
+ }, []), M = B((L, N = !1) => {
7028
7014
  if (p.current && p.current.playAnimation) {
7029
7015
  if (x && x[L] && (L = x[L]), p.current.setShowFullAvatar)
7030
7016
  try {
7031
- p.current.setShowFullAvatar(B.current);
7032
- } catch (te) {
7033
- console.warn("Error setting full body mode:", te);
7017
+ p.current.setShowFullAvatar(F.current);
7018
+ } catch ($) {
7019
+ console.warn("Error setting full body mode:", $);
7034
7020
  }
7035
7021
  if (L.includes("."))
7036
7022
  try {
7037
- p.current.playAnimation(L, null, 10, 0, 0.01, U);
7038
- } catch (te) {
7039
- console.warn(`Failed to play ${L}:`, te);
7023
+ p.current.playAnimation(L, null, 10, 0, 0.01, N);
7024
+ } catch ($) {
7025
+ console.warn(`Failed to play ${L}:`, $);
7040
7026
  try {
7041
7027
  p.current.setBodyMovement("idle");
7042
7028
  } catch (ge) {
@@ -7044,11 +7030,11 @@ const Ve = Me(({
7044
7030
  }
7045
7031
  }
7046
7032
  else {
7047
- const te = [".fbx", ".glb", ".gltf"];
7033
+ const $ = [".fbx", ".glb", ".gltf"];
7048
7034
  let ge = !1;
7049
- for (const Q of te)
7035
+ for (const j of $)
7050
7036
  try {
7051
- p.current.playAnimation(L + Q, null, 10, 0, 0.01, U), ge = !0;
7037
+ p.current.playAnimation(L + j, null, 10, 0, 0.01, N), ge = !0;
7052
7038
  break;
7053
7039
  } catch {
7054
7040
  }
@@ -7056,41 +7042,41 @@ const Ve = Me(({
7056
7042
  console.warn("Animation not found:", L);
7057
7043
  try {
7058
7044
  p.current.setBodyMovement("idle");
7059
- } catch (Q) {
7060
- console.warn("Fallback animation also failed:", Q);
7045
+ } catch (j) {
7046
+ console.warn("Fallback animation also failed:", j);
7061
7047
  }
7062
7048
  }
7063
7049
  }
7064
7050
  }
7065
- }, [x]), se = O(() => {
7051
+ }, [x]), ne = B(() => {
7066
7052
  p.current && p.current.onResize && p.current.onResize();
7067
7053
  }, []);
7068
7054
  return Fe(S, () => ({
7069
- speakText: P,
7070
- stopSpeaking: _,
7071
- pauseSpeaking: j,
7072
- resumeSpeaking: J,
7073
- resumeAudioContext: F,
7055
+ speakText: V,
7056
+ stopSpeaking: J,
7057
+ pauseSpeaking: Q,
7058
+ resumeSpeaking: K,
7059
+ resumeAudioContext: P,
7074
7060
  setMood: Ae,
7075
7061
  setTimingAdjustment: we,
7076
- playAnimation: E,
7077
- isReady: $,
7078
- isPaused: oe,
7062
+ playAnimation: M,
7063
+ isReady: ee,
7064
+ isPaused: ae,
7079
7065
  talkingHead: p.current,
7080
- handleResize: se,
7066
+ handleResize: ne,
7081
7067
  setBodyMovement: (L) => {
7082
7068
  if (p.current && p.current.setShowFullAvatar && p.current.setBodyMovement)
7083
7069
  try {
7084
- p.current.setShowFullAvatar(B.current), p.current.setBodyMovement(L);
7085
- } catch (U) {
7086
- console.warn("Error setting body movement:", U);
7070
+ p.current.setShowFullAvatar(F.current), p.current.setBodyMovement(L);
7071
+ } catch (N) {
7072
+ console.warn("Error setting body movement:", N);
7087
7073
  }
7088
7074
  },
7089
7075
  setMovementIntensity: (L) => p.current?.setMovementIntensity(L),
7090
7076
  playRandomDance: () => {
7091
7077
  if (p.current && p.current.setShowFullAvatar && p.current.playRandomDance)
7092
7078
  try {
7093
- p.current.setShowFullAvatar(B.current), p.current.playRandomDance();
7079
+ p.current.setShowFullAvatar(F.current), p.current.playRandomDance();
7094
7080
  } catch (L) {
7095
7081
  console.warn("Error playing random dance:", L);
7096
7082
  }
@@ -7098,15 +7084,15 @@ const Ve = Me(({
7098
7084
  playReaction: (L) => {
7099
7085
  if (p.current && p.current.setShowFullAvatar && p.current.playReaction)
7100
7086
  try {
7101
- p.current.setShowFullAvatar(B.current), p.current.playReaction(L);
7102
- } catch (U) {
7103
- console.warn("Error playing reaction:", U);
7087
+ p.current.setShowFullAvatar(F.current), p.current.playReaction(L);
7088
+ } catch (N) {
7089
+ console.warn("Error playing reaction:", N);
7104
7090
  }
7105
7091
  },
7106
7092
  playCelebration: () => {
7107
7093
  if (p.current && p.current.setShowFullAvatar && p.current.playCelebration)
7108
7094
  try {
7109
- p.current.setShowFullAvatar(B.current), p.current.playCelebration();
7095
+ p.current.setShowFullAvatar(F.current), p.current.playCelebration();
7110
7096
  } catch (L) {
7111
7097
  console.warn("Error playing celebration:", L);
7112
7098
  }
@@ -7114,9 +7100,9 @@ const Ve = Me(({
7114
7100
  setShowFullAvatar: (L) => {
7115
7101
  if (p.current && p.current.setShowFullAvatar)
7116
7102
  try {
7117
- B.current = L, p.current.setShowFullAvatar(L);
7118
- } catch (U) {
7119
- console.warn("Error setting showFullAvatar:", U);
7103
+ F.current = L, p.current.setShowFullAvatar(L);
7104
+ } catch (N) {
7105
+ console.warn("Error setting showFullAvatar:", N);
7120
7106
  }
7121
7107
  },
7122
7108
  lockAvatarPosition: () => {
@@ -7146,10 +7132,10 @@ const Ve = Me(({
7146
7132
  ...b
7147
7133
  },
7148
7134
  children: [
7149
- /* @__PURE__ */ pe(
7135
+ /* @__PURE__ */ me(
7150
7136
  "div",
7151
7137
  {
7152
- ref: G,
7138
+ ref: U,
7153
7139
  className: "talking-head-viewer",
7154
7140
  style: {
7155
7141
  width: "100%",
@@ -7158,7 +7144,7 @@ const Ve = Me(({
7158
7144
  }
7159
7145
  }
7160
7146
  ),
7161
- k && /* @__PURE__ */ pe("div", { className: "loading-overlay", style: {
7147
+ k && /* @__PURE__ */ me("div", { className: "loading-overlay", style: {
7162
7148
  position: "absolute",
7163
7149
  top: "50%",
7164
7150
  left: "50%",
@@ -7167,7 +7153,7 @@ const Ve = Me(({
7167
7153
  fontSize: "18px",
7168
7154
  zIndex: 10
7169
7155
  }, children: "Loading avatar..." }),
7170
- q && /* @__PURE__ */ pe("div", { className: "error-overlay", style: {
7156
+ q && /* @__PURE__ */ me("div", { className: "error-overlay", style: {
7171
7157
  position: "absolute",
7172
7158
  top: "50%",
7173
7159
  left: "50%",
@@ -7196,7 +7182,7 @@ const pt = Me(({
7196
7182
  style: s = {},
7197
7183
  avatarConfig: o = {}
7198
7184
  }, l) => {
7199
- const h = V(null), r = V(null), [u, a] = de(!0), [d, c] = de(null), [g, b] = de(!1), x = Ee(), S = o.ttsService || x.service, G = S === "browser" ? {
7185
+ const h = O(null), r = O(null), [u, a] = ce(!0), [d, c] = ce(null), [g, b] = ce(!1), x = Ee(), S = o.ttsService || x.service, U = S === "browser" ? {
7200
7186
  endpoint: "",
7201
7187
  apiKey: null,
7202
7188
  defaultVoice: "Google US English"
@@ -7212,7 +7198,7 @@ const pt = Me(({
7212
7198
  body: "F",
7213
7199
  avatarMood: "neutral",
7214
7200
  ttsLang: S === "browser" ? "en-US" : "en",
7215
- ttsVoice: o.ttsVoice || G.defaultVoice,
7201
+ ttsVoice: o.ttsVoice || U.defaultVoice,
7216
7202
  lipsyncLang: "en",
7217
7203
  // English lip-sync
7218
7204
  showFullAvatar: !0,
@@ -7220,31 +7206,31 @@ const pt = Me(({
7220
7206
  bodyMovement: "idle",
7221
7207
  movementIntensity: 0.5,
7222
7208
  ...o
7223
- }, B = {
7224
- ttsEndpoint: G.endpoint,
7225
- ttsApikey: G.apiKey,
7209
+ }, F = {
7210
+ ttsEndpoint: U.endpoint,
7211
+ ttsApikey: U.apiKey,
7226
7212
  ttsService: S,
7227
7213
  lipsyncModules: ["en"],
7228
7214
  cameraView: "upper"
7229
- }, H = O(async () => {
7215
+ }, C = B(async () => {
7230
7216
  if (!(!h.current || r.current))
7231
7217
  try {
7232
- if (a(!0), c(null), r.current = new Be(h.current, B), await r.current.showAvatar(p, (q) => {
7218
+ if (a(!0), c(null), r.current = new Be(h.current, F), await r.current.showAvatar(p, (q) => {
7233
7219
  if (q.lengthComputable) {
7234
- const N = Math.min(100, Math.round(q.loaded / q.total * 100));
7235
- t(N);
7220
+ const G = Math.min(100, Math.round(q.loaded / q.total * 100));
7221
+ t(G);
7236
7222
  }
7237
7223
  }), r.current.morphs && r.current.morphs.length > 0) {
7238
7224
  const q = r.current.morphs[0].morphTargetDictionary;
7239
7225
  console.log("Available morph targets:", Object.keys(q));
7240
- const N = Object.keys(q).filter(($) => $.startsWith("viseme_"));
7241
- console.log("Viseme morph targets found:", N), N.length === 0 && (console.warn("No viseme morph targets found! Lip-sync will not work properly."), console.log("Expected viseme targets: viseme_aa, viseme_E, viseme_I, viseme_O, viseme_U, viseme_PP, viseme_SS, viseme_TH, viseme_DD, viseme_FF, viseme_kk, viseme_nn, viseme_RR, viseme_CH, viseme_sil"));
7226
+ const G = Object.keys(q).filter((ee) => ee.startsWith("viseme_"));
7227
+ console.log("Viseme morph targets found:", G), G.length === 0 && (console.warn("No viseme morph targets found! Lip-sync will not work properly."), console.log("Expected viseme targets: viseme_aa, viseme_E, viseme_I, viseme_O, viseme_U, viseme_PP, viseme_SS, viseme_TH, viseme_DD, viseme_FF, viseme_kk, viseme_nn, viseme_RR, viseme_CH, viseme_sil"));
7242
7228
  }
7243
7229
  if (await new Promise((q) => {
7244
- const N = () => {
7245
- r.current.lipsync && Object.keys(r.current.lipsync).length > 0 ? (console.log("Lip-sync modules loaded:", Object.keys(r.current.lipsync)), q()) : (console.log("Waiting for lip-sync modules to load..."), setTimeout(N, 100));
7230
+ const G = () => {
7231
+ r.current.lipsync && Object.keys(r.current.lipsync).length > 0 ? (console.log("Lip-sync modules loaded:", Object.keys(r.current.lipsync)), q()) : (console.log("Waiting for lip-sync modules to load..."), setTimeout(G, 100));
7246
7232
  };
7247
- N();
7233
+ G();
7248
7234
  }), r.current && r.current.setShowFullAvatar)
7249
7235
  try {
7250
7236
  r.current.setShowFullAvatar(!0), console.log("Avatar initialized in full body mode");
@@ -7252,71 +7238,71 @@ const pt = Me(({
7252
7238
  console.warn("Error setting full body mode on initialization:", q);
7253
7239
  }
7254
7240
  a(!1), b(!0), n(r.current);
7255
- const C = () => {
7241
+ const E = () => {
7256
7242
  document.visibilityState === "visible" ? r.current?.start() : r.current?.stop();
7257
7243
  };
7258
- return document.addEventListener("visibilitychange", C), () => {
7259
- document.removeEventListener("visibilitychange", C);
7244
+ return document.addEventListener("visibilitychange", E), () => {
7245
+ document.removeEventListener("visibilitychange", E);
7260
7246
  };
7261
7247
  } catch (k) {
7262
7248
  console.error("Error initializing TalkingHead:", k), c(k.message || "Failed to initialize avatar"), a(!1), e(k);
7263
7249
  }
7264
7250
  }, []);
7265
- me(() => (H(), () => {
7251
+ de(() => (C(), () => {
7266
7252
  r.current && (r.current.stop(), r.current.dispose(), r.current = null);
7267
- }), [H]);
7268
- const y = O((k) => {
7253
+ }), [C]);
7254
+ const y = B((k) => {
7269
7255
  if (r.current && g)
7270
7256
  try {
7271
7257
  console.log("Speaking text:", k), console.log("Avatar config:", p), console.log("TalkingHead instance:", r.current), r.current.lipsync && Object.keys(r.current.lipsync).length > 0 ? (console.log("Lip-sync modules loaded:", Object.keys(r.current.lipsync)), r.current.setSlowdownRate && (r.current.setSlowdownRate(1.05), console.log("Applied timing adjustment for better lip-sync")), r.current.speakText(k)) : (console.warn("Lip-sync modules not ready, waiting..."), setTimeout(() => {
7272
7258
  r.current && r.current.lipsync ? (console.log("Lip-sync now ready, speaking..."), r.current.setSlowdownRate && (r.current.setSlowdownRate(1.05), console.log("Applied timing adjustment for better lip-sync")), r.current.speakText(k)) : console.error("Lip-sync still not ready after waiting");
7273
7259
  }, 500));
7274
- } catch (C) {
7275
- console.error("Error speaking text:", C), c(C.message || "Failed to speak text");
7260
+ } catch (E) {
7261
+ console.error("Error speaking text:", E), c(E.message || "Failed to speak text");
7276
7262
  }
7277
7263
  else
7278
7264
  console.warn("Avatar not ready for speaking. isReady:", g, "talkingHeadRef:", !!r.current);
7279
- }, [g, p]), I = O(() => {
7265
+ }, [g, p]), I = B(() => {
7280
7266
  r.current && (r.current.stopSpeaking(), r.current.setSlowdownRate && (r.current.setSlowdownRate(1), console.log("Reset timing to normal")));
7281
- }, []), z = O((k) => {
7267
+ }, []), z = B((k) => {
7282
7268
  r.current && r.current.setMood(k);
7283
- }, []), A = O((k) => {
7269
+ }, []), A = B((k) => {
7284
7270
  r.current && r.current.setSlowdownRate && (r.current.setSlowdownRate(k), console.log("Timing adjustment set to:", k));
7285
- }, []), Y = O((k, C = !1) => {
7271
+ }, []), Y = B((k, E = !1) => {
7286
7272
  if (r.current && r.current.playAnimation) {
7287
7273
  if (r.current.setShowFullAvatar)
7288
7274
  try {
7289
7275
  r.current.setShowFullAvatar(!0);
7290
- } catch (N) {
7291
- console.warn("Error setting full body mode:", N);
7276
+ } catch (G) {
7277
+ console.warn("Error setting full body mode:", G);
7292
7278
  }
7293
7279
  if (k.includes("."))
7294
7280
  try {
7295
- r.current.playAnimation(k, null, 10, 0, 0.01, C), console.log("Playing animation:", k);
7296
- } catch (N) {
7297
- console.log(`Failed to play ${k}:`, N);
7281
+ r.current.playAnimation(k, null, 10, 0, 0.01, E), console.log("Playing animation:", k);
7282
+ } catch (G) {
7283
+ console.log(`Failed to play ${k}:`, G);
7298
7284
  try {
7299
7285
  r.current.setBodyMovement("idle"), console.log("Fallback to idle animation");
7300
- } catch ($) {
7301
- console.warn("Fallback animation also failed:", $);
7286
+ } catch (ee) {
7287
+ console.warn("Fallback animation also failed:", ee);
7302
7288
  }
7303
7289
  }
7304
7290
  else {
7305
- const N = [".fbx", ".glb", ".gltf"];
7306
- let $ = !1;
7307
- for (const ie of N)
7291
+ const G = [".fbx", ".glb", ".gltf"];
7292
+ let ee = !1;
7293
+ for (const se of G)
7308
7294
  try {
7309
- r.current.playAnimation(k + ie, null, 10, 0, 0.01, C), console.log("Playing animation:", k + ie), $ = !0;
7295
+ r.current.playAnimation(k + se, null, 10, 0, 0.01, E), console.log("Playing animation:", k + se), ee = !0;
7310
7296
  break;
7311
7297
  } catch {
7312
- console.log(`Failed to play ${k}${ie}, trying next format...`);
7298
+ console.log(`Failed to play ${k}${se}, trying next format...`);
7313
7299
  }
7314
- if (!$) {
7300
+ if (!ee) {
7315
7301
  console.warn("Animation system not available or animation not found:", k);
7316
7302
  try {
7317
7303
  r.current.setBodyMovement("idle"), console.log("Fallback to idle animation");
7318
- } catch (ie) {
7319
- console.warn("Fallback animation also failed:", ie);
7304
+ } catch (se) {
7305
+ console.warn("Fallback animation also failed:", se);
7320
7306
  }
7321
7307
  }
7322
7308
  }
@@ -7335,8 +7321,8 @@ const pt = Me(({
7335
7321
  if (r.current && r.current.setShowFullAvatar && r.current.setBodyMovement)
7336
7322
  try {
7337
7323
  r.current.setShowFullAvatar(!0), r.current.setBodyMovement(k), console.log("Body movement set with full body mode:", k);
7338
- } catch (C) {
7339
- console.warn("Error setting body movement:", C);
7324
+ } catch (E) {
7325
+ console.warn("Error setting body movement:", E);
7340
7326
  }
7341
7327
  },
7342
7328
  setMovementIntensity: (k) => r.current?.setMovementIntensity(k),
@@ -7352,8 +7338,8 @@ const pt = Me(({
7352
7338
  if (r.current && r.current.setShowFullAvatar && r.current.playReaction)
7353
7339
  try {
7354
7340
  r.current.setShowFullAvatar(!0), r.current.playReaction(k), console.log("Reaction played with full body mode:", k);
7355
- } catch (C) {
7356
- console.warn("Error playing reaction:", C);
7341
+ } catch (E) {
7342
+ console.warn("Error playing reaction:", E);
7357
7343
  }
7358
7344
  },
7359
7345
  playCelebration: () => {
@@ -7368,8 +7354,8 @@ const pt = Me(({
7368
7354
  if (r.current && r.current.setShowFullAvatar)
7369
7355
  try {
7370
7356
  r.current.setShowFullAvatar(k), console.log("Show full avatar set to:", k);
7371
- } catch (C) {
7372
- console.warn("Error setting showFullAvatar:", C);
7357
+ } catch (E) {
7358
+ console.warn("Error setting showFullAvatar:", E);
7373
7359
  }
7374
7360
  },
7375
7361
  lockAvatarPosition: () => {
@@ -7389,7 +7375,7 @@ const pt = Me(({
7389
7375
  }
7390
7376
  }
7391
7377
  })), /* @__PURE__ */ Pe("div", { className: `talking-head-container ${i}`, style: s, children: [
7392
- /* @__PURE__ */ pe(
7378
+ /* @__PURE__ */ me(
7393
7379
  "div",
7394
7380
  {
7395
7381
  ref: h,
@@ -7401,7 +7387,7 @@ const pt = Me(({
7401
7387
  }
7402
7388
  }
7403
7389
  ),
7404
- u && /* @__PURE__ */ pe("div", { className: "loading-overlay", style: {
7390
+ u && /* @__PURE__ */ me("div", { className: "loading-overlay", style: {
7405
7391
  position: "absolute",
7406
7392
  top: "50%",
7407
7393
  left: "50%",
@@ -7410,7 +7396,7 @@ const pt = Me(({
7410
7396
  fontSize: "18px",
7411
7397
  zIndex: 10
7412
7398
  }, children: "Loading avatar..." }),
7413
- d && /* @__PURE__ */ pe("div", { className: "error-overlay", style: {
7399
+ d && /* @__PURE__ */ me("div", { className: "error-overlay", style: {
7414
7400
  position: "absolute",
7415
7401
  top: "50%",
7416
7402
  left: "50%",
@@ -7448,16 +7434,16 @@ const gt = Me(({
7448
7434
  },
7449
7435
  className: x = "",
7450
7436
  style: S = {},
7451
- animations: G = {},
7437
+ animations: U = {},
7452
7438
  autoSpeak: p = !1
7453
- }, B) => {
7454
- const H = V(null), y = V(null), I = V(u), z = V(null), A = V(null), Y = V(!1), k = V({ remainingText: null, originalText: null, options: null }), C = V([]), [q, N] = de(!0), [$, ie] = de(null), [oe, he] = de(!1), [ee, ne] = de(!1);
7455
- me(() => {
7456
- Y.current = ee;
7457
- }, [ee]), me(() => {
7439
+ }, F) => {
7440
+ const C = O(null), y = O(null), I = O(u), z = O(null), A = O(null), Y = O(!1), k = O({ remainingText: null, originalText: null, options: null }), E = O([]), [q, G] = ce(!0), [ee, se] = ce(null), [ae, pe] = ce(!1), [te, le] = ce(!1);
7441
+ de(() => {
7442
+ Y.current = te;
7443
+ }, [te]), de(() => {
7458
7444
  I.current = u;
7459
7445
  }, [u]);
7460
- const D = Ee(), v = s || D.service;
7446
+ const W = Ee(), v = s || W.service;
7461
7447
  let R;
7462
7448
  v === "browser" ? R = {
7463
7449
  service: "browser",
@@ -7467,20 +7453,20 @@ const gt = Me(({
7467
7453
  } : v === "elevenlabs" ? R = {
7468
7454
  service: "elevenlabs",
7469
7455
  endpoint: "https://api.elevenlabs.io/v1/text-to-speech",
7470
- apiKey: l || D.apiKey,
7471
- defaultVoice: o || D.defaultVoice || Ie.defaultVoice,
7472
- voices: D.voices || Ie.voices
7456
+ apiKey: l || W.apiKey,
7457
+ defaultVoice: o || W.defaultVoice || Ie.defaultVoice,
7458
+ voices: W.voices || Ie.voices
7473
7459
  } : v === "deepgram" ? R = {
7474
7460
  service: "deepgram",
7475
7461
  endpoint: "https://api.deepgram.com/v1/speak",
7476
- apiKey: l || D.apiKey,
7477
- defaultVoice: o || D.defaultVoice || Te.defaultVoice,
7478
- voices: D.voices || Te.voices
7462
+ apiKey: l || W.apiKey,
7463
+ defaultVoice: o || W.defaultVoice || Te.defaultVoice,
7464
+ voices: W.voices || Te.voices
7479
7465
  } : R = {
7480
- ...D,
7481
- apiKey: l !== null ? l : D.apiKey
7466
+ ...W,
7467
+ apiKey: l !== null ? l : W.apiKey
7482
7468
  };
7483
- const T = {
7469
+ const H = {
7484
7470
  url: t,
7485
7471
  body: e,
7486
7472
  avatarMood: n,
@@ -7490,127 +7476,127 @@ const gt = Me(({
7490
7476
  showFullAvatar: u,
7491
7477
  bodyMovement: h,
7492
7478
  movementIntensity: r
7493
- }, F = {
7479
+ }, P = {
7494
7480
  ttsEndpoint: R.endpoint,
7495
7481
  ttsApikey: R.apiKey,
7496
7482
  ttsService: v,
7497
7483
  lipsyncModules: ["en"],
7498
7484
  cameraView: a
7499
- }, P = O(async () => {
7500
- if (!(!H.current || y.current))
7485
+ }, V = B(async () => {
7486
+ if (!(!C.current || y.current))
7501
7487
  try {
7502
- N(!0), ie(null), y.current = new Be(H.current, F), console.log("Avatar config being passed:", {
7503
- url: T.url,
7504
- body: T.body,
7505
- avatarMood: T.avatarMood
7506
- }), await y.current.showAvatar(T, (se) => {
7507
- if (se.lengthComputable) {
7508
- const L = Math.min(100, Math.round(se.loaded / se.total * 100));
7488
+ G(!0), se(null), y.current = new Be(C.current, P), console.log("Avatar config being passed:", {
7489
+ url: H.url,
7490
+ body: H.body,
7491
+ avatarMood: H.avatarMood
7492
+ }), await y.current.showAvatar(H, (ne) => {
7493
+ if (ne.lengthComputable) {
7494
+ const L = Math.min(100, Math.round(ne.loaded / ne.total * 100));
7509
7495
  c(L);
7510
7496
  }
7511
- }), y.current?.avatar && console.log("Avatar body after initialization:", y.current.avatar.body), N(!1), he(!0), d(y.current);
7512
- const E = () => {
7497
+ }), y.current?.avatar && console.log("Avatar body after initialization:", y.current.avatar.body), G(!1), pe(!0), d(y.current);
7498
+ const M = () => {
7513
7499
  document.visibilityState === "visible" ? y.current?.start() : y.current?.stop();
7514
7500
  };
7515
- return document.addEventListener("visibilitychange", E), () => {
7516
- document.removeEventListener("visibilitychange", E);
7501
+ return document.addEventListener("visibilitychange", M), () => {
7502
+ document.removeEventListener("visibilitychange", M);
7517
7503
  };
7518
- } catch (E) {
7519
- console.error("Error initializing TalkingHead:", E), ie(E.message || "Failed to initialize avatar"), N(!1), g(E);
7504
+ } catch (M) {
7505
+ console.error("Error initializing TalkingHead:", M), se(M.message || "Failed to initialize avatar"), G(!1), g(M);
7520
7506
  }
7521
7507
  }, []);
7522
- me(() => (P(), () => {
7508
+ de(() => (V(), () => {
7523
7509
  y.current && (y.current.stop(), y.current.dispose(), y.current = null);
7524
- }), [P]);
7525
- const _ = O(async () => {
7510
+ }), [V]);
7511
+ const J = B(async () => {
7526
7512
  if (y.current)
7527
7513
  try {
7528
- const E = y.current.audioCtx || y.current.audioContext;
7529
- E && (E.state === "suspended" || E.state === "interrupted") && (await E.resume(), console.log("Audio context resumed"));
7530
- } catch (E) {
7531
- console.warn("Failed to resume audio context:", E);
7514
+ const M = y.current.audioCtx || y.current.audioContext;
7515
+ M && (M.state === "suspended" || M.state === "interrupted") && (await M.resume(), console.log("Audio context resumed"));
7516
+ } catch (M) {
7517
+ console.warn("Failed to resume audio context:", M);
7532
7518
  }
7533
- }, []), j = O(async (E, se = {}) => {
7534
- if (!y.current || !oe) {
7519
+ }, []), Q = B(async (M, ne = {}) => {
7520
+ if (!y.current || !ae) {
7535
7521
  console.warn("Avatar not ready for speaking");
7536
7522
  return;
7537
7523
  }
7538
- if (!E || E.trim() === "") {
7524
+ if (!M || M.trim() === "") {
7539
7525
  console.warn("No text provided to speak");
7540
7526
  return;
7541
7527
  }
7542
- await _(), k.current = { remainingText: null, originalText: null, options: null }, C.current = [], z.current = { text: E, options: se }, A.current && (clearInterval(A.current), A.current = null), ne(!1), Y.current = !1;
7543
- const L = E.split(/[.!?]+/).filter((W) => W.trim().length > 0);
7544
- C.current = L;
7545
- const U = {
7546
- lipsyncLang: se.lipsyncLang || "en",
7528
+ await J(), k.current = { remainingText: null, originalText: null, options: null }, E.current = [], z.current = { text: M, options: ne }, A.current && (clearInterval(A.current), A.current = null), le(!1), Y.current = !1;
7529
+ const L = M.split(/[.!?]+/).filter((D) => D.trim().length > 0);
7530
+ E.current = L;
7531
+ const N = {
7532
+ lipsyncLang: ne.lipsyncLang || "en",
7547
7533
  onSpeechEnd: () => {
7548
- A.current && (clearInterval(A.current), A.current = null), se.onSpeechEnd && se.onSpeechEnd(), b();
7534
+ A.current && (clearInterval(A.current), A.current = null), ne.onSpeechEnd && ne.onSpeechEnd(), b();
7549
7535
  }
7550
7536
  };
7551
7537
  try {
7552
- y.current.speakText(E, U);
7553
- } catch (W) {
7554
- console.error("Error speaking text:", W), ie(W.message || "Failed to speak text");
7538
+ y.current.speakText(M, N);
7539
+ } catch (D) {
7540
+ console.error("Error speaking text:", D), se(D.message || "Failed to speak text");
7555
7541
  }
7556
- }, [oe, b, _]);
7557
- me(() => {
7558
- oe && X && p && y.current && j(X);
7559
- }, [oe, X, p, j]);
7560
- const J = O(() => {
7542
+ }, [ae, b, J]);
7543
+ de(() => {
7544
+ ae && X && p && y.current && Q(X);
7545
+ }, [ae, X, p, Q]);
7546
+ const K = B(() => {
7561
7547
  if (y.current)
7562
7548
  try {
7563
- const E = y.current.isSpeaking || !1, se = y.current.audioPlaylist || [], L = y.current.speechQueue || [];
7564
- if (E || se.length > 0 || L.length > 0) {
7549
+ const M = y.current.isSpeaking || !1, ne = y.current.audioPlaylist || [], L = y.current.speechQueue || [];
7550
+ if (M || ne.length > 0 || L.length > 0) {
7565
7551
  A.current && (clearInterval(A.current), A.current = null);
7566
- let U = "";
7567
- L.length > 0 && (U = L.map((W) => W.text && Array.isArray(W.text) ? W.text.map((te) => te.word).join(" ") : W.text || "").join(" ")), k.current = {
7568
- remainingText: U || null,
7552
+ let N = "";
7553
+ L.length > 0 && (N = L.map((D) => D.text && Array.isArray(D.text) ? D.text.map(($) => $.word).join(" ") : D.text || "").join(" ")), k.current = {
7554
+ remainingText: N || null,
7569
7555
  originalText: z.current?.text || null,
7570
7556
  options: z.current?.options || null
7571
- }, y.current.speechQueue.length = 0, y.current.pauseSpeaking(), ne(!0), Y.current = !0;
7557
+ }, y.current.speechQueue.length = 0, y.current.pauseSpeaking(), le(!0), Y.current = !0;
7572
7558
  }
7573
- } catch (E) {
7574
- console.warn("Error pausing speech:", E);
7559
+ } catch (M) {
7560
+ console.warn("Error pausing speech:", M);
7575
7561
  }
7576
- }, []), Ae = O(async () => {
7577
- if (!(!y.current || !ee))
7562
+ }, []), Ae = B(async () => {
7563
+ if (!(!y.current || !te))
7578
7564
  try {
7579
- await _(), ne(!1), Y.current = !1;
7580
- const E = k.current?.remainingText, se = k.current?.originalText || z.current?.text, L = k.current?.options || z.current?.options || {}, U = E || se;
7581
- U && j(U, L);
7582
- } catch (E) {
7583
- console.warn("Error resuming speech:", E), ne(!1), Y.current = !1;
7565
+ await J(), le(!1), Y.current = !1;
7566
+ const M = k.current?.remainingText, ne = k.current?.originalText || z.current?.text, L = k.current?.options || z.current?.options || {}, N = M || ne;
7567
+ N && Q(N, L);
7568
+ } catch (M) {
7569
+ console.warn("Error resuming speech:", M), le(!1), Y.current = !1;
7584
7570
  }
7585
- }, [ee, j, _]), we = O(() => {
7586
- y.current && (y.current.stopSpeaking(), A.current && (clearInterval(A.current), A.current = null), ne(!1), Y.current = !1);
7571
+ }, [te, Q, J]), we = B(() => {
7572
+ y.current && (y.current.stopSpeaking(), A.current && (clearInterval(A.current), A.current = null), le(!1), Y.current = !1);
7587
7573
  }, []);
7588
- return Fe(B, () => ({
7589
- speakText: j,
7590
- pauseSpeaking: J,
7574
+ return Fe(F, () => ({
7575
+ speakText: Q,
7576
+ pauseSpeaking: K,
7591
7577
  resumeSpeaking: Ae,
7592
7578
  stopSpeaking: we,
7593
- resumeAudioContext: _,
7594
- isPaused: () => ee,
7595
- setMood: (E) => y.current?.setMood(E),
7596
- setBodyMovement: (E) => {
7597
- y.current && y.current.setBodyMovement(E);
7579
+ resumeAudioContext: J,
7580
+ isPaused: () => te,
7581
+ setMood: (M) => y.current?.setMood(M),
7582
+ setBodyMovement: (M) => {
7583
+ y.current && y.current.setBodyMovement(M);
7598
7584
  },
7599
- playAnimation: (E, se = !1) => {
7600
- y.current && y.current.playAnimation && y.current.playAnimation(E, null, 10, 0, 0.01, se);
7585
+ playAnimation: (M, ne = !1) => {
7586
+ y.current && y.current.playAnimation && y.current.playAnimation(M, null, 10, 0, 0.01, ne);
7601
7587
  },
7602
- playReaction: (E) => y.current?.playReaction(E),
7588
+ playReaction: (M) => y.current?.playReaction(M),
7603
7589
  playCelebration: () => y.current?.playCelebration(),
7604
- setShowFullAvatar: (E) => {
7605
- y.current && (I.current = E, y.current.setShowFullAvatar(E));
7590
+ setShowFullAvatar: (M) => {
7591
+ y.current && (I.current = M, y.current.setShowFullAvatar(M));
7606
7592
  },
7607
- isReady: oe,
7593
+ isReady: ae,
7608
7594
  talkingHead: y.current
7609
7595
  })), /* @__PURE__ */ Pe("div", { className: `simple-talking-avatar-container ${x}`, style: S, children: [
7610
- /* @__PURE__ */ pe(
7596
+ /* @__PURE__ */ me(
7611
7597
  "div",
7612
7598
  {
7613
- ref: H,
7599
+ ref: C,
7614
7600
  className: "talking-head-viewer",
7615
7601
  style: {
7616
7602
  width: "100%",
@@ -7619,7 +7605,7 @@ const gt = Me(({
7619
7605
  }
7620
7606
  }
7621
7607
  ),
7622
- q && /* @__PURE__ */ pe("div", { className: "loading-overlay", style: {
7608
+ q && /* @__PURE__ */ me("div", { className: "loading-overlay", style: {
7623
7609
  position: "absolute",
7624
7610
  top: "50%",
7625
7611
  left: "50%",
@@ -7628,7 +7614,7 @@ const gt = Me(({
7628
7614
  fontSize: "18px",
7629
7615
  zIndex: 10
7630
7616
  }, children: "Loading avatar..." }),
7631
- $ && /* @__PURE__ */ pe("div", { className: "error-overlay", style: {
7617
+ ee && /* @__PURE__ */ me("div", { className: "error-overlay", style: {
7632
7618
  position: "absolute",
7633
7619
  top: "50%",
7634
7620
  left: "50%",
@@ -7639,7 +7625,7 @@ const gt = Me(({
7639
7625
  zIndex: 10,
7640
7626
  padding: "20px",
7641
7627
  borderRadius: "8px"
7642
- }, children: $ })
7628
+ }, children: ee })
7643
7629
  ] });
7644
7630
  });
7645
7631
  gt.displayName = "SimpleTalkingAvatar";
@@ -7659,7 +7645,7 @@ const yt = Me(({
7659
7645
  },
7660
7646
  autoStart: h = !1
7661
7647
  }, r) => {
7662
- const u = V(null), a = V({
7648
+ const u = O(null), a = O({
7663
7649
  currentModuleIndex: 0,
7664
7650
  currentLessonIndex: 0,
7665
7651
  currentQuestionIndex: 0,
@@ -7669,18 +7655,18 @@ const yt = Me(({
7669
7655
  curriculumCompleted: !1,
7670
7656
  score: 0,
7671
7657
  totalQuestions: 0
7672
- }), d = V({
7658
+ }), d = O({
7673
7659
  onLessonStart: n,
7674
7660
  onLessonComplete: i,
7675
7661
  onQuestionAnswer: s,
7676
7662
  onCurriculumComplete: o,
7677
7663
  onCustomAction: l
7678
- }), c = V(null), g = V(null), b = V(null), x = V(null), S = V(null), G = V(null), p = V(null), B = V(X?.curriculum || {
7664
+ }), c = O(null), g = O(null), b = O(null), x = O(null), S = O(null), U = O(null), p = O(null), F = O(X?.curriculum || {
7679
7665
  title: "Default Curriculum",
7680
7666
  description: "No curriculum data provided",
7681
7667
  language: "en",
7682
7668
  modules: []
7683
- }), H = V({
7669
+ }), C = O({
7684
7670
  avatarUrl: t.avatarUrl || "/avatars/brunette.glb",
7685
7671
  avatarBody: t.avatarBody || "F",
7686
7672
  mood: t.mood || "happy",
@@ -7694,7 +7680,7 @@ const yt = Me(({
7694
7680
  animations: e,
7695
7681
  lipsyncLang: "en"
7696
7682
  });
7697
- me(() => {
7683
+ de(() => {
7698
7684
  d.current = {
7699
7685
  onLessonStart: n,
7700
7686
  onLessonComplete: i,
@@ -7702,13 +7688,13 @@ const yt = Me(({
7702
7688
  onCurriculumComplete: o,
7703
7689
  onCustomAction: l
7704
7690
  };
7705
- }, [n, i, s, o, l]), me(() => {
7706
- B.current = X?.curriculum || {
7691
+ }, [n, i, s, o, l]), de(() => {
7692
+ F.current = X?.curriculum || {
7707
7693
  title: "Default Curriculum",
7708
7694
  description: "No curriculum data provided",
7709
7695
  language: "en",
7710
7696
  modules: []
7711
- }, H.current = {
7697
+ }, C.current = {
7712
7698
  avatarUrl: t.avatarUrl || "/avatars/brunette.glb",
7713
7699
  avatarBody: t.avatarBody || "F",
7714
7700
  mood: t.mood || "happy",
@@ -7723,7 +7709,7 @@ const yt = Me(({
7723
7709
  lipsyncLang: "en"
7724
7710
  };
7725
7711
  }, [X, t, e]);
7726
- const y = O(() => (B.current || { modules: [] }).modules[a.current.currentModuleIndex]?.lessons[a.current.currentLessonIndex], []), I = O(() => y()?.questions[a.current.currentQuestionIndex], [y]), z = O((v, R) => R.type === "multiple_choice" || R.type === "true_false" ? v === R.answer : R.type === "code_test" && typeof v == "object" && v !== null ? v.passed === !0 : !1, []), A = O(() => {
7712
+ const y = B(() => (F.current || { modules: [] }).modules[a.current.currentModuleIndex]?.lessons[a.current.currentLessonIndex], []), I = B(() => y()?.questions[a.current.currentQuestionIndex], [y]), z = B((v, R) => R.type === "multiple_choice" || R.type === "true_false" ? v === R.answer : R.type === "code_test" && typeof v == "object" && v !== null ? v.passed === !0 : !1, []), A = B(() => {
7727
7713
  a.current.lessonCompleted = !0, a.current.isQuestionMode = !1;
7728
7714
  const v = a.current.totalQuestions > 0 ? Math.round(a.current.score / a.current.totalQuestions * 100) : 100;
7729
7715
  let R = "Congratulations! You've completed this lesson";
@@ -7747,9 +7733,9 @@ const yt = Me(({
7747
7733
  } catch {
7748
7734
  u.current.playCelebration();
7749
7735
  }
7750
- const T = B.current || { modules: [] }, F = T.modules[a.current.currentModuleIndex], P = a.current.currentLessonIndex < (F?.lessons?.length || 0) - 1, _ = a.current.currentModuleIndex < (T.modules?.length || 0) - 1, j = P || _, J = H.current || { lipsyncLang: "en" };
7736
+ const H = F.current || { modules: [] }, P = H.modules[a.current.currentModuleIndex], V = a.current.currentLessonIndex < (P?.lessons?.length || 0) - 1, J = a.current.currentModuleIndex < (H.modules?.length || 0) - 1, Q = V || J, K = C.current || { lipsyncLang: "en" };
7751
7737
  u.current.speakText(R, {
7752
- lipsyncLang: J.lipsyncLang,
7738
+ lipsyncLang: K.lipsyncLang,
7753
7739
  onSpeechEnd: () => {
7754
7740
  d.current.onCustomAction({
7755
7741
  type: "lessonCompleteFeedbackDone",
@@ -7758,17 +7744,17 @@ const yt = Me(({
7758
7744
  score: a.current.score,
7759
7745
  totalQuestions: a.current.totalQuestions,
7760
7746
  percentage: v,
7761
- hasNextLesson: j
7747
+ hasNextLesson: Q
7762
7748
  });
7763
7749
  }
7764
7750
  });
7765
7751
  }
7766
- }, [e.lessonComplete]), Y = O(() => {
7752
+ }, [e.lessonComplete]), Y = B(() => {
7767
7753
  a.current.curriculumCompleted = !0;
7768
- const v = B.current || { modules: [] };
7754
+ const v = F.current || { modules: [] };
7769
7755
  if (d.current.onCurriculumComplete({
7770
7756
  modules: v.modules.length,
7771
- totalLessons: v.modules.reduce((R, T) => R + T.lessons.length, 0)
7757
+ totalLessons: v.modules.reduce((R, H) => R + H.lessons.length, 0)
7772
7758
  }), u.current) {
7773
7759
  if (u.current.setMood("celebrating"), e.curriculumComplete)
7774
7760
  try {
@@ -7776,10 +7762,10 @@ const yt = Me(({
7776
7762
  } catch {
7777
7763
  u.current.playCelebration();
7778
7764
  }
7779
- const R = H.current || { lipsyncLang: "en" };
7765
+ const R = C.current || { lipsyncLang: "en" };
7780
7766
  u.current.speakText("Amazing! You've completed the entire curriculum! You're now ready to move on to more advanced topics. Well done!", { lipsyncLang: R.lipsyncLang });
7781
7767
  }
7782
- }, [e.curriculumComplete]), k = O(() => {
7768
+ }, [e.curriculumComplete]), k = B(() => {
7783
7769
  const v = y();
7784
7770
  a.current.isQuestionMode = !0, a.current.currentQuestionIndex = 0, a.current.totalQuestions = v?.questions?.length || 0, a.current.score = 0;
7785
7771
  const R = I();
@@ -7792,31 +7778,31 @@ const yt = Me(({
7792
7778
  question: R,
7793
7779
  score: a.current.score
7794
7780
  });
7795
- const T = () => {
7781
+ const H = () => {
7796
7782
  if (!u.current || !R) return;
7797
7783
  if (u.current.setMood("happy"), e.questionStart)
7798
7784
  try {
7799
7785
  u.current.playAnimation(e.questionStart, !0);
7800
- } catch (P) {
7801
- console.warn("Failed to play questionStart animation:", P);
7786
+ } catch (V) {
7787
+ console.warn("Failed to play questionStart animation:", V);
7802
7788
  }
7803
- const F = H.current || { lipsyncLang: "en" };
7804
- R.type === "code_test" ? u.current.speakText(`Let's test your coding skills! Here's your first challenge: ${R.question}`, { lipsyncLang: F.lipsyncLang }) : R.type === "multiple_choice" ? u.current.speakText(`Now let me ask you some questions. Here's the first one: ${R.question}`, { lipsyncLang: F.lipsyncLang }) : R.type === "true_false" ? u.current.speakText(`Let's start with some true or false questions. First question: ${R.question}`, { lipsyncLang: F.lipsyncLang }) : u.current.speakText(`Now let me ask you some questions. Here's the first one: ${R.question}`, { lipsyncLang: F.lipsyncLang });
7789
+ const P = C.current || { lipsyncLang: "en" };
7790
+ R.type === "code_test" ? u.current.speakText(`Let's test your coding skills! Here's your first challenge: ${R.question}`, { lipsyncLang: P.lipsyncLang }) : R.type === "multiple_choice" ? u.current.speakText(`Now let me ask you some questions. Here's the first one: ${R.question}`, { lipsyncLang: P.lipsyncLang }) : R.type === "true_false" ? u.current.speakText(`Let's start with some true or false questions. First question: ${R.question}`, { lipsyncLang: P.lipsyncLang }) : u.current.speakText(`Now let me ask you some questions. Here's the first one: ${R.question}`, { lipsyncLang: P.lipsyncLang });
7805
7791
  };
7806
7792
  if (u.current && u.current.isReady && R)
7807
- T();
7793
+ H();
7808
7794
  else if (u.current && u.current.isReady) {
7809
- const F = H.current || { lipsyncLang: "en" };
7810
- u.current.speakText("Now let me ask you some questions to test your understanding.", { lipsyncLang: F.lipsyncLang });
7795
+ const P = C.current || { lipsyncLang: "en" };
7796
+ u.current.speakText("Now let me ask you some questions to test your understanding.", { lipsyncLang: P.lipsyncLang });
7811
7797
  } else {
7812
- const F = setInterval(() => {
7813
- u.current && u.current.isReady && (clearInterval(F), R && T());
7798
+ const P = setInterval(() => {
7799
+ u.current && u.current.isReady && (clearInterval(P), R && H());
7814
7800
  }, 100);
7815
7801
  setTimeout(() => {
7816
- clearInterval(F);
7802
+ clearInterval(P);
7817
7803
  }, 5e3);
7818
7804
  }
7819
- }, [e.questionStart, y, I]), C = O(() => {
7805
+ }, [e.questionStart, y, I]), E = B(() => {
7820
7806
  const v = y();
7821
7807
  if (a.current.currentQuestionIndex < (v?.questions?.length || 0) - 1) {
7822
7808
  u.current && u.current.stopSpeaking && u.current.stopSpeaking(), a.current.currentQuestionIndex += 1;
@@ -7830,45 +7816,45 @@ const yt = Me(({
7830
7816
  question: R,
7831
7817
  score: a.current.score
7832
7818
  });
7833
- const T = () => {
7819
+ const H = () => {
7834
7820
  if (!u.current || !R) return;
7835
7821
  if (u.current.setMood("happy"), u.current.setBodyMovement("idle"), e.nextQuestion)
7836
7822
  try {
7837
7823
  u.current.playAnimation(e.nextQuestion, !0);
7838
- } catch (J) {
7839
- console.warn("Failed to play nextQuestion animation:", J);
7824
+ } catch (K) {
7825
+ console.warn("Failed to play nextQuestion animation:", K);
7840
7826
  }
7841
- const F = H.current || { lipsyncLang: "en" }, _ = y()?.questions?.length || 0, j = a.current.currentQuestionIndex >= _ - 1;
7827
+ const P = C.current || { lipsyncLang: "en" }, J = y()?.questions?.length || 0, Q = a.current.currentQuestionIndex >= J - 1;
7842
7828
  if (R.type === "code_test") {
7843
- const J = j ? `Great! Here's your final coding challenge: ${R.question}` : `Great! Now let's move on to your next coding challenge: ${R.question}`;
7844
- u.current.speakText(J, {
7845
- lipsyncLang: F.lipsyncLang
7829
+ const K = Q ? `Great! Here's your final coding challenge: ${R.question}` : `Great! Now let's move on to your next coding challenge: ${R.question}`;
7830
+ u.current.speakText(K, {
7831
+ lipsyncLang: P.lipsyncLang
7846
7832
  });
7847
7833
  } else if (R.type === "multiple_choice") {
7848
- const J = j ? `Alright! Here's your final question: ${R.question}` : `Alright! Here's your next question: ${R.question}`;
7849
- u.current.speakText(J, {
7850
- lipsyncLang: F.lipsyncLang
7834
+ const K = Q ? `Alright! Here's your final question: ${R.question}` : `Alright! Here's your next question: ${R.question}`;
7835
+ u.current.speakText(K, {
7836
+ lipsyncLang: P.lipsyncLang
7851
7837
  });
7852
7838
  } else if (R.type === "true_false") {
7853
- const J = j ? `Now let's try this final one: ${R.question}` : `Now let's try this one: ${R.question}`;
7854
- u.current.speakText(J, {
7855
- lipsyncLang: F.lipsyncLang
7839
+ const K = Q ? `Now let's try this final one: ${R.question}` : `Now let's try this one: ${R.question}`;
7840
+ u.current.speakText(K, {
7841
+ lipsyncLang: P.lipsyncLang
7856
7842
  });
7857
7843
  } else {
7858
- const J = j ? `Here's your final question: ${R.question}` : `Here's the next question: ${R.question}`;
7859
- u.current.speakText(J, {
7860
- lipsyncLang: F.lipsyncLang
7844
+ const K = Q ? `Here's your final question: ${R.question}` : `Here's the next question: ${R.question}`;
7845
+ u.current.speakText(K, {
7846
+ lipsyncLang: P.lipsyncLang
7861
7847
  });
7862
7848
  }
7863
7849
  };
7864
7850
  if (u.current && u.current.isReady && R)
7865
- T();
7851
+ H();
7866
7852
  else if (R) {
7867
- const F = setInterval(() => {
7868
- u.current && u.current.isReady && (clearInterval(F), T());
7853
+ const P = setInterval(() => {
7854
+ u.current && u.current.isReady && (clearInterval(P), H());
7869
7855
  }, 100);
7870
7856
  setTimeout(() => {
7871
- clearInterval(F);
7857
+ clearInterval(P);
7872
7858
  }, 5e3);
7873
7859
  }
7874
7860
  } else
@@ -7879,16 +7865,16 @@ const yt = Me(({
7879
7865
  totalQuestions: a.current.totalQuestions,
7880
7866
  score: a.current.score
7881
7867
  });
7882
- }, [e.nextQuestion, y, I]), q = O(() => {
7883
- const v = B.current || { modules: [] }, R = v.modules[a.current.currentModuleIndex];
7868
+ }, [e.nextQuestion, y, I]), q = B(() => {
7869
+ const v = F.current || { modules: [] }, R = v.modules[a.current.currentModuleIndex];
7884
7870
  if (a.current.currentLessonIndex < (R?.lessons?.length || 0) - 1) {
7885
7871
  a.current.currentLessonIndex += 1, a.current.currentQuestionIndex = 0, a.current.lessonCompleted = !1, a.current.isQuestionMode = !1, a.current.isTeaching = !1, a.current.score = 0, a.current.totalQuestions = 0;
7886
- const F = v.modules[a.current.currentModuleIndex], P = a.current.currentLessonIndex < (F?.lessons?.length || 0) - 1, _ = a.current.currentModuleIndex < (v.modules?.length || 0) - 1, j = P || _;
7872
+ const P = v.modules[a.current.currentModuleIndex], V = a.current.currentLessonIndex < (P?.lessons?.length || 0) - 1, J = a.current.currentModuleIndex < (v.modules?.length || 0) - 1, Q = V || J;
7887
7873
  d.current.onCustomAction({
7888
7874
  type: "lessonStart",
7889
7875
  moduleIndex: a.current.currentModuleIndex,
7890
7876
  lessonIndex: a.current.currentLessonIndex,
7891
- hasNextLesson: j
7877
+ hasNextLesson: Q
7892
7878
  }), d.current.onLessonStart({
7893
7879
  moduleIndex: a.current.currentModuleIndex,
7894
7880
  lessonIndex: a.current.currentLessonIndex,
@@ -7896,12 +7882,12 @@ const yt = Me(({
7896
7882
  }), u.current && (u.current.setMood("happy"), u.current.setBodyMovement("idle"));
7897
7883
  } else if (a.current.currentModuleIndex < (v.modules?.length || 0) - 1) {
7898
7884
  a.current.currentModuleIndex += 1, a.current.currentLessonIndex = 0, a.current.currentQuestionIndex = 0, a.current.lessonCompleted = !1, a.current.isQuestionMode = !1, a.current.isTeaching = !1, a.current.score = 0, a.current.totalQuestions = 0;
7899
- const P = v.modules[a.current.currentModuleIndex], _ = a.current.currentLessonIndex < (P?.lessons?.length || 0) - 1, j = a.current.currentModuleIndex < (v.modules?.length || 0) - 1, J = _ || j;
7885
+ const V = v.modules[a.current.currentModuleIndex], J = a.current.currentLessonIndex < (V?.lessons?.length || 0) - 1, Q = a.current.currentModuleIndex < (v.modules?.length || 0) - 1, K = J || Q;
7900
7886
  d.current.onCustomAction({
7901
7887
  type: "lessonStart",
7902
7888
  moduleIndex: a.current.currentModuleIndex,
7903
7889
  lessonIndex: a.current.currentLessonIndex,
7904
- hasNextLesson: J
7890
+ hasNextLesson: K
7905
7891
  }), d.current.onLessonStart({
7906
7892
  moduleIndex: a.current.currentModuleIndex,
7907
7893
  lessonIndex: a.current.currentLessonIndex,
@@ -7909,25 +7895,25 @@ const yt = Me(({
7909
7895
  }), u.current && (u.current.setMood("happy"), u.current.setBodyMovement("idle"));
7910
7896
  } else
7911
7897
  S.current && S.current();
7912
- }, []), N = O(() => {
7898
+ }, []), G = B(() => {
7913
7899
  const v = y();
7914
7900
  let R = null;
7915
7901
  if (v?.avatar_script && v?.body) {
7916
- const T = v.avatar_script.trim(), F = v.body.trim(), P = T.match(/[.!?]$/) ? " " : ". ";
7917
- R = `${T}${P}${F}`;
7902
+ const H = v.avatar_script.trim(), P = v.body.trim(), V = H.match(/[.!?]$/) ? " " : ". ";
7903
+ R = `${H}${V}${P}`;
7918
7904
  } else
7919
7905
  R = v?.avatar_script || v?.body || null;
7920
7906
  if (u.current && u.current.isReady && R) {
7921
7907
  a.current.isTeaching = !0, a.current.isQuestionMode = !1, a.current.score = 0, a.current.totalQuestions = 0, u.current.setMood("happy");
7922
- let T = !1;
7908
+ let H = !1;
7923
7909
  if (e.teaching)
7924
7910
  try {
7925
- u.current.playAnimation(e.teaching, !0), T = !0;
7926
- } catch (P) {
7927
- console.warn("Failed to play teaching animation:", P);
7911
+ u.current.playAnimation(e.teaching, !0), H = !0;
7912
+ } catch (V) {
7913
+ console.warn("Failed to play teaching animation:", V);
7928
7914
  }
7929
- T || u.current.setBodyMovement("gesturing");
7930
- const F = H.current || { lipsyncLang: "en" };
7915
+ H || u.current.setBodyMovement("gesturing");
7916
+ const P = C.current || { lipsyncLang: "en" };
7931
7917
  d.current.onLessonStart({
7932
7918
  moduleIndex: a.current.currentModuleIndex,
7933
7919
  lessonIndex: a.current.currentLessonIndex,
@@ -7938,7 +7924,7 @@ const yt = Me(({
7938
7924
  lessonIndex: a.current.currentLessonIndex,
7939
7925
  lesson: v
7940
7926
  }), u.current.speakText(R, {
7941
- lipsyncLang: F.lipsyncLang,
7927
+ lipsyncLang: P.lipsyncLang,
7942
7928
  onSpeechEnd: () => {
7943
7929
  a.current.isTeaching = !1, d.current.onCustomAction({
7944
7930
  type: "teachingComplete",
@@ -7956,17 +7942,17 @@ const yt = Me(({
7956
7942
  }
7957
7943
  });
7958
7944
  }
7959
- }, [e.teaching, y]), $ = O((v) => {
7960
- const R = I(), T = z(v, R);
7961
- if (T && (a.current.score += 1), d.current.onQuestionAnswer({
7945
+ }, [e.teaching, y]), ee = B((v) => {
7946
+ const R = I(), H = z(v, R);
7947
+ if (H && (a.current.score += 1), d.current.onQuestionAnswer({
7962
7948
  moduleIndex: a.current.currentModuleIndex,
7963
7949
  lessonIndex: a.current.currentLessonIndex,
7964
7950
  questionIndex: a.current.currentQuestionIndex,
7965
7951
  answer: v,
7966
- isCorrect: T,
7952
+ isCorrect: H,
7967
7953
  question: R
7968
7954
  }), u.current)
7969
- if (T) {
7955
+ if (H) {
7970
7956
  if (u.current.setMood("happy"), e.correct)
7971
7957
  try {
7972
7958
  u.current.playReaction("happy");
@@ -7974,13 +7960,13 @@ const yt = Me(({
7974
7960
  u.current.setBodyMovement("happy");
7975
7961
  }
7976
7962
  u.current.setBodyMovement("gesturing");
7977
- const P = y()?.questions?.length || 0;
7978
- a.current.currentQuestionIndex >= P - 1;
7979
- const _ = a.current.currentQuestionIndex < P - 1;
7980
- console.log("[CurriculumLearning] Answer feedback - questionIndex:", a.current.currentQuestionIndex, "totalQuestions:", P, "hasNextQuestion:", _);
7981
- const j = R.type === "code_test" ? `Great job! Your code passed all the tests! ${R.explanation || ""}` : `Excellent! That's correct! ${R.explanation || ""}`, J = H.current || { lipsyncLang: "en" };
7982
- u.current.speakText(j, {
7983
- lipsyncLang: J.lipsyncLang,
7963
+ const V = y()?.questions?.length || 0;
7964
+ a.current.currentQuestionIndex >= V - 1;
7965
+ const J = a.current.currentQuestionIndex < V - 1;
7966
+ console.log("[CurriculumLearning] Answer feedback - questionIndex:", a.current.currentQuestionIndex, "totalQuestions:", V, "hasNextQuestion:", J);
7967
+ const Q = R.type === "code_test" ? `Great job! Your code passed all the tests! ${R.explanation || ""}` : `Excellent! That's correct! ${R.explanation || ""}`, K = C.current || { lipsyncLang: "en" };
7968
+ u.current.speakText(Q, {
7969
+ lipsyncLang: K.lipsyncLang,
7984
7970
  onSpeechEnd: () => {
7985
7971
  d.current.onCustomAction({
7986
7972
  type: "answerFeedbackComplete",
@@ -7988,7 +7974,7 @@ const yt = Me(({
7988
7974
  lessonIndex: a.current.currentLessonIndex,
7989
7975
  questionIndex: a.current.currentQuestionIndex,
7990
7976
  isCorrect: !0,
7991
- hasNextQuestion: _,
7977
+ hasNextQuestion: J,
7992
7978
  score: a.current.score,
7993
7979
  totalQuestions: a.current.totalQuestions
7994
7980
  });
@@ -8002,10 +7988,10 @@ const yt = Me(({
8002
7988
  u.current.setBodyMovement("idle");
8003
7989
  }
8004
7990
  u.current.setBodyMovement("gesturing");
8005
- const P = y()?.questions?.length || 0, _ = a.current.currentQuestionIndex >= P - 1, j = a.current.currentQuestionIndex < P - 1;
8006
- console.log("[CurriculumLearning] Answer feedback (incorrect) - questionIndex:", a.current.currentQuestionIndex, "totalQuestions:", P, "hasNextQuestion:", j);
8007
- const J = R.type === "code_test" ? `Your code didn't pass all the tests. ${R.explanation || "Try again!"}` : `Not quite right, but don't worry! ${R.explanation || ""}${_ ? "" : " Let's move on to the next question."}`, Ae = H.current || { lipsyncLang: "en" };
8008
- u.current.speakText(J, {
7991
+ const V = y()?.questions?.length || 0, J = a.current.currentQuestionIndex >= V - 1, Q = a.current.currentQuestionIndex < V - 1;
7992
+ console.log("[CurriculumLearning] Answer feedback (incorrect) - questionIndex:", a.current.currentQuestionIndex, "totalQuestions:", V, "hasNextQuestion:", Q);
7993
+ const K = R.type === "code_test" ? `Your code didn't pass all the tests. ${R.explanation || "Try again!"}` : `Not quite right, but don't worry! ${R.explanation || ""}${J ? "" : " Let's move on to the next question."}`, Ae = C.current || { lipsyncLang: "en" };
7994
+ u.current.speakText(K, {
8009
7995
  lipsyncLang: Ae.lipsyncLang,
8010
7996
  onSpeechEnd: () => {
8011
7997
  d.current.onCustomAction({
@@ -8014,7 +8000,7 @@ const yt = Me(({
8014
8000
  lessonIndex: a.current.currentLessonIndex,
8015
8001
  questionIndex: a.current.currentQuestionIndex,
8016
8002
  isCorrect: !1,
8017
- hasNextQuestion: j,
8003
+ hasNextQuestion: Q,
8018
8004
  score: a.current.score,
8019
8005
  totalQuestions: a.current.totalQuestions
8020
8006
  });
@@ -8022,20 +8008,20 @@ const yt = Me(({
8022
8008
  });
8023
8009
  }
8024
8010
  else {
8025
- const P = y()?.questions?.length || 0;
8011
+ const V = y()?.questions?.length || 0;
8026
8012
  d.current.onCustomAction({
8027
8013
  type: "answerFeedbackComplete",
8028
8014
  moduleIndex: a.current.currentModuleIndex,
8029
8015
  lessonIndex: a.current.currentLessonIndex,
8030
8016
  questionIndex: a.current.currentQuestionIndex,
8031
- isCorrect: T,
8032
- hasNextQuestion: a.current.currentQuestionIndex < P - 1,
8017
+ isCorrect: H,
8018
+ hasNextQuestion: a.current.currentQuestionIndex < V - 1,
8033
8019
  score: a.current.score,
8034
8020
  totalQuestions: a.current.totalQuestions,
8035
8021
  avatarNotReady: !0
8036
8022
  });
8037
8023
  }
8038
- }, [e.correct, e.incorrect, I, y, z]), ie = O((v) => {
8024
+ }, [e.correct, e.incorrect, I, y, z]), se = B((v) => {
8039
8025
  const R = I();
8040
8026
  if (!v || typeof v != "object") {
8041
8027
  console.error("Invalid code test result format. Expected object with {passed: boolean, ...}");
@@ -8045,7 +8031,7 @@ const yt = Me(({
8045
8031
  console.warn("Current question is not a code test. Use handleAnswerSelect for other question types.");
8046
8032
  return;
8047
8033
  }
8048
- const T = {
8034
+ const H = {
8049
8035
  passed: v.passed === !0,
8050
8036
  results: v.results || [],
8051
8037
  output: v.output || "",
@@ -8060,10 +8046,10 @@ const yt = Me(({
8060
8046
  moduleIndex: a.current.currentModuleIndex,
8061
8047
  lessonIndex: a.current.currentLessonIndex,
8062
8048
  questionIndex: a.current.currentQuestionIndex,
8063
- testResult: T,
8049
+ testResult: H,
8064
8050
  question: R
8065
- }), p.current && p.current(T);
8066
- }, [I, z]), oe = O(() => {
8051
+ }), p.current && p.current(H);
8052
+ }, [I, z]), ae = B(() => {
8067
8053
  if (a.current.currentQuestionIndex > 0) {
8068
8054
  a.current.currentQuestionIndex -= 1;
8069
8055
  const v = I();
@@ -8079,26 +8065,26 @@ const yt = Me(({
8079
8065
  const R = () => {
8080
8066
  if (!u.current || !v) return;
8081
8067
  u.current.setMood("happy"), u.current.setBodyMovement("idle");
8082
- const T = H.current || { lipsyncLang: "en" };
8068
+ const H = C.current || { lipsyncLang: "en" };
8083
8069
  v.type === "code_test" ? u.current.speakText(`Let's go back to this coding challenge: ${v.question}`, {
8084
- lipsyncLang: T.lipsyncLang
8070
+ lipsyncLang: H.lipsyncLang
8085
8071
  }) : u.current.speakText(`Going back to: ${v.question}`, {
8086
- lipsyncLang: T.lipsyncLang
8072
+ lipsyncLang: H.lipsyncLang
8087
8073
  });
8088
8074
  };
8089
8075
  if (u.current && u.current.isReady && v)
8090
8076
  R();
8091
8077
  else if (v) {
8092
- const T = setInterval(() => {
8093
- u.current && u.current.isReady && (clearInterval(T), R());
8078
+ const H = setInterval(() => {
8079
+ u.current && u.current.isReady && (clearInterval(H), R());
8094
8080
  }, 100);
8095
8081
  setTimeout(() => {
8096
- clearInterval(T);
8082
+ clearInterval(H);
8097
8083
  }, 5e3);
8098
8084
  }
8099
8085
  }
8100
- }, [I]), he = O(() => {
8101
- const v = B.current || { modules: [] };
8086
+ }, [I]), pe = B(() => {
8087
+ const v = F.current || { modules: [] };
8102
8088
  if (v.modules[a.current.currentModuleIndex], a.current.currentLessonIndex > 0)
8103
8089
  a.current.currentLessonIndex -= 1, a.current.currentQuestionIndex = 0, a.current.lessonCompleted = !1, a.current.isQuestionMode = !1, a.current.isTeaching = !1, a.current.score = 0, a.current.totalQuestions = 0, d.current.onCustomAction({
8104
8090
  type: "lessonStart",
@@ -8110,8 +8096,8 @@ const yt = Me(({
8110
8096
  lesson: y()
8111
8097
  }), u.current && (u.current.setMood("happy"), u.current.setBodyMovement("idle"));
8112
8098
  else if (a.current.currentModuleIndex > 0) {
8113
- const F = v.modules[a.current.currentModuleIndex - 1];
8114
- a.current.currentModuleIndex -= 1, a.current.currentLessonIndex = (F?.lessons?.length || 1) - 1, a.current.currentQuestionIndex = 0, a.current.lessonCompleted = !1, a.current.isQuestionMode = !1, a.current.isTeaching = !1, a.current.score = 0, a.current.totalQuestions = 0, d.current.onCustomAction({
8099
+ const P = v.modules[a.current.currentModuleIndex - 1];
8100
+ a.current.currentModuleIndex -= 1, a.current.currentLessonIndex = (P?.lessons?.length || 1) - 1, a.current.currentQuestionIndex = 0, a.current.lessonCompleted = !1, a.current.isQuestionMode = !1, a.current.isTeaching = !1, a.current.score = 0, a.current.totalQuestions = 0, d.current.onCustomAction({
8115
8101
  type: "lessonStart",
8116
8102
  moduleIndex: a.current.currentModuleIndex,
8117
8103
  lessonIndex: a.current.currentLessonIndex
@@ -8121,30 +8107,30 @@ const yt = Me(({
8121
8107
  lesson: y()
8122
8108
  }), u.current && (u.current.setMood("happy"), u.current.setBodyMovement("idle"));
8123
8109
  }
8124
- }, [y]), ee = O(() => {
8110
+ }, [y]), te = B(() => {
8125
8111
  a.current.currentModuleIndex = 0, a.current.currentLessonIndex = 0, a.current.currentQuestionIndex = 0, a.current.isTeaching = !1, a.current.isQuestionMode = !1, a.current.lessonCompleted = !1, a.current.curriculumCompleted = !1, a.current.score = 0, a.current.totalQuestions = 0;
8126
- }, []), ne = O((v) => {
8112
+ }, []), le = B((v) => {
8127
8113
  console.log("Avatar is ready!", v);
8128
- const R = y(), T = R?.avatar_script || R?.body;
8129
- h && T && setTimeout(() => {
8114
+ const R = y(), H = R?.avatar_script || R?.body;
8115
+ h && H && setTimeout(() => {
8130
8116
  c.current && c.current();
8131
8117
  }, 10);
8132
8118
  }, [h, y]);
8133
8119
  Xe(() => {
8134
- c.current = N, g.current = q, b.current = A, x.current = C, S.current = Y, G.current = k, p.current = $;
8120
+ c.current = G, g.current = q, b.current = A, x.current = E, S.current = Y, U.current = k, p.current = ee;
8135
8121
  }), Fe(r, () => ({
8136
8122
  // Curriculum control methods
8137
- startTeaching: N,
8123
+ startTeaching: G,
8138
8124
  startQuestions: k,
8139
- handleAnswerSelect: $,
8140
- handleCodeTestResult: ie,
8141
- nextQuestion: C,
8142
- previousQuestion: oe,
8125
+ handleAnswerSelect: ee,
8126
+ handleCodeTestResult: se,
8127
+ nextQuestion: E,
8128
+ previousQuestion: ae,
8143
8129
  nextLesson: q,
8144
- previousLesson: he,
8130
+ previousLesson: pe,
8145
8131
  completeLesson: A,
8146
8132
  completeCurriculum: Y,
8147
- resetCurriculum: ee,
8133
+ resetCurriculum: te,
8148
8134
  getState: () => ({ ...a.current }),
8149
8135
  getCurrentQuestion: () => I(),
8150
8136
  getCurrentLesson: () => y(),
@@ -8153,8 +8139,8 @@ const yt = Me(({
8153
8139
  // Convenience methods that delegate to avatar (always check current ref)
8154
8140
  speakText: async (v, R = {}) => {
8155
8141
  await u.current?.resumeAudioContext?.();
8156
- const T = H.current || { lipsyncLang: "en" };
8157
- u.current?.speakText(v, { ...R, lipsyncLang: R.lipsyncLang || T.lipsyncLang });
8142
+ const H = C.current || { lipsyncLang: "en" };
8143
+ u.current?.speakText(v, { ...R, lipsyncLang: R.lipsyncLang || H.lipsyncLang });
8158
8144
  },
8159
8145
  resumeAudioContext: async () => {
8160
8146
  if (u.current?.resumeAudioContext)
@@ -8165,8 +8151,8 @@ const yt = Me(({
8165
8151
  if (R.state === "suspended" || R.state === "interrupted")
8166
8152
  try {
8167
8153
  await R.resume(), console.log("Audio context resumed via talkingHead");
8168
- } catch (T) {
8169
- console.warn("Failed to resume audio context:", T);
8154
+ } catch (H) {
8155
+ console.warn("Failed to resume audio context:", H);
8170
8156
  }
8171
8157
  } else
8172
8158
  console.warn("Audio context not available yet");
@@ -8198,8 +8184,8 @@ const yt = Me(({
8198
8184
  handleResize: () => u.current?.handleResize(),
8199
8185
  // Avatar readiness check (always returns current value)
8200
8186
  isAvatarReady: () => u.current?.isReady || !1
8201
- }), [N, k, $, ie, C, q, A, Y, ee, I, y]);
8202
- const D = H.current || {
8187
+ }), [G, k, ee, se, E, q, A, Y, te, I, y]);
8188
+ const W = C.current || {
8203
8189
  avatarUrl: "/avatars/brunette.glb",
8204
8190
  avatarBody: "F",
8205
8191
  mood: "happy",
@@ -8212,23 +8198,23 @@ const yt = Me(({
8212
8198
  showFullAvatar: !1,
8213
8199
  animations: e
8214
8200
  };
8215
- return /* @__PURE__ */ pe("div", { style: { width: "100%", height: "100%" }, children: /* @__PURE__ */ pe(
8201
+ return /* @__PURE__ */ me("div", { style: { width: "100%", height: "100%" }, children: /* @__PURE__ */ me(
8216
8202
  Ve,
8217
8203
  {
8218
8204
  ref: u,
8219
- avatarUrl: D.avatarUrl,
8220
- avatarBody: D.avatarBody,
8221
- mood: D.mood,
8222
- ttsLang: D.ttsLang,
8223
- ttsService: D.ttsService,
8224
- ttsVoice: D.ttsVoice,
8225
- ttsApiKey: D.ttsApiKey,
8226
- bodyMovement: D.bodyMovement,
8227
- movementIntensity: D.movementIntensity,
8228
- showFullAvatar: D.showFullAvatar,
8205
+ avatarUrl: W.avatarUrl,
8206
+ avatarBody: W.avatarBody,
8207
+ mood: W.mood,
8208
+ ttsLang: W.ttsLang,
8209
+ ttsService: W.ttsService,
8210
+ ttsVoice: W.ttsVoice,
8211
+ ttsApiKey: W.ttsApiKey,
8212
+ bodyMovement: W.bodyMovement,
8213
+ movementIntensity: W.movementIntensity,
8214
+ showFullAvatar: W.showFullAvatar,
8229
8215
  cameraView: "upper",
8230
- animations: D.animations,
8231
- onReady: ne,
8216
+ animations: W.animations,
8217
+ onReady: le,
8232
8218
  onLoading: () => {
8233
8219
  },
8234
8220
  onError: (v) => {