原文链接: http://blog.csdn.net/wohuozheng/article/details/55044484
上传页面
<%@ page language="Java" import="java.util.*" pageEncoding="utf-8"%>
<% String path = request.getContextPath();
String basePath = request.getScheme() + "://" + request.getServerName() + ":" + request.getServerPort()
+ path + "/";
String error = (String) request.getAttribute("error0");
%>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd">
<html xmlns="http://www.w3.org/1999/xhtml">
<head>
<meta charset="UTF-8">
<title></title>
<link rel="stylesheet" href="${pageContext.request.contextPath}/css/ssi-uploader.css"/>
<script src="${pageContext.request.contextPath}/js/jquery-2.1.1.min.js" type="text/javascript"></script>
<script src="${pageContext.request.contextPath}/js/ssi-uploader.js"></script>
</head>
<body>
<!--右半部分-->
<div class="right">
<!--头部导航栏-->
<div class="right_top">
<p id="location">位置>图片上传</p>
<a href="${pageContext.request.contextPath}/admin/exit"><p id="exit">退出</p></a>
</div>
<!--右部主要内容-->
<div class="right_main">
<!--图片上传-->
<div class="row">
<div class="col-md-12">
<h3>图片上传:</h3>
<input type="file" multiple id="ssi-upload3"/>
<input type="hidden" id="albumId" value="${param.id }"/>
</div>
</div>
<script type="text/javascript">
var num=document.getElementById("albumId").value;
//下一行的url即为你后台所走的action路径
$('#ssi-upload3').ssi_uploader({url:'${pageContext.request.contextPath}/admin/uploader?albumId='+num,dropZone:false,allowed:['jpg','gif','txt','png','pdf']});
</script>
</div>
<script type="text/javascript" src="js/jquery.js"></script>
<script type="text/javascript">
$(".menu dt").css({"background-color":"#404040"});
$(".menu dt img").attr("src","images/left/select_xl01.png");
$(function(){
$(".menu dd").hide();
$(".menu dt").click(function(){
$(".menu dt").css({"background-color":"#404040"})
$(this).css({"background-color": "#FF5258"});
$(this).parent().find('dd').removeClass("menu_chioce");
$(".menu dt img").attr("src","images/left/select_xl01.png");
$(this).parent().find('img').attr("src","images/left/select_xl.png");
$(".menu_chioce").slideUp();
$(this).parent().find('dd').slideToggle();
$(this).parent().find('dd').addClass("menu_chioce");
});
})
</script>
</body>
</html>
ssi-uploader.css内容
.icon, span.ban7, span.ban7w, span.ban10, span.ban23, span.check7, span.check23, span.exclamation7, span.exclamation23, span.trash7, span.trash10 {
background-image: url("images/sprite.png");
}
.icon, span.ban7, span.ban7w, span.ban10, span.ban23, span.check7, span.check23, span.exclamation7, span.exclamation23, span.trash7, span.trash10 {
background-image: url("images/sprite.png");
}
.ssi-infoTooltip, .ssi-tooltipText {
border: 1px #b7b7b7 solid;
border-radius: 6px;
padding: 7px;
color: #fff;
display: none;
background-color: #151515;
position: absolute;
font-size: 14px;
font-weight: 500;
opacity: 1;
z-index: 30000;
}
.ssi-button {
display: inline-block;
text-align: center;
vertical-align: middle;
font-size: 12px;
text-decoration: none;
border: 1px solid #aeaeae;
cursor: pointer;
padding: 6px 6px;
margin: 0 0 0 2px;
border-radius: 3px;
color: whitesmoke;
}
.ssi-button.error {
background: #cf5144;
}
.ssi-button.error:hover {
background: #ab4b3f;
}
.ssi-button.error:active {
background: #8f493e;
}
.ssi-button.info {
background: #006cbc;
}
.ssi-button.info:hover {
background: #0054a0;
}
.ssi-button.info:active {
background: #004d8e;
}
.ssi-button.success {
background: #40b056;
}
.ssi-button.success:hover {
background: #389e48;
}
.ssi-button.success:active {
background: #2f963b;
}
.ssi-button[disabled] {
opacity: 0.8;
pointer-events: none;
}
.ssi-statusLabel {
padding: 2px 6px;
text-align: center;
font-size: 10px;
color: #fff;
font-weight: 600;
border-radius: 2px;
}
.ssi-statusLabel.error {
background: #cf5144;
}
.ssi-statusLabel.success {
background: #40b056;
}
.selected {
opacity: 0.4;
}
.ssi-previewBox {
float: left;
width: 100%;
color: #ccc;
padding: 10px;
}
.ssi-dropZonePreview {
min-height: 300px;
border: 2px dashed #ccc;
content: 'Drag n Drop Files';
}
#ssi-DropZoneBack {
z-index: -1;
overflow: hidden;
}
.ssi-removeBtn {
margin: 5px 0 5px 0;
padding: 0;
}
.ssi-uploader::after {
content: ' ';
display: block;
clear: both;
}
.ssi-uploadFiles {
position: relative;
float: left;
border: 1px solid #aaaaaa;
overflow: hidden;
border-radius: 3px;
width: 180px;
min-height: 32px;
margin: 2px 2px 2px 0;
font-size: 15px;
vertical-align: middle;
line-height: 30px;
-webkit-transition: height .3s;
transition: height .3s;
background: #FFFFFF;
padding-right: 1px;
}
span.ban7 {
background-position: 0px -18px;
background-repeat: no-repeat;
overflow: hidden;
display: block;
width: 18px;
height: 18px;
}
span.ban7w {
background-position: 0px -36px;
background-repeat: no-repeat;
overflow: hidden;
display: block;
width: 18px;
height: 18px;
background-color: #cf5144;
margin-top: 2px;
height: 17px;
}
span.ban10 {
background-position: 0px 0px;
background-repeat: no-repeat;
overflow: hidden;
display: block;
width: 18px;
height: 18px;
}
span.ban23 {
background-position: 0px -126px;
background-repeat: no-repeat;
overflow: hidden;
display: block;
width: 31px;
height: 31px;
}
span.check7 {
background-position: 0px -54px;
background-repeat: no-repeat;
overflow: hidden;
display: block;
width: 18px;
height: 18px;
background-color: #40b056;
margin-top: 2px;
height: 17px;
}
span.check23 {
background-position: 0px -157px;
background-repeat: no-repeat;
overflow: hidden;
display: block;
width: 31px;
height: 31px;
}
span.exclamation7 {
background-position: 0px -72px;
background-repeat: no-repeat;
overflow: hidden;
display: block;
width: 18px;
height: 18px;
margin-top: 2px;
background-color: #cf5144;
height: 17px;
border-radius: 3px;
}
span.exclamation23 {
background-position: 0px -188px;
background-repeat: no-repeat;
overflow: hidden;
display: block;
width: 31px;
height: 31px;
}
span.trash7 {
background-position: 0px -108px;
background-repeat: no-repeat;
overflow: hidden;
display: block;
width: 18px;
height: 18px;
}
span.trash10 {
background-position: 0px -90px;
background-repeat: no-repeat;
overflow: hidden;
display: block;
width: 18px;
height: 18px;
}
.ssi-previewBox.ssi-dragOver, .ssi-dragOver .ssi-dropZone {
color: #ba2919;
border-color: #ba2919;
}
.ssi-buttonWrapper {
float: left;
padding: 5px;
}
.ssi-noPreviewMessage {
position: relative;
z-index: 1;
border-radius: 4px;
margin: 1px;
float: right;
width: 35px;
height: 31px;
padding: 0;
}
.ssi-noPreviewMessage span {
margin: 0 auto;
}
.ssi-noPreviewSubMessage {
width: 15px;
height: 15px;
padding: 0;
}
.ssi-totalvalue {
float: right;
margin: 2px;
}
.ssi-upImgTd {
position: relative;
}
.ssi-upImgTd .fa-spin {
display: inline-block;
position: absolute;
top: 45%;
left: 45%;
}
.ssi-uploadProgressNoPreview {
position: absolute;
display: block;
text-align: center;
width: 0;
height: 35px;
background: #5cb85c;
-webkit-transition: width .3s;
transition: width .3s;
opacity: 0.6;
}
.ssi-uploadNoDropZone {
border: 1px solid #ccc;
}
.ssi-uploadProgress {
margin-top: 4px;
display: block;
text-align: center;
width: 0;
height: 10px;
background: #5cb85c;
-webkit-transition: width .3s;
transition: width .3s;
}
.ssi-uploadProgressNoPre {
position: absolute;
height: 19px;
margin-top: 0;
opacity: 0.6;
}
.ssi-uploaderNP {
position: relative;
}
.ssi-uploaderNP::after {
content: ' ';
display: block;
clear: both;
}
.ssi-uploadDetails {
width: 180px;
max-height: 0;
top: 37px;
background: #FFFFFF;
position: absolute;
-webkit-transition: max-height .2s ease-out;
transition: max-height .2s ease-out;
border-radius: 3px;
overflow: hidden;
padding-right: 2px;
}
.ssi-uploadBoxWrapper {
float: left;
}
.ssi-uploadBoxOpened {
max-height: 200px;
z-index: 2000;
overflow: auto;
border: 0.1mm solid #dcdcdc;
-webkit-transition: max-height .5s ease-out;
transition: max-height .5s ease-out;
}
table.ssi-fileList {
font-size: 10px;
margin: 5px;
}
table.ssi-fileList tr td:first-child {
border: 0.1mm solid #dcdcdc;
/*border: 0.1mm solid black;*/
width: 89%;
position: relative;
}
table.ssi-fileList tr td:nth-child(2) {
padding-left: 7px;
}
table.ssi-fileList tr {
line-height: 18px;
}
table.ssi-fileList tr.ssi-space > td {
border: none;
padding-bottom: 2px;
}
.ssi-uploadProgress.hide {
margin-top: 0;
opacity: 0;
-webkit-transition: opacity 1.3s;
transition: opacity 1.3s;
}
.ssi-canceledProgressBar {
width: 100% !important;
background: #d9534f;
}
.ssi-imgToUploadTable h2 {
margin: 0;
}
.ssi-hidden {
display: none;
}
.ssi-imgToUploadTable tr:first-child td:first-child {
height: 126px;
}
.ssi-imgToUploadTable tr td {
width: 140px;
}
.ssi-imgToUploadTable {
border: 1px solid #e1e1e1;
color: #000000;
font-size: 15px;
margin-right: 4px;
box-shadow: 0 10px 6px -6px #777;
padding: 5px;
display: inline-block;
width: 150px;
-ms-word-break: break-all;
word-break: break-all;
word-break: break-word;
-webkit-hyphens: auto;
-ms-hyphens: auto;
hyphens: auto;
}
.ssi-imgToUpload {
width: 140px;
height: 128px;
}
.ssi-btnIn {
float: left;
}
.ssi-ieCompatibilityForm {
display: none;
}
span.ssi-InputLabel input[type="file"] {
display: none;
}
.ssi-abortUpload {
padding: 0;
}
.ssi-abortUpload .ban7w {
margin: 0;
}
.ssi-removeBtnNP {
border: none;
color: #ff696d;
font-size: 11px;
margin: 0;
padding: 0;
}
.ssi-InputLabel.disabled, .ssi-InputLabel.disabled:hover, .ssi-InputLabel.disabled:active {
cursor: not-allowed;
background: #5cb85c;
opacity: .65;
}
.ssi-check {
color: #005900;
}
.ssi-boxHover {
cursor: pointer;
}
.ssi-upI.imgTd {
position: relative;
}
/*@author http://codepen.io/tevko/pen/DdsnK*/
.document-item {
display: inline-block;
width: 69px;
height: 74px;
color: black;
position: absolute;
top: 50%;
left: 50%;
-webkit-transform: translate(-50%, -50%);
transform: translate(-50%, -50%);
background: inherit;
}
.document-item::before {
position: absolute;
width: 69px;
height: 74px;
left: 0;
top: -7px;
content: '';
border: solid 2px #920035;
}
.document-item::after {
content: attr(filetype);
left: -4px;
padding: 0px 2px;
text-align: right;
line-height: 1.3;
position: absolute;
background-color: #000;
color: #fff;
font-size: 11px;
text-transform: uppercase;
letter-spacing: 1px;
top: 9px;
}
.document-item .fileCorner {
width: 0;
height: 0;
border-style: solid;
border-width: 13px 0 0 13px;
border-color: white transparent transparent #920035;
position: absolute;
top: -7px;
left: 61px;
}
ssi-uploader.js
/*
* error:an teleiwsei to upload kai iparxei ena sti lista pou den exei patithei
* */
(function (root, factory) {
//@author http://ifandelse.com/its-not-hard-making-your-library-support-amd-and-commonjs/
if (typeof module === "object" && module.exports) {
module.exports = factory(require("jQuery"));
} else {
factory(root.jQuery);
}
}(this, function ($) {
var Ssi_upload = function (element, options) {
this.options = options;
this.$element = '';
this.language = locale[this.options.locale];
this.uploadList = [];
this.totalProgress = [];
this.toUpload = [];
this.imgNames = [];
this.totalFilesLength = 0;
this.successfulUpload = 0;
this.aborted = 0;
this.abortedWithError = 0;
this.pending = 0;
this.inProgress = 0;
this.currentListLength = 0;
this.init(element);
};
Ssi_upload.prototype.init = function (element) {
$(element).addClass('ssi-uploadInput')
.after(this.$element = $('<div class="ssi-uploader">'));
var $chooseBtn = $('' +
'<span class="ssi-InputLabel">' +
'<button class="ssi-button success">' + this.language.chooseFiles + '</button>' +
'</span>').append(element);
var $uploadBtn = $('<button id="ssi-uploadBtn" class="ssi-button success ssi-hidden" >' +
'<span class="ssi-btnIn">' + this.language.upload + ' </span>' +
'<div id="ssi-up_loading" class="ssi-btnIn"></div></button>');
var $clearBtn = $('<button id="ssi-clearBtn" class="ssi-hidden ssi-button info" >' + this.language.clear +
'</button>');
var $abortBtn = $('<button id="ssi-abortBtn" class="ssi-button error ssi-cancelAll ssi-hidden" ><span class="inBtn">' + this.language.abort + ' </span></button>');
this.$element.append($('<div class="ssi-buttonWrapper">').append($chooseBtn, $abortBtn, $uploadBtn, $clearBtn));
var $uploadBox;
if (!this.options.preview) {
this.$element.addClass('ssi-uploaderNP');
var $fileList = $('<table id="ssi-fileList" class="ssi-fileList"></table>');
var $namePreview = $('<span class="ssi-namePreview"></span>');
var $mainBox = $('<div id="ssi-uploadFiles" class="ssi-tooltip ssi-uploadFiles ' + (this.options.dropZone ? 'ssi-dropZone' : '') + '"><div id="ssi-uploadProgressNoPreview" class="ssi-uploadProgressNoPreview"></div></div>')
.append($namePreview);
var $uploadDetails = $('<div class="ssi-uploadDetails"></div>').append($fileList);
$uploadBox = $('<div class="ssi-uploadBoxWrapper ssi-uploadBox"></div>').append($mainBox, $uploadDetails);
this.$element.prepend($uploadBox);
} else {
$uploadBox = $('<div id="ssi-previewBox" class="ssi-uploadBox ssi-previewBox ' + (this.options.dropZone ? 'ssi-dropZonePreview ssi-dropZone"><div id="ssi-DropZoneBack">' + this.language.drag + '</div>' : '">') + '</div>');
this.$element.append($uploadBox);
}
var thisS = this;
var $input = $chooseBtn.find(".ssi-uploadInput");
$chooseBtn.find('button').click(function () {
$input.trigger('click');
});
$input.on('change', function () { //choose files
thisS.toUploadFiles(this.files);
$input.val('');
});
//drag n drop
if (thisS.options.dropZone) {
$uploadBox.on("drop", function (e) {
e.preventDefault();
$uploadBox.removeClass("ssi-dragOver");
var files = e.originalEvent.dataTransfer.files;
thisS.toUploadFiles(files);
});
$uploadBox.on("dragover", function (e) {
e.preventDefault();
$uploadBox.addClass("ssi-dragOver");
return false;
});
$uploadBox.on("dragleave", function (e) {
e.preventDefault();
$uploadBox.removeClass("ssi-dragOver");
return false;
});
}
if (!thisS.options.preview) {
$mainBox.click(function () {
if (thisS.currentListLength > 1)
$uploadDetails.toggleClass('ssi-uploadBoxOpened');
})
}
$clearBtn.click(function () { //choose files completed and pending files
thisS.clear();
});
var $tooltip;
$uploadBox.on('mouseenter', '.ssi-statusLabel', function (e) { //the tooltip
var $eventTarget = $(e.currentTarget);
var title = $eventTarget.attr('data-status');
if (!title || title === '') {
return;
}
var tooltipHeight = '35';
if ($eventTarget.hasClass('ssi-noPreviewSubMessage')) {
tooltipHeight = 0;
}
$tooltip = $('<div class="ssi-infoTooltip">'
+ title +
'</div>')
.appendTo(thisS.$element)
.css({top: $eventTarget.position().top - tooltipHeight, left: $eventTarget.position().left - 5})
.fadeIn('slow');
});
$uploadBox.on('mouseleave', '.ssi-statusLabel', function () {
if ($tooltip)
$tooltip.remove();
});
$uploadBox.on('click', '.ssi-removeBtn', function (e) { //remove the file from list
var $currentTarget = $(e.currentTarget);
var index = $currentTarget.data('delete'); //get file's index
thisS.pending--; //reduce pending number by 1
thisS.currentListLength--; //reduce current list length by 1
if (thisS.pending === 0) {
$uploadBtn.prop('disabled', true); //if there is no more files disable upload button
}
if (thisS.options.preview) { //if preview is true
$currentTarget.parents('table.ssi-imgToUploadTable').remove(); //remove table
} else {
var target = $currentTarget.parents('tr.ssi-toUploadTr'); //find the tr of file
$namePreview.html((thisS.currentListLength) + ' files'); //set the main name to the remaining files
target.prev().remove();// remove empty tr (using id for margin between rows)
target.remove();// remove the file
if (thisS.currentListLength === 1) { //if only one file left in the list
setLastElementName(thisS); //set main preview to display the name
}
}
thisS.toUpload[index] = null; //set the file's obj to null (we don't splice it because we need to keep the same indexes)
thisS.imgNames[index] = null; //set the file's name to null
if (thisS.currentListLength === 0) { // if no more files in the list
if (!thisS.options.dropZone) { // if drag and drop is disabled
$uploadBox.removeClass('ssi-uploadNoDropZone');
}
$clearBtn.addClass('ssi-hidden');
$uploadBtn.addClass('ssi-hidden');
}
});
$uploadBox.on('click', '.ssi-abortUpload', function (e) {//abort one element
var $eventTarget = $(e.currentTarget);
var index = $eventTarget.data('delete');// get the element id
thisS.abort(index); // abort request
});
//----------------------------UPLOADFILES------------------------------------
$uploadBtn.click(function () {// upload the files
thisS.uploadFiles();
});
$abortBtn.click(function () { // abort all requests
thisS.abortAll();
});
};
Ssi_upload.prototype.abortAll = function () {
for (var i = 0; i < this.uploadList.length; i++) { //all element in the list
if (typeof this.uploadList[i] === 'object') {// check if not deleted
this.abort(i)
}
}
};
Ssi_upload.prototype.toUploadFiles = function (files) {
if (typeof this.options.maxNumberOfFiles === 'number') {
if ((this.inProgress + this.pending) >= this.options.maxNumberOfFiles) {// if in progress files + pending files are more than the number that we have define as max number of files pre download
return;//don't do anything
}
}
var thisS = this,
j = 0,
length,
imgContent = '',
$uploadBtn = this.$element.find('#ssi-uploadBtn'),
$clearBtn = this.$element.find('#ssi-clearBtn'),
$fileList = this.$element.find('#ssi-fileList'),
$uploadBox = this.$element.find('.ssi-uploadBox'),
imgs = [];
if ((this.inProgress === 0 && this.pending === 0)) { //if no file are pending or are in progress
this.clear(); //clear the list
}
var extErrors = [], sizeErrors = [], errorMessage = '';
var toUploadLength, filesLength = length = toUploadLength = files.length;
if (typeof this.options.maxNumberOfFiles === 'number') {//check if requested files agree with our arguments
if (filesLength > this.options.maxNumberOfFiles - (this.inProgress + this.pending)) { //if requested files is more than we need
filesLength = toUploadLength = this.options.maxNumberOfFiles - (this.inProgress + this.pending); // set variable to the number of files we need
}
}
//
for (var i = 0; i < filesLength; i++) {
var file = files[i],
ext = file.name.getExtension();// get file's extension
if ($.inArray(ext, this.options.allowed) === -1) { // if requested file not allowed
if (length > filesLength) {//there are more file we dont pick
filesLength++;//the add 1 more loop
} else {
toUploadLength--;
}
if ($.inArray(ext, extErrors) === -1) {//if we see first time this extension
extErrors.push(ext); //push it to extErrors variable
}
} else if ((file.size * Math.pow(10, -6)).toFixed(2) > this.options.maxFileSize) {//if file size is more than we ask
if (length > filesLength) {
filesLength++;
} else {
toUploadLength--;
}
sizeErrors.push(cutFileName(file.name, ext, 15));//register a size error
} else if ($.inArray(file.name, this.imgNames) === -1) {// if the file is not already in the list
$uploadBtn.prop("disabled", false);
setupReader(file);
this.pending++; // we have one more file that is pending to be uploaded
this.currentListLength++;// we have one more file in the list
} else {
if (length > filesLength) {
filesLength++;
} else {
toUploadLength--;
}
}
}
var extErrorsLength = extErrors.length, sizeErrorsLength = sizeErrors.length;
if (extErrorsLength + sizeErrorsLength > 0) { // in the end expose all errors
if (extErrorsLength > 0) {
errorMessage = this.language.extError.replaceText(extErrors.toString().replace(/,/g, ', '));
}
if (sizeErrorsLength > 0) {
errorMessage += this.language.sizeError.replaceText(sizeErrors.toString().replace(/,/g, ', '), this.options.maxFileSize + 'mb');
}
this.options.errorHandler.method(errorMessage, this.options.errorHandler.error);
}
function setupReader() {
var index = thisS.totalFilesLength + thisS.pending;
if (index === 0) {//do it only the first time
if (thisS.options.preview) {
if (!thisS.options.dropZone) {
$uploadBox.addClass('ssi-uploadNoDropZone')
}
}
$uploadBtn.removeClass('ssi-hidden');
$clearBtn.removeClass('ssi-hidden');
}
$clearBtn.prop('disabled', false);
thisS.toUpload[index] = file;
var filename = file.name;
var ext = filename.getExtension(); //get file's extension
thisS.imgNames[index] = filename; //register file's name
if (thisS.options.preview) {
var getTemplate = function (content) {
return '<table class="ssi-imgToUploadTable ssi-pending">' +
'<tr><td class="ssi-upImgTd">' + content + '</td></tr>' +
'<tr><td><div id="ssi-uploadProgress' + index + '" class="ssi-hidden ssi-uploadProgress"></div></td></tr>' +
'<tr><td><button data-delete="' + index + '" class=" ssi-button error ssi-removeBtn"><span class="trash10 trash"></span></button></td></tr>' +
'<tr><td>' + cutFileName(filename, ext, 15) + '</td></tr></table>'
};
var fileType = file.type.split('/');
if (fileType[0] == 'image') {
$uploadBtn.prop("disabled", true);
$clearBtn.prop("disabled", true);
var fileReader = new FileReader();
fileReader.onload = function () {
imgContent += getTemplate('<img class="ssi-imgToUpload" src=""/><i class="fa-spin fa fa-spinner fa-pulse"></i>'); // set the files element without the img
imgs[index] = fileReader.result;
j++;
if (toUploadLength === j) {// if all elements are in place lets load images
$uploadBox.append(imgContent);
$uploadBtn.prop("disabled", false);
$clearBtn.prop("disabled", false);
setTimeout(function () {
setImg();//and load the images
}, 10);
imgContent = '';
toUploadLength = [];
}
};
fileReader.readAsDataURL(file);
} else {
imgs[index] = null;
$uploadBox.append(getTemplate('<div class="document-item" href="test.mov" filetype="' + ext + '"><span class = "fileCorner"></span></div>'));
j++;
}
} else {
thisS.$element.find('.ssi-namePreview').html((index === 0 ? cutFileName(filename, ext, 13) : (thisS.currentListLength + 1) + ' ' + thisS.language.files));//set name preview
$fileList.append('<tr class="ssi-space"><td></td></tr>' +//append files element to dom
'<tr class="ssi-toUploadTr ssi-pending"><td><div id="ssi-uploadProgress' + index + '" class="ssi-hidden ssi-uploadProgress ssi-uploadProgressNoPre"></div>' +
'<span>' + cutFileName(filename, ext, 20) + '</span></td>' +
'<td><a data-delete="' + index + '" class="ssi-button ssi-removeBtn ssi-removeBtnNP"><span class="trash7 trash"></span></a></td></tr>');
}
var setImg = function () {//load the images
for (var i = 0; i < imgs.length; i++) {
if (imgs[i] !== null) {
$uploadBox.find("#ssi-uploadProgress" + i).parents('table.ssi-imgToUploadTable')
.find('.ssi-imgToUpload')
.attr('src', imgs[i]) //set src of the image
.next().remove();//remove the spinner
imgs[i] = null;
}
}
imgs = [];
};
}
};
var clearCompleted = function (thisS) {//clear all completed files
var $completed = thisS.$element.find('.ssi-completed');
thisS.successfulUpload = 0;
thisS.aborted = 0;
thisS.abortedWithError = 0;
if (!thisS.options.preview)$completed.prev('tr').remove();
$completed.remove();
};
var clearPending = function (thisS) {//clear all pending files
var $pending = thisS.$element.find('.ssi-pending');
var length = thisS.imgNames.length;
for (var i = 0; i < length; i++) {
if (thisS.imgNames[i] === null) {
thisS.toUpload.splice(i, 1);
thisS.imgNames.splice(i, 1);
}
}
thisS.toUpload.splice(-thisS.pending, thisS.pending);
thisS.imgNames.splice(-thisS.pending, thisS.pending);
thisS.pending = 0;
if (!thisS.options.preview)$pending.prev('tr').remove();
$pending.remove();
};
Ssi_upload.prototype.clear = function (action) {//clean the list of all non in progress files
switch (action) {
case 'pending':
clearPending(this);
break;
case 'completed':
clearCompleted(this);
break;
default:
clearPending(this);
clearCompleted(this);
}
var $uploadBtn = this.$element.find('#ssi-uploadBtn'),
$clearBtn = this.$element.find('#ssi-clearBtn');
this.currentListLength = getCurrentListLength(this);
if (this.inProgress === 0) { //if no file are uploading right now
this.totalProgress = [];
}
if ((this.currentListLength === 0)) { // if no items in the list
$clearBtn.addClass('ssi-hidden');
$uploadBtn.addClass('ssi-hidden');
this.totalFilesLength = 0;
if (!this.options.dropZone) {
this.$element.find('.ssi-uploadBox').removeClass('ssi-uploadNoDropZone')
}
}
$clearBtn.prop('disabled', true);
$uploadBtn.prop('disabled', true);
if (!this.options.preview) {
setNamePreview(this);
}
};
var setNamePreview = function (thisS) {//set the name preview according to the remaining elements in the list
if (thisS.currentListLength > 1) {//if more than one element left
thisS.$element.find('.ssi-namePreview').html(thisS.currentListLength + ' files'); // set the name preview to the length of the remaining items
} else if (thisS.currentListLength === 1) {//if one left
setLastElementName(thisS); // set the name of the element
} else { //if no elements left
thisS.$element.find('.ssi-uploadDetails').removeClass('ssi-uploadBoxOpened');
thisS.$element.find('#ssi-fileList').empty();//empty list
thisS.$element.find('.ssi-namePreview').empty();//empty the name preview
}
};
Ssi_upload.prototype.uploadFiles = function () {// upload the pending files
if (this.pending > 0) {
this.$element.find('#ssi-abortBtn').removeClass('ssi-hidden');
this.$element.find('.ssi-removeBtn')
.addClass('ssi-abortUpload')
.removeClass('ssi-removeBtn')
.children('span').removeClass('trash7 trash10 trash')
.addClass((this.options.preview ? 'ban7w' : 'ban7'));//transform remove button to abort button
var $uploadBtn = this.$element.find('#ssi-uploadBtn'),
$clearBtn = this.$element.find('#ssi-clearBtn');
$uploadBtn.prop("disabled", true);
var thisS = this,
formData = new FormData(),//set the form data
i = this.totalFilesLength;
if (this.totalFilesLength !== 0 && !this.options.preview) {
setNamePreview(this);
}
this.inProgress += this.pending;// add pending to in progress
this.totalFilesLength += this.pending;// this variable is to prevent id duplication during uploads
this.pending = 0;
if (this.inProgress === this.currentListLength) {// disable the clear button if no items in list we can be remove
$clearBtn.prop("disabled", true);
}
while (this.toUpload[i] === null) { // do it until you find a file
i++;
}
formData.append('files[]', thisS.toUpload[i]);//append the first file to the form data
$.each(this.options.data, function (key, value) {// append all extra data
formData.append(key, value);
});
if (typeof this.options.beforeUpload === 'function') {
try {
this.options.beforeUpload();// execute the beforeUpload callback
} catch (err) {
console.log('There is an error in beforeUpload callback');
console.log(err);
thisS.abortAll();
return;
}
}
thisS.$element.find('input.ssi-uploadInput').trigger('beforeUpload.ssi-uploader');
ajaxLoopRequest(formData, i);// make the request
}
//--------------start of ajax request-----------------------
function ajaxLoopRequest(formData, ii) {
var selector = 'table.ssi-imgToUploadTable';
if (!thisS.options.preview) {
selector = 'tr.ssi-toUploadTr'
}
var uploadBar = thisS.$element.find('#ssi-uploadProgress' + ii);//get the file's progress bar
uploadBar.removeClass('ssi-hidden') //make it visible
.parents(selector).removeClass('ssi-pending');
var ajaxOptions = $.extend({}, {//store the request to the uploadList variable
xhr: function () {
var xhr = new window.XMLHttpRequest();
xhr.upload.addEventListener('progress', function (e) {// add event listener to progress
if (e.lengthComputable) {
var percentComplete = (e.loaded / e.total) * 100;// calculate the progress
if (uploadBar) {
uploadBar.css({
width: percentComplete + '%'//update the progress bar width according to the progress
});
}
thisS.totalProgress[ii] = percentComplete;//store the progress to the array
var sum = arraySum(thisS.totalProgress) / (thisS.inProgress + thisS.successfulUpload);//and calculate the overall progress
if (!thisS.options.preview) {
thisS.$element.find('#ssi-uploadProgressNoPreview')
.removeClass('ssi-hidden')
.css({
width: sum + '%'
});
}
$uploadBtn.find('#ssi-up_loading').html(Math.ceil(sum) + '%');// add to upload button the current overall progress percent number
}
}, false);
return xhr;
},
async: true,
beforeSend: function (xhr) {
thisS.uploadList[ii] = xhr;
$uploadBtn.find('#ssi-up_loading') //add spiner to uploadbutton
.html('<i class="fa fa-spinner fa-pulse"></i>');
if (typeof thisS.options.beforeEachUpload === 'function') {
try {
var msg = thisS.options.beforeEachUpload({// execute the beforeEachUpload callback and save the returned value
name: thisS.toUpload[ii].name,//send some info of the file
type: thisS.toUpload[ii].type,
size: (thisS.toUpload[ii].size / 1024).toFixed(2)
}, xhr);
} catch (err) {
console.log('There is an error in beforeEachUpload callback');
console.log(err);
thisS.abortAll();
return;
}
}
thisS.$element.find('input.ssi-uploadInput').trigger('beforeEachUpload.ssi-uploader');
if (xhr.status === 0) {
if (xhr.statusText === 'canceled') {//if user used beforeEachUpload to abort the request
if (typeof msg === 'undefined') {//if no message
msg = false; //because user have already aborted the request set to false or anything else except undefined to prevent to abort it again
}
thisS.abortedWithError++;// we have one error more
thisS.abort(ii, msg);//call the abort function
}
}
},
type: 'POST',
data: formData,
cache: false,
contentType: false,
processData: false,
url: thisS.options.url,
error: function (request, error) {
if (error !== 'abort') {
uploadBar.addClass('ssi-canceledProgressBar');
var msg = thisS.language.error;
thisS.abortedWithError++;//add one more error
thisS.totalProgress.splice(ii, 1); //remove from progress array
if (!thisS.options.preview) {
msg = '<span class="exclamation7"></span>';
}
setElementMessage(thisS, ii, 'error', msg, thisS.language.serverError);
thisS.totalProgress[ii] = '';
thisS.inProgress--;
$clearBtn.prop("disabled", false);
if (typeof thisS.options.onEachUpload === 'function') {//execute the onEachUpload callback
try {
thisS.options.onEachUpload({//and return some info
uploadStatus: 'error',
name: thisS.toUpload[ii].name,
size: (thisS.toUpload[ii].size / 1024).toFixed(2),
type: thisS.toUpload[ii].type
});
} catch (err) {
console.log('There is an error in onEachUpload callback');
console.log(err);
}
}
if (getCompleteStatus(thisS)) {//if no more elements in progress
finishUpload(thisS);
}
console.log(arguments);//log the error
console.log(" Ajax error: " + error);
}
}
}, thisS.options.ajaxOptions);
$.ajax(ajaxOptions).done(function (responseData, textStatus, jqXHR) {
var msg, title = '', dataType = 'error', spanClass = 'exclamation', data;
try {
data = $.parseJSON(responseData);
} catch (err) {
data = responseData;
}
if (thisS.options.responseValidation) {
var valData = thisS.options.responseValidation;
if (typeof valData.validationKey === 'object' && valData.resultKey == 'validationKey') {
if (data.hasOwnProperty(valData.validationKey.success)) {
cb(true);
} else {
cb(false, data[valData.validationKey.error]);
}
} else {
if (data[valData.validationKey] == valData.success) {
cb(true);
} else {
cb(false, data[valData.resultKey]);
}
}
} else {
if (jqXHR.status == 200) {
cb(true);
} else {
cb(false, data);
}
}
function cb(result, data) {
if (result) {//if response type is success
dataType = 'success';
msg = thisS.language.success;
spanClass = 'check';
thisS.successfulUpload++;// one more successful upload
} else {
uploadBar.addClass('ssi-canceledProgressBar');
if (thisS.options.preview) {
msg = thisS.language.error;
}
title = data;
thisS.abortedWithError++;
}
}
if (!thisS.options.preview) {
msg = '<span class="' + spanClass + '7"></span>';
}
setElementMessage(thisS, ii, dataType, msg, title);
if (typeof thisS.options.onEachUpload === 'function') {//execute the onEachUpload callback
try {
thisS.options.onEachUpload({//and return some info
uploadStatus: dataType,
name: thisS.toUpload[ii].name,
size: (thisS.toUpload[ii].size / 1024).toFixed(2),
type: thisS.toUpload[ii].type
});
} catch (err) {
console.log('There is an error in onEachUpload callback');
console.log(err);
}
}
thisS.$element.find('input.ssi-uploadInput').trigger('onEachUpload.ssi-uploader');
thisS.inProgress--;//one less in progress upload
$clearBtn.prop("disabled", false);
if (getCompleteStatus(thisS)) {//if no more files in progress
finishUpload(thisS);
}
// thisS.totalProgress[ii]='';
thisS.uploadList[ii] = '';
thisS.toUpload[ii] = '';
thisS.imgNames[ii] = '';
});
//--------------end of ajax request-----------------------
i = ii;
i++;//Go to the next element
while (thisS.toUpload[i] === null) {// do it until you find a file
i++;
}
if (i < thisS.toUpload.length) {// if more files exist start the next request
formData = new FormData();
$.each(thisS.options.data, function (key, value) {
formData.append(key, value);
});
formData.append('files[]', thisS.toUpload[i]);
ajaxLoopRequest(formData, i);
}
}
};
var setElementMessage = function (thisS, index, msgType, msg, title) {
var className = '', elementSelector = 'table.ssi-imgToUploadTable', element;
if (!thisS.options.preview) {
className = 'ssi-noPreviewSubMessage';
elementSelector = 'tr.ssi-toUploadTr';
if (thisS.currentListLength === 1) {
thisS.errors = title;
}
}
element = thisS.$element.find(".ssi-abortUpload[data-delete='" + index + "']");
element.parents(elementSelector).addClass('ssi-completed');
element.after(getResultMessage(msgType, msg, title, className))
.remove();
};
var getCompleteStatus = function (thisS) {//check if file are in progress
return (thisS.inProgress === 0);
};
var getResultMessage = function (type, msg, title, classes) {//return a message label
return '<span class="ssi-statusLabel ' + classes + ' ' + type + '" data-status="' + title + '">' + msg + '</span>';
};
var getCurrentListLength = function (thisS) { //get the list length
return (thisS.inProgress + thisS.successfulUpload + thisS.aborted + thisS.abortedWithError + thisS.pending);
};
var setLastElementName = function (thisS) { //if one file in list get the last file's name and put it to the name preview
var fileName = thisS.$element.find('#ssi-fileList').find('span').html();//find the only span left
var ext = fileName.getExtension();//get the extension
thisS.$element.find('.ssi-uploadDetails').removeClass('ssi-uploadBoxOpened');
thisS.$element.find('.ssi-namePreview').html(cutFileName(fileName, ext, 15));//short the name and put it to the name preview
};
Ssi_upload.prototype.abort = function (index, title) {//abort a request
if (typeof title === 'undefined') {//if no title
this.uploadList[index].abort();// abort the element
this.totalProgress[index] = '';
title = 'Aborted';
this.aborted++;// one more aborted file
} else if (typeof title !== 'string') {//if not string that means that the request aborted with the beforeUpload callback and no message returned
title = '';
}
//nothing of the above happened that means the user aborted the request with the beforeUpload callback and returned a message
var msg = this.language.aborted;
if (!this.options.preview) {
msg = '<span class="ban7w"></span>';
}
setElementMessage(this, index, 'error', msg, title);
this.$element.find('#ssi-uploadProgress' + index).removeClass('ssi-hidden').addClass('ssi-canceledProgressBar');
this.toUpload[index] = undefined;
this.uploadList[index] = undefined;
this.imgNames[index] = undefined;
this.$element.find('#ssi-clearBtn').prop("disabled", false);
this.inProgress--;//one less in progress file
if (getCompleteStatus(this)) {//if no more file in progress
finishUpload(this);
}
};
var finishUpload = function (thisS) {//when every uplaod ends
thisS.$element.find('#ssi-abortBtn').addClass('ssi-hidden');
if (!thisS.options.preview) {//display tha main message in the name preview
var type = 'error', title = '', msg = '';
if (thisS.abortedWithError > 0) { //if no errors
if (thisS.totalFilesLength === 1) {// if only one file in the list
title = thisS.errors; //display the error
} else {//else display something more general message
title = thisS.language.someErrorsOccurred
}
msg = '<span class="exclamation23"></span>';
} else if (thisS.aborted > 0 && thisS.successfulUpload === 0) {//if all request aborted
msg = '<span class="ban23"></span>';
title = thisS.language.aborted;
} else if (thisS.successfulUpload > 0) {// all request were successfull
type = 'success';
msg = '<span class="check23"></span>';
title = thisS.language.sucUpload;
}
thisS.$element.find('.ssi-namePreview').append(getResultMessage(type, msg, title, 'ssi-noPreviewMessage'));//show the message in the name preview
thisS.$element.find('#ssi-uploadProgressNoPreview') //remove main overall progress bar
.removeAttr('styles')
.addClass('ssi-hidden');
}
if (typeof thisS.options.onUpload === 'function') {
try {
thisS.options.onUpload();//execute the on Upload callback
} catch (err) {
console.log('There is an error in onUpload callback');
console.log(err);
}
}
thisS.$element.find('input.ssi-uploadInput').trigger('onUpload.ssi-uploader');
var $uploadBtn = thisS.$element.find('#ssi-uploadBtn');
thisS.$element.find('#ssi-clearBtn').prop("disabled", false);
$uploadBtn.prop("disabled", false)
.find('#ssi-up_loading')
.empty();
if (thisS.pending === 0) {
$uploadBtn.addClass('ssi-hidden');
thisS.toUpload = [];
thisS.imgNames = [];
thisS.totalFilesLength = 0;
}
thisS.uploadList = [];
thisS.totalProgress = [];
thisS.currentListLength = getCurrentListLength(thisS);
thisS.successfulUpload = 0;
thisS.aborted = 0;
thisS.abortedWithError = 0;
thisS.inProgress = 0;
};
$.fn.ssi_uploader = function (opts) {
var defaults = {
url: '',
data: {},
locale: 'en',
preview: true,
dropZone: true,
maxNumberOfFiles: '',
responseValidation: false,
maxFileSize: 5,
ajaxOptions: {},
onUpload: function () {
},
onEachUpload: function () {
},
beforeUpload: function () {
},
beforeEachUpload: function () {
},
allowed: ['jpg', 'jpeg', 'png', 'bmp', 'gif'],
errorHandler: {
method: function (msg) {
alert(msg);
},
success: 'success',
error: 'error'
}
};
var options = $.extend(true, defaults, opts);
return this.each(function () {
var $element = $(this);
if ($element.is('input[type="file"]')) {
if ($element.data('ssi_upload')) return;
var ssi_upload = new Ssi_upload(this, options);
$element.data('ssi_upload', ssi_upload);
} else {
console.log('The targeted element is not file input.')
}
});
};
//functions
String.prototype.replaceText = function () {//replace $ with variables
var args = Array.apply(null, arguments);
var text = this;
for (var i = 0; i < args.length; i++) {
text = text.replace('$' + (i + 1), args[i])
}
return text;
};
String.prototype.getExtension = function () {//returns the extension of a path or file
return this.split('.').pop().toLowerCase();
};
var cutFileName = function (word, ext, maxLength) {//shorten the name
if (typeof ext === 'undefined')ext = '';
if (typeof maxLength === 'undefined')maxLength = 10;
var min = 4;
if (maxLength < min)return;
var extLength = ext.length;
var wordLength = word.length;
if ((wordLength - 2) > maxLength) {
word = word.substring(0, maxLength);
var wl = word.length - extLength;
word = word.substring(0, wl);
return word + '...' + ext;
} else return word;
};
var arraySum = function (arr) {//return the sum of an array
var sum = 0;
for (var i = 0; i < arr.length; i++) {
if (typeof arr[i] === 'number')
sum += arr[i];
}
return sum;
};
var locale = {
en: {
success: 'Success',
sucUpload: 'Successful upload',
chooseFiles: '选择图片',
uploadFailed: 'Upload failed',
serverError: 'Internal server error',
error: 'Error',
abort: 'Abort',
aborted: 'Aborted',
files: 'files',
upload: '开始上传',
clear: '清空',
drag: 'Drag n Drop',
sizeError: '$1 exceed the size limit of $2',// $1=file name ,$2=max ie( example.jpg has has exceed the size limit of 2mb)
extError: '$1 file types are not supported',//$1=file extension ie(exe files are not supported)
someErrorsOccurred: 'Some errors occurred!'
},
gr: {
success: 'Επιτυχία',
sucUpload: 'Επιτυχής μεταφόρτωση',
chooseFiles: 'Επιλέξτε αρχεία',
uploadFailed: 'Η μεταφόρτωση απέτυχε!',
serverError: 'Εσωτερικό σφάλμα διακομιστή!',
error: 'Σφάλμα',
abort: 'Διακοπή',
aborted: 'Διακόπηκε',
files: 'αρχεία',
upload: 'Μεταφόρτωση',
clear: 'Εκκαθάριση',
drag: 'Συρετε εδώ...',
sizeError: '$1 έχει ξεπεράσει το όριο των $2.',// $1=file name ,$2=max file size ie( example.jpg has has exceed the size limit of 2mb)
extError: '$1 αρχεία δεν υποστηρίζονται.',// $1=file extension ie(exe files are not supported)
someErrorsOccurred: 'Σημειώθηκαν ορισμένα λάθη!'
}
};
}));
到这里只需要在后台action接受处理
@RequestMapping("uploader")
public String upload(HttpServletRequest request,HttpServletResponse response,int albumId,Map<String, Object> model){
Culture culture=new Culture();
MultipartHttpServletRequest Murequest = (MultipartHttpServletRequest)request;
Map<String, MultipartFile> files = Murequest.getFileMap();//得到文件map对象
String upaloadUrl ="D:/upload/photo/";//得到当前工程路径拼接上文件名
File dir = new File(upaloadUrl);
if(!dir.exists())//目录不存在则创建
dir.mkdirs();
for(MultipartFile file :files.values()){
String fileName=file.getOriginalFilename();//相片的名字
adminBiz.addPhoto(culture,fileName,albumId);//根据需求存储自己需要的信息到数据库,我这里是存储相片的名字及它所关联的相册的id
File tagetFile = new File(upaloadUrl+fileName);//创建文件对象
if(!tagetFile.exists()){//文件名不存在 则新建文件,并将文件复制到新建文件中
try {
tagetFile.createNewFile();
} catch (IOException e) {
e.printStackTrace();
}
try {
file.transferTo(tagetFile);//到这里就可以上传了,以下是处理图片及允许gif的上传
//图片扩展名
String types=fileName.substring(fileName.lastIndexOf(".")+1).toLowerCase();
//以1024*768大小改变图片,如果是gif则放开限制,如果需要存储原图则不需要处理
if(!types.contains("gif")){
Thumbnails.of(tagetFile).size(1024,768).toFile(tagetFile);
}
} catch (IllegalStateException e) {
e.printStackTrace();
} catch (IOException e) {
e.printStackTrace();
}
}
}
return "根据需要返回的页面";
}