warrior 2 månader sedan
förälder
incheckning
502c6046e0

+ 1 - 0
angular.json

@@ -133,6 +133,7 @@
             "assets": [
               "projects/live-app/src/assets/js/AgoraRTC_N-4.14.0.js",
               "projects/live-app/src/assets/js/agora-rtm-2.2.0.min.js",
+              "projects/live-app/src/assets/js/vap.min.js",
               {
                 "glob": "**/*",
                 "input": "projects/live-app/public"

+ 1 - 0
package.json

@@ -28,6 +28,7 @@
     "parse": "^5.3.0",
     "qiniu-js": "^3.1.2",
     "rxjs": "~7.8.0",
+    "svgaplayerweb": "^2.3.2",
     "swiper": "^11.1.14",
     "tslib": "^2.3.0",
     "zone.js": "~0.14.3"

BIN
projects/live-app/public/svga/102599头像框.svga


BIN
projects/live-app/public/video/圣诞福袋1334.mp4


+ 1 - 1
projects/live-app/src/app/components/avatar/avatar.component.html

@@ -1,6 +1,5 @@
 <div
   class="pendant"
-  [style.background-image]="'url(' + frame + ')'"
   [style.height]="frameWt + 'px'"
   [style.width]="frameWt + 'px'"
 >
@@ -11,4 +10,5 @@
     [src]="avatar"
     alt=""
   />
+  <div class="frame-item1" [id]="frameId"></div>
 </div>

+ 10 - 2
projects/live-app/src/app/components/avatar/avatar.component.scss

@@ -5,10 +5,18 @@
   justify-content: center;
   align-items: center;
   background-size: 100% 100%;
+  position: relative;
   .avatar {
-    width: 60px;
-    height: 60px;
+    width: 48px;
+    height: 48px;
     z-index: 1;
     border-radius: 50%;
   }
+  .frame-item1{
+    position: absolute;
+    top: 0;
+    left: 0;
+    width: 100%;
+    height: 100%;
+  }
 }

+ 39 - 7
projects/live-app/src/app/components/avatar/avatar.component.ts

@@ -1,5 +1,5 @@
 import { Component, Input, OnInit } from '@angular/core';
-
+import SVGA from 'svgaplayerweb';
 @Component({
   selector: 'app-avatar',
   templateUrl: './avatar.component.html',
@@ -7,14 +7,46 @@ import { Component, Input, OnInit } from '@angular/core';
   standalone: true,
 })
 export class AvatarComponent implements OnInit {
-  @Input('avatar') avatar: string = 'https://file-cloud.fmode.cn/DXNgcD6zo6/20221202/j6p8kb034039.png' //头像
-  @Input('frame') frame: string = 'https://file-cloud.fmode.cn/Qje9D4bqol/20241109/vv1tvb032259054.png' //头像框
-  @Input('frameWt') frameWt: number = 80 //外框大小
-  @Input('avatarWt') avatarWt: number = 60 //头像大小
+  @Input('avatar') avatar: string =
+    'https://file-cloud.fmode.cn/DXNgcD6zo6/20221202/j6p8kb034039.png'; //头像
+  @Input('frame') frame: string = '/svga/102599头像框.svga'; //头像框
+  @Input('frameId') frameId: string = 'avatar-frame'; //头像框id
+
+  @Input('frameWt') frameWt: number = 80; //外框大小
+  @Input('avatarWt') avatarWt: number = 48; //头像大小
+
+  player: any; //头像框动画
 
-  constructor() { }
+  constructor() {}
 
   ngOnInit() {
+    setTimeout(() => {
+      console.log('init-avatar');
+      this.initSVGA();
+    }, 0);
+  }
+  ngOnDestroy(): void {
+    this.player.clearDynamicObjects();
+    delete this.player;
+  }
+  initSVGA() {
+    this.player = new SVGA.Player(`#${this.frameId}`);
+    this.player.clearsAfterStop = false;
+    this.player.onFinished(() => {
+      console.log('finished');
+    });
+    // this.player.onPercentage((val:any)=> console.log(val))
+    let parser = new SVGA.Parser(); // 如果你需要支持 IE6+,那么必须把同样的选择器传给 Parser。
+    parser.load(
+      this.frame,
+      (videoItem) => {
+        console.log('load success');
+        this.player.setVideoItem(videoItem);
+        this.player.startAnimation();
+      },
+      (err) => {
+        console.error('头像框加载错误:',err);
+      }
+    );
   }
-
 }

+ 3 - 2
projects/live-app/src/app/components/gift-modal/gift-modal.component.html

@@ -79,8 +79,9 @@
     </div>
   </ng-template>
 </ion-modal>
-@if (isShowGiftModal) {
+<!-- @if (isShowGiftModal) {
 <div class="modal-gift-img" (click)="onCloseGiftModal()">
   <img [src]="currentGift?.imgUrl" alt="" />
 </div>
-}
+} -->
+<div id="vap-warp"></div>

+ 5 - 0
projects/live-app/src/app/components/gift-modal/gift-modal.component.scss

@@ -151,4 +151,9 @@
     transform: scale(1.2); /* 放大到原始大小 */
     bottom: 102.5641vw;
   }
+}
+#vap-warp{
+  position: fixed;
+  top: 0;
+  z-index: 999;
 }

+ 51 - 14
projects/live-app/src/app/components/gift-modal/gift-modal.component.ts

@@ -11,6 +11,8 @@ import {
 } from '../../../modules/ionic-standalone.modules';
 import { AccountService } from '../../../services/account.service';
 import { MessageService } from '../../../services/message.service';
+// import Vap from 'video-animation-player'
+declare const Vap: any;
 @Component({
   selector: 'app-gift-modal',
   templateUrl: './gift-modal.component.html',
@@ -52,10 +54,11 @@ export class GiftModalComponent implements OnInit {
     private loadingCtrl: LoadingController,
     public accServ: AccountService,
     public msgSerrvice: MessageService
-    ) {}
-
+  ) {
+  }
   async ngOnInit() {
-    this.giftList = this.msgSerrvice.giftList
+    this.giftList = this.msgSerrvice.giftList;
+    // this.initPlayer()
   }
   async openModal() {
     let uid: any = Parse.User.current()?.id;
@@ -102,13 +105,14 @@ export class GiftModalComponent implements OnInit {
                 loading.dismiss();
                 _this.sendEmit.emit(); //触发父组件的sendEmit事件
                 _this.isOpenGift = false;
-                _this.isShowGiftModal = true;
+                // _this.isShowGiftModal = true;
                 _this.publishGiftMessage(_this.currentGift.id, _this.giftCount);
-                setTimeout(() => {
-                  _this.isShowGiftModal = false;
-                  console.log(_this.isShowGiftModal);
-                  console.log('5s后关闭');
-                }, 5000);
+                // setTimeout(() => {
+                //   _this.isShowGiftModal = false;
+                //   console.log(_this.isShowGiftModal);
+                //   console.log('5s后关闭');
+                // }, 5000);
+                this.initPlayer()
               })
               .catch((err) => {
                 _this.isOpenGift = false;
@@ -121,15 +125,48 @@ export class GiftModalComponent implements OnInit {
     });
     await alert.present();
   }
-  onCloseGiftModal(){
-    if(!this.isShowGiftModal) this.isShowGiftModal = false
+
+  
+  initPlayer(){
+    let json = this.currentGift.config
+    // json = {"info":{"v":2,"f":56,"w":750,"h":1334,"fps":15,"videoW":1136,"videoH":1344,"aFrame":[754,0,375,667],"rgbFrame":[0,0,750,1334],"isVapx":0,"orien":0}}
+    let dom = document.getElementById('vap-warp');
+    let vapPlayer = new Vap.default({
+      container: dom, // 要渲染的载体,dom元素
+      src: this.currentGift.video, // vap动画地址
+      config: json, // 播放vap动画需要的 json文件。必填
+      width: window.innerWidth, // 容器宽度
+      height: window.innerHeight, // 容器高度
+      fps: 30, // 帧数,json文件中有这个视频的帧数的,可以看一下,
+      mute: true, // 静音
+      type: 2, // 组件基于type字段做了实例化缓存,不同的VAP实例应该使用不同的type值(如0、1、2等)
+      loop: false, // 循环
+      precache: true, // 预加载视频,下载完再播。小动画建议边下边播,大动画还是先下后播吧,因为太大了或者网络不好,会一卡一卡的。
+      beginPoint: 0, // 起始播放时间点(单位秒),在一些浏览器中可能无效
+      accurate: true, // 是否启用精准模式(使用requestVideoFrameCallback提升融合效果,浏览器不兼容时自动降级)
+    });
+    vapPlayer.play(); // 开始播放
+    vapPlayer.on('ended', () => {
+      // 监听播放完成的事件
+      vapPlayer.destroy();
+      vapPlayer = null;
+      console.log(123);
+    });
+    vapPlayer.on('playering', function() { console.log('playering'); })
+  }
+
+  onCloseGiftModal() {
+    if (!this.isShowGiftModal) this.isShowGiftModal = false;
   }
 
-  publishGiftMessage(gid:string,count:number) {
+  publishGiftMessage(gid: string, count: number) {
     this.msgSerrvice.subscribeMessage(this.toUid, {
       message: true,
       presence: true,
-    }); //进入对方主播频道发送聊天邀请
-    this.msgSerrvice.publishMessage(`ONUSERSENDGIFT_${gid}_${count}`,this.toUid);
+    }); //触发礼物消息
+    this.msgSerrvice.publishMessage(
+      `ONUSERSENDGIFT_${gid}_${count}`,
+      this.toUid
+    );
   }
 }

Filskillnaden har hållts tillbaka eftersom den är för stor
+ 0 - 0
projects/live-app/src/assets/js/vap.min.js


+ 1 - 0
projects/live-app/src/index.html

@@ -11,6 +11,7 @@
 	<script type="text/javascript" src="https://res.wx.qq.com/open/js/jweixin-1.6.0.js"></script>
   <script src="assets/js/AgoraRTC_N-4.14.0.js"></script>
   <script src="assets/js/agora-rtm-2.2.0.min.js"></script>
+  <script src="assets/js/vap.min.js"></script>
 </head>
 <body>
   <app-root></app-root>

+ 1 - 0
projects/live-app/src/modules/user/profile/profile.component.html

@@ -23,6 +23,7 @@
           <app-avatar
             [avatar]="profile?.get('user')?.get('avatar')"
             style="z-index: 99"
+            frameId="profile-avatar-frame"
           />
           <div class="top-right-block">
             <div class="top-left-title">{{ profile?.get("name") }}</div>

+ 1 - 1
projects/live-app/src/services/aichart.service.ts

@@ -156,7 +156,7 @@ export class AiChatService {
   }
   async getGift(type?: string): Promise<any> {
     let where = type ? `AND "type" = '${type}'` : '';
-    let sql = `SELECT "objectId" AS "id","name","price","order","imgUrl","type","rightsMap"
+    let sql = `SELECT "objectId" AS "id","name","price","order","imgUrl","video","type","rightsMap","config"
     FROM "GiftModule"
     WHERE "company" = '${this.company}'
     ${where}

Vissa filer visades inte eftersom för många filer har ändrats