XAvatar.js 14 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424
  1. //const log$E = new Logger$1("Avatar")
  2. import BillboardStatus from "./enum/BillboardStatus.js"
  3. import {avatarLoader} from "./XAvatarLoader.js"
  4. import XAnimationController from "./XAnimationController.js"
  5. import XAvatarComopnent from "./XAvatarComopnent.js"
  6. import XStateMachine from "./XStateMachine.js"
  7. import XAvatarBillboardComponent from "./XAvatarBillboardComponent.js"
  8. import util from "./util.js"
  9. const castRayOffsetY = .01;
  10. const castRayTeleportationOffset = 10;
  11. export default class XAvatar {
  12. constructor({id: e, avatarType: t, priority: r, avatarManager: n, assets: o, status: a}) {
  13. E(this, "id", "-1");
  14. E(this, "priority", 0);
  15. E(this, "isRender", !1);
  16. E(this, "distLevel", 0);
  17. E(this, "isInLoadingList", !1);
  18. E(this, "isHide", !1);
  19. E(this, "component");
  20. E(this, "controller");
  21. E(this, "stateMachine");
  22. E(this, "bbComponent");
  23. E(this, "_avatarType");
  24. E(this, "clothesList", []);
  25. E(this, "isSelected", !1);
  26. E(this, "pendingLod", !1);
  27. E(this, "_previousReceivedPosition", new BABYLON.Vector3(0,1e4,0));
  28. E(this, "_avatarPosition");
  29. E(this, "_avatarRotation");
  30. E(this, "_avatarScale");
  31. E(this, "rootNode");
  32. E(this, "distToCam", 1e11);
  33. E(this, "enableNickname", !0);
  34. E(this, "distance", 1e11);
  35. E(this, "isCulling", !1);
  36. E(this, "reslevel", 0);
  37. E(this, "isInLoadingQueue", !1);
  38. E(this, "_isRayCastEnable");
  39. E(this, "_scene");
  40. E(this, "_avatarManager");
  41. E(this, "_transparent", 0);
  42. E(this, "hide", ()=>(this.isHide = !0,
  43. this._hide(),
  44. !this.isRender));
  45. E(this, "_show", ()=>{
  46. var e;
  47. this.isHide || (this.setIsPickable(!0),
  48. this.priority == 0 && (this.rootNode.setEnabled(!0),
  49. this.isRender = !0,
  50. this.avatarManager._updateBillboardStatus(this, BillboardStatus.SHOW),
  51. (e = this.controller) == null || e.playAnimation(this.controller.onPlay, this.controller.loop)))
  52. }
  53. );
  54. E(this, "show", ()=>(this.isHide = !1,
  55. this._show(),
  56. !!this.isRender));
  57. E(this, "setAnimations", e=>{
  58. this.controller.animations = e
  59. }
  60. );
  61. E(this, "attachToAvatar", (e,t=!1,r={
  62. x: 0,
  63. y: 0,
  64. z: 0
  65. },n=!1,o,a)=>this.bbComponent.attachToAvatar(this, e, t, r, n, o, a));
  66. E(this, "detachFromAvatar", (e,t=!1)=>this.bbComponent.detachFromAvatar(this, e, t));
  67. E(this, "getBbox", (e={})=>this.bbComponent.getBbox(this, e));
  68. this.id = e,
  69. this._avatarManager = n,
  70. this._scene = this.avatarManager.scene,
  71. this.clothesList = o,
  72. this._avatarType = t,
  73. this.priority = r || 0,
  74. this.controller = new XAnimationController(this),
  75. this.component = new XAvatarComopnent,
  76. this.stateMachine = new XStateMachine(this._scene),
  77. this.bbComponent = new XAvatarBillboardComponent(this._scene),
  78. this.rootNode = new BABYLON.TransformNode(e,this._avatarManager.scene),
  79. this._avatarScale = a.avatarScale == null ? 1 : a.avatarScale,
  80. this._avatarRotation = a.avatarRotation == null ? {
  81. pitch: 0,
  82. yaw: 0,
  83. roll: 0
  84. } : a.avatarRotation,
  85. this._avatarPosition = a.avatarPosition == null ? {
  86. x: 0,
  87. y: 0,
  88. z: 0
  89. } : a.avatarPosition,
  90. this.setPosition(this._avatarPosition),
  91. this.setRotation(this._avatarRotation),
  92. this.setScale(this.scale),
  93. this._isRayCastEnable = avatarSetting.isRayCastEnable,
  94. this._scene.registerBeforeRender(()=>{
  95. this.tick()
  96. }
  97. )
  98. }
  99. tick() {
  100. this.cullingTick()
  101. }
  102. cullingTick() {
  103. var e;
  104. this.isCulling && ((e = this.rootNode) == null || e.getChildMeshes().forEach(t=>{
  105. this.distToCam < 50 ? t.visibility = 0 : t.visibility = this._transparent
  106. }
  107. ))
  108. }
  109. setTransParentThresh(e) {
  110. this._transparent = e
  111. }
  112. get isNameVisible() {
  113. return this.bbComponent.isNameVisible
  114. }
  115. get isBubbleVisible() {
  116. return this.bbComponent.isBubbleVisible
  117. }
  118. get isGiftButtonsVisible() {
  119. return this.bbComponent.isGiftButtonsVisible
  120. }
  121. get words() {
  122. return this.bbComponent.words
  123. }
  124. get nickName() {
  125. return this.bbComponent.nickName
  126. }
  127. get giftButtons() {
  128. return this.bbComponent.giftButtons
  129. }
  130. get bubble() {
  131. return this.bbComponent.bubble
  132. }
  133. get nameBoard() {
  134. return this.bbComponent.nameBoard
  135. }
  136. get avatarManager() {
  137. return this._avatarManager
  138. }
  139. set withinVisibleRange(e) {
  140. this.bbComponent.withinVisualRange = e
  141. }
  142. setNicknameStatus(e) {
  143. return this.bbComponent.setNicknameStatus(e)
  144. }
  145. setBubbleStatus(e) {
  146. return this.bbComponent.setBubbleStatus(e)
  147. }
  148. setButtonsStatus(e) {
  149. return this.bbComponent.setBubbleStatus(e)
  150. }
  151. setGiftButtonsVisible(e) {
  152. return this.bbComponent.setGiftButtonsVisible(e)
  153. }
  154. get avatarType() {
  155. return this._avatarType
  156. }
  157. attachBody(e) {
  158. return this.component.addBodyComp(this, e)
  159. }
  160. attachDecoration(e) {
  161. return this.component.addClothesComp(this, e)
  162. }
  163. detachDecoration(e) {
  164. return this.component.clearClothesComp(e)
  165. }
  166. detachDecorationAll() {
  167. return this.component.clearAllClothesComps()
  168. }
  169. get skeleton() {
  170. return this.component.skeleton
  171. }
  172. get position() {
  173. return this._avatarPosition
  174. }
  175. get rotation() {
  176. return this._avatarRotation
  177. }
  178. get scale() {
  179. return this._avatarScale
  180. }
  181. _hide_culling() {
  182. this.bbComponent.updateBillboardStatus(this, BillboardStatus.HIDE),
  183. this.isCulling = !0
  184. }
  185. _show_culling() {
  186. this.isCulling && (this.rootNode && this.rootNode.getChildMeshes().forEach(e=>{
  187. e.visibility = 1
  188. }
  189. ),
  190. this.bbComponent.updateBillboardStatus(this, BillboardStatus.SHOW),
  191. this.isCulling = !1)
  192. }
  193. _hide() {
  194. !this.isHide || (this.setIsPickable(!1),
  195. this.priority == 0 ? (this.rootNode.setEnabled(!1),
  196. this.isRender = !1,
  197. this.bbComponent.updateBillboardStatus(this, BillboardStatus.HIDE)) : this.isRender && (this.avatarManager.currentLODUsers[this.distLevel]--,
  198. this.removeAvatarFromScene()))
  199. }
  200. rotate(e, t, r) {
  201. return this.stateMachine.roll(this, e, t, r)
  202. }
  203. set isRayCastEnable(e) {
  204. this._isRayCastEnable = e
  205. }
  206. get isRayCastEnable() {
  207. return this._isRayCastEnable
  208. }
  209. getAvatarId() {
  210. return this.id
  211. }
  212. getAvaliableAnimations() {
  213. const e = avatarLoader.avaliableAnimation.get(this.avatarType);
  214. return e || []
  215. }
  216. setPosition(e, t=!1) {
  217. this._avatarPosition = e;
  218. if (this.rootNode) {
  219. const r = util.ue4Position2Xverse(this._avatarPosition);
  220. let n = !1;
  221. if(this.avatarManager.getMainAvatar()){
  222. if(this.id == this.avatarManager.getMainAvatar().id){
  223. Math.abs(r.y - this._previousReceivedPosition.y) > castRayOffsetY && (n = !0);
  224. if(r.subtract(this._previousReceivedPosition).length() > castRayTeleportationOffset){
  225. n = !0
  226. }
  227. }
  228. }
  229. this._isRayCastEnable ? n || t ? this._castRay(e).then(o=>{
  230. this.rootNode.position = r,
  231. this.rootNode.position.y -= o
  232. }
  233. ).catch(o=>{
  234. Promise.reject(o)
  235. }
  236. ) : (this.rootNode.position.x = r.x,
  237. this.rootNode.position.z = r.z) : this.rootNode.position = r,
  238. this._previousReceivedPosition = r.clone()
  239. }
  240. return Promise.resolve(e)
  241. }
  242. setRotation(e) {
  243. this._avatarRotation = e;
  244. if (this.rootNode) {
  245. const t = {
  246. pitch: e.pitch,
  247. yaw: e.yaw + 180,
  248. roll: e.roll
  249. }
  250. const r = util.ue4Rotation2Xverse(t);
  251. this.rootNode.rotation = r
  252. }
  253. }
  254. setAvatarVisible(e) {
  255. if(this.rootNode){
  256. this.rootNode.setEnabled(e),
  257. this.rootNode.getChildMeshes().forEach(t=>{
  258. t.setEnabled(e)
  259. })
  260. }
  261. }
  262. setScale(e) {
  263. this._avatarScale = e,
  264. this.rootNode && (this.rootNode.scaling = new BABYLON.Vector3(e,e,e)),
  265. this.bbComponent.bbox && this.getBbox()
  266. }
  267. _removeAvatarFromScene() {
  268. var e, t;
  269. this.isRender = !1,
  270. (e = this.controller) == null || e.detachAnimation(),
  271. this.component.dispose(this),
  272. (t = this.avatarManager.sceneManager) == null || t.lightComponent.removeShadow(this)
  273. }
  274. removeAvatarFromScene() {
  275. this._removeAvatarFromScene(),
  276. this._disposeBillBoard()
  277. }
  278. _disposeBillBoard() {
  279. this.bbComponent.disposeBillBoard(this)
  280. }
  281. addComponent(e, t, r, n) {
  282. return this.component.changeClothesComp(this, e, t, r, n)
  283. }
  284. _castRay(e) {
  285. return new Promise((t,r)=>{
  286. var d;
  287. const n = util.ue4Position2Xverse(e)
  288. , o = new BABYLON.Vector3(0,-1,0)
  289. , a = 1.5 * this.scale
  290. , s = 100 * a
  291. , l = a
  292. , u = new BABYLON.Vector3(n.x,n.y + l,+n.z)
  293. , c = new BABYLON.Ray(u,o,s)
  294. , h = (d = this.avatarManager.sceneManager) == null ? void 0 : d.getGround(e);
  295. if (!h || h.length <= 0)
  296. return logger.warn(`\u89D2\u8272 id= ${this.id} \u627E\u4E0D\u5230\u5730\u9762\uFF0C\u5F53\u524D\u9AD8\u5EA6\u4E3A\u4E0B\u53D1\u9AD8\u5EA6`),
  297. t(0);
  298. let f = c.intersectsMeshes(h);
  299. if (f.length > 0)
  300. return t(f[0].distance - l);
  301. if (o.y = 1,
  302. f = c.intersectsMeshes(h),
  303. f.length > 0)
  304. return t(-(f[0].distance - l))
  305. }
  306. )
  307. }
  308. setPickBoxScale(e) {
  309. return this.bbComponent.setPickBoxScale(e)
  310. }
  311. setIsPickable(e) {
  312. return this.bbComponent.setIsPickable(this, e)
  313. }
  314. createPickBoundingbox(e) {
  315. return this.bbComponent.createPickBoundingbox(this, e)
  316. }
  317. scaleBbox(e) {
  318. this.bbComponent.bbox && this.bbComponent.bbox.scale(e)
  319. }
  320. rotateTo(e, t, r) {
  321. return this.stateMachine.rotateTo(this, e, t, r)
  322. }
  323. faceTo(e, t) {
  324. return this.stateMachine.lookAt(this, e, t)
  325. }
  326. removeObserver() {
  327. this.stateMachine.disposeObsever()
  328. }
  329. move(e, t, r, n, o) {
  330. return this.stateMachine.moveTo(this, e, t, r, n, o)
  331. }
  332. initNameboard(e=1) {
  333. return this.bbComponent.initNameboard(this, e)
  334. }
  335. initBubble(e=1) {
  336. return this.bbComponent.initBubble(this, e)
  337. }
  338. say(e, {id: t, isUser: r, background: n, font: o="Arial", fontsize: a=38, fontcolor: s="#ffffff", fontstyle: l="bold", linesize: u=22, linelimit: c, offsets: h={
  339. x: 0,
  340. y: 0,
  341. z: 40
  342. }, scale: f=this._avatarScale, compensationZ: d=11.2, reregistAnyway: _=!0}) {
  343. return this.bbComponent.say(this, e, {
  344. id: t,
  345. isUser: r,
  346. background: n,
  347. font: o,
  348. fontsize: a,
  349. fontcolor: s,
  350. fontstyle: l,
  351. linesize: u,
  352. linelimit: c,
  353. offsets: h,
  354. scale: f,
  355. compensationZ: d,
  356. reregistAnyway: _
  357. })
  358. }
  359. silent() {
  360. return this.bbComponent.silent()
  361. }
  362. setNickName(e, {id: t, isUser: r, background: n, font: o="Arial", fontsize: a=40, fontcolor: s="#ffffff", fontstyle: l="bold", linesize: u=22, linelimit: c, offsets: h={
  363. x: 0,
  364. y: 0,
  365. z: 15
  366. }, scale: f=this._avatarScale, compensationZ: d=0, reregistAnyway: _=!1}) {
  367. return this.bbComponent.setNickName(this, e, {
  368. id: t,
  369. isUser: r,
  370. background: n,
  371. font: o,
  372. fontsize: a,
  373. fontcolor: s,
  374. fontstyle: l,
  375. linesize: u,
  376. linelimit: c,
  377. offsets: h,
  378. scale: f,
  379. compensationZ: d,
  380. reregistAnyway: _
  381. })
  382. }
  383. generateButtons(e=null, t=this._avatarScale, r=85) {
  384. return this.bbComponent.generateButtons(this, e, t, r)
  385. }
  386. clearButtons() {
  387. return this.bbComponent.clearButtons()
  388. }
  389. attachExtraProp(e, t, r, n) {
  390. return this.component.addDecoComp(this, e, t, r, n)
  391. }
  392. showExtra(e) {
  393. return this.component.showExtra(e)
  394. }
  395. hideExtra(e) {
  396. return this.component.hideExtra(e)
  397. }
  398. disposeExtra() {
  399. return this.component.disposeExtra()
  400. }
  401. getSkeletonPositionByName(e) {
  402. var t;
  403. if (this.skeleton) {
  404. const r = this.skeleton.bones.find(n=>n.name.replace("Clone of ", "") == e);
  405. if (r && r.getTransformNode() && ((t = r.getTransformNode()) == null ? void 0 : t.position)) {
  406. const n = r.getTransformNode().position;
  407. return util.xversePosition2Ue4({
  408. x: n.x,
  409. y: n.y,
  410. z: n.z
  411. })
  412. }
  413. }
  414. }
  415. shootTo(e, t, r=2, n=10, o={
  416. x: 0,
  417. y: 0,
  418. z: 150
  419. }) {
  420. return this.stateMachine.sendObjectTo(this, e, t, r, n, o)
  421. }
  422. }