【java】springMVC+eaui實現頭像上傳預覽功能

功能需求描述

  1. 需要一個能夠顯示員工頭像的區域,點擊區域可更新圖片。
  2. 圖片爲服務器文件存儲(之所以不放到數據庫中,爲了防止數據庫過大導致備份和遷移時效率降低)

思路描述

上傳員工頭像功能開發流程:

  1. 頭像上傳區域:
    1.1 設置頭像點擊事件
    1.2 設置默認頭像
    1.3 在點擊事件中,增加圖片上傳預覽的彈出框
    1.4 圖片上傳後預覽
    1.5 增加返回參數,能夠返回保存到服務器上的圖片路徑給父頁面

  2. 圖片保存顯示
    2.1 根據圖片路徑,刷新當前圖片顯示
    2.2 點擊保存後,將最新的圖片路徑保存到實體內
    2.3 編輯後能正常顯示頭像圖片信息

用到的主要技術

  1. 圖片預覽用到了var reader = new FileReader();渲染方法,讀取本地上傳的緩存圖片。
  2. 圖片上傳需要用到文件流以及File對象持久化的一些方法

處理流程

在這裏插入圖片描述

核心代碼

1. 設置圖片顯示區域,綁定點擊事件uploadImage。同時,增加一個記錄圖片上傳後返回路徑的隱藏input,實現圖片文件路徑的保存

<div class="col-xs-2" align="right">
	 <img src="${pageContext.request.contextPath}/image/login/userDefault.jpg" id="img"
                                 name="img" οnclick="javascript:uploadImage(this.id);"
                                 style="cursor:pointer;width:147px;height:206px;">
	 <input type="hidden" id="photoPath" name="photoPath" value="${entity.photoPath}">
</div>

2. 點擊事件函數(此處方法給封裝過的方法,用的是layui的組件,後臺用的springmvc,其他框架可根據自己框架進行調整。無非就是給後臺傳遞一個參數,然後跳轉到另外一個頁面)

    //頭像圖片點擊函數
    function uploadImage() {
        //彈出圖片上傳
        var url = "${pageContext.request.contextPath}/administration/hrManage/personInfo/toImageUploadJsp.do";
        var obj = {
            area: ['40%', '70%'],
            url: url,
            title: '上傳圖片',
            id: 'personInfoAdd'
        };
        getDialogPage(obj);
    }

3. 後臺處理點擊後,跳轉到圖片上傳頁面的方法

@RequestMapping("/toImageUploadJsp")
	public ModelAndView toImageUploadJsp(){
		ModelAndView modelAndView =  new ModelAndView();
		try {
			modelAndView.addObject("formBtn", getFormBut(EditStatus.valueOf(1), false, false));//表單按鈕
			modelAndView.setViewName("/web/administration/hrManage/imageUpload");
		} catch (Exception e) {
			log.error("跳轉到跳轉到圖片上傳頁面失敗",e);
			modelAndView.setViewName("error/500");
		}
		return modelAndView;
	}

4. 上傳頁面代碼

<%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding="UTF-8" %>
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>
<!DOCTYPE>
<html>
<head>
    <title>用戶簽名</title>
    <meta http-equiv="Content-Type" content="text/html; charset=UTF-8">
    <jsp:include page="/initlib/initCommon.jsp"></jsp:include>
    <jsp:include page="/initlib/initEditCss.jsp"></jsp:include>
    <style type="text/css">
    </style>
</head>
<body>
<div style="width: 96%; height: 90%;">
    <legend>基本信息</legend>
    <hr style="margin-top:-20px;margin-left: 4%">
    <form id="dataForm" class="form-horizontal" role="form" method="post">
        <div class="form-group form-group-xs">
            <label for="uploadFile" class="col-xs-2 control-label"><a class="require"><i
                    class="icon-Asterisk"></i></a>上傳文件</label>
            <div class="col-xs-2">
                <input type="file" name="uploadFile" id="uploadFile" style="font-size:
                10px;font-family: Microsoft YaHei;border-style: inset;border-width: 2px;padding: 1px;" οnchange="preview(this)">
            </div>
        </div>
        <div class="form-group form-group-xs">
            <label for="previewImg" class="col-xs-2 control-label"><a class="require"><i
                    class="icon-Asterisk"></i></a>預覽圖片</label>
            <div class="col-xs-6">
                <img id="previewImg" style="width:147px;height:206px;"/>
            </div>
        </div>
    </form>
    <div id="footer">${formBtn}</div>
</div>
</body>
</html>
<script>
    $(document).ready(function () {

    });

    function saveClick() {
        if ($("#uploadFile").val() == "") {
            layer.msg('請選擇要上傳的文件', {icon: 0});
            return;
        }
        layer.confirm('上傳將會清空原有頭像,是否繼續操作?', {
                btn: ['確認', '取消'] //按鈕
            }, function () {
                var index = layer.load();
                $.ajaxFileUpload({
                    url: "${pageContext.request.contextPath}/administration/hrManage/personInfo/imageUpload.do",
                    secureuri: false,
                    fileElementId: "uploadFile",
                    dataType: 'text',
                    type: "POST",
                    success: function (data, status) {
                        layer.close(index);
                        var res = data.substring((data.indexOf('>') + 1), (data.indexOf('}') + 1));
                        var json = $.parseJSON(res);
                        if (json.success) {
                            //todo 處理返回的圖片路徑
                            //parent.$("#photoPath").attr("src",json.obj);
                            parent.initImage(json.obj);
                            layer.msg(json.msg, {icon: 6, time: 1000}, function () {
                                closeClick();
                            });
                        } else {
                            layer.msg(json.msg, {icon: 5});
                        }
                    },
                    error: function (data, status, e) {
                    }
                });
            }, function () {
            }
        );
    }
    //預覽圖片
    function preview(obj) {
        var file = obj.files[0];
        //file.size 單位爲byte  可以做上傳大小控制
        console.log("file.size = " + file.size);
        var reader = new FileReader();
        //讀取文件過程方法
        reader.onabort = function (e) {
            console.log("中斷讀取....");
        }
        reader.onerror = function (e) {
            console.log("讀取異常....");
        }
        reader.onload = function (e) {
            var img = document.getElementById("previewImg");
            img.src = e.target.result;
        }
        reader.readAsDataURL(file)
    }
</script>

Tips: 頁面中包含三部分內容:
1) 添加一個file類型的輸入框,用於選擇本地可上傳的文件。
2) 增加了一個function preview(obj)函數,用於處理上傳後的圖片預覽功能
3) 添加一個function saveClick()函數,用於處理圖片文件校驗、上傳圖片以及圖片回調問題
4)上傳成功後的回調函數parent.initImage(json.obj);將在後面進行介紹

5.圖片流後臺保存函數

@ResponseBody
	@RequestMapping("/imageUpload")
	public Json imageUpload(HttpSession session, @RequestParam("uploadFile") CommonsMultipartFile uplodaFile) {
		Json json = new Json();
		try {
			String contentType = uplodaFile.getContentType();
			String fileName = DateUtil.getNowDateTime("YYYY-MM-DD")+uplodaFile.getOriginalFilename();
			String folderPath = "E:/userImage";
			if (uplodaFile.isEmpty()) {
				json.setSuccess(false);
				json.setMsg("上傳圖片不正確");
				return json;
			}
			try {
				File targetFile = new File(folderPath);
				if (!targetFile.exists()) {
					targetFile.mkdirs();
				}
				FileOutputStream out = new FileOutputStream(folderPath +"/"+ fileName);
				out.write(uplodaFile.getBytes());
				out.flush();
				out.close();
			} catch (Exception e) {
				json.setSuccess(false);
				json.setMsg("上傳圖片失敗");
				return json;
			}
			json.setSuccess(true);
			//返回圖片路徑
			json.setObj(folderPath+"/"+fileName);
			json.setMsg("上傳圖片成功");
		} catch (Exception e) {
			log.error(message, e);
			json.setSuccess(false);
			json.setMsg("上傳圖片失敗"+e.getMessage());
		}
		return json;
	}
  1. 前臺回調函數功能,1. 保存返回的圖片路徑,2. 動態加載圖片
//初始化員工頭像
    function initImage(url) {
        if (url != undefined && url != "") {
            $("#img").attr("src", "${pageContext.request.contextPath}/administration/hrManage/personInfo/getImage.do?path=" + url);
            $("#photoPath").val(url);
        } else if ("${entity.photoPath}" != "") {
            $("#img").attr("src", "${pageContext.request.contextPath}/administration/hrManage/personInfo/getImage.do?path=" + "${entity.photoPath}");
        }
    }
  1. 上文中,調用了一個getImage的後臺函數,是因爲我們將圖片保存到服務器上項目外的文件夾內,工程文件無法直接通過路徑對圖片進行讀取。因此需要額外處理。
@ResponseBody
	@RequestMapping("/getImage")
	public void getImage(String path, HttpServletRequest request, HttpServletResponse response) {
		OutputStream os = null;
		try {
			BufferedImage image = ImageIO.read(new File(path));
			response.setContentType("image/png");
			os = response.getOutputStream();
			ImageIO.write(image, "gif", os);
		} catch (IOException e) {
			e.printStackTrace();
		}
	}

總結

  1. 處理圖片上傳預覽,本次由於時間關係採用自行設計開發的功能頁面,如果此需求其他模塊均需要使用,儘量採用開源的圖片上傳組件,例如Web Uploader一類的。一個是頁面設計更美觀、合理。第二個也是方便集成
  2. 顯示圖片的方案,本文中採用的方式爲通過文件流的形式,將服務器上存儲的圖片以流的形式讀取到頁面,並返回給前臺。如果你的服務器上已經配置了nginx,建議還是用nginx配置的方式實現圖片等靜態資源的直接讀取功能。(如果有時間,後面可以針對這一細節進行說明)
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章