vue音乐播放条

先看效果

再看代码

cpp 复制代码
<template>
  <div class="footer-player z-30 flex items-center p-2">
    <div v-if="isShow" class="h-12 w-60 overflow-hidden">
      <div :style="activeStyle" class="open-detail-control-wrap">
        <div class="flex h-full w-40 items-center">
          <div ref="triggerRef" class="relative" @click="handleArrowClick">
            <n-image
              class="size-12"
              :src="currentSong?.al?.picUrl"
              :preview-disabled="true"
              :style="{filter:isHover ? 'blur(1px)' : 'none'}"
            />
            <transition v-show="isHover" name="fade">
              <div class="flex-items-justify-center absolute left-0 top-0 z-10  size-12 bg-black/60">
                <n-icon :component="KeyboardArrowUpOutlined" size="35" color="white" />
              </div>
            </transition>
          </div>
          <div class="ml-4">
            <p class="flex items-center text-base">
              <n-ellipsis style="max-width: 150px">
                {{ currentSong?.name }}
              </n-ellipsis>
              <heart-icon
                :id="mainStore.currentPlaySong.id" class="ml-2" :like="mainStore.currentPlaySong.like"
                @like-success="likeSuccess"
              /> 
            </p>
            <n-ellipsis>
              <p>{{ formateSongsAuthor(currentSong?.ar || []) }}</p>
            </n-ellipsis>
          </div>
        </div>

        <div class="flex h-12 items-center">
          <n-icon
            size="35" :component="KeyboardArrowDownOutlined" class="ml-4"
            @click="mainStore.setShowMusicDetail(false)"
          />
          <div class="ml-4">
            <div class="circleContainer" @click="handleLikeHeartClick">
              <heart-icon
                :id="mainStore.currentPlaySong.id"
                ref="heardLikeRef" :like="mainStore.currentPlaySong.like"
                :size="25" :trigger-click="true" @like-success="likeSuccess"
              /> 
            </div>
          </div>
          <div class="circleContainer ml-4" @click="subscribeModalRef?.show()">
            <n-icon :component="AddBoxOutlined" :size="20" />
          </div>
        </div>
      </div>
    </div>

    <div :style="{opacity:isShow ? '1' : '0.6'}" class="control flex flex-1 flex-col items-center">
      <div v-if="!isShow" class="footer-player absolute z-50 w-full" />
      <div style="width:300px" class="flex items-center justify-between">
        <n-icon
          class="custom-icon" :size="22" :component="currentPlayModeIcon"
          @click="handlePlayModeClick"
        />
        <n-icon
          class="prev custom-icon" :size="22" :component="SkipPreviousSharp"
          @click="handlePrevClick"
        />
        <div
          class="flex size-8 items-center justify-center rounded-full  bg-neutral-200/60 
        hover:bg-neutral-200 dark:bg-slate-100/20 
        dark:hover:bg-slate-100/40" @click="togglePlayStatus"
        >
          <n-icon :size="mainStore.playing ? 14 : 20" :component="mainStore.playing ? StopIcon :PlayArrowSharp" 
        </div>
        <n-icon
          class="next custom-icon" :size="22" :component="SkipNextSharp"
          @click="handleNextClick"
        />
      </div>
      <div class="mt-1 flex items-center">
        <span v-if="isShow" class="mr-2 text-xs opacity-50">{{ currentPlayTime }}</span>
        <div class="flex flex-1 items-center" :style="{width:progressWidth+'px'}">
          <slider-bar
            v-model="percentage"
            :load-value="progressValue"
            @on-done="handleSliderDone"
            @change="handleSliderChange"
          />
        </div>
        <span v-if="isShow" class="ml-2 text-xs opacity-50">
          <n-time format="mm:ss" :time="currentSong?.dt" />
        </span>
      </div>
    </div>

    <div v-if="isShow" class="flex w-60 items-center justify-end">
      <n-popover
        placement="bottom"
        trigger="hover"
      >
        <template #trigger>
          <n-icon
            :component="volume === 0 ? VolumeOffRound : VolumeUpRound" :size="25" class="custom-icon mr-2"
            @click="handleVolumeClick"
          />
        </template>
        <n-slider
          :value="volume" vertical style="height:100px"
          @update-value="handleVolumeChange"
        />
      </n-popover>
      <n-icon
        :component="List" :size="25" class="custom-icon mr-2"
        @click="playListRef?.show()"
      />
    </div>

    <audio
      ref="audioRef"
      :src="currentSong?.url"
      preload="auto" @timeupdate="handleTimeupdate" @ended="handleEnded"
      @playing="handlePlaying" @progress="updateBuffer" @loadeddata="handleLoadeddata"
      @error="handleError" @waiting="handleWaiting" 
    />

    <play-list ref="playListRef" />
    <music-detail v-if="mainStore.currentPlaySong?.id" ref="musicDetailRef" />
    <subscribe-play-list-modal
      v-if="mainStore.currentPlaySong?.id" ref="subscribeModalRef" 
      :tracks="mainStore.currentPlaySong?.id"
    />
  </div>
</template>
相关推荐
星光一影4 分钟前
教育培训机构消课管理系统智慧校园艺术舞蹈美术艺术培训班扣课时教务管理系统
java·spring boot·mysql·vue·mybatis·uniapp
雨季~~9 小时前
前端使用ffmpeg进行视频格式转换 (WebM → MP4)
前端·typescript·ffmpeg·vue
不是,你来真的啊?9 小时前
Vue3响应式原理(源码)【reactive,ref,computed】
前端·vue·源码
zq322061241 天前
若依VUE和NET8的意框架部署到IIS
vue·.net
灰海1 天前
为什么给<a>标签设置了download属性, 浏览器没有下载而是打开新标签!!
前端·vue·html·下载·download
全栈陈序员1 天前
你对 SPA 单页面应用的理解?它的优缺点分别是什么?如何实现 SPA 应用?
前端·vue.js·学习·前端框架·vue
麦麦大数据1 天前
F056 知识图谱飞机问答系统
人工智能·flask·vue·问答系统·知识图谱·neo4j·飞机
我这一生如履薄冰~1 天前
element-plus去除el-dropdown组件当鼠标移入文本时会出现边框
前端·elementui·vue
你脸上有BUG2 天前
TreeSelect 组件 showCheckedStrategy 属性不生效问题
前端·vue
૮・ﻌ・2 天前
小兔鲜电商项目(一):项目准备、Layout模块、Home模块
前端·javascript·vue