呼叫台功能页面布局【canvas绘制音频频谱图】【绘制音量控制滑块】 (示例使用.net framework mvc)
呼叫台功能页面布局【canvas绘制音频频谱图】 (示例使用.net framework mvc)、
界面效果:
1、起始框架界面雏形图
前端页面雏形图:
Layout = "~/areas/usmain/Views/Shared/_LayoutEdit.cshtml"; 布局页自己整吧,我这也是引用的

@{ Layout = "~/areas/usmain/Views/Shared/_LayoutEdit.cshtml"; ViewBag.Title = "即时广播"; } <style> .layui-form-pane .layui-form-switch, .layui-form-pane .layui-form-radio { margin-top: 1px; margin-left: 10px; } .box2-left { position: absolute; top: 0; left: 0; right: 240px; padding: 0px !important; } .usnbox { border: 1px solid #E7ECF1; padding: 8px; margin-bottom: 8px; margin-top: 0px !important; background-color: #ffffff; } #switchspan { vertical-align: middle; } .switchhead { padding: 0px !important; /* vertical-align: middle; */ } .switchheadright { float: right } .switchheadleft { float: left } .callhead { overflow: hidden; /*父元素高度塌陷*/ } .layui-form-radio { display: inline-block; vertical-align: middle; line-height: 28px; padding-right: 0px; cursor: pointer; font-size: 0px; margin: 6px 0px 0px 0px; } .microphone { float: right; width: 48%; } .broadcast { float: left; position: absolute; width: 48%; } .ldiv2, .ldiv3 { position: relative; /*width:100%;*/ } .box2-right .box2-1 .layui-form-label { width: 35%; margin-left: 5px } .box2-right .box2-1 .layui-input-inline { width: 55%; } .ldiv3 .ldiv3-f { float: left; position: absolute; width: 24%; overflow: auto; } .ldiv3 .ldiv3-r { float: right; width: 75%; overflow: auto; } .box2-2 { margin-top: 6px; } .box2-right { width: 230px !important; float: right; } .usnboxtop { border-bottom: 1px solid #EEF1F5; line-height: 28px; padding: 0px !important; padding-left: 8px !important; height: 40px; } .usnboxleft { float: left; /*color: #3598DC;*/ color: black !important; font-size: 15px; /* font-weight: bold; */ } /*高度*/ .ldiv1 .usnbox { height: 200px; /*background-color:red !important;*/ } .ldiv2 .usnbox { height: 150px; /*background-color:red !important;*/ } .ldiv3 .usnbox { height: 300px; /*background-color:red !important;*/ } .ldiv4 .usnbox { height: 80px; } .box2-2 .ustree { height: 612px; } </style>

<form class="layui-form layui-form-pane layui-form-item us-form" id="us-form" usdata="{usurl:'/extavs/avs_task/usgetentity',ussurl:'/extavs/avs_task/usupdate',usselecturl:'/extavs/avs_task/usgetselect',usload:'1',usclose:'1',usrefresh:'1'}"> <div class="usnbox callhead"> <div class="switchheadleft"> <div class="usnboxbody usnboxbody_rtm switchhead"> <div class="layui-inline switch"> <span id="switchspan">呼叫台总开关:</span> <input class="switchbtn" type="checkbox" name="set_isrun" lay-skin="switch" lay-text="开启|关闭"> </div> </div> </div> <div class="switchheadright"> <input type="radio" name="con" disabled> <span id="switchspan">未连接</span> </div> </div> <div class="box2"> @*左侧*@ <div class="box2-left"> <div class="ldiv1"> @*音谱图*@ <div class="usnbox"> <div class="usnboxbody usnboxbody_rtm"> <div class="layui-form-item"> <div class="layui-inline"> <label class="layui-form-label">开始时间<span class="usStar">*</span></label> <div class="layui-input-inline"> <input type="text" name="execute_time" autocomplete="off" placeholder="任务执行时间,默认08:00" ustitle="任务执行时间,默认08:00" class="layui-input usdatetime" usdata="{key:'1',datetype:'time',dateformat:'HH:mm:ss'}" value="08:00:00"> </div> </div> </div> </div> </div> </div> <div class="ldiv2"> @*广播音乐*@ <div class="usnbox broadcast"> <div class="usnboxbody usnboxbody_rtm"> <div class="usnboxtop"> <div class="usnboxleft">广播音乐</div> <div class="usnboxright"> </div> </div> <div class="layui-form-item"> <div class="layui-inline"> <label class="layui-form-label">开始时间<span class="usStar">*</span></label> <div class="layui-input-inline"> </div> </div> </div> </div> </div> @*麦克风*@ <div class="usnbox microphone"> <div class="usnboxbody usnboxbody_rtm"> <div class="usnboxtop"> <div class="usnboxleft">麦克风</div> <div class="usnboxright"> </div> </div> <div class="layui-form-item"> <div class="layui-inline"> <label class="layui-form-label">开始时间<span class="usStar">*</span></label> <div class="layui-input-inline"> </div> </div> </div> </div> </div> <br style='clear:both' /><!--清除浮动--> </div> <div class="ldiv3"> @*列表*@ <div class="ldiv3-f"> <div class="usnbox playul"> <div class="usnboxtop"> <div class="usnboxleft"><i class="us-icon"></i>新增列表</div> <div class="usnboxright"> </div> </div> <ul id="ustree1" class="ztree ustree" usurl="/extavs/foldertree/useditselecttree" uscheck="3" datagridid="usdatagrid" inputs="folderid:$id" loadclickid=".btnreloadtree"></ul> </div> </div> <div class="ldiv3-r"> @*播放列表*@ <div class="usnbox playlist"> <div class="usnboxtop"> <div class="usnboxleft"><i class="us-icon"></i>播放列表</div> <div class="usnboxright"> </div> </div> <div class="layui-form-item"> <div class="layui-inline"> <label class="layui-form-label">开始时间<span class="usStar">*</span></label> <div class="layui-input-inline"> </div> </div> </div> </div> </div> <br style='clear:both' /><!--清除浮动--> </div> <div class="ldiv4"> @*播放进度条*@ <div class="usnbox"> <div class="usnboxtop"> <div class="usnboxleft"><i class="us-icon"></i></div> <div class="usnboxright"> </div> </div> </div> </div> </div> @*右侧*@ <div class="box2-right"> <div class="box2-1"> <div style="margin-top:0;overflow:auto;" id="conditioninstall1" class="box-left-border"> <div class="layui-inline"> <label class="layui-form-label">名称<span class="usStar">*</span></label> <div class="layui-input-inline"> <input type="text" name="soft_name" lay-verify="required" autocomplete="off" placeholder="呼叫台名称" class="layui-input ustips" ustitle="默认名称:呼叫台任务"> </div> </div> <div class="layui-inline"> <label class="layui-form-label">优先级<span class="usStar">*</span></label> <div class="layui-input-inline"> <input type="text" name="soft_name" lay-verify="required" autocomplete="off" placeholder="优先级" class="layui-input ustips" ustitle="值越大,优先级越高"> </div> </div> <div class="layui-form-item us-submitsave"> <div class="uscenter"> <button class="layui-btn" lay-submit="" lay-filter="submit" data-pwid="ussubmit"><i class="us-icon"></i>提交</button> @* <button type="button" class="layui-btn layui-btn-primary" data-pwid="usclose"><i class="us-icon"></i>取消</button>*@ </div> </div> </div> </div> <div class="box2-2"> <div style="margin-top:0;overflow:auto;" id="conditioninstal2" class="box-left-border"> <div class="usnboxtop"> <div class="usnboxleft"><i class="us-icon"></i>接收成员</div> <div class="usnboxright"> </div> </div> <ul id="ustree" class="ztree ustree" usurl="/usrtm/roomtree/useditselecttree?ctlip=1" uscheck="4" usonclickv2="usonclickv2"></ul> <input type="text" name="receiver" placeholder="接受成员" style="display:none"> </div> </div> </div> </div> </form>
1、参考网站显示频谱图(代码仅供出现频谱效果做参考)
完整文档:
HTML5 WebAudioAPI(三)--绘制频谱图 (shuzhiduo.com)
文档效果图:
个人案例效果图:(频谱颜色进行了调节)
参考文章第二部分: HTML5 WebAudioAPI(三)--绘制频谱图 (shuzhiduo.com)(两种暂时不清楚有什么区别)
1/1 添加频谱div,<canvas></canvas>
1/2 编写js 暂时使用固定音频数据实现效果

<script type="text/javascript"> var url = '/upload/avs/0f7213c0-bd81-46f3-8bcd-3c112eec949620221127.mp3'; if (!window.AudioContext) { alert('您的浏览器不支持AudioContext'); } else { //创建上下文 var atx = new AudioContext(); var source = null; //使用Ajax获取音频文件 var request = new XMLHttpRequest(); request.open('GET', url, true); request.responseType = 'arraybuffer';//配置数据的返回类型 //加载完成 request.onload = function () { var arraybuffer = request.response; atx.decodeAudioData(arraybuffer, function (buffer) { //创建分析器 var analyser = atx.createAnalyser(); source = atx.createBufferSource(); //将source与分析器链接 source.connect(analyser); //将分析器与destination链接,这样才能形成到达扬声器的通路 analyser.connect(atx.destination); //将解码后的buffer数据复制给source source.buffer = buffer; //播放 source.start(0); //开始绘制频谱图 var canvas = document.getElementById('canvas'), cwidth = canvas.width, cheight = canvas.height - 2, meterWidth = 10,//能量条的宽度 gap = 2,//能量条的间距 meterNum = 800 / (10 + 2);//计算当前画布上能画多少条 var ctx = canvas.getContext('2d'); var capHeight = 2,//冒头的高度 capStyle = '#fff',//冒头的颜色 capYPositionArray = [];//将上一面各个冒头的位置保存到这个数组1e9fff //定义一个渐变样式用于画图 var gradient = ctx.createLinearGradient(0, 0, 0, 300); //gradient.addColorStop(1, '#0f0'); //gradient.addColorStop(0.5, '#ff0'); //gradient.addColorStop(0, '#f00'); gradient.addColorStop(1, '#1e9fff');//低音颜色 gradient.addColorStop(0.5, '#70bbf2');//中音颜色 gradient.addColorStop(0, '#1e9fff');//高音颜色 //绘制频谱图 function drawSpectrum() { var array = new Uint8Array(analyser.frequencyBinCount); analyser.getByteFrequencyData(array); var step = Math.round(array.length / meterNum);//计算从analyser中的采样步长 //清理画布 ctx.clearRect(0, 0, cwidth, cheight); //对信源数组进行抽样遍历,画出每个频谱条 for (var i = 0; i < meterNum; i++) { var value = array[i * step]; //取样作为y轴的值 //绘制缓慢降落的冒头 if (capYPositionArray.length < Math.round(meterNum)) { capYPositionArray.push(value);//初始化保存冒头位置的数组,将第一个画面位置保存 } ctx.fillStyle = capStyle; //1.开始绘制冒头 if (value < capYPositionArray[i]) { //使用前一次数据 ctx.fillRect(i * 12, cheight - (--capYPositionArray[i]), meterWidth, capHeight); } else { //否则,直接使用当前数据并记录 ctx.fillRect(i * 12, cheight - value, meterWidth, capHeight); capYPositionArray[i] = value; } //2.开始绘制频谱条 ctx.fillStyle = gradient; ctx.fillRect(i * 12/*频谱条的宽度+条间距*/, cheight - value + capHeight, meterWidth, cheight); } requestAnimationFrame(drawSpectrum); } requestAnimationFrame(drawSpectrum); }, function (e) { console.info('处理出错'); }); } request.send(); //绑定播放按钮 $('#playBtn').click(function () { var icon = $(this).find('i');; icon.toggleClass('glyphicon-play').toggleClass('glyphicon-pause'); //停止播放 source.stop(); }); } </script>
出现了频谱显示效果
2、媒体播放进度条布局
传送门
直接拷贝了全部代码(上一代码更新)

@{ Layout = "~/areas/usmain/Views/Shared/_LayoutEdit.cshtml"; ViewBag.Title = "即时广播"; } <style> .layui-form-pane .layui-form-switch, .layui-form-pane .layui-form-radio { margin-top: 1px; margin-left: 10px; } .box2-left { position: absolute; top: 0; left: 0; right: 240px; padding: 0px !important; } .usnbox { border: 1px solid #E7ECF1; padding: 8px; margin-bottom: 8px; margin-top: 0px !important; background-color: #ffffff; } #switchspan { vertical-align: middle; } .switchhead { padding: 0px !important; /* vertical-align: middle; */ } .switchheadright { float: right } .switchheadleft { float: left } .callhead { overflow: hidden; /*父元素高度塌陷*/ } .layui-form-radio { display: inline-block; vertical-align: middle; line-height: 28px; padding-right: 0px; cursor: pointer; font-size: 0px; margin: 6px 0px 0px 0px; } .microphone { float: right; width: 48%; } .broadcast { float: left; position: absolute; width: 48%; } .ldiv2, .ldiv3 { position: relative; /*width:100%;*/ } .box2-right .box2-1 .layui-form-label { width: 35%; margin-left: 5px } .box2-right .box2-1 .layui-input-inline { width: 55%; } .ldiv3 .ldiv3-f { float: left; position: absolute; width: 24%; overflow: auto; } .ldiv3 .ldiv3-r { float: right; width: 75%; overflow: auto; } .box2-2 { margin-top: 6px; } .box2-right { width: 230px !important; float: right; } .usnboxtop { border-bottom: 1px solid #EEF1F5; line-height: 28px; padding: 0px !important; padding-left: 8px !important; height: 40px; } .usnboxleft { float: left; /*color: #3598DC;*/ color: black !important; font-size: 15px; /* font-weight: bold; */ } /*高度*/ .ldiv1 .usnbox { height: 200px; /*background-color:red !important;*/ } .ldiv2 .usnbox { height: 150px; /*background-color:red !important;*/ } .ldiv3 .usnbox { height: 300px; /*background-color:red !important;*/ } .ldiv4 .usnbox { height: 80px; background-color: transparent !important; } .box2-2 .ustree { height: 612px; } #canvas { width: 100%; height: 200px; /*background: black;*/ } </style> <style> /* 控制区域盒子 */ .control-back { width: 97%; height: 80px; /*bottom: 0;*/ position: absolute; background-color: rgba(255, 255, 255, 0.8); } /* 控制按钮 */ .control { width: 100%; height: 30px; /*margin-top:40px;*/ } .control a { margin: 0 5px; display: inline-block; } .control a:hover { opacity: 50%; } .control-btn { width: 130px; height: 30px; margin: 0 auto; } /* 上一首 */ .up { width: 30px; height: 30px; /*background: url(../img/up.png) no-repeat;*/ background-size: 20px; background-position: 50% 50%; } /* 暂停播放 */ .play-pause { width: 30px; height: 30px; /*background: url(../img/play.png) no-repeat;*/ background-size: 30px; background-position: 50% 50%; } /* 下一首 */ .down { width: 30px; height: 30px; /*background: url(../img/down.png) no-repeat;*/ background-size: 20px; background-position: 50% 50%; } /* 右侧控制按钮 */ .control-right { /* width: 180px; */ height: 30px; margin-left: calc(50% + 70px); margin-top: -30px; display: flex; /*align-items: center;*/ } /*声音进度条*/ /*.volume-back {*/ /*padding: px 0;*/ /*cursor: pointer; margin-top: 10px !important; }*/ /* 播放模式 */ .mode { width: 30px; height: 30px; /*background: url(../img/sequence.png) no-repeat;*/ background-size: 20px; background-position: left 50%; cursor: pointer; } /* 声音控制 */ /*.volume { width: 30px; height: 30px;*/ /*background: url(../img/volume.png) no-repeat;*/ /*background-size: 20px; background-position: left 50%; cursor: pointer; }*/ /* .volume-back { padding: 5px 0; cursor: pointer; } .volume-all { width: 100px; height: 2px; background-color: #e5e5e5; } .volume-now { width: 100px; height: 2px; margin-top: -2px; max-width: 100px; background-color: #5192fe; } .volume-text { margin-left: 10px; font-size: 14px; }*/ </style> <style> /* 进度条 */ .progress-bar { width: 99%; margin: 15px 15px 5px 15px; /*padding: 5px 0;*/ cursor: pointer; /*float: left;*/ } /* 当前播放进度 */ .progress-now { width: 0; height: 5px; margin-top: -5px; background-color: #5192fe; } /* 总播放进度 */ .progress-all { width:97%; height: 5px; background-color: #dee2e6; } /*文本div*/ .playfiletext { display: inline-block; width: 99%; height: 20px; margin-left: 15px; text-align: center; color: rgba(128, 130, 133, 0.8); cursor: default; overflow: hidden; } /* 播放时间进度 文本 */ .time { float: right; font-size: 1px; display: inline-block; width: 90px; height: 21px; margin-right:15px; text-align: center; color: rgba(128, 130, 133, 0.8); cursor: default; overflow: hidden; } /* 播放名称 文本 */ .playname{ float:left; font-size:1px; } </style> <form class="layui-form layui-form-pane layui-form-item us-form" id="us-form" usdata="{usurl:'/extavs/avs_task/usgetentity',ussurl:'/extavs/avs_task/usupdate',usselecturl:'/extavs/avs_task/usgetselect',usload:'1',usclose:'1',usrefresh:'1'}"> <div class="usnbox callhead"> <div class="switchheadleft"> <div class="usnboxbody usnboxbody_rtm switchhead"> <div class="layui-inline switch"> <span id="switchspan">呼叫台总开关:</span> <input class="switchbtn" type="checkbox" name="set_isrun" lay-skin="switch" lay-text="开启|关闭"> </div> </div> </div> <div class="switchheadright"> <input type="radio" name="con" disabled> <span id="switchspan">未连接</span> </div> </div> <div class="box2"> @*左侧*@ <div class="box2-left"> <div class="ldiv1"> @*音谱图*@ <div class="usnbox"> <canvas id="canvas"></canvas> </div> </div> <div class="ldiv2"> @*广播音乐*@ <div class="usnbox broadcast"> <div class="usnboxbody usnboxbody_rtm"> <div class="usnboxtop"> <div class="usnboxleft">广播音乐</div> <div class="usnboxright"> </div> </div> <div class="layui-form-item"> <div class="layui-inline"> <label class="layui-form-label">开始时间<span class="usStar">*</span></label> <div class="layui-input-inline"> </div> </div> </div> </div> </div> @*麦克风*@ <div class="usnbox microphone"> <div class="usnboxbody usnboxbody_rtm"> <div class="usnboxtop"> <div class="usnboxleft">麦克风</div> <div class="usnboxright"> </div> </div> <div class="layui-form-item"> <div class="layui-inline"> <label class="layui-form-label">开始时间<span class="usStar">*</span></label> <div class="layui-input-inline"> </div> </div> </div> </div> </div> <br style='clear:both' /><!--清除浮动--> </div> <div class="ldiv3"> @*列表*@ <div class="ldiv3-f"> <div class="usnbox playul"> <div class="usnboxtop"> <div class="usnboxleft"><i class="us-icon"></i>新增列表</div> <div class="usnboxright"> </div> </div> <ul id="ustree1" class="ztree ustree" usurl="/extavs/foldertree/useditselecttree" uscheck="3" datagridid="usdatagrid" inputs="folderid:$id" loadclickid=".btnreloadtree"></ul> </div> </div> <div class="ldiv3-r"> @*播放列表*@ <div class="usnbox playlist"> <div class="usnboxtop"> <div class="usnboxleft"><i class="us-icon"></i>播放列表</div> <div class="usnboxright"> </div> </div> <div class="layui-form-item"> <div class="layui-inline"> <label class="layui-form-label">开始时间<span class="usStar">*</span></label> <div class="layui-input-inline"> </div> </div> </div> </div> </div> <br style='clear:both' /><!--清除浮动--> </div> <div class="ldiv4"> @*播放进度条*@ <div class="usnbox"> @*<div class="usnboxtop"> </div>*@ @*<div class="usnboxleft"><i class="us-icon"></i></div> <div class="usnboxright"> </div>*@ <!-- 控制区 --> <div class="control-back"> <!-- 进度条 --> <div class="progress-bar"> <div class="progress-all"></div> <div class="progress-now"></div> </div> @*文本*@ <div class="playfiletext"> <span class="playname">高三英语</span> <span class="time">00:00/00:00</span> <br style='clear:both' /><!--清除浮动--> </div> <!-- 控制按钮 --> <div class="control"> <!-- 上一首、下一首、暂停播放 --> <div class="control-btn"> <a href="#" class="up"><i class="us-icon"></i></a> <a href="#" class="play-pause" onclick="setPlay()"><i class="us-icon"></i></a> <a href="#" class="down"><i class="us-icon"></i></a> </div> <!-- 播放模式、声音 --> <div class="control-right"> <a href="#" class="mode"><i class="us-icon"></i></a> @*<a href="#" class="volume" onclick="setMuted()"><i class="us-icon"></i></a>*@ @*<div class="volume-back"> <div class="volume-all"></div> <div class="volume-now"></div> </div> <span class="volume-text">100</span>*@ </div> </div> </div> </div> </div> </div> @*右侧*@ <div class="box2-right"> <div class="box2-1"> <div style="margin-top:0;overflow:auto;" id="conditioninstall1" class="box-left-border"> <div class="layui-inline"> <label class="layui-form-label">名称<span class="usStar">*</span></label> <div class="layui-input-inline"> <input type="text" name="soft_name" lay-verify="required" autocomplete="off" placeholder="呼叫台名称" class="layui-input ustips" ustitle="默认名称:呼叫台任务"> </div> </div> <div class="layui-inline"> <label class="layui-form-label">优先级<span class="usStar">*</span></label> <div class="layui-input-inline"> <input type="text" name="soft_name" lay-verify="required" autocomplete="off" placeholder="优先级" class="layui-input ustips" ustitle="值越大,优先级越高"> </div> </div> <div class="layui-form-item us-submitsave"> <div class="uscenter"> <button class="layui-btn" lay-submit="" lay-filter="submit" data-pwid="ussubmit"><i class="us-icon"></i>提交</button> @* <button type="button" class="layui-btn layui-btn-primary" data-pwid="usclose"><i class="us-icon"></i>取消</button>*@ </div> </div> </div> </div> <div class="box2-2"> <div style="margin-top:0;overflow:auto;" id="conditioninstal2" class="box-left-border"> <div class="usnboxtop"> <div class="usnboxleft"><i class="us-icon"></i>接收成员</div> <div class="usnboxright"> </div> </div> <ul id="ustree" class="ztree ustree" usurl="/usrtm/roomtree/useditselecttree?ctlip=1" uscheck="4" usonclickv2="usonclickv2"></ul> <input type="text" name="receiver" placeholder="接受成员" style="display:none"> </div> </div> </div> </div> </form> @*频谱图*@ <script> var url = '/upload/avs/0f7213c0-bd81-46f3-8bcd-3c112eec949620221127.mp3'; if (!window.AudioContext) { alert('您的浏览器不支持AudioContext'); } else { //创建上下文 var atx = new AudioContext(); var source = null; //使用Ajax获取音频文件 var request = new XMLHttpRequest(); request.open('GET', url, true); request.responseType = 'arraybuffer';//配置数据的返回类型 //加载完成 request.onload = function () { var arraybuffer = request.response; atx.decodeAudioData(arraybuffer, function (buffer) { //创建分析器 var analyser = atx.createAnalyser(); source = atx.createBufferSource(); //将source与分析器链接 source.connect(analyser); //将分析器与destination链接,这样才能形成到达扬声器的通路 analyser.connect(atx.destination); //将解码后的buffer数据复制给source source.buffer = buffer; //播放 source.start(0); //开始绘制频谱图 var canvas = document.getElementById('canvas'), cwidth = canvas.width, cheight = canvas.height - 2, meterWidth = 10,//能量条的宽度 gap = 2,//能量条的间距 meterNum = 800 / (10 + 2);//计算当前画布上能画多少条 var ctx = canvas.getContext('2d'); var capHeight = 2,//冒头的高度 capStyle = '#fff',//冒头的颜色 capYPositionArray = [];//将上一面各个冒头的位置保存到这个数组1e9fff //定义一个渐变样式用于画图 var gradient = ctx.createLinearGradient(0, 0, 0, 300); //gradient.addColorStop(1, '#0f0'); //gradient.addColorStop(0.5, '#ff0'); //gradient.addColorStop(0, '#f00'); gradient.addColorStop(1, '#1e9fff');//低音颜色 gradient.addColorStop(0.5, '#70bbf2');//中音颜色 gradient.addColorStop(0, '#1e9fff');//高音颜色 //绘制频谱图 function drawSpectrum() { var array = new Uint8Array(analyser.frequencyBinCount); analyser.getByteFrequencyData(array); var step = Math.round(array.length / meterNum);//计算从analyser中的采样步长 //清理画布 ctx.clearRect(0, 0, cwidth, cheight); //对信源数组进行抽样遍历,画出每个频谱条 for (var i = 0; i < meterNum; i++) { var value = array[i * step]; //取样作为y轴的值 //绘制缓慢降落的冒头 if (capYPositionArray.length < Math.round(meterNum)) { capYPositionArray.push(value);//初始化保存冒头位置的数组,将第一个画面位置保存 } ctx.fillStyle = capStyle; //1.开始绘制冒头 if (value < capYPositionArray[i]) { //使用前一次数据 ctx.fillRect(i * 12, cheight - (--capYPositionArray[i]), meterWidth, capHeight); } else { //否则,直接使用当前数据并记录 ctx.fillRect(i * 12, cheight - value, meterWidth, capHeight); capYPositionArray[i] = value; } //2.开始绘制频谱条 ctx.fillStyle = gradient; ctx.fillRect(i * 12/*频谱条的宽度+条间距*/, cheight - value + capHeight, meterWidth, cheight); } requestAnimationFrame(drawSpectrum); } requestAnimationFrame(drawSpectrum); }, function (e) { console.info('处理出错'); }); } request.send(); //绑定播放按钮 $('#playBtn').click(function () { var icon = $(this).find('i');; icon.toggleClass('glyphicon-play').toggleClass('glyphicon-pause'); //停止播放 source.stop(); }); } </script>
3、音乐点击播放-进度条显示
布局效果图:
3-1、界面设定放置进度条添加img标签以及进度条div

@*播放进度条*@ <div class="ldiv4"> <div class="usnbox"> @*<div class="usnboxtop"> </div>*@ @*<div class="usnboxleft"><i class="us-icon"></i></div> <div class="usnboxright"> </div>*@ <!-- 控制区 --> <div class="control-back"> <!-- 控制按钮 --> <div class="control"> <!-- 上一首、下一首、暂停播放 --> <img class="mode" src="~/assets2/avs/images/mode1.png" onclick="playmodectr()" alt="1" /> <img class="up" src="~/assets2/avs/images/up.png" onclick="playctr(2)" /> <img class="play-pause" src="~/assets2/avs/images/stop.png" onclick="playctr(3)" alt="1" /> <img class="down" src="~/assets2/avs/images/down.png" onclick="playctr(4)" /> @*<a class="up"><i class="us-icon"></i></a> <a class="play-pause" onclick="setPlay()"><i class="us-icon"></i></a> <a class="down"><i class="us-icon"></i></a>*@ </div> <div class="control1"> <!-- 进度条 --> <div class="progress-bar"> <div class="progress-all"> <div class="progress-now"> <div class="progress-nowctor"> </div> </div> </div> </div> @*文本*@ <div class="playfiletext"> <span class="playname">暂无播放文件</span> <span class="time">00:00/00:00</span> <br style='clear:both' /><!--清除浮动--> </div> </div> </div> </div> </div>

/* 控制区域盒子 */ .control-back { width: 97%; height: 60px; /*bottom: 0;*/ position: absolute; background-color: rgba(255, 255, 255, 0.8); } .control1 { width: 75%; float: right; height: 40px; margin-top: 15px; } /* 控制按钮 */ .control { width: 25%; float: left; height: 40px; margin-top: 15px; } .control .mode { margin-right: 20px; } .control img { margin-right: 15px; width: 30px; height: 30px; cursor: pointer; } /* .control a { margin: 0 5px; display: inline-block; } .control a:hover { opacity: 50%; }*/ /*.control-btn { width: 130px; height: 30px; margin: 0 auto; }*/ /* 上一首 */ /*.up { width: 30px; height: 30px;*/ /*background: url(../img/up.png) no-repeat;*/ /*background-size: 20px; background-position: 50% 50%; }*/ /* 暂停播放 */ /*.play-pause { width: 30px; height: 30px;*/ /*background: url(../img/play.png) no-repeat;*/ /*background-size: 30px; background-position: 50% 50%; }*/ /* 下一首 */ /*.down { width: 30px; height: 30px;*/ /*background: url(../img/down.png) no-repeat;*/ /*background-size: 20px; background-position: 50% 50%; }*/ /* 右侧控制按钮 */ /*.control-right {*/ /* width: 180px; */ /*height: 30px; margin-left: calc(50% + 70px); margin-top: -30px; display: flex;*/ /*align-items: center;*/ /*}*/ /*声音进度条*/ /*.volume-back {*/ /*padding: px 0;*/ /*cursor: pointer; margin-top: 10px !important; }*/ /* 播放模式 */ .mode { width: 30px; height: 30px; /*background: url(../img/sequence.png) no-repeat;*/ background-size: 20px; background-position: left 50%; cursor: pointer; } /* 声音控制 */ /*.volume { width: 30px; height: 30px;*/ /*background: url(../img/volume.png) no-repeat;*/ /*background-size: 20px; background-position: left 50%; cursor: pointer; }*/ /* .volume-back { padding: 5px 0; cursor: pointer; } .volume-all { width: 100px; height: 2px; background-color: #e5e5e5; } .volume-now { width: 100px; height: 2px; margin-top: -2px; max-width: 100px; background-color: #5192fe; } .volume-text { margin-left: 10px; font-size: 14px; }*/ /* 进度条 */ .progress-bar { width: 100%; margin-top: 10px; /*margin: 15px 15px 5px 15px;*/ /*padding: 5px 0;*/ cursor: pointer; /*position:absolute;*/ /*float: left;*/ } /* 当前播放进度 */ .progress-now { width: 0; height: 10px; border-radius: 10px; margin-top: -10px; background-color: #5192fe; position: relative; } /*滑块*/ .progress-nowctor { width: 15px; height: 15px; background: white; /*position: absolute;*/ bottom: 0; top: 0; /*margin: auto 0;*/ border-radius: 50%; border: 2px solid #1e9fff; cursor: pointer; /*transition: left 0.1s linear 0s;*/ margin-top: -5px; position: absolute; /*position: relative;*/ left: 0px; } /* 总播放进度 */ .progress-all { /*width: 97%;*/ height: 10px; border-radius: 10px; background-color: #dee2e6; } /*文本div*/ .playfiletext { display: inline-block; width: 100%; height: 20px; /* margin-left: 15px;*/ margin-top: 10px; text-align: center; color: rgba(128, 130, 133, 0.8); cursor: default; overflow: hidden; } /* 播放时间进度 文本 */ .time { float: right; font-size: 10px; display: inline-block; width: 90px; height: 21px; /*margin-right: 15px;*/ text-align: right; color: rgba(128, 130, 133, 0.8); cursor: default; overflow: hidden; } /* 播放名称 文本 */ .playname { float: left; font-size: 10px; } a { cursor: pointer; }
3-2、添加auido标签 ,src最开始可以写一个固定媒体文件路径(相对路径)
3-2、编写js代码实现播放音乐动态走进度条
和下面绘制声音进度条方法一致需要在window.onload中添加鼠标滑动、点击进度条系列事件
//获取进度条滑动最大位置值 var yuecha = progressall.offsetWidth - progressnowctor.offsetWidth;
//获取元素 var progressall = document.getElementsByClassName("progress-all")[0];//音乐进度条 var progressnowctor = document.getElementsByClassName("progress-nowctor")[0];//音乐进度滑块

//鼠标放到上面触发事件onmouseover progressnowctor.onmouseover = function () { //鼠标按下按钮触发事件onmouseover progressnowctor.onmousedown = function (ev) { let e = ev || window.event; //兼容性 let mouseX = e.clientX; //鼠标按下的位置(此时滑块所在位置) //鼠标移动发生 window.onmousemove = function (ev) { let e1 = ev || window.event; var nowx = e1.clientX;//当前移动的位置x let moveL = nowx - mouseX; //鼠标移动的距离 // 判断最大值和最小值 if (moveL <= 0) { moveL = 0; } if (moveL >= yuecha) { moveL = yuecha; } // 改变滑块left值 progressnowctor.style.left = moveL + 'px'; //快进时间 var allTime = myAduio.duration; var ytime = (progressnowctor.offsetLeft) * allTime / yuecha; var nytime = ""; //转换显示 nytime = getTimeStr(ytime); if (isNaN(allTime)) { nytime = "00:00"; allTime = "00:00"; } else { allTime = getTimeStr(allTime); } if (nytime != "00:00") { //设置快进 sspeed(ytime); } progressTime.innerText = nytime + '/' + allTime; progress_now.style.width = progressnowctor.offsetLeft + progressnowctor.offsetWidth / 2 + 'px'; return false //取消默认事件 } //移开鼠标 progressnowctor.onmouseout = function () { progressnowctor.onmouseover = false; return false; } //松开时执行 window.onmouseup = function () { window.onmousemove = false //解绑移动事件 return false } } //移开鼠标 progressnowctor.onmouseout = function () { progressnowctor.onmouseover = false; return false; } return false } // 点击音乐进度条 progressall.onclick = function (ev) { //获取柱状条左边距离 var progressallL = progressall.offsetLeft; var current = progressall.offsetParent; if (current != null) { progressallL += current.offsetLeft; } var clickClientX = ev.clientX;//点击位置 let left = clickClientX - progressallL - progressnowctor.offsetWidth / 2;//获取点击相对条的位置 -按钮宽度/2 if (left <= 0) { left = 0; } if (left >= yuecha) { left = yuecha; } // 改变滑块left值 progressnowctor.style.left = left + 'px'; //快进时间 var allTime = myAduio.duration; var ytime = (progressnowctor.offsetLeft) * allTime / yuecha; var nytime = ""; //转换显示 nytime = getTimeStr(ytime); if (isNaN(allTime)) { nytime = "00:00"; allTime = "00:00"; } else { allTime = getTimeStr(allTime); } if (nytime != "00:00") { //设置快进 sspeed(ytime); } progressTime.innerText = nytime + '/' + allTime; progress_now.style.width = progressnowctor.offsetLeft + progressnowctor.offsetWidth / 2 + 'px'; return false //取消默认事件 }
3-3、设置媒体播放、进度条滑快滑动、显示媒体名称+时长
//获取相关元素 var myAduio = document.getElementsByTagName('audio')[0];//aduio元素 //var myAduio = $("#playaudio"); var progressTime = document.getElementsByClassName('time')[0];//进度条时间div var progressplayname = document.getElementsByClassName('playname')[0];//进度条名称div let progress_now = document.getElementsByClassName('progress-now')[0];//显示当前进度div //let progress_bar = document.getElementsByClassName('progress-bar')[0]; var playState = false;//播放状态 //控制区域播放暂停按钮 var play_pause = document.getElementsByClassName('play-pause')[0];
3-4、编写实现js代码--控制播放

if (p == 3) { if (play_pause.alt == 1) { if (src == "") { playitemArr[0]["color"] = 1; //变色、设置为播放状态 $("#playaudio").attr("src", playitemArr[0]["murl"]); newu = 0; u = newu; } else { playitemArr[u]["color"] = 1; } //播放 --换图片 play_pause.src = "/assets2/avs/images/start.png"; play_pause.alt = 2; setPlay(true); } else { //暂停 --换图片 play_pause.src = "/assets2/avs/images/stop.png"; playitemArr[u]["color"] = 2; play_pause.alt = 1; setPlay(false); } }

/** * 媒体控制公共方法1 * @param {any} p 不同功能值 */ function playctr(p) { var src = $("#playaudio").attr("src"); var u = -1; if (src != "") { u = getUrlReTable(src); } var url = ""; //新下标 var newu = u; //播放模式 if (p == 1) { //获取播放模式 var mode = document.getElementsByClassName("mode")[0]; //顺序播放 if (mode.alt == 1) { if (u == playitemArr.length - 1) { newu = -1; } else { newu = u + 1; } }//列表循环 else if (mode.alt == 2) { if (u != playitemArr.length - 1) { newu = u + 1; } else { newu = 0; } }//单曲循环 else if (mode.alt == 3) { newu = u; }//随机播放 else if (mode.alt == 4) { //随机下标 var i = RandomNumBoth(0, playitemArr.length - 1); newu = i; } if (mode.alt != 3) { playitemArr[u]["color"] = 0; } if (newu != -1) { url = playitemArr[newu]["murl"]; playitemArr[newu]["color"] = 1; $("#playaudio").attr("src", url); setPlay(true); } else { //列表循环结束停止 newu = u; url = playitemArr[u]["murl"]; play_pause.src = "/assets2/avs/images/stop.png"; play_pause.alt = 1; playitemArr[u]["color"] = -1; $("#playaudio").attr("src", url); } } //上一首 if (p == 2) { if (src != "") { if (u > 0) { $("#playaudio").attr("src", playitemArr[u - 1]["murl"]); setPlay(true); playitemArr[u - 1]["color"] = 1; playitemArr[u]["color"] = 0; newu = u - 1; } } } //播放+暂停 if (p == 3) { if (play_pause.alt == 1) { if (src == "") { playitemArr[0]["color"] = 1; $("#playaudio").attr("src", playitemArr[0]["murl"]); newu = 0; u = newu; } else { playitemArr[u]["color"] = 1; } //播放 play_pause.src = "/assets2/avs/images/start.png"; play_pause.alt = 2; setPlay(true); } else { //暂停 play_pause.src = "/assets2/avs/images/stop.png"; playitemArr[u]["color"] = 2; play_pause.alt = 1; setPlay(false); } } //下一首 if (p == 4) { if (src != "") { if (u < playitemArr.length - 1) { $("#playaudio").attr("src", playitemArr[u + 1]["murl"]); setPlay(true); playitemArr[u + 1]["color"] = 1; playitemArr[u]["color"] = 0; newu = u + 1; } } } inittabledata(playitemArr); if (u == -1) { document.getElementsByClassName('playname')[0].innerText = "暂无播放文件"; } else { document.getElementsByClassName('playname')[0].innerText = playitemArr[newu]["name"]; } }
3-2 js中暂时获取所需对象
var myAduio = document.getElementsByTagName('audio')[0];//获取audio对象 var progressTime = document.getElementsByClassName('time')[0];//进度条时间 var progressplayname = document.getElementsByClassName('playname')[0];//进度条名称 var playState = false;//播放状态
3-3 控制播放按钮有对应点击事件,编写播放事件代码
点击事件

// 设置播放状态 function setPlay(state) { var play_pause = document.getElementsByClassName('play-pause')[0]; if (state == null) { // 如果歌曲为暂停状态,那么获取到的state则为true,将state设置为true我们就播放 state = myAduio.paused; } // 清除计时器,不然会出现多个计时器同时进行 //clearTimeout(rollT); if (state == true) { myAduio.play(); //设置为播放图标 //play_pause.style.backgroundImage = 'url(../img/pause.png)'; play_pause.innerHTML = '<i class="us-icon"></i>'; //换播放图标 playState = true; // 开始播放的同时,同时开始设置时间进度文本,歌词滚动以及进度条位置 setTimeText(); //lyricsRoll(); //歌词滚动 setProgress(); } else { myAduio.pause(); //play_pause.style.backgroundImage = 'url(../img/play.png)'; play_pause.innerHTML = '<i class="us-icon"></i>';//换暂停图标 playState = false; } }
开始播放的同时,同时开始设置时间进度文本,歌词滚动(暂时未实现)以及进度条位置(时长动态进展)

// 设置进度文本 function setTimeText() { var nowTime = myAduio.currentTime; var allTime = myAduio.duration; // 计算时间,若为个位数,补0 if (Math.floor(nowTime % 60) < 10) { nowTime = Math.floor(nowTime / 60) + ':0' + Math.floor(nowTime % 60); } else { nowTime = Math.floor(nowTime / 60) + ':' + Math.floor(nowTime % 60); } if (Math.floor(allTime % 60) < 10) { allTime = Math.floor(allTime / 60) + ':0' + Math.floor(allTime % 60); } else { allTime = Math.floor(allTime / 60) + ':' + Math.floor(allTime % 60); } progressTime.innerText = nowTime + '/' + allTime; // 每0.1秒执行一次 if (myAduio.paused == false) { setTimeout(setTimeText, 100); } }
进度条相应进展

// 设置进度条进度 function setProgress() { let progress_now = document.getElementsByClassName('progress-now')[0]; let progress_bar = document.getElementsByClassName('progress-bar')[0]; let progress = Math.floor( (myAduio.currentTime / myAduio.duration) * progress_bar.clientWidth ); progress_now.style.width = progress + 'px'; if (myAduio.paused == false) { setTimeout(setProgress, 100); } }
到此步效果完整代码

@{ Layout = "~/areas/usmain/Views/Shared/_LayoutEdit.cshtml"; ViewBag.Title = "即时广播"; } <style> .layui-form-pane .layui-form-switch, .layui-form-pane .layui-form-radio { margin-top: 1px; margin-left: 10px; } .box2-left { position: absolute; top: 0; left: 0; right: 240px; padding: 0px !important; } .usnbox { border: 1px solid #E7ECF1; padding: 8px; margin-bottom: 8px; margin-top: 0px !important; background-color: #ffffff; } #switchspan { vertical-align: middle; } .switchhead { padding: 0px !important; /* vertical-align: middle; */ } .switchheadright { float: right } .switchheadleft { float: left } .callhead { overflow: hidden; /*父元素高度塌陷*/ } .layui-form-radio { display: inline-block; vertical-align: middle; line-height: 28px; padding-right: 0px; cursor: pointer; font-size: 0px; margin: 6px 0px 0px 0px; } .microphone { float: right; width: 48%; } .broadcast { float: left; position: absolute; width: 48%; } .ldiv2, .ldiv3 { position: relative; /*width:100%;*/ } .box2-right .box2-1 .layui-form-label { width: 35%; margin-left: 5px } .box2-right .box2-1 .layui-input-inline { width: 55%; } .ldiv3 .ldiv3-f { float: left; position: absolute; width: 24%; overflow: auto; } .ldiv3 .ldiv3-r { float: right; width: 75%; overflow: auto; } .box2-2 { margin-top: 6px; } .box2-right { width: 230px !important; float: right; } .usnboxtop { border-bottom: 1px solid #EEF1F5; line-height: 28px; padding: 0px !important; padding-left: 8px !important; height: 40px; } .usnboxleft { float: left; /*color: #3598DC;*/ color: black !important; font-size: 15px; /* font-weight: bold; */ } /*高度*/ .ldiv1 .usnbox { height: 200px; /*background-color:red !important;*/ } .ldiv2 .usnbox { height: 150px; /*background-color:red !important;*/ } .ldiv3 .usnbox { height: 300px; /*background-color:red !important;*/ } .ldiv4 .usnbox { height: 80px; background-color: transparent !important; } .box2-2 .ustree { height: 612px; } #canvas { width: 100%; height: 200px; /*background: black;*/ } </style> <style> /* 控制区域盒子 */ .control-back { width: 97%; height: 80px; /*bottom: 0;*/ position: absolute; background-color: rgba(255, 255, 255, 0.8); } /* 控制按钮 */ .control { width: 100%; height: 30px; /*margin-top:40px;*/ } .control a { margin: 0 5px; display: inline-block; } .control a:hover { opacity: 50%; } .control-btn { width: 130px; height: 30px; margin: 0 auto; } /* 上一首 */ .up { width: 30px; height: 30px; /*background: url(../img/up.png) no-repeat;*/ background-size: 20px; background-position: 50% 50%; } /* 暂停播放 */ .play-pause { width: 30px; height: 30px; /*background: url(../img/play.png) no-repeat;*/ background-size: 30px; background-position: 50% 50%; } /* 下一首 */ .down { width: 30px; height: 30px; /*background: url(../img/down.png) no-repeat;*/ background-size: 20px; background-position: 50% 50%; } /* 右侧控制按钮 */ .control-right { /* width: 180px; */ height: 30px; margin-left: calc(50% + 70px); margin-top: -30px; display: flex; /*align-items: center;*/ } /*声音进度条*/ /*.volume-back {*/ /*padding: px 0;*/ /*cursor: pointer; margin-top: 10px !important; }*/ /* 播放模式 */ .mode { width: 30px; height: 30px; /*background: url(../img/sequence.png) no-repeat;*/ background-size: 20px; background-position: left 50%; cursor: pointer; } /* 声音控制 */ /*.volume { width: 30px; height: 30px;*/ /*background: url(../img/volume.png) no-repeat;*/ /*background-size: 20px; background-position: left 50%; cursor: pointer; }*/ /* .volume-back { padding: 5px 0; cursor: pointer; } .volume-all { width: 100px; height: 2px; background-color: #e5e5e5; } .volume-now { width: 100px; height: 2px; margin-top: -2px; max-width: 100px; background-color: #5192fe; } .volume-text { margin-left: 10px; font-size: 14px; }*/ </style> <style> /* 进度条 */ .progress-bar { width: 99%; margin: 15px 15px 5px 15px; /*padding: 5px 0;*/ cursor: pointer; /*float: left;*/ } /* 当前播放进度 */ .progress-now { width: 0; height: 5px; margin-top: -5px; background-color: #5192fe; } /* 总播放进度 */ .progress-all { width:97%; height: 5px; background-color: #dee2e6; } /*文本div*/ .playfiletext { display: inline-block; width: 99%; height: 20px; margin-left: 15px; text-align: center; color: rgba(128, 130, 133, 0.8); cursor: default; overflow: hidden; } /* 播放时间进度 文本 */ .time { float: right; font-size: 1px; display: inline-block; width: 90px; height: 21px; margin-right:15px; text-align: center; color: rgba(128, 130, 133, 0.8); cursor: default; overflow: hidden; } /* 播放名称 文本 */ .playname{ float:left; font-size:1px; } a { cursor:pointer; } </style> <form class="layui-form layui-form-pane layui-form-item us-form" id="us-form" usdata="{usurl:'/extavs/avs_task/usgetentity',ussurl:'/extavs/avs_task/usupdate',usselecturl:'/extavs/avs_task/usgetselect',usload:'1',usclose:'1',usrefresh:'1'}"> <!-- 音乐 --> <audio src="/upload/avs/0f7213c0-bd81-46f3-8bcd-3c112eec949620221127.mp3"></audio> <div class="usnbox callhead"> <div class="switchheadleft"> <div class="usnboxbody usnboxbody_rtm switchhead"> <div class="layui-inline switch"> <span id="switchspan">呼叫台总开关:</span> <input class="switchbtn" type="checkbox" name="set_isrun" lay-skin="switch" lay-text="开启|关闭"> </div> </div> </div> <div class="switchheadright"> <input type="radio" name="con" disabled> <span id="switchspan">未连接</span> </div> </div> <div class="box2"> @*左侧*@ <div class="box2-left"> <div class="ldiv1"> @*音谱图*@ <div class="usnbox"> <canvas id="canvas"></canvas> </div> </div> <div class="ldiv2"> @*广播音乐*@ <div class="usnbox broadcast"> <div class="usnboxbody usnboxbody_rtm"> <div class="usnboxtop"> <div class="usnboxleft">广播音乐</div> <div class="usnboxright"> </div> </div> <div class="layui-form-item"> <div class="layui-inline"> <label class="layui-form-label">开始时间<span class="usStar">*</span></label> <div class="layui-input-inline"> </div> </div> </div> </div> </div> @*麦克风*@ <div class="usnbox microphone"> <div class="usnboxbody usnboxbody_rtm"> <div class="usnboxtop"> <div class="usnboxleft">麦克风</div> <div class="usnboxright"> </div> </div> <div class="layui-form-item"> <div class="layui-inline"> <label class="layui-form-label">开始时间<span class="usStar">*</span></label> <div class="layui-input-inline"> </div> </div> </div> </div> </div> <br style='clear:both' /><!--清除浮动--> </div> <div class="ldiv3"> @*列表*@ <div class="ldiv3-f"> <div class="usnbox playul"> <div class="usnboxtop"> <div class="usnboxleft"><i class="us-icon"></i>新增列表</div> <div class="usnboxright"> </div> </div> <ul id="ustree1" class="ztree ustree" usurl="/extavs/foldertree/useditselecttree" uscheck="3" datagridid="usdatagrid" inputs="folderid:$id" loadclickid=".btnreloadtree"></ul> </div> </div> <div class="ldiv3-r"> @*播放列表*@ <div class="usnbox playlist"> <div class="usnboxtop"> <div class="usnboxleft"><i class="us-icon"></i>播放列表</div> <div class="usnboxright"> </div> </div> <div class="layui-form-item"> <div class="layui-inline"> <label class="layui-form-label">开始时间<span class="usStar">*</span></label> <div class="layui-input-inline"> </div> </div> </div> </div> </div> <br style='clear:both' /><!--清除浮动--> </div> <div class="ldiv4"> @*播放进度条*@ <div class="usnbox"> @*<div class="usnboxtop"> </div>*@ @*<div class="usnboxleft"><i class="us-icon"></i></div> <div class="usnboxright"> </div>*@ <!-- 控制区 --> <div class="control-back"> <!-- 进度条 --> <div class="progress-bar"> <div class="progress-all"></div> <div class="progress-now"></div> </div> @*文本*@ <div class="playfiletext"> <span class="playname">-</span> <span class="time">00:00/00:00</span> <br style='clear:both' /><!--清除浮动--> </div> <!-- 控制按钮 --> <div class="control"> <!-- 上一首、下一首、暂停播放 --> <div class="control-btn"> <a class="up"><i class="us-icon"></i></a> <a class="play-pause" onclick="setPlay()"><i class="us-icon"></i></a> <a class="down"><i class="us-icon"></i></a> </div> <!-- 播放模式、声音 --> <div class="control-right"> <a href="#" class="mode"><i class="us-icon"></i></a> @*<a href="#" class="volume" onclick="setMuted()"><i class="us-icon"></i></a>*@ @*<div class="volume-back"> <div class="volume-all"></div> <div class="volume-now"></div> </div> <span class="volume-text">100</span>*@ </div> </div> </div> </div> </div> </div> @*右侧*@ <div class="box2-right"> <div class="box2-1"> <div style="margin-top:0;overflow:auto;" id="conditioninstall1" class="box-left-border"> <div class="layui-inline"> <label class="layui-form-label">名称<span class="usStar">*</span></label> <div class="layui-input-inline"> <input type="text" name="soft_name" lay-verify="required" autocomplete="off" placeholder="呼叫台名称" class="layui-input ustips" ustitle="默认名称:呼叫台任务"> </div> </div> <div class="layui-inline"> <label class="layui-form-label">优先级<span class="usStar">*</span></label> <div class="layui-input-inline"> <input type="text" name="soft_name" lay-verify="required" autocomplete="off" placeholder="优先级" class="layui-input ustips" ustitle="值越大,优先级越高"> </div> </div> <div class="layui-form-item us-submitsave"> <div class="uscenter"> <button class="layui-btn" lay-submit="" lay-filter="submit" data-pwid="ussubmit"><i class="us-icon"></i>提交</button> @* <button type="button" class="layui-btn layui-btn-primary" data-pwid="usclose"><i class="us-icon"></i>取消</button>*@ </div> </div> </div> </div> <div class="box2-2"> <div style="margin-top:0;overflow:auto;" id="conditioninstal2" class="box-left-border"> <div class="usnboxtop"> <div class="usnboxleft"><i class="us-icon"></i>接收成员</div> <div class="usnboxright"> </div> </div> <ul id="ustree" class="ztree ustree" usurl="/usrtm/roomtree/useditselecttree?ctlip=1" uscheck="4" usonclickv2="usonclickv2"></ul> <input type="text" name="receiver" placeholder="接受成员" style="display:none"> </div> </div> </div> </div> </form> @*频谱图*@ <script> var url = '/upload/avs/0f7213c0-bd81-46f3-8bcd-3c112eec9496202211271.mp3'; if (!window.AudioContext) { alert('您的浏览器不支持AudioContext'); } else { //创建上下文 var atx = new AudioContext(); var source = null; //使用Ajax获取音频文件 var request = new XMLHttpRequest(); request.open('GET', url, true); request.responseType = 'arraybuffer';//配置数据的返回类型 //加载完成 request.onload = function () { var arraybuffer = request.response; atx.decodeAudioData(arraybuffer, function (buffer) { //创建分析器 var analyser = atx.createAnalyser(); source = atx.createBufferSource(); //将source与分析器链接 source.connect(analyser); //将分析器与destination链接,这样才能形成到达扬声器的通路 analyser.connect(atx.destination); //将解码后的buffer数据复制给source source.buffer = buffer; //播放 source.start(0); //开始绘制频谱图 var canvas = document.getElementById('canvas'), cwidth = canvas.width, cheight = canvas.height - 2, meterWidth = 10,//能量条的宽度 gap = 2,//能量条的间距 meterNum = 800 / (10 + 2);//计算当前画布上能画多少条 var ctx = canvas.getContext('2d'); var capHeight = 2,//冒头的高度 capStyle = '#fff',//冒头的颜色 capYPositionArray = [];//将上一面各个冒头的位置保存到这个数组1e9fff //定义一个渐变样式用于画图 var gradient = ctx.createLinearGradient(0, 0, 0, 300); //gradient.addColorStop(1, '#0f0'); //gradient.addColorStop(0.5, '#ff0'); //gradient.addColorStop(0, '#f00'); gradient.addColorStop(1, '#1e9fff');//低音颜色 gradient.addColorStop(0.5, '#70bbf2');//中音颜色 gradient.addColorStop(0, '#1e9fff');//高音颜色 //绘制频谱图 function drawSpectrum() { var array = new Uint8Array(analyser.frequencyBinCount); analyser.getByteFrequencyData(array); var step = Math.round(array.length / meterNum);//计算从analyser中的采样步长 //清理画布 ctx.clearRect(0, 0, cwidth, cheight); //对信源数组进行抽样遍历,画出每个频谱条 for (var i = 0; i < meterNum; i++) { var value = array[i * step]; //取样作为y轴的值 //绘制缓慢降落的冒头 if (capYPositionArray.length < Math.round(meterNum)) { capYPositionArray.push(value);//初始化保存冒头位置的数组,将第一个画面位置保存 } ctx.fillStyle = capStyle; //1.开始绘制冒头 if (value < capYPositionArray[i]) { //使用前一次数据 ctx.fillRect(i * 12, cheight - (--capYPositionArray[i]), meterWidth, capHeight); } else { //否则,直接使用当前数据并记录 ctx.fillRect(i * 12, cheight - value, meterWidth, capHeight); capYPositionArray[i] = value; } //2.开始绘制频谱条 ctx.fillStyle = gradient; ctx.fillRect(i * 12/*频谱条的宽度+条间距*/, cheight - value + capHeight, meterWidth, cheight); } requestAnimationFrame(drawSpectrum); } requestAnimationFrame(drawSpectrum); }, function (e) { console.info('处理出错'); }); } request.send(); //绑定播放按钮 $('#playBtn').click(function () { var icon = $(this).find('i');; icon.toggleClass('glyphicon-play').toggleClass('glyphicon-pause'); //停止播放 source.stop(); }); } </script> @*媒体播放进度条*@ <script> var myAduio = document.getElementsByTagName('audio')[0]; var progressTime = document.getElementsByClassName('time')[0];//进度条时间 var progressplayname = document.getElementsByClassName('playname')[0];//进度条名称 var playState = false;//播放状态 console.error("myAduio"); console.error(myAduio); console.error("myAduio"); //页面加载完毕执行的方法 window.onload = function () { //initialLyrics(); //lyricsStyle = getComputedStyle(lyricsFirst, null); //setLyrics(0); //setMouseEvent(); //setTimeText(); }; // 设置播放状态 function setPlay(state) { var play_pause = document.getElementsByClassName('play-pause')[0]; if (state == null) { // 如果歌曲为暂停状态,那么获取到的state则为true,将state设置为true我们就播放 state = myAduio.paused; } // 清除计时器,不然会出现多个计时器同时进行 //clearTimeout(rollT); if (state == true) { myAduio.play(); //设置为播放图标 //play_pause.style.backgroundImage = 'url(../img/pause.png)'; play_pause.innerHTML = '<i class="us-icon"></i>'; //换播放图标 playState = true; // 开始播放的同时,同时开始设置时间进度文本,歌词滚动以及进度条位置 setTimeText(); //lyricsRoll(); //歌词滚动 setProgress(); } else { myAduio.pause(); //play_pause.style.backgroundImage = 'url(../img/play.png)'; play_pause.innerHTML = '<i class="us-icon"></i>';//换暂停图标 playState = false; } } // 设置进度文本 function setTimeText() { var nowTime = myAduio.currentTime; var allTime = myAduio.duration; // 计算时间,若为个位数,补0 if (Math.floor(nowTime % 60) < 10) { nowTime = Math.floor(nowTime / 60) + ':0' + Math.floor(nowTime % 60); } else { nowTime = Math.floor(nowTime / 60) + ':' + Math.floor(nowTime % 60); } if (Math.floor(allTime % 60) < 10) { allTime = Math.floor(allTime / 60) + ':0' + Math.floor(allTime % 60); } else { allTime = Math.floor(allTime / 60) + ':' + Math.floor(allTime % 60); } progressTime.innerText = nowTime + '/' + allTime; // 每0.1秒执行一次 if (myAduio.paused == false) { setTimeout(setTimeText, 100); } } // 设置进度条进度 function setProgress() { let progress_now = document.getElementsByClassName('progress-now')[0]; let progress_bar = document.getElementsByClassName('progress-bar')[0]; let progress = Math.floor( (myAduio.currentTime / myAduio.duration) * progress_bar.clientWidth ); progress_now.style.width = progress + 'px'; if (myAduio.paused == false) { setTimeout(setProgress, 100); } } ////好像是歌词 //let goto = document.getElementsByClassName('goto')[0]; //goto.onmouseup = function () { // nowLine = line; // myAduio.currentTime = timeArray1[line]; // setLyrics(line - 1); // setPlay(true); // lyricsMove = false; // lyricsTime_a[0].style.display = lyricsTime_a[1].style.display = lyricsTime.style.display = // 'none'; // document.onmouseup = null; //}; </script>
4、播放音量控制、输入音量控制布局
效果:
html:

<div class="ldiv2"> @*广播音乐*@ <div class="usnbox broadcast"> <div class="usnboxbody usnboxbody_rtm"> <div class="usnboxtop"> <div class="usnboxleft">广播音乐</div> <div class="usnboxright"> </div> </div> <div class="broadcastcontr"> @*图标*@ <div class="bicon"> <a class="bicon-a" onclick="setPlay1()"><i class="us-icon"></i></a> </div> @*音量条*@ <div class="bbox"> <div class="bbox-tiao"> <div class="bboxcricle" id="bboxcricle"> <div id="bboxvals">0</div> </div> @*//音量显示条*@ <div class="bboxcricle1"> </div> </div> </div> </div> </div> </div> @*麦克风*@ <div class="usnbox microphone"> <div class="usnboxbody usnboxbody_rtm"> <div class="usnboxtop"> <div class="usnboxleft">麦克风</div> <div class="usnboxright"> </div> </div> <div class="microphonecontr"> @*图标*@ <div class="micon"> <a class="micon-a" onclick="setPlay2()"><i class="us-icon"></i></a> </div> @*进度条*@ <div class="mbox"> <div class="mbox-tiao"> <div class="mboxcricle"> <div id="mboxvals">0</div> </div> @*//音量显示条*@ <div class="mboxcricle1"> </div> </div> </div> </div> </div> </div> <br style='clear:both' /><!--清除浮动--> </div>
css:

@*广播音乐*@ <style> /*盒子*/ .broadcastcontr { overflow: hidden; height: 100px; position: sticky; } /*图标*/ .bicon { width: 10%; float: left; } .bicon a i { font-size: 30px; line-height: 100px; margin-left: 10px; color: #1e9fff; } /*进度条盒子*/ .bbox { width: 90%; /*height: 10px;*/ /*border-radius: 10px;*/ /*background: #dee2e6;*/ /*position: absolute;*/ top: 0; bottom: 0; left: 0; right: 0; /*margin: auto;*/ /*cursor: pointer;*/ float: right; margin-top: 55px; /*position: absolute;*/ /* position: relative;*/ } /*进度条*/ .bbox-tiao { width: 100%; height: 10px; border-radius: 10px; background: #dee2e6; /*position: absolute;*/ top: 0; bottom: 0; left: 0; right: 0; cursor: pointer; position: relative; } /* 音量大小条 */ .bboxcricle1 { width: 0; height: 10px; margin-top: -10px; border-radius: 10px; background-color: #5192fe; } /*控制按钮*/ .bboxcricle { width: 20px; height: 20px; background: #1e9fff; /*position: absolute;*/ bottom: 0; top: 0; /*margin: auto 0;*/ border-radius: 50%; cursor: pointer; /*transition: left 0.1s linear 0s;*/ margin-top: -5px; position: absolute; /*position: relative;*/ left: 0px; } /*数字*/ #bboxvals:after { content: ""; width: 0px; height: 0px; border-top: 6px solid #1e9fff; border-left: 6px solid transparent; border-right: 6px solid transparent; border-bottom: 6px solid transparent; display: block; margin-left: 11px; font-family: "微软雅黑"; } /*数字框*/ #bboxvals { position: absolute; font-size: 20px; top: -45px; left: -10px; width: 35px; height: 35px; line-height: 35px; text-align: center; background: #1e9fff; color: white; } </style> @*麦克风*@ <style> /*盒子*/ .microphonecontr { overflow: hidden; height: 100px; } /*图标*/ .micon { width: 10%; float: left; } .micon a i { font-size: 30px; line-height: 100px; margin-left: 10px; color: #1e9fff; } .mbox { width: 90%; top: 0; bottom: 0; left: 0; right: 0; /*margin: auto;*/ cursor: pointer; float: right; margin-top: 55px; } /*进度条*/ .mbox-tiao { width: 100%; height: 10px; border-radius: 10px; background: #dee2e6; /*position: absolute;*/ top: 0; bottom: 0; left: 0; right: 0; cursor: pointer; position: relative; } .mboxcricle { width: 20px; height: 20px; background: #1e9fff; /*position: absolute;*/ bottom: 0; top: 0; /*margin: auto 0;*/ border-radius: 50%; cursor: pointer; /*transition: left 0.1s linear 0s;*/ margin-top: -5px; position: absolute; } /* 音量大小条 */ .mboxcricle1 { width: 0; height: 10px; margin-top: -10px; border-radius: 10px; background-color: #5192fe; } /*数字*/ #mboxvals:after { content: ""; width: 0px; height: 0px; border-top: 6px solid #1e9fff; border-left: 6px solid transparent; border-right: 6px solid transparent; border-bottom: 6px solid transparent; display: block; margin-left: 11px; font-family: "微软雅黑"; } /*数字框*/ #mboxvals { position: absolute; font-size: 20px; top: -45px; left: -10px; width: 35px; height: 35px; line-height: 35px; text-align: center; background: #1e9fff; color: white; } </style>
对滑块按钮css基础上更改样式-背景色为白色,添加2px边框、修改外边距使其居中
background: white; border: 2px solid #1e9fff;
margin-top: -7px;
编写JS实现滑块滑动
参考过的两个网站(参考没有出现效果)
https://www.jb51.net/article/105841.htm
(4条消息) JS——实现音量控制拖动_SSSkyCong的博客-CSDN博客_js控制音量
window.onload() 方法用于在网页加载完毕后立刻执行的操作,即当 HTML 文档加载完毕后,立刻执行某个方法。
window.onload() 通常用于 <body> 元素,在页面完全载入后(包括图片、css文件等等)执行脚本代码。
<script> window.onload = function () {
……
……
} </script>
4-1、获取滑动条、滑动按钮div
//var box1 = document.getElementsByClassName("bbox")[0];//放进度条div var bbox = document.getElementsByClassName("bbox-tiao")[0];//进度显示条bar var bboxcricle = document.getElementsByClassName("bboxcricle")[0];//进度按钮box var bboxvals = document.getElementById("bboxvals");//音量文本 var bboxcricle1 = document.getElementsByClassName("bboxcricle1")[0];//音量大小条 var mbox = document.getElementsByClassName("mbox-tiao")[0];//进度显示条bar var mboxcricle = document.getElementsByClassName("mboxcricle")[0];//进度按钮box var mboxvals = document.getElementById("mboxvals");//音量文本 var mboxcricle1 = document.getElementsByClassName("mboxcricle1")[0];//音量大小条
4-2、设置最开始默认值(默认50%)
//默认值 mboxvals.innerHTML =50;//显示数值 bboxvals.innerHTML = 50;//显示数值 bboxcricle1.style.width = bbox.offsetWidth / 2 + bboxcricle.offsetWidth / 2 + "px"; //蓝色条1长度 (进度条总长/2+滑块宽/2) mboxcricle1.style.width = bbox.offsetWidth / 2 + bboxcricle.offsetWidth / 2 + "px";//蓝色条2长度 bboxcricle.style.left = bbox.offsetWidth / 2 + "px";//滑块1位置 (进度条总长/2) mboxcricle.style.left = bbox.offsetWidth / 2 + "px";//滑块2位置 bboxvals.style.display = "none";//数值默认不显示 mboxvals.style.display = "none";//数值默认不显示
4-3、获取滑块滑到的最大长度
//滑动到最大位置px值 (进度条宽-滑块宽) var cha = bbox.offsetWidth - bboxcricle.offsetWidth; var mcha = mbox.offsetWidth - mboxcricle.offsetWidth;
4-4、设置一个变量标记状态(标记鼠标操作状态)
var ifBool = 0;//标记状态--是否按下
4-5、滑动滑块触发事件
对滑块添加鼠标放在上面事件onmouseover(放在上面事件中包括鼠标点击该滑块触发事件、取消点击触发事件)--两个滑块响应代码雷同

//鼠标放到上面触发事件onmouseover bboxcricle.onmouseover = function () { //鼠标按下按钮触发事件onmouseover //bboxvals.style.display = "";//音量大小显示 bboxcricle.onmousedown = function (ev) { let e = ev || window.event; //兼容性 let mouseX = e.clientX; //鼠标按下的位置(此时滑块所在位置) //鼠标移动发生 window.onmousemove = function (ev) { bboxvals.style.display = "";//音量大小显示 let e1 = ev || window.event; var nowx = e1.clientX;//当前移动的位置x let moveL = nowx - mouseX; //鼠标移动的距离 if (moveL <= 0) { moveL = 0; } if (moveL >= cha) { moveL = cha; } // 改变left值 bboxcricle.style.left = moveL + 'px'; // 计算数值 let bili = moveL / cha * 100; bboxvals.innerHTML = Math.ceil(bili); //音量大小条 bboxcricle1.style.width = bboxcricle.offsetLeft + bboxcricle.offsetWidth / 2 + 'px'; return false //取消默认事件 } //移开鼠标 bboxcricle.onmouseout = function () { bboxcricle.onmouseover = false; bboxvals.style.display = "none"; return false; } //松开时执行 window.onmouseup = function () { window.onmousemove = false //解绑移动事件 bboxvals.style.display = "none"; return false } } //移开鼠标 bboxcricle.onmouseout = function () { bboxcricle.onmouseover = false; return false; } return false }

//鼠标放到上面触发事件onmouseover mboxcricle.onmouseover = function () { //鼠标按下按钮触发事件onmouseover //mboxvals.style.display = "";//音量大小显示 mboxcricle.onmousedown = function (ev) { let e = ev || window.event; //兼容性 let mouseX = e.clientX; //鼠标按下的位置(此时滑块所在位置) //鼠标移动发生 window.onmousemove = function (ev) { mboxvals.style.display = "";//音量大小显示 let e1 = ev || window.event; var nowx = e1.clientX;//当前移动的位置x let moveL = nowx - mouseX; //鼠标移动的距离 // 判断最大值和最小值 if (moveL <= 0) { moveL = 0; } if (moveL >= mcha) { moveL = mcha; } // 改变left值 mboxcricle.style.left = moveL + 'px'; // 计算数值 let bili = moveL / mcha * 100; mboxvals.innerHTML = Math.ceil(bili); //音量大小条 mboxcricle1.style.width = mboxcricle.offsetLeft + mboxcricle.offsetWidth / 2 + 'px'; return false //取消默认事件 } //移开鼠标 mboxcricle.onmouseout = function () { mboxcricle.onmouseover = false; mboxvals.style.display = "none"; return false; } //松开时执行 window.onmouseup = function () { window.onmousemove = false //解绑移动事件 mboxvals.style.display = "none"; return false } } //移开鼠标 mboxcricle.onmouseout = function () { mboxcricle.onmouseover = false; return false; } return false }
4-6、点击进度条触发事件
滑块响应滑到点击进度条位置

// 点击音量条 bbox.onclick = function (ev) { //获取柱状条左边距离 var bboxL = bbox.offsetLeft; var current = bbox.offsetParent; if (current != null) { bboxL += current.offsetLeft; } var clickClientX = ev.clientX;//点击位置 let left = clickClientX - bboxL - bboxcricle.offsetWidth / 2;//获取点击相对条的位置 -按钮宽度/2 if (left <= 0) { left = 0; } if (left >= cha) { left = cha; } bboxcricle.style.left = left + 'px'; let bili = left / cha * 100; bboxvals.innerHTML = Math.ceil(bili); //音量大小条 bboxcricle1.style.width = bboxcricle.offsetLeft + bboxcricle.offsetWidth / 2 + 'px'; return false }

// 点击音量条 mbox.onclick = function (ev) { //获取柱状条左边距离 var mboxL = mbox.offsetLeft; var current = mbox.offsetParent; if (current != null) { mboxL += current.offsetLeft; } var clickClientX = ev.clientX;//点击位置 let left = clickClientX - mboxL - mboxcricle.offsetWidth / 2;//获取点击相对条的位置 -按钮宽度/2 if (left <= 0) { left = 0; } if (left >= mcha) { left = mcha; } mboxcricle.style.left = left + 'px'; let bili = left / cha * 100; mboxvals.innerHTML = Math.ceil(bili); //音量大小条 mboxcricle1.style.width = mboxcricle.offsetLeft + mboxcricle.offsetWidth / 2 + 'px'; return false }
4-7、当前未实现光标放在滑块上显示当前音量大小效果
4-8、实现滑块滑动、并在滑动期间显示音量大小数据
完整js代码:

@*广播音乐进度条*@ <script> window.onload = function () { //var box1 = document.getElementsByClassName("bbox")[0];//放进度条div var bbox = document.getElementsByClassName("bbox-tiao")[0];//进度显示条bar var bboxcricle = document.getElementsByClassName("bboxcricle")[0];//进度按钮box var bboxvals = document.getElementById("bboxvals");//音量文本 var bboxcricle1 = document.getElementsByClassName("bboxcricle1")[0];//音量大小条 var mbox = document.getElementsByClassName("mbox-tiao")[0];//进度显示条bar var mboxcricle = document.getElementsByClassName("mboxcricle")[0];//进度按钮box var mboxvals = document.getElementById("mboxvals");//音量文本 var mboxcricle1 = document.getElementsByClassName("mboxcricle1")[0];//音量大小条 //默认值 mboxvals.innerHTML =50; bboxvals.innerHTML = 50; bboxcricle1.style.width = bbox.offsetWidth / 2 + bboxcricle.offsetWidth / 2 + "px"; mboxcricle1.style.width = bbox.offsetWidth / 2 + bboxcricle.offsetWidth / 2 + "px"; bboxcricle.style.left = bbox.offsetWidth / 2 + "px"; mboxcricle.style.left = bbox.offsetWidth / 2 + "px"; bboxvals.style.display = "none"; mboxvals.style.display = "none"; //滑动到最大位置px值 var cha = bbox.offsetWidth - bboxcricle.offsetWidth; var mcha = mbox.offsetWidth - mboxcricle.offsetWidth; var ifBool = 0;//标记状态--是否按下 //鼠标放到上面触发事件onmouseover bboxcricle.onmouseover = function () { //鼠标按下按钮触发事件onmouseover //bboxvals.style.display = "";//音量大小显示 bboxcricle.onmousedown = function (ev) { let e = ev || window.event; //兼容性 let mouseX = e.clientX; //鼠标按下的位置(此时滑块所在位置) //鼠标移动发生 window.onmousemove = function (ev) { bboxvals.style.display = "";//音量大小显示 let e1 = ev || window.event; var nowx = e1.clientX;//当前移动的位置x let moveL = nowx - mouseX; //鼠标移动的距离 if (moveL <= 0) { moveL = 0; } if (moveL >= cha) { moveL = cha; } // 改变left值 bboxcricle.style.left = moveL + 'px'; // 计算数值 let bili = moveL / cha * 100; bboxvals.innerHTML = Math.ceil(bili); //音量大小条 bboxcricle1.style.width = bboxcricle.offsetLeft + bboxcricle.offsetWidth / 2 + 'px'; return false //取消默认事件 } //移开鼠标 bboxcricle.onmouseout = function () { bboxcricle.onmouseover = false; bboxvals.style.display = "none"; return false; } //松开时执行 window.onmouseup = function () { window.onmousemove = false //解绑移动事件 bboxvals.style.display = "none"; return false } } //移开鼠标 bboxcricle.onmouseout = function () { bboxcricle.onmouseover = false; return false; } return false } // 点击音量条 bbox.onclick = function (ev) { //获取柱状条左边距离 var bboxL = bbox.offsetLeft; var current = bbox.offsetParent; if (current != null) { bboxL += current.offsetLeft; } var clickClientX = ev.clientX;//点击位置 let left = clickClientX - bboxL - bboxcricle.offsetWidth / 2;//获取点击相对条的位置 -按钮宽度/2 if (left <= 0) { left = 0; } if (left >= cha) { left = cha; } bboxcricle.style.left = left + 'px'; let bili = left / cha * 100; bboxvals.innerHTML = Math.ceil(bili); //音量大小条 bboxcricle1.style.width = bboxcricle.offsetLeft + bboxcricle.offsetWidth / 2 + 'px'; return false } //鼠标放到上面触发事件onmouseover mboxcricle.onmouseover = function () { //鼠标按下按钮触发事件onmouseover //mboxvals.style.display = "";//音量大小显示 mboxcricle.onmousedown = function (ev) { let e = ev || window.event; //兼容性 let mouseX = e.clientX; //鼠标按下的位置(此时滑块所在位置) //鼠标移动发生 window.onmousemove = function (ev) { mboxvals.style.display = "";//音量大小显示 let e1 = ev || window.event; var nowx = e1.clientX;//当前移动的位置x let moveL = nowx - mouseX; //鼠标移动的距离 // 判断最大值和最小值 if (moveL <= 0) { moveL = 0; } if (moveL >= mcha) { moveL = mcha; } // 改变left值 mboxcricle.style.left = moveL + 'px'; // 计算数值 let bili = moveL / mcha * 100; mboxvals.innerHTML = Math.ceil(bili); //音量大小条 mboxcricle1.style.width = mboxcricle.offsetLeft + mboxcricle.offsetWidth / 2 + 'px'; return false //取消默认事件 } //移开鼠标 mboxcricle.onmouseout = function () { mboxcricle.onmouseover = false; mboxvals.style.display = "none"; return false; } //松开时执行 window.onmouseup = function () { window.onmousemove = false //解绑移动事件 mboxvals.style.display = "none"; return false } } //移开鼠标 mboxcricle.onmouseout = function () { mboxcricle.onmouseover = false; return false; } return false } // 点击音量条 mbox.onclick = function (ev) { //获取柱状条左边距离 var mboxL = mbox.offsetLeft; var current = mbox.offsetParent; if (current != null) { mboxL += current.offsetLeft; } var clickClientX = ev.clientX;//点击位置 let left = clickClientX - mboxL - mboxcricle.offsetWidth / 2;//获取点击相对条的位置 -按钮宽度/2 if (left <= 0) { left = 0; } if (left >= mcha) { left = mcha; } mboxcricle.style.left = left + 'px'; let bili = left / cha * 100; mboxvals.innerHTML = Math.ceil(bili); //音量大小条 mboxcricle1.style.width = mboxcricle.offsetLeft + mboxcricle.offsetWidth / 2 + 'px'; return false } } </script>

// 16、定义全局变量localStream let audioCtx = null; // 音频上下文 let source = null; // 音频源 let sysStream = null; // 系统声音音频流 let micStream = null;// 录音产生的音频流 录音产生的音频流、麦克风收集到的音频数据 let localStream = null;// 录音产生的音频流 录音产生的音频流、麦克风收集到的音频数据 let extraGain = null; //麦克风控制 let analyser = null; // 用于分析音频实时数据的节点(分析器) let track = null; let stream_dest = null; //定义全局变量pc1 var pc1; //获取呼叫台基本信息 function getCallInfo() { var url = "/extavs/avs_call/getcallTaskInfo"; ushttp.UsAjaxJSONV2(url, "", false, false, function (d) { //呼叫台基本信息 $("input[name=cname]").val(d.cname); $("input[name=cguid]").val(d.cguid); $("input[name=rank]").val(d.rank); $("input[name=id]").val(d.id); $("input[name=receiver]").val(d.receiver); //反填接收成员 let _cfg = { ustreeid: "ustree",// 控件名称 us_in_type: 1,//1.设置复选框选中节点 2.设置选择节点,可能没有复选框 us_para_key: "id",//当配置us_out_type=2的时候,配置这个,默认为id us_para_split: ",",//返回逗号分割的使用逗号,还是什么特殊字符 us_para_value: "", //当us_in_type = 1 的时候,设置的默认值; } //var receiver = $("input[name=receiver]").val(); var receiver = d.receiver; _cfg.us_para_value = receiver; if (receiver != null) { usformtool.ustree_setselect(_cfg); } }); } //媒体分类列表显示 function playlistustree() { var url = "/extavs/Avs_Call/getplayList"; ushttp.UsAjaxJSONV2(url, "", false, false, function (d) { //console.error(d); if (d.code == 0) { //$("#nav").find('span.layui-nav-bar').remove(); var da = d.results.data; if (d.results.data.length > 0) { $.each(da, function (index, value) { var name = da[index]['name']; var id = da[index]['id']; var $li = "<li class='layui-menu-item-divider' id='l" + id + "'><div class='li'><div class='lia'><a class='lianame' id='a" + id + "' onclick=getplayItem('" + id + "','" + name + "')>" + name + "</a></div><div class='aul'><a class= 'updnote' onclick =updplayList('" + id + "','" + name + "')> <i class='us-icon' style='color:#1e9fff'></i></a ><a class='deltnote' onclick=delplayList('" + id + "','" + name + "')><i class='us-icon' style='color:rgb(245, 108, 108)'></i></a></div></div></li>"; $("#nav").append($li); }) //列表添加完后再次执行渲染 xuanran(da[0]['id'], da[0]['name']); } } else { usbasic.errorMsg(d.msg); } }); } /** * * @param {any} 分类列表id * @param {any} 分类列表name */ function xuanran(l, n) { layui.use('element', function () { var element = layui.element; var layFilter = $("#nav").attr('lay-filter'); element.render('nav', layFilter); }); if (l != "") { //初始页面第一个li点击事件 getplayItem(l, n); } } /** * 获取指定分类列表下的媒体文件 * @param {any} id 分类列表id * @param {any} name 分类列表name */ function getplayItem(id, name) { $("input[name=lguid]").val(id); $("input[name=lname]").val(name); $(".lianame").css("color", "black"); $("#a" + id).css("color", "#1e9fff"); var url = "/extavs/avs_call/getlistitem?lguid=" + id; ushttp.UsAjaxJSONV2(url, "", false, false, function (d) { //usbasic.successMsg(mess); if (d.msg != "") { usbasic.warnMsg(d.msg); } else { //反序列化 --反填 var dtinfo = JSON.parse(d.data); ////格式化数据-映射表格 initDataTable(dtinfo); } }); } /** * 初始化table * @param {any} dt 媒体数据 */ function initDataTable(dt) { playitemArr = dt; layui.use(['table', 'form'], function () { var table = layui.table; itemtable = table; var form1 = layui.form; form = form1; inittabledata(dt); }); //监听开关事件 form.on('switch(setcall_isrun)', function (data) { var x = data.elem.checked;//判断开关状态 if (x == true) { start(); $(".callstatediv").css("background-color", "#67C23A"); $("#callstatetext").css("color", "#67C23A"); document.getElementById("callstatetext").innerText = "已连接"; //获取音量标签值设置麦克风音量 //var m = mboxvals.innerText; //ctrmic(m); var s = bboxvals.innerText; ctrsys(s); } else { hangup();//挂断 } }); } /** *映射表格 * @param {any} dt 媒体数据 */ function inittabledata(dt) { //将dt数据序列化保存的input里面提交 //$("#us_date_jie_us").val(JSON.stringify(dt)); itemtable.render({ elem: '#playlistItemInfo', cols: [[ //表头 { field: 'showid', align: 'center', title: '序号', width: '10%' } , { field: 'name', title: '名称', align: 'center', width: '60%' } , { field: 'mguid', title: '文件id', align: 'center', width: 10, hide: true } , { field: 'murl', title: '文件路径', align: 'center', width: 10, hide: true } , { title: '操作', align: 'center', width: '15%', templet: operate } , { title: '移动', align: 'center', width: '15%', templet: operatemove } ]], limit: 1000, data: dt , height: '250' , done: function (res, curr, count) { //数据渲染完的回调 var that = this.elem.next(); res.data.forEach(function (item, index) { if (item.color == 1 || item.color == 2 || item.color == -1) { var tr = that.find(".layui-table-box tbody tr[data-index='" + index + "']"); tr.css("color", "#5192fe"); } }); } }); } /** * 操作模板列l * @param {any} obj */ function operate(obj) { //获取行数id var rowid = obj.LAY_INDEX; var state = 0; //播放状态 var aicon = ""; var color = ""; if (playitemArr[rowid - 1]["color"] == 1) { aicon = ""; state = 5; } var src = $("#playaudio").attr("src"); if (rowid - 1 == getUrlReTable(src) || playitemArr[rowid - 1]["color"] == -1) { color = "style='color:#5192fe'"; } return '<a class="playitem" onclick="opeitem(' + rowid + ',' + state + ')"><i class="us-icon" ' + color + '>' + aicon + '</i></a> <a onclick="opeitem(' + rowid + ',1)"><i class="us-icon" ' + color + '></i></a>'; } /** *移动模板列 * @param {any} obj */ function operatemove(obj) { var posbtn = "" if (playitemArr.length > 1) { //获取行数id var rowid = obj.LAY_INDEX; var color = ""; if (playitemArr[rowid - 1]["color"] == 1 || playitemArr[rowid - 1]["color"] == 2 || playitemArr[rowid - 1]["color"] == -1) { aicon = ""; state = 5; color = "style='color:#5192fe'"; } var up = '<a onclick="opeitem(' + rowid + ',3)"><i class="us-icon" ' + color + '></i></a> '; var down = '<a onclick="opeitem(' + rowid + ',4)"><i class="us-icon" ' + color + '></i></a>'; if (rowid == 1) { posbtn = down; } else if (rowid == playitemArr.length) { posbtn = up; } else { posbtn = up + down; } } return posbtn; } /** * 操作列模板点击事件操作媒体文件 * @param {any} rid 当前行id * @param {any} m 不同执行方法 0播放 1删除 3上移 4下移 5暂停 */ function opeitem(rid, m) { var lguid = $("input[name=lguid]").val();//播放列表id var listname = $("input[name=lname]").val();//播放列表name var updurl = "/extavs/avs_call/editlistitem?isdel=del" + "&lguid=" + lguid + "&lname=" + listname; if (m == 0) { for (var i = 0; i < playitemArr.length; i++) { if (playitemArr[i]["color"] == 1) { play_pause.alt = 1; } playitemArr[i]["color"] = 0; } //播放 playitemArr[rid - 1]["color"] = 1; var url = playitemArr[rid - 1]["murl"]; inittabledata(playitemArr); //设置路径 $("#playaudio").attr("src", url); document.getElementsByClassName('playname')[0].innerText = playitemArr[rid - 1]["name"]; //console.error(playitemArr[rid - 1]["name"]); playctr(3); } if (m == 1) { //删除 var cnfstr = "您确实要删除改媒体文件吗?"; usalert.UsConfirm(cnfstr, function (b) { if (b) { //获取对应下标进行数组删除 let getLocation = playitemArr.indexOf(playitemArr[rid - 1]); playitemArr.splice(getLocation, 1); renumber();//整理 //调用api删除 updurl = updurl + "&playlistItem=" + JSON.stringify(playitemArr); updplayItem(updurl); } }); } if (m == 3) { //上移 var c1 = playitemArr[rid - 1]; var c2 = playitemArr[rid - 2]; playitemArr[rid - 1] = c2; playitemArr[rid - 2] = c1; //重新编号 renumber(); //调用api修改 updurl = updurl + "&playlistItem=" + JSON.stringify(playitemArr); updplayItem(updurl); } if (m == 4) { //下移 var c1 = playitemArr[rid - 1]; var c2 = playitemArr[rid]; playitemArr[rid - 1] = c2; playitemArr[rid] = c1; //重新编号 renumber(); //调用api修改 updurl = updurl + "&playlistItem=" + JSON.stringify(playitemArr); updplayItem(updurl); } if (m == 5) { //暂停 playitemArr[rid - 1]["color"] = 2; inittabledata(playitemArr); playctr(3); } } //新增播放列表 function addplayList() { var cguid = $("input[name=cguid]").val(); var url = "/extavs/avs_call/edit?isdel=add&cguid=" + cguid; usopen.UsSystemOpenURL('<i class="us-icon"></i>新增', url, "400", "300", function () { //console.log(uscommon.isRefreshTable()); if (uscommon.isRefreshTable()) { us_tree_auto_click(); } }); } /** * 修改播放列表名称 * @param {any} id 列表分类id * @param {any} name 列表分类名称 */ function updplayList(id, name) { //console.error(JSON.stringify(playitemArr).toString()); var lguid = $("input[name=lguid]").val();//播放列表id var cguid = $("input[name=cguid]").val(); getplayItem(id, name); var url = "/extavs/avs_call/editlist?isdel=upd&cguid=" + cguid + "&lguid=" + id + "&lname=" + name + "&playlist_item=" + escape(JSON.stringify(playitemArr)).replace(/%/g, '%25'); usopen.UsSystemOpenURL('<i class="us-icon"></i>编辑-[' + name + "]", url, "400", "300", function () { if (uscommon.isRefreshTable()) { us_tree_auto_click(); } }); } /** * 删除播放列表 * @param {any} id 列表分类id * @param {any} name 列表分类名称 */ function delplayList(id, name) { var cnfstr = "您确实要删除[" + name + "]媒体分类列表吗?"; usalert.UsConfirm(cnfstr, function (b) { if (b) { //var lguid = $("input[name=lguid]").val();//播放列表id var cguid = $("input[name=cguid]").val(); var url = "/extavs/avs_call/usdelete?cguid=" + cguid + "&lguid=" + id; ushttp.UsAjaxJSONV2(url, "", false, false, function (d) { if (d.result == 0) { usbasic.successMsg(d.msg); } else { usbasic.errorMsg(d.msg); } }); } }); } //选择添加媒体 function addplayItem() { var lguid = $("input[name=lguid]").val();//播放列表id var listname = $("input[name=lname]").val();//播放列表name if (lguid == "") { usbasic.warnMsg("请选择媒体分类列表"); } else { var url = "/extavs/avs_medium/selecttree?mrmodel=1&ctlip=1"; //var spanid2 = "idtnoteid" + addnoteid; usopen.UsSystemOpenURLParent('<i class="us-icon"></i>选择媒体', url, "500", "580", function () { var vReturn = uscommon.getReturnData(); if (vReturn != "") { var json = JSON.parse(vReturn); if (json.length == 0) { usbasic.warnMsg("选择媒体数据有误,请重新选择!"); return; } else { for (var i = 0; i < json.length; i++) { //映射table var orderindex = playitemArr.length + 1; var nc = { "showid": orderindex, "murl": "", "name": json[i].v, "mguid": json[i].k, "color": 0 }; playitemArr.push(nc); } //console.log(nc); console.debug(playitemArr); //inittabledata(playitemArr); //调用api添加 var url = "/extavs/avs_call/editlistitem?isdel=add" + "&lguid=" + lguid + "&lname=" + listname + "&playlistItem=" + JSON.stringify(playitemArr); updplayItem(url); } } }) } } /** * 公共方法1 操作媒体文件方法 * @param {any} urls 请求api路径 */ function updplayItem(urls) { ushttp.UsAjaxJSONV2(urls, "", false, false, function (d) { if (d.result == 0) { usbasic.successMsg(d.msg); } else { usbasic.errorMsg(d.msg); } }); } //公共方法2 列表重新编号 function renumber() { for (var i = 0; i < playitemArr.length; i++) { playitemArr[i]["showid"] = i + 1; inittabledata(playitemArr); } } //var box1 = document.getElementsByClassName("bbox")[0];//放进度条div var bbox = document.getElementsByClassName("bbox-tiao")[0];//进度显示条bar var bboxcricle = document.getElementsByClassName("bboxcricle")[0];//进度按钮box var bboxvals = document.getElementById("bboxvals");//音量文本 var bboxcricle1 = document.getElementsByClassName("bboxcricle1")[0];//音量大小条 var mbox = document.getElementsByClassName("mbox-tiao")[0];//进度显示条bar var mboxcricle = document.getElementsByClassName("mboxcricle")[0];//进度按钮box var mboxvals = document.getElementById("mboxvals");//音量文本 var mboxcricle1 = document.getElementsByClassName("mboxcricle1")[0];//音量大小条 var progressall = document.getElementsByClassName("progress-all")[0];//音乐进度条 var progressnowctor = document.getElementsByClassName("progress-nowctor")[0];//音乐进度滑块 var myAduio = document.getElementsByTagName('audio')[0]; //var myAduio = $("#playaudio"); var progressTime = document.getElementsByClassName('time')[0];//进度条时间 var progressplayname = document.getElementsByClassName('playname')[0];//进度条名称 let progress_now = document.getElementsByClassName('progress-now')[0]; let progress_bar = document.getElementsByClassName('progress-bar')[0]; var playState = false;//播放状态 //控制区域播放暂停按钮 var play_pause = document.getElementsByClassName('play-pause')[0]; //一开始加载系统声音进度条、麦克风进度条、媒体播放进度条点击事件 window.onload = function () { //默认值 mboxvals.innerHTML = 50; bboxvals.innerHTML = 50; bboxcricle1.style.width = bbox.offsetWidth / 2 + bboxcricle.offsetWidth / 2 + "px"; mboxcricle1.style.width = bbox.offsetWidth / 2 + bboxcricle.offsetWidth / 2 + "px"; bboxcricle.style.left = bbox.offsetWidth / 2 + "px"; mboxcricle.style.left = bbox.offsetWidth / 2 + "px"; bboxvals.style.display = "none"; mboxvals.style.display = "none"; //滑动到最大位置px值 var cha = bbox.offsetWidth - bboxcricle.offsetWidth; var mcha = mbox.offsetWidth - mboxcricle.offsetWidth; var yuecha = progressall.offsetWidth - progressnowctor.offsetWidth; var ifBool = 0;//标记状态--是否按下 //鼠标放到上面触发事件onmouseover bboxcricle.onmouseover = function () { //鼠标按下按钮触发事件onmouseover //bboxvals.style.display = "";//音量大小显示 bboxcricle.onmousedown = function (ev) { let e = ev || window.event; //兼容性 let mouseX = e.clientX; //鼠标按下的位置(此时滑块所在位置) //鼠标移动发生 window.onmousemove = function (ev) { bboxvals.style.display = "";//音量大小显示 let e1 = ev || window.event; var nowx = e1.clientX;//当前移动的位置x let moveL = nowx - mouseX; //鼠标移动的距离 if (moveL <= 0) { moveL = 0; } if (moveL >= cha) { moveL = cha; } // 改变left值 bboxcricle.style.left = moveL + 'px'; // 计算数值 let bili = moveL / cha * 100; bboxvals.innerHTML = Math.ceil(bili); //音量大小条 bboxcricle1.style.width = bboxcricle.offsetLeft + bboxcricle.offsetWidth / 2 + 'px'; //改变音量 ctrsys(Math.ceil(bili)); return false //取消默认事件 } //移开鼠标 bboxcricle.onmouseout = function () { bboxcricle.onmouseover = false; bboxvals.style.display = "none"; return false; } //松开时执行 window.onmouseup = function () { window.onmousemove = false //解绑移动事件 bboxvals.style.display = "none"; return false } } //移开鼠标 bboxcricle.onmouseout = function () { bboxcricle.onmouseover = false; return false; } return false } // 点击音量条 bbox.onclick = function (ev) { //获取柱状条左边距离 var bboxL = bbox.offsetLeft; var current = bbox.offsetParent; if (current != null) { bboxL += current.offsetLeft; } var clickClientX = ev.clientX;//点击位置 let left = clickClientX - bboxL - bboxcricle.offsetWidth / 2;//获取点击相对条的位置 -按钮宽度/2 if (left <= 0) { left = 0; } if (left >= cha) { left = cha; } bboxcricle.style.left = left + 'px'; let bili = left / cha * 100; bboxvals.innerHTML = Math.ceil(bili); //音量大小条 bboxcricle1.style.width = bboxcricle.offsetLeft + bboxcricle.offsetWidth / 2 + 'px'; ////改变音量 ctrsys(Math.ceil(bili)); return false } //鼠标放到上面触发事件onmouseover mboxcricle.onmouseover = function () { //鼠标按下按钮触发事件onmouseover //mboxvals.style.display = "";//音量大小显示 mboxcricle.onmousedown = function (ev) { let e = ev || window.event; //兼容性 let mouseX = e.clientX; //鼠标按下的位置(此时滑块所在位置) //鼠标移动发生 window.onmousemove = function (ev) { mboxvals.style.display = "";//音量大小显示 let e1 = ev || window.event; var nowx = e1.clientX;//当前移动的位置x let moveL = nowx - mouseX; //鼠标移动的距离 // 判断最大值和最小值 if (moveL <= 0) { moveL = 0; } if (moveL >= mcha) { moveL = mcha; } // 改变left值 mboxcricle.style.left = moveL + 'px'; // 计算数值 let bili = moveL / mcha * 100; mboxvals.innerHTML = Math.ceil(bili); //音量大小条 mboxcricle1.style.width = mboxcricle.offsetLeft + mboxcricle.offsetWidth / 2 + 'px'; //改变音量 if (extraGain != "") { ctrmic(Math.ceil(bili)); } return false //取消默认事件 } //移开鼠标 mboxcricle.onmouseout = function () { mboxcricle.onmouseover = false; mboxvals.style.display = "none"; return false; } //松开时执行 window.onmouseup = function () { window.onmousemove = false //解绑移动事件 mboxvals.style.display = "none"; return false } } //移开鼠标 mboxcricle.onmouseout = function () { mboxcricle.onmouseover = false; return false; } return false } // 点击音量条 mbox.onclick = function (ev) { //获取柱状条左边距离 var mboxL = mbox.offsetLeft; var current = mbox.offsetParent; if (current != null) { mboxL += current.offsetLeft; } var clickClientX = ev.clientX;//点击位置 let left = clickClientX - mboxL - mboxcricle.offsetWidth / 2;//获取点击相对条的位置 -按钮宽度/2 if (left <= 0) { left = 0; } if (left >= mcha) { left = mcha; } mboxcricle.style.left = left + 'px'; let bili = left / cha * 100; mboxvals.innerHTML = Math.ceil(bili); //音量大小条 mboxcricle1.style.width = mboxcricle.offsetLeft + mboxcricle.offsetWidth / 2 + 'px'; //改变音量 if (extraGain != "") { ctrmic(Math.ceil(bili)); } return false } //鼠标放到上面触发事件onmouseover progressnowctor.onmouseover = function () { //鼠标按下按钮触发事件onmouseover progressnowctor.onmousedown = function (ev) { let e = ev || window.event; //兼容性 let mouseX = e.clientX; //鼠标按下的位置(此时滑块所在位置) //鼠标移动发生 window.onmousemove = function (ev) { let e1 = ev || window.event; var nowx = e1.clientX;//当前移动的位置x let moveL = nowx - mouseX; //鼠标移动的距离 // 判断最大值和最小值 if (moveL <= 0) { moveL = 0; } if (moveL >= yuecha) { moveL = yuecha; } // 改变滑块left值 progressnowctor.style.left = moveL + 'px'; //快进时间 var allTime = myAduio.duration; var ytime = (progressnowctor.offsetLeft) * allTime / yuecha; var nytime = ""; //转换显示 nytime = getTimeStr(ytime); if (isNaN(allTime)) { nytime = "00:00"; allTime = "00:00"; } else { allTime = getTimeStr(allTime); } if (nytime != "00:00") { //设置快进 sspeed(ytime); } progressTime.innerText = nytime + '/' + allTime; progress_now.style.width = progressnowctor.offsetLeft + progressnowctor.offsetWidth / 2 + 'px'; return false //取消默认事件 } //移开鼠标 progressnowctor.onmouseout = function () { progressnowctor.onmouseover = false; return false; } //松开时执行 window.onmouseup = function () { window.onmousemove = false //解绑移动事件 return false } } //移开鼠标 progressnowctor.onmouseout = function () { progressnowctor.onmouseover = false; return false; } return false } // 点击音乐进度条 progressall.onclick = function (ev) { //获取柱状条左边距离 var progressallL = progressall.offsetLeft; var current = progressall.offsetParent; if (current != null) { progressallL += current.offsetLeft; } var clickClientX = ev.clientX;//点击位置 let left = clickClientX - progressallL - progressnowctor.offsetWidth / 2;//获取点击相对条的位置 -按钮宽度/2 if (left <= 0) { left = 0; } if (left >= yuecha) { left = yuecha; } // 改变滑块left值 progressnowctor.style.left = left + 'px'; //快进时间 var allTime = myAduio.duration; var ytime = (progressnowctor.offsetLeft) * allTime / yuecha; var nytime = ""; //转换显示 nytime = getTimeStr(ytime); if (isNaN(allTime)) { nytime = "00:00"; allTime = "00:00"; } else { allTime = getTimeStr(allTime); } if (nytime != "00:00") { //设置快进 sspeed(ytime); } progressTime.innerText = nytime + '/' + allTime; progress_now.style.width = progressnowctor.offsetLeft + progressnowctor.offsetWidth / 2 + 'px'; return false //取消默认事件 } } //切换播放模式 function playmodectr() { var mode = document.getElementsByClassName("mode")[0]; //列表循环 if (mode.alt == 1) { mode.alt = 2; mode.src = "/assets2/avs/images/mode4.png"; }//单曲循环 else if (mode.alt == 2) { mode.alt = 3; mode.src = "/assets2/avs/images/mode2.png"; }//随机播放 else if (mode.alt == 3) { mode.alt = 4; mode.src = "/assets2/avs/images/mode3.png"; }//顺序播放 else if (mode.alt == 4) { mode.alt = 1; mode.src = "/assets2/avs/images/mode1.png"; } } /** * 控制媒体播放播放、暂停 * @param {any} state 判断播放暂停 */ function setPlay(state) { //if (state == null) { // // 如果歌曲为暂停状态,那么获取到的state则为true,将state设置为true我们就播放 // state = myAduio.paused; //} // 清除计时器,不然会出现多个计时器同时进行 //clearTimeout(rollT); if (state == true) { myAduio.play(); //设置为播放图标 //play_pause.style.backgroundImage = 'url(../img/pause.png)'; playState = true; // 开始播放的同时,同时开始设置时间进度文本,歌词滚动以及进度条位置 setTimeText(); //lyricsRoll(); //歌词滚动 setProgress(); } else { myAduio.pause(); //play_pause.style.backgroundImage = 'url(../img/play.png)'; //play_pause.innerHTML = '<i class="us-icon"></i>';//换暂停图标 playState = false; } } //播放结束触发事件 myAduio.addEventListener('ended', function () { //媒体播放结束 playctr(1); }, false); // 设置进度文本 function setTimeText() { var nowTime = myAduio.currentTime; var allTime = myAduio.duration; // 计算时间,若为个位数,补0 nowTime = getTimeStr(nowTime); aTime = allTime; if (isNaN(allTime)) { allTime = "00:00"; nowTime = "00:00"; } else { allTime = getTimeStr(allTime); } progressTime.innerText = nowTime + '/' + allTime; // 每0.1秒执行一次 if (myAduio.paused == false) { setTimeout(setTimeText, 100); } } // 设置进度条进度 function setProgress() { let progress = Math.floor( (myAduio.currentTime / myAduio.duration) * progressall.clientWidth ); progress_now.style.width = progress + 'px'; progressnowctor.style.left = progress - progressnowctor.offsetWidth / 2 + 'px'; if (myAduio.paused == false) { setTimeout(setProgress, 100); } } /** * 格式化显示时间字符串 00:00 * @param {any} t 时间 ---秒 */ function getTimeStr(t) { var reTimeStr = ""; if (Math.floor(t % 60) < 10) { reTimeStr = Math.floor(t / 60) + ':0' + Math.floor(t % 60); } else { reTimeStr = Math.floor(t / 60) + ':' + Math.floor(t % 60); } return reTimeStr; } /** * 媒体控制公共方法1 * @param {any} p 不同功能值 */ function playctr(p) { var src = $("#playaudio").attr("src"); var u = -1; if (src != "") { u = getUrlReTable(src); } var url = ""; //新下标 var newu = u; //播放模式 if (p == 1) { //获取播放模式 var mode = document.getElementsByClassName("mode")[0]; //顺序播放 if (mode.alt == 1) { if (u == playitemArr.length - 1) { newu = -1; } else { newu = u + 1; } }//列表循环 else if (mode.alt == 2) { if (u != playitemArr.length - 1) { newu = u + 1; } else { newu = 0; } }//单曲循环 else if (mode.alt == 3) { newu = u; }//随机播放 else if (mode.alt == 4) { //随机下标 var i = RandomNumBoth(0, playitemArr.length - 1); newu = i; } if (mode.alt != 3) { playitemArr[u]["color"] = 0; } if (newu != -1) { url = playitemArr[newu]["murl"]; playitemArr[newu]["color"] = 1; $("#playaudio").attr("src", url); setPlay(true); } else { //列表循环结束停止 newu = u; url = playitemArr[u]["murl"]; play_pause.src = "/assets2/avs/images/stop.png"; play_pause.alt = 1; playitemArr[u]["color"] = -1; $("#playaudio").attr("src", url); } } //上一首 if (p == 2) { if (src != "") { if (u > 0) { $("#playaudio").attr("src", playitemArr[u - 1]["murl"]); setPlay(true); playitemArr[u - 1]["color"] = 1; playitemArr[u]["color"] = 0; newu = u - 1; } } } //播放+暂停 if (p == 3) { if (play_pause.alt == 1) { if (src == "") { playitemArr[0]["color"] = 1; $("#playaudio").attr("src", playitemArr[0]["murl"]); newu = 0; u = newu; } else { playitemArr[u]["color"] = 1; } //播放 play_pause.src = "/assets2/avs/images/start.png"; play_pause.alt = 2; setPlay(true); } else { //暂停 play_pause.src = "/assets2/avs/images/stop.png"; playitemArr[u]["color"] = 2; play_pause.alt = 1; setPlay(false); } } //下一首 if (p == 4) { if (src != "") { if (u < playitemArr.length - 1) { $("#playaudio").attr("src", playitemArr[u + 1]["murl"]); setPlay(true); playitemArr[u + 1]["color"] = 1; playitemArr[u]["color"] = 0; newu = u + 1; } } } inittabledata(playitemArr); if (u == -1) { document.getElementsByClassName('playname')[0].innerText = "暂无播放文件"; } else { document.getElementsByClassName('playname')[0].innerText = playitemArr[newu]["name"]; } } /** * 公共方法三 根据当前媒体url获取其下标 * @param {any} u 媒体路径值 */ function getUrlReTable(u) { for (var i = 0; i < playitemArr.length; i++) { if (playitemArr[i]["murl"] == u) { return i; } } } /** * 公共方法四 返回随机值 * @param {any} Min 最小 * @param {any} Max 最大 */ function RandomNumBoth(Min, Max) { var Range = Max - Min; var Rand = Math.random(); var num = Min + Math.round(Rand * Range); //四舍五入 return num; } //呼叫台开启 function start() { //initMain() const AudioContext = window.AudioContext || window.webkitAudioContext; audioCtx = new AudioContext(); //获取系统媒体stream getSysStream(); //混音 if (sysStream != null && micStream != null) { getNewStream(sysStream, micStream) } else if (sysStream != null) { localStream = sysStream; } else { localStream = micStream; } //绘制频谱 initAudioData(localStream); //实现呼叫 call(); } /** * //混音 * @param {any} SysStream 系统媒体流 * @param {any} micStream 麦克风媒体流 */ function getNewStream(SysStream, micStream) { if (!SysStream.getAudioTracks().length) { SysStream.addTrack(micStream.getAudioTracks()[0]) return SysStream; } var context = new AudioContext(); var baseSource = context.createMediaStreamSource(SysStream); var extraSource = context.createMediaStreamSource(micStream); var dest = context.createMediaStreamDestination(); var baseGain = context.createGain(); extraGain = context.createGain(); baseGain.gain.value = 0.5; extraGain.gain.value = 0.5; //混音 baseSource.connect(baseGain).connect(dest); extraSource.connect(extraGain).connect(dest); //gainNode extraGain.connect(context.destination); //设置麦克风音量 ctrmic(); localStream = dest.stream; } /** * 音频数据处理--绘制频谱 * @param {any} stream 媒体流 */ function initAudioData(stream) { //localStream = stream; // 创建音频上下文 audioCtx = new (window.AudioContext || window.webkitAudioContext)(); // 创建音频源 -将声音输入这个对象 source = audioCtx.createMediaStreamSource(stream); // 创建音频分析节点 analyser = audioCtx.createAnalyser(); // fftSize决定了能够获取到的音频数据的数量 analyser.fftSize = 4096; // 音频源连接至analyser source.connect(analyser); // analyserNode再连接至扬声器播放--本人不需要暂时注释掉了 analyser.connect(audioCtx.destination); // 简单用定时器来绘制波形图,该文档使用requestAnimationFrame来以屏幕刷新的评率来反复执行绘制函数 //animateFrame = setInterval(drawWaver, 60); //开始绘制频谱图 var canvas = document.getElementById('canvas'), cwidth = canvas.width, cheight = canvas.height - 2, meterWidth = 10,//能量条的宽度 gap = 2,//能量条的间距 meterNum = 800 / (10 + 2);//计算当前画布上能画多少条 var ctx = canvas.getContext('2d'); var capHeight = 2,//冒头的高度 capStyle = '#fff',//冒头的颜色 capYPositionArray = [];//将上一面各个冒头的位置保存到这个数组1e9fff //定义一个渐变样式用于画图 var gradient = ctx.createLinearGradient(0, 0, 0, 300); //gradient.addColorStop(1, '#0f0'); //gradient.addColorStop(0.5, '#ff0'); //gradient.addColorStop(0, '#f00'); gradient.addColorStop(1, '#1e9fff');//低音颜色 gradient.addColorStop(0.5, '#70bbf2');//中音颜色 gradient.addColorStop(0, '#1e9fff');//高音颜色 //绘制频谱图 function drawSpectrum() { var array = new Uint8Array(analyser.frequencyBinCount); analyser.getByteFrequencyData(array); var step = Math.round(array.length / meterNum);//计算从analyser中的采样步长 //清理画布 ctx.clearRect(0, 0, cwidth, cheight); //对信源数组进行抽样遍历,画出每个频谱条 for (var i = 0; i < meterNum; i++) { var value = array[i * step]; //取样作为y轴的值 //绘制缓慢降落的冒头 if (capYPositionArray.length < Math.round(meterNum)) { capYPositionArray.push(value);//初始化保存冒头位置的数组,将第一个画面位置保存 } ctx.fillStyle = capStyle; //1.开始绘制冒头 if (value < capYPositionArray[i]) { //使用前一次数据 ctx.fillRect(i * 12, cheight - (--capYPositionArray[i]), meterWidth, capHeight); } else { //否则,直接使用当前数据并记录 ctx.fillRect(i * 12, cheight - value, meterWidth, capHeight); capYPositionArray[i] = value; } //2.开始绘制频谱条 ctx.fillStyle = gradient; ctx.fillRect(i * 12/*频谱条的宽度+条间距*/, cheight - value + capHeight, meterWidth, cheight); } //用requestAnimationFrame来以屏幕刷新的评率来反复执行绘制函数 requestAnimationFrame(drawSpectrum); } //用requestAnimationFrame来以屏幕刷新的评率来反复执行绘制函数 requestAnimationFrame(drawSpectrum); } /** * 公共方法 处理错误 * @param {any} err 错误信息值 */ function handleError(err) { console.log("Failed to call getUserMedia", err); } //实现call function call() { var offerOptions = { offerToReceiveAudio: 1, offerToReceiveVideo: 0 } pc1 = new RTCPeerConnection(); // RTCPeerConnection 的属性 onicecandidate (是一个事件触发器 event handler) 能够让函数在事件icecandidate发生在实例 RTCPeerConnection 上时被调用。 只要本地代理ICE 需要通过信令服务器传递信息给其他对等端时就会触发。 这让本地代理与其他对等体相协商而浏览器本身在使用时无需知道任何详细的有关信令技术的细节,只需要简单地应用这种方法就可使用您选择的任何消息传递技术将ICE候选发送到远程对等方。 //pc1.onicecandidate = (e) => { // pc2.addIceCandidate(e.candidate) // .catch(handleError); // console.log('pc1 ICE candidate:', e.candidate); //} //console.error(localStream); pc1.addStream(localStream); //pc1.addStream(localStream1); pc1.createOffer(offerOptions) .then(getOffer) .catch(handleError); } /** * 获取offer和answer 实现RTC * @param {any} offer */ function getOffer(offer) { //获取到了offer pc1.setLocalDescription(offer); /* console.error(offer);*/ var sdp64 = window.btoa(offer.sdp) // 第三方接口需要base64编码的sdp数据 //调用第三方接口并获取返回的answer var Answer = getAnswer(sdp64); //解码 var bitmap = window.atob(Answer); // 解码 var RTCSessionDescription1 = { type: "answer", sdp: bitmap } pc1.setRemoteDescription(new RTCSessionDescription(RTCSessionDescription1), function () { //pc1.createAnswer(function (bitmap) { // pc1.setLocalDescription(offer, function () { // // send the answer to the remote connection // }) //}) }); //console.error(Answer); //console.error(bitmap); } /** * 第三方提供推流技术 从第三方获取answer * @param {any} sdp64 base64编码的sdp数据 */ function getAnswer(sdp64) { //获取呼叫台id var answer = ""; var cguid = $("input[name=cguid]").val(); var url = "/extavs/avs_call/start?cguid=" + cguid + "&offer=" + sdp64; ushttp.UsAjaxJSONV2(url, "", false, false, function (d) { //console.error(d); if (d.msg != "") { usbasic.errorMsg(d.msg); } else { answer = d.data; } }); return answer; } //呼叫台关闭 function hangup() { pc1.close(); pc1 = null; $(".callstatediv").css("background-color", "#909399"); $("#callstatetext").css("color", "#909399"); document.getElementById("callstatetext").innerText = "未连接"; } //获取系统媒体stream function getSysStream() { //获取音源 将音源放入audioContext中 // 获取界面auido标签 const audioElement = document.querySelector('audio'); if (track == null) { //通过使用 createMediaElementSource() 方法,创建了一个音源 track = audioCtx.createMediaElementSource(audioElement); stream_dest = audioCtx.createMediaStreamDestination(); } track.connect(stream_dest); sysStream = stream_dest.stream;//获取系统声音stream } //获取麦克风stream function getmicStream() { var constraints = { video: false, audio: true, }; if (!navigator.mediaDevices || !navigator.mediaDevices.getUserMedia) { console.error('浏览器不支持getUserMedia'); return; } else { navigator.mediaDevices.getUserMedia(constraints).then( function (stream) { micStream = stream; } ).catch(handleError); } } //麦克风音量控制 function ctrmic() { var m = mboxvals.innerText; if (extraGain != null) { if (document.getElementById("mimg").alt == 1) { extraGain.gain.setValueAtTime(m / 100, audioCtx.currentTime); } else { extraGain.gain.setValueAtTime(0, audioCtx.currentTime); } } } //系统音乐音量控制 function ctrsys() { var b = bboxvals.innerText; const playaudio = document.querySelector('audio#playaudio'); if (document.getElementById("bimg").alt == 1) { playaudio.volume = b / 100; } else { playaudio.volume = 0; } } /** * 系统音乐快进 * @param {any} p 秒 */ function sspeed(p) { const playaudio = document.querySelector('audio#playaudio'); playaudio.currentTime = p; } //系统静音和开启声音 function setPlay1() { //获取状态 var bimg = document.getElementById("bimg"); const playaudio = document.querySelector('audio#playaudio'); //静音 if (bimg.alt == 1) { bimg.alt = 2; bimg.src = "/assets2/avs/images/close.png"; ctrsys(); } else { //开启音量alt bimg.alt = 1; bimg.src = "/assets2/avs/images/open.png"; ctrsys(); } } //麦克风静音和开启声音 function setPlay2() { //获取状态 var mimg = document.getElementById("mimg"); //静音 if (mimg.alt == 1) { mimg.alt = 2; mimg.src = "/assets2/avs/images/micclose.png"; if (extraGain != null) { ctrmic(); } } else { mimg.alt = 1; mimg.src = "/assets2/avs/images/mic.png"; if (extraGain != null) { ctrmic(); } } }

.layui-form-pane .layui-form-switch, .layui-form-pane .layui-form-radio { margin-top: 1px; margin-left: 10px; } /*状态按钮*/ .callstatediv { width: 15px; height: 15px; background-color: #909399; float: left; border-radius: 50%; margin: 5px 10px 0px 0px; /* margin: 0 auto; */ } #callstatetext { float: right; /* margin-top: 5px; */ margin: 2px 10px 0px 0px; } .box2-left { position: absolute; top: 0; left: 0; right: 240px; padding: 0px !important; } .usnbox { border: 1px solid #E7ECF1; padding: 8px; margin-bottom: 8px; margin-top: 0px !important; background-color: #ffffff; } #switchspan { vertical-align: middle; } .switchhead { padding: 0px !important; /* vertical-align: middle; */ } .switchheadright { float: right } .switchheadleft { float: left } .callhead { overflow: hidden; /*父元素高度塌陷*/ } .layui-form-radio { display: inline-block; vertical-align: middle; line-height: 28px; padding-right: 0px; cursor: pointer; font-size: 0px; margin: 6px 0px 0px 0px; } .microphone { float: right; width: 48%; } .broadcast { float: left; position: absolute; width: 48%; } .ldiv2, .ldiv3 { position: relative; /*width:100%;*/ } .box2-right .box2-1 .layui-form-label { width: 35%; margin-left: 5px } .box2-right .box2-1 .layui-input-inline { width: 55%; } .ldiv3 .ldiv3-f { float: left; position: absolute; width: 20%; overflow: auto; } .ldiv3 .ldiv3-r { float: right; width: 79%; overflow: auto; } .box2-2 { margin-top: 6px; } .box2-right { width: 230px !important; float: right; } .usnboxtop { border-bottom: 1px solid #EEF1F5; line-height: 28px; padding: 0px !important; padding-left: 8px !important; height: 40px; } .usnboxleft { float: left; /*color: #3598DC;*/ color: black !important; font-size: 15px; /* font-weight: bold; */ } /*高度*/ .ldiv1 .usnbox { height: 200px; /*background-color:red !important;*/ } .ldiv2 .usnbox { height: 150px; /*background-color:red !important;*/ } .ldiv3 .usnbox { height: 300px; /*background-color:red !important;*/ } .ldiv4 .usnbox { height: 60px; background-color: transparent !important; } .box2-2 .ustree { height: 592px; } #canvas { width: 100%; height: 200px; /*background: black;*/ } /* 控制区域盒子 */ .control-back { width: 97%; height: 60px; /*bottom: 0;*/ position: absolute; background-color: rgba(255, 255, 255, 0.8); } .control1 { width: 75%; float: right; height: 40px; margin-top: 15px; } /* 控制按钮 */ .control { width: 25%; float: left; height: 40px; margin-top: 15px; } .control .mode { margin-right: 20px; } .control img { margin-right: 15px; width: 30px; height: 30px; cursor: pointer; } /* .control a { margin: 0 5px; display: inline-block; } .control a:hover { opacity: 50%; }*/ /*.control-btn { width: 130px; height: 30px; margin: 0 auto; }*/ /* 上一首 */ /*.up { width: 30px; height: 30px;*/ /*background: url(../img/up.png) no-repeat;*/ /*background-size: 20px; background-position: 50% 50%; }*/ /* 暂停播放 */ /*.play-pause { width: 30px; height: 30px;*/ /*background: url(../img/play.png) no-repeat;*/ /*background-size: 30px; background-position: 50% 50%; }*/ /* 下一首 */ /*.down { width: 30px; height: 30px;*/ /*background: url(../img/down.png) no-repeat;*/ /*background-size: 20px; background-position: 50% 50%; }*/ /* 右侧控制按钮 */ /*.control-right {*/ /* width: 180px; */ /*height: 30px; margin-left: calc(50% + 70px); margin-top: -30px; display: flex;*/ /*align-items: center;*/ /*}*/ /*声音进度条*/ /*.volume-back {*/ /*padding: px 0;*/ /*cursor: pointer; margin-top: 10px !important; }*/ /* 播放模式 */ .mode { width: 30px; height: 30px; /*background: url(../img/sequence.png) no-repeat;*/ background-size: 20px; background-position: left 50%; cursor: pointer; } /* 声音控制 */ /*.volume { width: 30px; height: 30px;*/ /*background: url(../img/volume.png) no-repeat;*/ /*background-size: 20px; background-position: left 50%; cursor: pointer; }*/ /* .volume-back { padding: 5px 0; cursor: pointer; } .volume-all { width: 100px; height: 2px; background-color: #e5e5e5; } .volume-now { width: 100px; height: 2px; margin-top: -2px; max-width: 100px; background-color: #5192fe; } .volume-text { margin-left: 10px; font-size: 14px; }*/ /* 进度条 */ .progress-bar { width: 100%; margin-top: 10px; /*margin: 15px 15px 5px 15px;*/ /*padding: 5px 0;*/ cursor: pointer; /*position:absolute;*/ /*float: left;*/ } /* 当前播放进度 */ .progress-now { width: 0; height: 10px; border-radius: 10px; margin-top: -10px; background-color: #5192fe; position: relative; } /*滑块*/ .progress-nowctor { width: 15px; height: 15px; background: white; /*position: absolute;*/ bottom: 0; top: 0; /*margin: auto 0;*/ border-radius: 50%; border: 2px solid #1e9fff; cursor: pointer; /*transition: left 0.1s linear 0s;*/ margin-top: -5px; position: absolute; /*position: relative;*/ left: 0px; } /* 总播放进度 */ .progress-all { /*width: 97%;*/ height: 10px; border-radius: 10px; background-color: #dee2e6; } /*文本div*/ .playfiletext { display: inline-block; width: 100%; height: 20px; /* margin-left: 15px;*/ margin-top: 10px; text-align: center; color: rgba(128, 130, 133, 0.8); cursor: default; overflow: hidden; } /* 播放时间进度 文本 */ .time { float: right; font-size: 10px; display: inline-block; width: 90px; height: 21px; /*margin-right: 15px;*/ text-align: right; color: rgba(128, 130, 133, 0.8); cursor: default; overflow: hidden; } /* 播放名称 文本 */ .playname { float: left; font-size: 10px; } a { cursor: pointer; } .layui-nav { position: relative; padding: 0px 0px 0px 0px; margin-top: 10px; height: 250px; /* background-color: #393D49; */ color: #fff; border-radius: 2px; font-size: 0; box-sizing: border-box; } .layui-nav .aul { float: right; } .layui-nav .lia { width: 60%; float: left; } .layui-nav .aul .updnote { margin-right: 10px; } .layui-nav .layui-menu-item-divider { margin: 10px 0px 0px 10px; height: 20px; } .ldiv3 .playlistusul { height: 250px; /*overflow-y: overlay;*/ /*overflow-y: hidden;*/ overflow: auto; width: 100%; } /*@*广播音乐*@*/ /*盒子*/ .broadcastcontr { overflow: hidden; height: 100px; position: sticky; } /*图标*/ .bicon { width: 10%; float: left; margin-top: 35px; } .bicon img { width: 30px; height: 30px; cursor: pointer; } /*进度条盒子*/ .bbox { width: 90%; /*height: 10px;*/ /*border-radius: 10px;*/ /*background: #dee2e6;*/ /*position: absolute;*/ top: 0; bottom: 0; left: 0; right: 0; /*margin: auto;*/ /*cursor: pointer;*/ float: right; margin-top: 55px; /*position: absolute;*/ /* position: relative;*/ } /*进度条*/ .bbox-tiao { width: 100%; height: 10px; border-radius: 10px; background: #dee2e6; /*position: absolute;*/ top: 0; bottom: 0; left: 0; right: 0; cursor: pointer; position: relative; } /* 音量大小条 */ .bboxcricle1 { width: 0; height: 10px; margin-top: -10px; border-radius: 10px; background-color: #5192fe; } /*控制按钮*/ .bboxcricle { width: 15px; height: 15px; background: white; /*position: absolute;*/ bottom: 0; top: 0; /*margin: auto 0;*/ border-radius: 50%; border: 2px solid #1e9fff; cursor: pointer; /*transition: left 0.1s linear 0s;*/ margin-top: -5px; position: absolute; /*position: relative;*/ left: 0px; } /*数字*/ #bboxvals:after { content: ""; width: 0px; height: 0px; border-top: 6px solid #1e9fff; border-left: 6px solid transparent; border-right: 6px solid transparent; border-bottom: 6px solid transparent; display: block; margin-left: 11px; font-family: "微软雅黑"; } /*数字框*/ #bboxvals { position: absolute; font-size: 20px; top: -45px; left: -10px; width: 35px; height: 35px; line-height: 35px; text-align: center; background: #1e9fff; color: white; } /*@*麦克风*@*/ /*盒子*/ .microphonecontr { overflow: hidden; height: 100px; } /*图标*/ .micon { width: 10%; float: left; margin-top: 35px; } .micon img { width: 30px; height: 25px; cursor: pointer; } .mbox { width: 90%; top: 0; bottom: 0; left: 0; right: 0; /*margin: auto;*/ cursor: pointer; float: right; margin-top: 55px; } /*进度条*/ .mbox-tiao { width: 100%; height: 10px; border-radius: 10px; background: #dee2e6; /*position: absolute;*/ top: 0; bottom: 0; left: 0; right: 0; cursor: pointer; position: relative; } .mboxcricle { width: 15px; height: 15px; background: white; /*position: absolute;*/ border: 2px solid #1e9fff; bottom: 0; top: 0; /*margin: auto 0;*/ border-radius: 50%; cursor: pointer; /*transition: left 0.1s linear 0s;*/ margin-top: -5px; position: absolute; } /* 音量大小条 */ .mboxcricle1 { width: 0; height: 10px; margin-top: -10px; border-radius: 10px; background-color: #5192fe; } /*数字*/ #mboxvals:after { content: ""; width: 0px; height: 0px; border-top: 6px solid #1e9fff; border-left: 6px solid transparent; border-right: 6px solid transparent; border-bottom: 6px solid transparent; display: block; margin-left: 11px; font-family: "微软雅黑"; } /*数字框*/ #mboxvals { position: absolute; font-size: 20px; top: -45px; left: -10px; width: 35px; height: 35px; line-height: 35px; text-align: center; background: #1e9fff; color: white; }

@{ Layout = "~/areas/usmain/Views/Shared/_LayoutEdit.cshtml"; ViewBag.Title = "即时广播"; } <link href="/assets2/avs/css/avs_call.css?cssdate=@ViewBag.CssVersion" rel="stylesheet" /> <form class="layui-form layui-form-pane layui-form-item us-form" id="us-form" usdata="{usurl:'',ussurl:'/extavs/avs_call/updatecalltask',usselecturl:'',usload:'1',usclose:'1',usrefresh:'1'}"> <!-- 音乐 --> <audio id="playaudio" src=""></audio>@*系统音乐*@ <!--<audio id="playaudio1" src="" controls></audio>-->@*系统音乐*@ <div class="usnbox callhead"> <div class="switchheadleft"> <div class="usnboxbody usnboxbody_rtm switchhead"> <div class="layui-inline switch"> <span id="switchspan">呼叫台总开关:</span> <input class="switchbtn" type="checkbox" lay-filter="setcall_isrun" name="set_isrun" lay-skin="switch" lay-text="开启|关闭"> </div> </div> </div> <div class="switchheadright"> <div class="callstatediv"></div> <div id="callstatetext" style="color: #909399">未连接</div> </div> </div> <div class="box2"> @*左侧*@ <div class="box2-left"> <div class="ldiv1"> @*音谱图*@ <div class="usnbox"> <canvas id="canvas"></canvas> </div> </div> <div class="ldiv2"> @*广播音乐*@ <div class="usnbox broadcast"> <div class="usnboxbody usnboxbody_rtm"> <div class="usnboxtop"> <div class="usnboxleft">广播音乐</div> <div class="usnboxright"> </div> </div> <div class="broadcastcontr"> @*图标*@ <div class="bicon"> @*<a class="bicon-a" onclick="setPlay1()"><i class="us-icon bs"></i></a>*@ <img id="bimg" src="~/assets2/avs/images/open.png" alt="1" onclick="setPlay1()" /> </div> @*音量条*@ <div class="bbox"> <div class="bbox-tiao"> <div class="bboxcricle" id="bboxcricle"> <div id="bboxvals">0</div> </div> @*//音量显示条*@ <div class="bboxcricle1"> </div> </div> </div> </div> </div> </div> @*麦克风*@ <div class="usnbox microphone"> <div class="usnboxbody usnboxbody_rtm"> <div class="usnboxtop"> <div class="usnboxleft">麦克风</div> <div class="usnboxright"> </div> </div> <div class="microphonecontr"> @*图标*@ <div class="micon"> @*<a class="micon-a" onclick="setPlay2()"><i class="us-icon ms"></i></a>*@ <img id="mimg" src="~/assets2/avs/images/mic.png" alt="1" onclick="setPlay2()" /> </div> @*进度条*@ <div class="mbox"> <div class="mbox-tiao"> <div class="mboxcricle"> <div id="mboxvals">0</div> </div> @*//音量显示条*@ <div class="mboxcricle1"> </div> </div> </div> </div> </div> </div> <br style='clear:both' /><!--清除浮动--> </div> <div class="ldiv3"> @*列表*@ <div class="ldiv3-f"> <div class="usnbox playul"> <div class="usnboxtop"> <div class="usnboxleft"><i class="us-icon"></i>新增列表</div> <div class="usnboxright"> <a class="addtnote" onclick="addplayList()"><i class="us-icon"></i>添加</a> </div> </div> <div class="playlistusul"> <ul class="layui-nav" id="nav" layui-filter="test"></ul> </div> </div> </div> <div class="ldiv3-r"> @*播放列表*@ <div class="usnbox playlist"> <div class="usnboxtop"> <div class="usnboxleft"><i class="us-icon"></i>播放列表</div> <div class="usnboxright"> <a class="addtnote" onclick="addplayItem()"><i class="us-icon"></i>添加</a> </div> </div> @*选择文件内容*@ <table id="playlistItemInfo" lay-filter="playlistItemInfo"> </table> </div> </div> <br style='clear:both' /><!--清除浮动--> </div> @*播放进度条*@ <div class="ldiv4"> <div class="usnbox"> @*<div class="usnboxtop"> </div>*@ @*<div class="usnboxleft"><i class="us-icon"></i></div> <div class="usnboxright"> </div>*@ <!-- 控制区 --> <div class="control-back"> <!-- 控制按钮 --> <div class="control"> <!-- 上一首、下一首、暂停播放 --> <img class="mode" src="~/assets2/avs/images/mode1.png" onclick="playmodectr()" alt="1" /> <img class="up" src="~/assets2/avs/images/up.png" onclick="playctr(2)" /> <img class="play-pause" src="~/assets2/avs/images/stop.png" onclick="playctr(3)" alt="1" /> <img class="down" src="~/assets2/avs/images/down.png" onclick="playctr(4)" /> @*<a class="up"><i class="us-icon"></i></a> <a class="play-pause" onclick="setPlay()"><i class="us-icon"></i></a> <a class="down"><i class="us-icon"></i></a>*@ </div> <div class="control1"> <!-- 进度条 --> <div class="progress-bar"> <div class="progress-all"> <div class="progress-now"> <div class="progress-nowctor"> </div> </div> </div> </div> @*文本*@ <div class="playfiletext"> <span class="playname">暂无播放文件</span> <span class="time">00:00/00:00</span> <br style='clear:both' /><!--清除浮动--> </div> </div> </div> </div> </div> </div> @*右侧*@ <div class="box2-right"> <div class="box2-1"> <div style="margin-top:0;overflow:auto;" id="conditioninstall1" class="box-left-border"> <div class="layui-inline"> <label class="layui-form-label">名称<span class="usStar">*</span></label> <div class="layui-input-inline"> <input type="text" name="cname" lay-verify="required" autocomplete="off" placeholder="呼叫台名称" class="layui-input ustips" ustitle="默认名称:呼叫台任务"> <input type="text" id="cguid" name="cguid" lay-verify="required" autocomplete="off" placeholder="呼叫台id" style="display:none"> <input type="text" id="id" name="id" lay-verify="required" autocomplete="off" placeholder="呼叫台表id" style="display:none"> <input type="text" name="lguid" lay-verify="required" autocomplete="off" placeholder="播放列表id" style="display:none"> <input type="text" name="lname" lay-verify="required" autocomplete="off" placeholder="播放列表名称" style="display:none"> <input type="text" name="receiver" placeholder="接受成员" style="display:none"> </div> </div> <div class="layui-inline"> <label class="layui-form-label">优先级<span class="usStar">*</span></label> <div class="layui-input-inline"> <input type="text" name="rank" lay-verify="required" autocomplete="off" placeholder="优先级" class="layui-input ustips" ustitle="值越大,优先级越高"> </div> </div> <div class="layui-form-item us-submitsave"> <div class="uscenter"> <button class="layui-btn" lay-submit="" lay-filter="submit" data-pwid="ussubmit"><i class="us-icon"></i>提交</button> @* <button type="button" class="layui-btn layui-btn-primary" data-pwid="usclose"><i class="us-icon"></i>取消</button>*@ </div> </div> </div> </div> <div class="box2-2"> <div style="margin-top:0;overflow:auto;" id="conditioninstal2" class="box-left-border"> <div class="usnboxtop"> <div class="usnboxleft"><i class="us-icon"></i>接收成员</div> <div class="usnboxright"></div> </div> <div style="margin-top:0;overflow:auto;" id="conditioninstall"> <ul id="ustree" class="ztree ustree" usurl="/usrtm/roomtree/useditselecttree?ver=4" uscheck="4" usonclickv2="usonclickv2"></ul> </div> </div> </div> </div> </div> </form> <script src="@this.ViewBag.OSSURL/assets2/avs/js/callrtc.js?jsdate=@ViewBag.JSVersion"></script> @*//媒体列表管理*@ <script> var listid = ""; var playitemArr = new Array(); //媒体信息 var itemtable;//table控制变量 var form; var cguid = $("input[name=cguid]").val(); var lguid = $("input[name=lguid]").val();//播放列表id $(function () { //获取麦克风stream getmicStream(); }) //树加载完成,默认选择第一个数据 --播放列表 function ustree_finish() { //获取呼叫台信息反填 getCallInfo(); //加载分类列表 playlistustree(); } function usonclickv2() { let _cfg = { ustreeid: "ustree",// 控件名称 us_in_type: 1,//1.获取复选框选中节点 2.获取选择节点,可能没有复选框 us_out_type: 1, //1.node节点返回 2.按配置的ID逗号分割返回 3.按配置的ID数组返回 us_para_dtype: "dtype", us_para_dtype_v: "r", } var treedata = usformtool.ustree_getselect(_cfg); //获取选中的数据 var tbase = usformtool.ustree_getzvalue(treedata, { value_list: "id,name" }); var receiver = ""; for (var i = 0; i < tbase.length; i++) { receiver = receiver + "," + tbase[i]["k"]; } $("input[name=receiver]").val(receiver.substring(1)); //呼叫台基本信息 var cguid = $("input[name=cguid]").val(); var name = $("input[name=cname]").val(); var rank = $("input[name=rank]").val(); var id = $("input[name=id]").val(); var data = {}; data["id"] = id; data["cguid"] = cguid; data["cname"] = name; data["rank"] = rank; data["receiver"] = receiver.substring(1); //data["userinfo"] = JSON.stringify(data); data = JSON.stringify(data); var url = "/extavs/avs_call/updatecalltask"; ushttp.UsAjaxJSONV2(url, data, false, false, function (d) { if (d.result == 0) { usbasic.successMsg(d.msg); } else { usbasic.errorMsg(d.msg); } }); } </script>
本文来自博客园,作者:じ逐梦,转载请注明原文链接:https://www.cnblogs.com/ZhuMeng-Chao/p/16931483.html
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 无需6万激活码!GitHub神秘组织3小时极速复刻Manus,手把手教你使用OpenManus搭建本
· Manus爆火,是硬核还是营销?
· 终于写完轮子一部分:tcp代理 了,记录一下
· 别再用vector<bool>了!Google高级工程师:这可能是STL最大的设计失误
· 单元测试从入门到精通