当前位置: 首页 > news >正文

vue3+ts封装类似于微信消息的组件

组件代码如下:

<template><div:class="['voice-message', { sent: isSent, received: !isSent }]":style="{ backgroundColor: backgroundColor }"@click="togglePlayback"><!-- isSent为false在左侧,为true在右侧--><!-- 语言条要按照语音时长显示不同的宽度,所以增加了一块宽度,发送者的时候,加在左侧,接收者的时候,加在右侧--><div v-if="isSent" :style="`width:${(duration / 10) * 30}px`"></div><span class="duration" v-if="isSent">{{ duration }}''&nbsp;</span><div :class="['voice-icon', { 'sent-icon': isSent }]"><div :class="['small']" :style="smallStyle"></div><div :class="['middle', { animate: isPlaying }]" :style="middleStyle"></div><div :class="['large', { animate: isPlaying }]" :style="largeStyle"></div></div><span class="duration" :style="{ color: iconColor }" v-if="!isSent">{{ duration }}&nbsp;''</span><div v-if="!isSent" :style="`width:${(duration / 10) * 30}px`"></div></div>
</template><script setup lang="ts">
import { ref, computed, withDefaults, onBeforeUnmount } from "vue";// 使用 withDefaults 提供默认值
const props = withDefaults(defineProps<{isSent?: boolean;iconColor?: string;backgroundColor?: string;smallSize?: number;middleSize?: number;largeSize?: number;duration?: number;audioSrc?: string;}>(),{isSent: false,iconColor: "#000000",backgroundColor: "",smallSize: 10,middleSize: 20,largeSize: 30,duration: 0,audioSrc: ""}
);const isPlaying = ref(false);
let audio: HTMLAudioElement | null = null;// 计算动态样式
const smallStyle = computed(() => ({color: props.iconColor,width: `${props.smallSize}px`,height: `${props.smallSize}px`,marginRight: -props.smallSize + "px"
}));const middleStyle = computed(() => ({color: props.iconColor,width: `${props.middleSize}px`,height: `${props.middleSize}px`,marginRight: -props.middleSize + "px"
}));const largeStyle = computed(() => ({color: props.iconColor,width: `${props.largeSize}px`,height: `${props.largeSize}px`,marginRight: "1px"
}));// 切换播放状态的函数
const togglePlayback = () => {if (isPlaying.value) {pauseVoice();} else {playVoice(props.audioSrc || "");}
};// 播放音频的函数
const playVoice = (voiceSrc: string) => {if (!voiceSrc) {console.error("音频源不能为空");return;}// 如果音频上下文不存在,则创建新的 HTMLAudioElementif (!audio) {audio = new Audio(voiceSrc);} else {audio.src = voiceSrc;}isPlaying.value = true;// 播放音频audio.play().catch(error => console.error("音频播放失败", error));// 监听播放结束事件audio.onended = () => {isPlaying.value = false;};
};// 暂停音频的函数
const pauseVoice = () => {isPlaying.value = false;if (audio) {audio.pause();}
};// 组件卸载时销毁音频上下文
onBeforeUnmount(() => {if (audio) {audio.pause();audio = null;}
});defineExpose({pauseVoice
});
</script><style scoped>
.voice-message {display: inline-flex;align-items: center;cursor: pointer;border-radius: 10px;padding: 4px 12px;
}.voice-message.sent {justify-content: flex-end;
}.voice-message.received {justify-content: flex-start;
}.voice-icon {display: flex;align-items: center;
}.voice-icon.sent-icon {transform: rotate(180deg);
}.small,
.middle,
.large {border-style: solid;border-top-color: transparent;border-left-color: transparent;border-bottom-color: transparent;border-radius: 50%;box-sizing: border-box;vertical-align: middle;display: inline-block;background-color: transparent; /* 默认背景颜色为透明 */
}.middle.animate {animation: show2 3s ease-in-out infinite;
}.large.animate {animation: show3 3s ease-in-out infinite;
}@keyframes show2 {0% {opacity: 0;}30% {opacity: 1;}100% {opacity: 0;}
}@keyframes show3 {0% {opacity: 0;}60% {opacity: 1;}100% {opacity: 0;}
}.duration {margin-left: 8px;font-size: 20px;color: #ffffff;font-weight: 400;
}
</style>

使用时:

<VoicePlayback:isSent="false"iconColor="#ffffff"backgroundColor="rgba(255 255 255 / 20%)":smallSize="5":middleSize="16":largeSize="28":duration="30"audioSrc="http://music.163.com/song/media/outer/url?id=447925558.mp3"
/>

相关文章:

vue3+ts封装类似于微信消息的组件

组件代码如下&#xff1a; <template><div:class"[voice-message, { sent: isSent, received: !isSent }]":style"{ backgroundColor: backgroundColor }"click"togglePlayback"><!-- isSent为false在左侧&#xff0c;为true在右…...

ES6 reduce方法详解:示例、应用场景与实用技巧

在JavaScript中&#xff0c;reduce 方法是一个非常强大的数组方法&#xff0c;它允许你将数组中的元素归并&#xff08;reduce&#xff09;为单个值。reduce 方法执行一个由你提供的reducer函数&#xff08;归并函数&#xff09;&#xff0c;将其结果汇总为单一的返回值。 一.…...

java后端保存的本地图片通过ip+端口直接访问

直接上代码吧 package com.ydx.emms.datapro.controller;import org.springframework.context.annotation.Configuration; import org.springframework.web.servlet.config.annotation.ResourceHandlerRegistry; import org.springframework.web.servlet.config.annotation.…...

2024 年高教社杯全国大学生数学建模竞赛B题4小问解题思路(第二版)

原文链接&#xff1a;https://www.cnblogs.com/qimoxuan/articles/18399415 问题 1&#xff1a;抽样检测方案设计 详细解题思路&#xff1a; 确定抽样检测目标&#xff1a;企业需要确定一个可接受的次品率上限&#xff08;标称值&#xff09;&#xff0c;以及在该次品率下&am…...

docker-nginx数据卷挂载

一、案例1-利用Nginx容器部署静态资源 1.1、需求: 创建Nginx容器&#xff0c; 修改nginx容器内的html目录下的index.html文件,查看变化将静态资源部署到nginx的html目录 1.2、修改html目录下的index.html文件,查看变化 因为docker运用得最小化系统环境&#xff0c;解决办法就…...

项目实战 ---- 商用落地视频搜索系统(8)---优化(2)---查询逻辑层优化

目录 背景 技术衡量与方案 一种可实现方案 可实现方案及设计描述 可能存在的问题 一种创新实现方案 方案的改良设计 策略公式 优化的实现 完整代码 代码解释 异常场景的考量 处理方式 运行注意事项 运行结果 结果优化对比与解释 背景 在项目实战 ---- 商用落地…...

山东大学机试试题合集

&#x1f370;&#x1f370;&#x1f370;高分篇已经涵盖了绝大多数的机试考点&#xff0c;由于临近预推免&#xff0c;各校的机试蜂拥而至&#xff0c;我们接下来先更一些各高校机试题合集&#xff0c;算是对前边学习成果的深入学习&#xff0c;也是对我们代码能力的锻炼。加油…...

餐厅食品留样管理系统小程序的设计

管理员账户功能包括&#xff1a;系统首页&#xff0c;个人中心&#xff0c;窗口负责人管理&#xff0c;窗口员工管理&#xff0c;冰柜管理&#xff0c;排班信息管理&#xff0c;留样食品管理&#xff0c;教育宣传管理&#xff0c;系统管理 微信端账号功能包括&#xff1a;系统…...

亚马逊运营:如何提高亚马逊销量和运营效率?

不少亚马逊卖家们为了扩大业务规模和提高销量&#xff0c;会创建多个卖家账户来同时运营多个亚马逊店铺。问题是&#xff0c;这种多店铺运营模式并非没有风险——亚马逊运营的一个重要方面就是账户的健康管理。一旦某个账户出现问题&#xff0c;亚马逊的算法就可能会启动关联检…...

设计模式背后的设计原则和思想

设计模式背后的设计原则和思想是一套指导我们如何设计高质量软件系统的准则和方法论。这些原则和思想不仅有助于提升软件的可维护性、可扩展性和可复用性&#xff0c;还能帮助开发团队更好地应对复杂多变的需求。以下是一些核心的设计原则和思想&#xff1a; 1. 设计原则 设计…...

项目总体框架

一.后端&#xff08;包装servlet&#xff09; 使用BaseServlet进行请求的初步处理&#xff08;利用继承进行执行这个&#xff09; 在BaseServlet中 处理请求的类型找到对象的方法&#xff0c;并使用注解找到参数名&#xff0c;执行参数自动注入。 package com.csdn.controlle…...

k8s Prometheus

一、部署 Prometheus kubectl create ns kube-ops# 创建 prometheus-cm.yaml apiVersion: v1 kind: ConfigMap metadata:name: prometheus-confignamespace: kube-ops data:prometheus.yml: |global:scrape_interval: 15s # 表示 prometheus 抓取指标数据的频率&#xff0c;默…...

glsl着色器学习(九)屏幕像素空间和设置颜色

在上一篇文章中&#xff0c;使用的是裁剪空间进行绘制&#xff0c;这篇文章使用屏幕像素空间的坐标进行绘制。 上一篇的顶点着色器大概是这样子的 回归一下顶点着色的主要任务&#xff1a; 通常情况下&#xff0c;顶点着色器会进行一系列的矩阵变换操作&#xff0c;将输入的顶…...

前端框架有哪些?

前言 用户体验是每个开发网站的企业中的重中之重。无论后台有多方面的操作和功能&#xff0c;用户的视图和体验都必须是无缝的最友好的。这需要使用前端框架来简化交互式、以用户为中心的网站的开发。 前端框架是一种用于简化Web开发的工具&#xff0c;它提供了一套预定义的代…...

分类预测|基于黑翅鸢优化轻量级梯度提升机算法数据预测Matlab程序BKA-LightGBM多特征输入多类别输出 含对比

分类预测|基于黑翅鸢优化轻量级梯度提升机算法数据预测Matlab程序BKA-LightGBM多特征输入多类别输出 含对比 文章目录 一、基本原理BKA&#xff08;Black Kite Algorithm&#xff09;的原理LightGBM分类预测模型的原理BKA与LightGBM的模型流程总结 二、实验结果三、核心代码四、…...

利用大模型实时提取和检索多模态数据探索-利用 Indexify 进行文档分析

概览 传统的文本提取方法常常无法理解非结构化内容&#xff0c;因此提取数据的数据往往是错误的。本文将探讨使用 Indexify&#xff0c;一个用于实时多模态数据提取的开源框架&#xff0c;来更好地分析pdf等非结构化文件。我将介绍如何设置 Indexify&#xff0c;包括服务器设置…...

函数式接口实现策略模式

函数式接口实现策略模式 1.案例背景 我们在日常开发中&#xff0c;大多会写if、else if、else 这样的代码&#xff0c;但条件太多时&#xff0c;往往嵌套无数层if else,阅读性很差&#xff0c;比如如下案例&#xff0c;统计学生的数学课程的成绩&#xff1a; 90-100分&#…...

鸿蒙Next-拉起支付宝的三种方式——教程

鸿蒙Next-拉起支付宝的三种方式——教程 鸿蒙Next系统即将上线&#xff0c;应用市场逐渐丰富、很多APP都准备接入支付宝做支付功能&#xff0c;目前来说有三种方式拉起支付宝&#xff1a;通过支付宝SDK拉起、使用OpenLink拉起、传入支付宝包名使用startAbility拉起。以上的三种…...

Vue.js 组件化开发:父子组件通信与组件注册详解

Vue.js 组件化开发&#xff1a;父子组件通信与组件注册详解 简介&#xff1a; 在 Vue.js 的开发中&#xff0c;组件是构建应用的重要基础。掌握组件的创建与使用&#xff0c;尤其是父子组件的通信和组件的注册与命名&#xff0c;是开发中不可或缺的技能。本文将详细探讨这些内容…...

【HTTP、Web常用协议等等】前端八股文面试题

HTTP、Web常用协议等等 更新日志 2024年9月5日 —— 什么情况下会导致浏览器内存泄漏&#xff1f; 文章目录 HTTP、Web常用协议等等更新日志1. 网络请求的状态码有哪些&#xff1f;1&#xff09;1xx 信息性状态码2&#xff09;2xx 成功状态码3&#xff09;3xx 重定向状态码4&…...

XCTF-web-easyupload

试了试php&#xff0c;php7&#xff0c;pht&#xff0c;phtml等&#xff0c;都没有用 尝试.user.ini 抓包修改将.user.ini修改为jpg图片 在上传一个123.jpg 用蚁剑连接&#xff0c;得到flag...

【Redis技术进阶之路】「原理分析系列开篇」分析客户端和服务端网络诵信交互实现(服务端执行命令请求的过程 - 初始化服务器)

服务端执行命令请求的过程 【专栏简介】【技术大纲】【专栏目标】【目标人群】1. Redis爱好者与社区成员2. 后端开发和系统架构师3. 计算机专业的本科生及研究生 初始化服务器1. 初始化服务器状态结构初始化RedisServer变量 2. 加载相关系统配置和用户配置参数定制化配置参数案…...

渲染学进阶内容——模型

最近在写模组的时候发现渲染器里面离不开模型的定义,在渲染的第二篇文章中简单的讲解了一下关于模型部分的内容,其实不管是方块还是方块实体,都离不开模型的内容 🧱 一、CubeListBuilder 功能解析 CubeListBuilder 是 Minecraft Java 版模型系统的核心构建器,用于动态创…...

Keil 中设置 STM32 Flash 和 RAM 地址详解

文章目录 Keil 中设置 STM32 Flash 和 RAM 地址详解一、Flash 和 RAM 配置界面(Target 选项卡)1. IROM1(用于配置 Flash)2. IRAM1(用于配置 RAM)二、链接器设置界面(Linker 选项卡)1. 勾选“Use Memory Layout from Target Dialog”2. 查看链接器参数(如果没有勾选上面…...

MySQL用户和授权

开放MySQL白名单 可以通过iptables-save命令确认对应客户端ip是否可以访问MySQL服务&#xff1a; test: # iptables-save | grep 3306 -A mp_srv_whitelist -s 172.16.14.102/32 -p tcp -m tcp --dport 3306 -j ACCEPT -A mp_srv_whitelist -s 172.16.4.16/32 -p tcp -m tcp -…...

JAVA后端开发——多租户

数据隔离是多租户系统中的核心概念&#xff0c;确保一个租户&#xff08;在这个系统中可能是一个公司或一个独立的客户&#xff09;的数据对其他租户是不可见的。在 RuoYi 框架&#xff08;您当前项目所使用的基础框架&#xff09;中&#xff0c;这通常是通过在数据表中增加一个…...

A2A JS SDK 完整教程:快速入门指南

目录 什么是 A2A JS SDK?A2A JS 安装与设置A2A JS 核心概念创建你的第一个 A2A JS 代理A2A JS 服务端开发A2A JS 客户端使用A2A JS 高级特性A2A JS 最佳实践A2A JS 故障排除 什么是 A2A JS SDK? A2A JS SDK 是一个专为 JavaScript/TypeScript 开发者设计的强大库&#xff…...

mac 安装homebrew (nvm 及git)

mac 安装nvm 及git 万恶之源 mac 安装这些东西离不开Xcode。及homebrew 一、先说安装git步骤 通用&#xff1a; 方法一&#xff1a;使用 Homebrew 安装 Git&#xff08;推荐&#xff09; 步骤如下&#xff1a;打开终端&#xff08;Terminal.app&#xff09; 1.安装 Homebrew…...

Webpack性能优化:构建速度与体积优化策略

一、构建速度优化 1、​​升级Webpack和Node.js​​ ​​优化效果​​&#xff1a;Webpack 4比Webpack 3构建时间降低60%-98%。​​原因​​&#xff1a; V8引擎优化&#xff08;for of替代forEach、Map/Set替代Object&#xff09;。默认使用更快的md4哈希算法。AST直接从Loa…...

Neko虚拟浏览器远程协作方案:Docker+内网穿透技术部署实践

前言&#xff1a;本文将向开发者介绍一款创新性协作工具——Neko虚拟浏览器。在数字化协作场景中&#xff0c;跨地域的团队常需面对实时共享屏幕、协同编辑文档等需求。通过本指南&#xff0c;你将掌握在Ubuntu系统中使用容器化技术部署该工具的具体方案&#xff0c;并结合内网…...