web页面 之 图片上传
关于图片上传,在web领域这是个经典问题之一!任何网站都需要牵扯到图片上传保存的问题!
关于图片上传,存储的方式有两种,一种直接上传到服务器再把路径返回给客户端然后显示,另一个是直接在客户端本地显示,上传的图片是从本机的内存中读取的!这两种的最大区别就是:减小服务端的压力!增加用户的友好性体验!废话不多说,直接上代码:
第一种:form表单+iframe标签(兼容所有浏览器的Bug组合,注意点:图片会先上传在服务端保存然后在客户端显示,这会给服务器带来压力,不过没别的办法!上传存储时先存在临时文件,用户确认之后,再放在正式文件中)
HTML:
<form action="/up_img/" method="POST" target="ifr" enctype="multipart/form-data" id="f2">
{% csrf_token %}
<iframe name="ifr" id="ifr" style="display: none">
</iframe>
<div class="form-group">
<label for="inputPassword3" class="col-sm-2 control-label"></label>
<div class="col-sm-6">
<div style="z-index: 600;position: relative">
<img style="width: 80px;height: 80px;margin-top: -60%;margin-left: -100%" src="" id="show_img">
</div>
<div style="z-index: 800;position: relative;opacity: 0">
<input type="file" style="width: 80px;height: 80px;margin-top: -200%;margin-left: -100%" id="up-img" name="avatar">
</div>
</div>
</form>
js:
<script type="text/javascript" src="/static/jquery-3.2.1.js"></script>
<script>
$('#up-img').change(function () {
document.getElementById("ifr").onload=loadIframe;
$('#f2')[0].submit()
});
function loadIframe() {
var content = document.getElementById('ifr').contentWindow.document.body.innerText;
$('#show_img').attr('src',content);
$('#id_avatar').val(content)
}
$('#img-code').click(function () {
$(this).attr('src',$(this).attr('src')+'?')
})
</script>
views:
#头像上传
def up_img(request):
if request.method == 'GET':
return HttpResponse('o12!')
else:
file_obj = request.FILES.get('avatar') # 取文件时,需以FILES获取文件数据
file_path = ('static/img/' + file_obj.name)
f = open(file_path, 'wb') # 以字节方式打开空文件,拼接文件路径
for chunk in file_obj.chunks():
f.write(chunk)
f.close()
return HttpResponse(file_path)
第二种,利用ajax或是现在浏览器的对象实现的图片预览
HTML:
<div class="pics">
<div style="margin-left: 5px;position: relative">
{{ obj.avatar }}
<input type="file" id="imgSelect">
<img id="previewImg" src="/static/images/default.jpg" alt="点击上传图片" title="点击上传图片">
</div>
</div>
JS
<script>
$(function () {
bindAvatar()
});
function bindAvatar() {
if(window.URL.createObjectURL){
bindAvatar2();
}
else if(window.FileReader){
bindAvatar3()
}else{
bindAvatar1();
}
}
//ajax #需要上传到服务器
function bindAvatar1() {
document.getElementById("imgSelect").onchange=function () {
var formData = new FormData();
formData.append("files",$("#imgSelect")[0].files[0]);
$.ajax({
url: "/upload_images/",
type:"POST",
data:formData,
contentType:false,
processData:false,
dataType:"JSON",
success:function (arg) {
$("#previewImg").attr("src",arg.url)
}
})
}
}
//以下两种方法,否是利用现在浏览器的对象,直接从本机的内存中获取!
//兼容性不高
function bindAvatar2() {
document.getElementById("imgSelect").onchange=function () {
var obj = this.files[0]; //获取当前文件对象
var v = window.URL.createObjectURL(obj);//把当前文件对象传入URL方法,获取当前文件的路径
document.getElementById("previewImg").src = v;
document.getElementById("previewImg").onload=function () {
window.URL.revokeObjectURL(v); //图片加载完成之后,释放
}
}
}
//兼容性不高
function bindAvatar3() {
document.getElementById("imgSelect").onchange=function () {
var obj = this.files[0];
var reader = new FileReader(); //创建一个FileReader对象
reader.onload = function () {
console.log(this.result);
document.getElementById("previewImg").src=this.result;
};//有内容对象就会加载,执行函数; this.result 指获取的文件对象(具体信息)
reader.readAsDataURL(obj);//读取对象,在浏览器上显示
}
}
</script>
CSS: 位置在页面的左上角
div.pics{
width: 145px;
height: 150px;
position: absolute;
top:15%;
right: 7%;
border-left: 1px dotted darkgray;
overflow: hidden;
}
div.pics img{
width: 135px;
height: 150px;
border-radius: 12px;
opacity: 1;
}
div.pics #imgSelect{
position: absolute;
top:0;
left: 0;
opacity: 0;
border-radius: 12px;
width: 135px;
height: 150px;
}
views函数
def upload_images(request):
file_obj = request.FILES.get("files")
file_path = os.path.join("static/images",file_obj.name)
with open(file_path,"wb") as f:
for chunk in file_obj.chunks():
f.write(chunk)
dic = {
"error":0,
"url":'/'+file_path,
"message":" 错了...."
}
return HttpResponse(json.dumps(dic))
urls
url(r'^upload_images/', views.upload_images,name="imag"),
浙公网安备 33010602011771号