HTML5下Base64圖片處理結合攝像頭抓拍裁切
最近要實現一個現場報名功能,採用B/S結構系統實現現場報名,現場採集使用者資訊錄入系統。
前端使用bootstrap框架,後臺使用ASP.NET MVC4。
剛開始只需要使用者提供身份證,用讀卡器讀出身份證的資訊自動填充到輸入框中,然後補充其他資訊儲存即可。
身份證讀卡器就是這貨,USB介面。
做了個操作介面:
讀身份證資訊比較好辦,呼叫讀卡器介面對應的方法即可。
通過實驗發現介面方法讀取頭像照片時,得到的是Base64格式的jpg圖片,並且不包含“data:image/jpg;base64,”這段頭資訊,需要自己手工加上。圖片尺寸為102*126畫素,在圖片上右擊看屬性:
提交報名資訊時,後臺將獲取的Base64字串轉換成jpg並儲存在指定路徑下:
本來功能也就完成了,後來使用者提出沒帶身份證報名的情況,需要增加從檔案選擇照片和現場用攝像頭拍照兩種方式,先感慨一下需求變更,還是要想辦法實現功能。
分析後決定將檔案選取和攝像頭拍照用彈窗來操作,取得的圖片直接展示在頭像框處,並且為了和身份證讀卡器讀出的圖片格式相容,都設為Base64格式。這樣就形成了統一思路,不論用什麼方式獲得頭像照片(讀身份證、檔案選取、攝像頭拍照),均以Base64格式展示在操作介面,這樣提交到後臺處理時方式是一樣的。
================================= 分割一下 =================================
從檔案中選取照片的處理
瀏覽照片選中時,用js控制在操作介面中展示選中照片,同時父視窗頭像框處展示經過Base64處理過的影象。點選右上角關閉按鈕或右下角確定按鈕時,關閉當前彈窗。
元素"imgFile"為圖片選擇視窗中要展示的圖片,"imgAvatar"為父視窗中的頭像框,"hPhoto"為父視窗記錄Base64內容的隱藏域,注意去掉了"data:image/jpeg;base64,"這段頭資訊,只保留圖片資料內容。
此時頭像框中圖片格式與讀身份證得到的圖片格式一樣,後臺儲存方法都不用改。即使選擇的圖片格式不是jpg的,仍然會在後臺程式碼中自動轉換成jpg格式。
=================================再分割一下=================================
攝像頭拍照的處理稍微麻煩一下,主要在於拍照的圖片是橫版的,但系統要求的頭像圖片是豎版的,需要進行裁切。
攝像頭就是普通那種USB介面的攝像頭,免驅動的。
網頁呼叫攝像頭拍照有多種方案,對比後採用的是flash方式。
專案中引用需要的資原始檔:
頁面中呼叫:
<script src="/assets/js/jquery-1.8.3.min.js" type="text/javascript"></script>
<script src="/assets/js/webcam/jquery.webcam.js"></script>
思路是這樣的:flash顯示攝像頭實時畫面,點選“拍照”按鈕時捕獲當前畫面,然後按比例裁切中間一部分影象展示在畫布中。
攝像頭實時畫面設定為320*240畫素,按照頭像實際尺寸計算,應該擷取拍照畫面中間的194*240區域。
為了方便操作者預覽,在攝像頭實時畫面的左右兩側增加了一個半透明區域,意思是這兩塊區域要刪掉,只保留中間一部分。
彈窗中左側是攝像頭畫面,下方有“拍照”按鈕,拍照的圖片自動裁切後顯示在右側,父視窗同步顯示拍照結果。
左右兩側的半透明區域是用css控制的div透明度,注意flash呼叫攝像頭的z-index數值,要將半透明區域疊加到flash之上才行。
攝像頭畫面只保留中間的194*240區域的內容,因此拍照後要將原始圖片從(63,0)位置開始裁切大小為194*240區域的影象,js程式碼是image = ctx.getImageData(63, 0, 194, 240);
顯示攝像頭畫面和抓拍畫面的html:
其中,id為“webcam”的div在頁面載入時會append上flash,由flash呼叫攝像頭。
=================================待改進地方 =================================
1、程式中bootstrap框架採用ACE1.3.3版本,開啟對話視窗時,是將彈窗檔案解析後附加在本頁中,因此會受本月的指令碼和程式碼影響。從檔案選取圖片功能用預設的對話視窗可以實現功能,但攝像頭拍照功能則不能生效,我只能用模態視窗來實現效果,並且在點選“拍照”按鈕時將抓拍的圖片回傳給父視窗。
2、因客戶只使用IE瀏覽器,並且版本也固定,因此可以不用考慮過多相容問題。身份證讀卡器使用Activex控制元件註冊,如果是火狐或谷歌瀏覽器要載入不同的控制元件。另外實時攝像頭畫面兩側半透明區域只在IE下起作用,其他瀏覽器要再處理。
=================================總結=================================
1、通過三種不同方式獲取頭像資訊,傳到後臺儲存時已經處理成同樣的格式,這也是程式碼分離原則的體現。以頭像框為中轉站,前臺js各種處理,達到同樣格式的Base64圖片;後臺獲取圖片字串,統一儲存成jpg格式。也相當於呼叫後臺的一個方法時,通過各種手段將傳入引數統一好格式,伺服器端方法只需要接收到引數內容處理即可,不需要再做更多情況判斷。
2、不同版本的bootstrap有一定的瀏覽器相容問題,特別是jquery版本。某些時候使用原生js是更好的選擇。
3、花哨的功能儘量少,用最簡單的方式實現功能,穩定性是最好的。
附:程式碼檔案
父頁面部分程式碼
<input type="hidden" id="hPhoto" name="hPhoto" />
<input type="file" id="picFile" name="picFile" onchange="selectPicFile()" style="display:none;" />
<img id="imgAvatar" alt="" src="/assets/avatars/default.jpg" width="102" height="126" />
<div class="col-sm-4 align-left">
<a href="#" role="button" onclick="CapturePicture()"><i class="fa fa-camera fa-1x" title="從攝像頭拍照"> 拍照</i></a>
<br />
<a href="FilePicture" role="button" data-toggle="modal" data-target="#FilePicture"><i class="fa fa-folder-open fa-1x" title="從檔案中選擇"> 檔案</i></a>
</div>
<div id="FilePicture" class="modal fade" tabindex="-1">
<div class="modal-dialog">
<div class="modal-content">
</div><!-- /.modal-content -->
</div><!-- /.modal-dialog -->
</div>
<script type="text/javascript">
jQuery(function ($) {
$("#FilePicture").on("hidden.bs.modal", function () {
$(this).removeData("bs.modal");
});
function CapturePicture() {
return window.showModalDialog("CapturePicture", GetResult, "dialogWidth=620px,dialogHeight=400px");
}
function GetResult(imageContent) {
document.getElementById('imgAvatar').src = imageContent;
document.getElementById('hPhoto').value = imageContent.substring(imageContent.indexOf(";base64,") + 8);
}
});
</script>
檔案選擇子頁面(FilePicture)
@{
Layout = null;
}
<!DOCTYPE html>
<html>
<head>
<meta http-equiv="X-UA-Compatible" content="IE=edge" />
<meta charset="utf-8" />
<title></title>
<script type="text/javascript">
function showImage(file) {
var imageContent = '';
if (!file.files || !file.files[0]) {
return;
}
var reader = new FileReader();
reader.onload = function (evt) {
imageContent = evt.target.result;
document.getElementById('imgFile').src = imageContent;
document.getElementById('imgAvatar').src = imageContent;
document.getElementById('hPhoto').value = imageContent.substring(imageContent.indexOf(";base64,") + 8);
}
reader.readAsDataURL(file.files[0]);
}
</script>
</head>
<body class="no-skin">
<div class="modal-header">
<button type="button" class="close" data-dismiss="modal" aria-hidden="true">×</button>
<h3 class="smaller lighter blue no-margin">選擇照片</h3><h5>(尺寸:102*126畫素或等比例)</h5>
</div>
<div class="modal-body">
<table width="100%" border="0" cellpadding="0" cellspacing="0">
<tr>
<td align="left">
<input type="file" id="picFile" name="picFile" onchange="showImage(this)" />
</td>
</tr>
<tr>
<td> </td>
</tr>
<tr>
<td>
<img id="imgFile" style="height:220px;" alt="" />
</td>
</tr>
</table>
</div>
<div class="modal-footer">
<button type="button" data-dismiss="modal" data-bb-handler="success" class="btn btn-sm btn-success">
<i class="ace-icon fa fa-check"></i> 確定
</button>
</div>
</body>
</html>
攝像頭抓拍子頁面(CapturePicture)
@{
Layout = null;
}
<!doctype html>
<html>
<head>
<meta charset="utf-8">
<title>拍照</title>
<style type="text/css">
#webcam {
width: 320px;
}
#webcam {
position:relative;
}
object {
display:block; /* HTML5 fix */
position:relative;
z-index:100;
}
.div1{
width:320px;
height:240px;
position:relative;
border:1px solid #cccccc;
}
.div2{
width:63px;
height:240px;
position:absolute;
left:0;
top:0;
background:#000000;
z-index:9999;
opacity:0.3;
filter:alpha(opacity:30);
moz-opacity:0.3;
}
.div3{
width:63px;
height:240px;
position:absolute;
right:0;
top:0;
background:#000000;
z-index:9999;
opacity:0.3;
filter:alpha(opacity:30);
moz-opacity:0.3;
}
</style>
<script src="/assets/js/jquery-1.8.3.min.js" type="text/javascript"></script>
<script src="/assets/js/webcam/jquery.webcam.js"></script>
<script type="text/javascript">
var pos = 0;
var ctx = null;
var cam = null;
var saveCB;
var image = [];
$(document).ready(function () {
var canvas = document.getElementById("canvas");
if (canvas.getContext) {
ctx = document.getElementById("canvas").getContext("2d");
ctx.clearRect(0, 0, 320, 240);
var img = new Image();
img.src = "";
img.onload = function () {
ctx.drawImage(img, 0, 0);
}
image = ctx.getImageData(0, 0, 320, 240);
}
if (canvas.toDataURL) {
ctx = canvas.getContext("2d");
image = ctx.getImageData(63, 0, 194, 240);
saveCB = function (data) {
var col = data.split(";");
var img = image;
for (var i = 63; i < 257; i++) {
var tmp = parseInt(col[i]);
img.data[pos + 0] = (tmp >> 16) & 0xff;
img.data[pos + 1] = (tmp >> 8) & 0xff;
img.data[pos + 2] = tmp & 0xff;
img.data[pos + 3] = 0xff;
pos += 4;
}
if (pos >= 4 * 194 * 240) {
ctx.putImageData(img, 0, 0);
pos = 0;
}
};
} else {
saveCB = function (data) {
image.push(data);
pos += 4 * 194;
if (pos >= 4 * 194 * 240) {
pos = 0;
}
};
}
jQuery("#webcam").webcam({
mode: "callback",
swffile: "/assets/js/webcam/jscam_canvas_only.swf",
onCapture: function () {
webcam.save();
var canvas = document.getElementById("canvas")
var imageContent = canvas.toDataURL("image/png")
var callBack = window.dialogArguments;
if (callBack != undefined && callBack != null) {
callBack(imageContent);
}
},
onSave: saveCB,
debug: function (type, string) {
jQuery("#status").html(type + ": " + string);
},
onLoad: function () {
var cams = webcam.getCameraList();
for (var i in cams) {
jQuery("#cams").append("<li>" + cams[i] + "</li>");
}
}
});
});
</script>
</head>
<body class="no-skin" style="margin:10px;">
<table width="100%" border="0" cellpadding="0" cellspacing="0">
<tr>
<td height="56"><ul id="cams"></ul></td>
<td width="50"> </td>
<td><p id="status"></p></td>
</tr>
<tr style="height:3px;">
<td><hr /></td>
<td></td>
<td><hr /></td>
</tr>
<tr>
<td colspan="3"> </td>
</tr>
<tr>
<td align="center">
攝像頭畫面
</td>
<td></td>
<td align="center">
拍照結果
</td>
</tr>
<tr>
<td align="center">
<div id="webcam" class="div1">
<div class="div2"></div>
<div class="div3"></div>
</div>
</td>
<td></td>
<td align="center">
<div>
<canvas id="canvas" width="194" height="240"></canvas>
</div>
</td>
</tr>
<tr>
<td align="center"><a href="javascript:webcam.capture();void(0);">拍照</a></td>
<td></td>
<td></td>
</tr>
<tr>
<td colspan="3" height="20"> </td>
</tr>
<tr>
<td colspan="3" height="50" align="center" style="background-color:#cccccc"><input type="button" value="完成" onclick="window.close();" /></td>
</tr>
</table>
</body>
</html>
相關推薦
HTML5下Base64圖片處理結合攝像頭抓拍裁切
最近要實現一個現場報名功能,採用B/S結構系統實現現場報名,現場採集使用者資訊錄入系統。 前端使用bootstrap框架,後臺使用ASP.NET MVC4。 剛開始只需要使用者提供身份證,用讀卡器讀出身份證的資訊自動填充到輸入框中,然後補充其他資訊儲存即可。 身份證讀卡器就
Android圖片上傳(頭像裁切+原圖原樣)
還是那句話,最近專案比較忙拖了很久這篇文章終於完成了! 先看一下效果圖: (一)頭像裁切、上傳伺服器(效果圖) 一般都是有圓形顯示頭像的,這裡我自定義了一個ImageView,頁面很乾淨但是看著很上檔次吧! 點選頭像從底部彈出一個對話方塊,提示使用者頭像來自相機或者相簿,這
圖片處理之 Base64
col ack 頁面 發送 http 簡單 文件大小 pan class 網頁上的圖片資源如果采用 http 形式的 url 的話都會額外發送一次請求,網頁發送的 http 請求次數越多,會造成頁面加載速度越慢。而采用Base64格式的編碼,將圖片轉化為字符串後,圖
base64圖片上傳處理方式
adb 信息 als 上傳圖片 上傳 文件 chang exist match 前臺傳圖片的base64格式,後臺處理方式//處理圖片信息 返回對應的路徑public function uploadBaseIma($imgArr){ $result = array()
前端性能優化------------圖片處理Css Sprites&Base64
大於 字符 ebp 錯誤 過程 inf 嵌入 定位 性能 Css Sprites Css Sprites我們叫做雪碧圖或者css精靈,其原理就是將許多小的圖片合到一張大的圖片中,然後使用background-image引用圖片,使用background-position來定
還在羨慕微信/微博的圖片處理?-android酷炫圖片處理(下)
微信一向是android開發者們模仿的物件,上篇文章中,我介紹了一個和微信圖片壓縮,壓縮效果差不多的庫Luban,這篇文章還會介紹高仿微信從檔案系統選擇圖片。此外微博載入超長大圖功能也很酷炫(其實微信朋友圈也有),這篇文章也給出了實現這種效果的功能庫,當然,除此之外還有很多其他酷炫效果的
將圖片檔案轉化為位元組陣列字串,並對其進行Base64編碼處理和 對位元組陣列字串進行Base64解碼並生成圖片
public static String imageToBase64(String path) { // 將圖片檔案轉化為位元組陣列字串,並對其進行Base64編碼處理 byte[] data = null; // 讀取圖片位元組
(python)subprocess利用ffmpeg處理多目錄下的圖片合成某一幀率的視訊
import os import subprocess path="/home/jinbeibei/File/video_prediction2018/iclr2017mcnet-master/data/DAVIS/Annotations/480p" for f
關於實現接收base64圖片資料並以圖片儲存到本地的處理
public function saveBase64File($img,$name=''){ $base_img = str_replace('data:image/jpeg;base64,','', $img); // 設定檔案路
基於HTML5 Canvase的線上畫圖及圖片處理工具
簡介 這是基於HTML5的Canvas而實現的線上畫圖及簡單圖片處理的工具,是我的計算機圖形學期末課程設計作業。主要功能包括:畫圖、顏色反轉、轉灰度圖、陰影效果、橫向漸變、縱向漸變等。處理
結合springmvc,使用ajax上傳base64圖片資料
一、前端: <input type="file" id="myImage" name="myImage"/> <script type="text/javascript"> $("#myImage").bind("ch
前端開發之使用base64模式處理圖片
最近在做訊息推送,涉及到圖片處理這一塊,於是就使用base64的方式處理圖片.做一個簡單的總結.算是備忘.如果能幫到大家最好. 一.什麼是base64 Base64就是一種基於64個可列印字元來表示二進位制資料的方法。 (百度百科) 二.如何使用
base64圖片在各種瀏覽器的相容性處理
IE瀏覽器目前最高的版本是v11,而微軟放棄了IE,轉向新的瀏覽器開發,並取名為Edge。base64圖片在IE9及以後的圖片均能顯示沒有問題,而Firefox, Chrome, Safari等非IE瀏覽器都能正常顯示,所以顯得IE瀏覽器比較low。那麼相容性究竟應該怎麼來處理呢? 分三種情況。 (1)IE
如何使用 HTML5 的picture元素處理響應式圖片
圖片在響應式網頁設計中是出了名的最具挑戰性的方面之一。今天我們就來看看如何使用 <picture> 元素來處理響應式圖片. 讓我們先了解一下問題 固定寬度,畫素完美的網站設計已經離我們遠去了。在寬屏顯示器,網際網路電視,多尺寸的平板電腦和智慧手機的今天,我們的設計必須應付一切可能,將寬由 32
html5 canvas 載入圖片URL並轉換成base64
非同步載入圖片到canvas並拿掉data:image;base64部分。 function convertImgToBase64(url, callback, outputFormat){
Linux下使用v4l2程式設計操作攝像頭裝置獲取圖片
進行操作前請參考我的另一篇部落格: 看懂之後再研究下面的程式: /***************************************************** * 檔名:GetYuyv.c * 檔案描述:linux下使用v4l2程式設計操作
通過圖片地址,將圖片處理成base64,使用ajax上傳圖片
需求 群裡的一個小朋友一直要求我幫他實現以下,我就寫了一個案例。需求就是,他用canvas生成了一個base64格式的圖片,然後需要將這個圖片上傳到伺服器上面去。 程式碼 <!doctype html> <html lang="en"
base64加密圖片處理
兩種 例子 鏈接 replace html htm 加密 with open 加密圖片 場景:下載html中內嵌的base64加密圖片 舉個例子,博客園的插入圖片有兩種方式,一是引用圖片鏈接,二是直接粘貼2進制圖片文件。以第二種方式的圖片則是以base64加密的方式內嵌在
css3圖片處理方式 object-fit
含義 class 替換 down 區域 尺寸 屬性 obj over .fill { object-fit: fill; } .contain { object-fit: contain; } .cover { object-fit: cover; } .none { o
Android 中圖能夠用到的圖片處理類 BitmapUtils
andro radius title can rup decode eww row 上下 Android在實際開發中非常多時候都要對圖片進行一定的處理,這裏總結的BitmapUtils 類包含一下幾個功能: 1.Android圖片倒影, 2.Android圖片模糊處理,