HTML5学习总结-04 音频&视频播放
一 音频播放
1 Audio(音频)
HTML5提供了播放音频文件的标准
2 control(控制器)
control属性攻添加播放,暂停和音量空间。
3 标签定义声音
<audio>
例子:
<!DOCTYPE html>
<html>
<head>
<meta charset="utf-8" />
<title></title>
</head>
<body>
<button id="btn" onclick="playMusic()">播放</button>
<button id="mutedBtn" onclick="muteMusic()">静音</button>
<audio id="audio" src="source/Morning.mp3" controls="controls" >您的浏览器不支持标签</audio>
<script>
function playMusic(){
var audioObj = document.getElementById("audio");
var btn = document.getElementById("btn");
console.log("step1 audioObj.paused="+audioObj.paused);
if( audioObj.paused){
btn.innerText ="暂停";
audioObj.play()
}else{
btn.innerText ="播放";
audioObj.pause();
}
}
function muteMusic(){
var audioObj = document.getElementById("audio");
var mutedBtn = document.getElementById("mutedBtn");
console.log( audioObj.muted);
if( audioObj.muted ){
audioObj.muted= "";
mutedBtn.innerText= "取消静音"
}else{
audioObj.muted= "muted";
mutedBtn.innerText= "静音"
}
}
</script>
</body>
</html>
二 视频播放
1 Video(视频)
HTML5提供了播放视频文件的标准
2 control(控制器)
control属性攻添加播放,暂停和音量空间。
3 标签定义声音
<video>
4 属性
width: 宽
height: 高
5 例子
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title></title> </head> <body> <video controls="controls">您的浏览器不支持标签 <source src="source/video1.mp4"></source> <source src="source/video1.ogv"></source> </video> </body> </html>
三 video捕获摄像头画面
1 通过video元素调用摄像头捕获画面
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title></title> <style> #myDiv {} </style> </head> <body> <div> <video width="640" height="480" autoplay></video> <canvas width="640" height="480"></canvas> <br> <button id="drawBtn" style="width: 100%;height: 50px;">拍照</button> </div> <script> var video = document.querySelector(\'video\'); var canvas = document.querySelector(\'canvas\'); // video捕获摄像头画面 navigator.webkitGetUserMedia({ video: true }, success, error); function success(stream) { video.src = window.webkitURL.createObjectURL(stream); video.play(); } function error(err) { alert(\'video error: \' + err) } //canvas var context = canvas.getContext(\'2d\'); setTimeout(function() { //把当前视频帧内容渲染到画布上 context.drawImage(video, 0, 0, 640, 480); }, 5000); var button= document.getElementById(\'drawBtn\'); button.onclick = function(){ context.drawImage(video, 0, 0, 640, 480); } </script> </body> </html>
运行页面后,浏览器出于安全性考虑,会询问是否允许当前页面访问你的摄像头设备,点击“允许”后便能直接在 <video> 上看到摄像头捕获到的画面了:
直接在页面中显示base64 编码的图片
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title></title> </head> <body> <img src=\'data:image/jpg;base64,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ceaLj3NsPV9jWhVtflaf3O58xaHr2v8AhwznSZZLfz9vmfuFfdtzj7ynHU1sf8LG8cf9BGT/AMA4v/iK+haK41hJxVlN/wBfM+gqZ/h6kuephotvq7N/+knzbpXhnxD4x1gyvDOfOfdPeTqQq++T1OOgH8q6X4ieGdR0TxBb65p0DvaRJDtkVd3lPGAo3D0wq89K9toqlg48rV9e5nLiKs68aiglFJrl8nbr8ux4YPjN4jA/489LP/bKT/4uuT8TeJr3xVqSX99FbxypEIQIFIXAJPcnn5jX0/RSlhak1aU/w/4JVDPMLQnz0sMk/wDF/wAA8P8AiP8A8if4K/68v/acVeh/DP8A5J5pX0l/9GvXW0VtChy1HO/SxwYnM/bYSOF5bWk3e/e+lreZ82eN/CV34W1ubET/ANnyuWtpwvy4PO3PZh0x7ZrpdH+M+o2VkkGo6dHfyIoUTCYxM3u3BBP5V7XNDFcRNFNGkkbDDI6ggj3BqlBoOjWpzb6TYRH1jtkX+Qr6R5tSrUlDFUuZrrex4nsmneLPH/EPjvV/GGn2kem+HLuGS2u0uo54Waf5lDYGAg9c/hWq/wAZb+xRI9R8MNHPj5sztEG9wrISB+Jr1sAAAAYAqKe3guojFcQxzRnqkihgfwNYfXsK0oSoe6v7zvr5j5Jb3Pnfxz45/wCEz+wf8S77H9k8z/lv5m/ft/2RjG39a6z4O+GbqO7m1+6haOAxGK23jG/JGWHsAMZ75PpXpsfhnQIpBJHoemo453LaRg/nitQAAAAYArXEZrB4b6th4csfW/mKNJ83NJnnnxl/5E22/wCv5P8A0B65Hw38Vv8AhH/D9ppX9i/aPs6keb9q2bssT02HHX1r3GivnJ0ZOfPGVvke9h8yoQwqw1ejzpO/xNfkjyP/AIXf/wBS9/5O/wD2uuL8S+JJPGfiezvI7BoHCJAsKv5hbDE56D+90xX0hRUTw9SatKenob4fNsJhp+0o4a0v8bf5o8i+N/39D+k//tOm+IviTplwt3ol/wCGxeJBI0IL3GMlSV3DC5U8djmvX6KqVCTlKUZWv5GNHNKMaNOlVpc3Jez5mt3foj5wsPDvi6XQ724sLa/h048vArsvmj2T+PHfitfwv480rwpa+UnhgC+A2zXHn/O579VJX6DiveKKiOEcGnGWvpc6qufxrxlCvRvFvpJx++25BZ3H2uxt7nbs86JZNuc4yM4zU9FFdh867N6BRRRQIKKKKACiiigAooooAKKKKACiiigAooooAKKKKACiiigAooooAKKKKACiiigAooooAKKKKACiiigAooooAKKKKACiiigAooooAKKKKACiiigAooooAKKKKACiiigAooooAKKKKACiiigAooooAKKKKACiiigAooooAKKKKACiiigAooooAKKKKACiiigAooooAKKKKACiiigAooooAKKKKACiiigAooooAKKKKACiiigAooooAKKKKACiiigAooooAKKKKACiiigAooooAKKKKAP/2Q==\'/> </body> </html>
1)data:image/png;base64是什么?
参考 http://blog.csdn.net/c_mihoo/article/details/12774719
Base64 主要不是加密,它主要的用途是把一些二进制数转成普通字符用于网络传输。由于一些二进制字符在传输协议中属于控制字符,不能直接传送需要转换一下。针对图片进行Base64编码后,减少一次网络请求。但也不缓存图片了。
2)在线图片转Base64
http://tool.css-js.com/base64.html
3)java实现图片与base64字符串之间的转换
package test; import java.io.FileInputStream; import java.io.FileOutputStream; import java.io.IOException; import java.io.InputStream; import java.io.OutputStream; import sun.misc.BASE64Decoder; import sun.misc.BASE64Encoder; public class Base64Test { //图片转化成base64字符串 public static String GetImageStr() {//将图片文件转化为字节数组字符串,并对其进行Base64编码处理 String imgFile = "e://quant.png";//待处理的图片 InputStream in = null; byte[] data = null; //读取图片字节数组 try { in = new FileInputStream(imgFile); data = new byte[in.available()]; in.read(data); in.close(); } catch (IOException e) { e.printStackTrace(); } //对字节数组Base64编码 BASE64Encoder encoder = new BASE64Encoder(); return encoder.encode(data);//返回Base64编码过的字节数组字符串 } //base64字符串转化成图片 public static boolean GenerateImage(String imgStr) { //对字节数组字符串进行Base64解码并生成图片 if (imgStr == null) //图像数据为空 return false; BASE64Decoder decoder = new BASE64Decoder(); try { //Base64解码 byte[] b = decoder.decodeBuffer(imgStr); for(int i=0;i<b.length;++i) { if(b[i]<0) {//调整异常数据 b[i]+=256; } } //生成jpeg图片 String imgFilePath = "e://111.png";//新生成的图片 OutputStream out = new FileOutputStream(imgFilePath); out.write(b); out.flush(); out.close(); return true; } catch (Exception e) { return false; } } public static void main(String[] args) { String strImg = GetImageStr(); System.out.println(strImg); } }
2 上传画面到服务器
var curFrame; //当前帧
function savePic(){
console.log("curFrame=\n"+curFrame);
$.ajax({
url : \'/TestH5/SnapPicAction\',
type : "POST",
data : {
\'date\': \'告警\' + Date.now() ,
\'pic\': \'<img src="\' + curFrame + \'" />\'
},
success: function(){
console.log(\'submit done\')
},
error: function(err){
// cache.reqTime = 0;
console.log(\'error: \' + err)
}
});
}
把捕获的数据帧发送到后台。完整代码如下:
<!DOCTYPE html> <html> <head> <meta charset="UTF-8"> <title></title> <style> #myDiv { } </style> </head> <body> <div> <video width="640" height="480" autoplay></video> <canvas width="640" height="480"></canvas> <br> <button id="drawBtn" style="width: 50%;height: 50px;">拍照</button> <button id="savePicBtn" style="width: 50%;height: 50px;">保存</button> </div> <script src="js/jquery-3.1.0.js"></script> <script> var video = document.querySelector(\'video\'); var canvas = document.querySelector(\'canvas\'); var curFrame; //当前帧 // video捕获摄像头画面 navigator.webkitGetUserMedia({ video : true }, success, error); function success(stream) { video.src = window.webkitURL.createObjectURL(stream); video.play(); } function error(err) { alert(\'video error: \' + err) } //canvas var context = canvas.getContext(\'2d\'); setTimeout(function() { //把当前视频帧内容渲染到画布上 context.drawImage(video, 0, 0, 640, 480); }, 5000); var button = document.getElementById(\'drawBtn\'); button.onclick = function() { context.drawImage(video, 0, 0, 640, 480); } $(document).ready(function() { }); //捕获并保存帧内容 function captureAndSaveFrame(){ context.drawImage(video, 0, 0, 640, 480); curFrame = canvas.toDataURL(); //转为base64并保存 } function savePic(){ console.log("curFrame=\n"+curFrame); $.ajax({ url : \'/TestH5/SnapPicAction\', type : "POST", data : { \'date\': \'告警\' + Date.now() , \'pic\': \'<img src="\' + curFrame + \'" />\' }, success: function(){ console.log(\'submit done\') }, error: function(err){ // cache.reqTime = 0; console.log(\'error: \' + err) } }); } var savePicBtn = document.getElementById(\'savePicBtn\'); savePicBtn.onclick = function() { captureAndSaveFrame(); savePic(); } </script> </body> </html>
3 保存数据帧的后台业务逻辑
SnapPicAction.java
package com.mobile.action; import java.io.File; import java.io.FileOutputStream; import java.io.IOException; import javax.servlet.ServletException; import javax.servlet.http.HttpServlet; import javax.servlet.http.HttpServletRequest; import javax.servlet.http.HttpServletResponse; import com.mobile.util.Base64; /** * Servlet implementation class SnapPicAction */ public class SnapPicAction extends HttpServlet { private static final long serialVersionUID = 1L; public SnapPicAction() { super(); } protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { System.out.println("--- doGet SnapPicAction"); response.getWriter().append("Served at: ").append(request.getContextPath()); } protected void doPost(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException { response.setContentType("text/html;charset=utf8"); System.out.println("--- doPost SnapPicActionn --------------------"); String date = request.getParameter("date"); String pic = request.getParameter("pic"); System.out.println("***step0 pic=" + pic); int beginIdx = pic.indexOf("\"") + 1; int lastIdx = pic.lastIndexOf("\""); String base64Pic = pic.substring(beginIdx, lastIdx).replace("data:image/png;base64,", ""); decodeBase64ToImage(base64Pic, "E://temp3//", "aaa.png"); } public static void decodeBase64ToImage(String base64, String path, String imgName) { try { FileOutputStream write = new FileOutputStream(new File(path + imgName)); byte[] decoderBytes = Base64.decode(base64); write.write(decoderBytes); write.close(); } catch (IOException e) { e.printStackTrace(); } } }
Base64.java
package com.mobile.util; public class Base64 { /** * Base64编码表。 */ private static final char[] BASE64CODE = { \'A\', \'B\', \'C\', \'D\', \'E\', \'F\', \'G\', \'H\', \'I\', \'J\', \'K\', \'L\', \'M\', \'N\', \'O\', \'P\', \'Q\', \'R\', \'S\', \'T\', \'U\', \'V\', \'W\', \'X\', \'Y\', \'Z\', \'a\', \'b\', \'c\', \'d\', \'e\', \'f\', \'g\', \'h\', \'i\', \'j\', \'k\', \'l\', \'m\', \'n\', \'o\', \'p\', \'q\', \'r\', \'s\', \'t\', \'u\', \'v\', \'w\', \'x\', \'y\', \'z\', \'0\', \'1\', \'2\', \'3\', \'4\', \'5\', \'6\', \'7\', \'8\', \'9\', \'+\', \'/\', }; /** * Base64解码表。 */ private static final byte[] BASE64DECODE = { -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, // 注意两个63,为兼容SMP, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, 62, -1, 63, -1, 63, // “/”和“-”都翻译成63。 52, 53, 54, 55, 56, 57, 58, 59, 60, 61, -1, -1, -1, 0, -1, -1, -1, 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, // 注意两个0: 15, 16, 17, 18, 19, 20, 21, 22, 23, 24, 25, -1, -1, -1, -1, -1, // “A”和“=”都翻译成0。 -1, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, -1, -1, -1, -1, -1, }; private static final int HEX_255 = 0x0000ff; private static final int HEX_16515072 = 0xfc0000; private static final int HEX_258048 = 0x3f000; private static final int HEX_4032 = 0xfc0; private static final int HEX_63 = 0x3f; private static final int HEX_16711680 = 0xff0000; private static final int HEX_65280 = 0x00ff00; private static final int NUMBER_TWO = 2; private static final int NUMBER_THREE = 3; private static final int NUMBER_FOUR = 4; private static final int NUMBER_SIX = 6; private static final int NUMBER_EIGHT = 8; private static final int NUMBER_TWELVE = 12; private static final int NUMBER_SIXTEEN = 16; private static final int NUMBER_EIGHTEEN = 18; /** * 构造方法私有化,防止实例化。 */ private Base64() { } /** * Base64编码。将字节数组中字节3个一组编码成4个可见字符。 * * @param b * 需要被编码的字节数据。 * @return 编码后的Base64字符串。 */ public static String encode(byte[] b) { int code = 0; // 按实际编码后长度开辟内存,加快速度 StringBuffer sb = new StringBuffer(((b.length - 1) / NUMBER_THREE) << NUMBER_TWO + NUMBER_FOUR); // 进行编码 for (int i = 0; i < b.length; i++) { code |= (b[i] << (NUMBER_SIXTEEN - i % NUMBER_THREE * NUMBER_EIGHT)) & (HEX_255 << (NUMBER_SIXTEEN - i % NUMBER_THREE * NUMBER_EIGHT)); if (i % NUMBER_THREE == NUMBER_TWO || i == b.length - 1) { sb.append(BASE64CODE[(code & HEX_16515072) >>> NUMBER_EIGHTEEN]); sb.append(BASE64CODE[(code & HEX_258048) >>> NUMBER_TWELVE]); sb.append(BASE64CODE[(code & HEX_4032) >>> NUMBER_SIX]); sb.append(BASE64CODE[code & HEX_63]); code = 0; } } // 对于长度非3的整数倍的字节数组,编码前先补0,编码后结尾处编码用=代替, // =的个数和短缺的长度一致,以此来标识出数据实际长度 if (b.length % NUMBER_THREE > 0) { sb.setCharAt(sb.length() - 1, \'=\'); } if (b.length % NUMBER_THREE == 1) { sb.setCharAt(sb.length() - NUMBER_TWO, \'=\'); } return sb.toString(); } /** * Base64解码。 * * @param code * 用Base64编码的ASCII字符串 * @return 解码后的字节数据 */ public static byte[] decode(String code) { // 检查参数合法性 if (code == null) { return null; } int len = code.length(); if (len % NUMBER_FOUR != 0) { throw new IllegalArgumentException("Base64 string length must be 4*n"); } if (code.length() == 0) { return new byte[0]; } // 统计填充的等号个数 int pad = 0; if (code.charAt(len - 1) == \'=\') { pad++; } if (code.charAt(len - NUMBER_TWO) == \'=\') { pad++; } // 根据填充等号的个数来计算实际数据长度 int retLen = len / NUMBER_FOUR * NUMBER_THREE - pad; // 分配字节数组空间 byte[] ret = new byte[retLen]; // 查表解码 char ch1, ch2, ch3, ch4; int i; for (i = 0; i < len; i += NUMBER_FOUR) { int j = i / NUMBER_FOUR * NUMBER_THREE; ch1 = code.charAt(i); ch2 = code.charAt(i + 1); ch3 = code.charAt(i + NUMBER_TWO); ch4 = code.charAt(i + NUMBER_THREE); int tmp = (BASE64DECODE[ch1] << NUMBER_EIGHTEEN) | (BASE64DECODE[ch2] << NUMBER_TWELVE) | (BASE64DECODE[ch3] << NUMBER_SIX) | (BASE64DECODE[ch4]); ret[j] = (byte) ((tmp & HEX_16711680) >> NUMBER_SIXTEEN); if (i < len - NUMBER_FOUR) { ret[j + 1] = (byte) ((tmp & HEX_65280) >> NUMBER_EIGHT); ret[j + NUMBER_TWO] = (byte) ((tmp & HEX_255)); } else { if (j + 1 < retLen) { ret[j + 1] = (byte) ((tmp & HEX_65280) >> NUMBER_EIGHT); } if (j + NUMBER_TWO < retLen) { ret[j + NUMBER_TWO] = (byte) ((tmp & HEX_255)); } } } return ret; } }
web.xml
<?xml version="1.0" encoding="UTF-8"?> <web-app xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns="http://java.sun.com/xml/ns/javaee" xsi:schemaLocation="http://java.sun.com/xml/ns/javaee http://java.sun.com/xml/ns/javaee/web-app_3_0.xsd" id="WebApp_ID" version="3.0"> <display-name>TestH5</display-name> <servlet> <servlet-name>SnapPicAction</servlet-name> <servlet-class>com.mobile.action.SnapPicAction</servlet-class> </servlet> <servlet-mapping> <servlet-name>SnapPicAction</servlet-name> <url-pattern>/SnapPicAction</url-pattern> </servlet-mapping> </web-app>
jquery CDN
<script src=”http://cdn.static.runoob.com/libs/jquery/1.10.2/jquery.min.js”>
</script>
参考资料:
data:image/png;base64是什么
http://blog.csdn.net/c_mihoo/article/details/12774719