webuploader插件 前端实现图片旋转后上传

前端上传图片正向的图片,上传后就被旋转了。这是因为,图片中包含许多属性来记录拍摄信息。引入EXIF就可以读取这些属性。
引入exif.js文件
exif.js文件下载地址:http://code.ciaoca.com/javascript/exif-js/
载入 JavaScript 文件

<script src="exif.js"></script>

EXIF中,包含一个Orientation参数,用来记录拍摄照片时的方向。在使用PS或者其他软件旋转图片时,图片旋转了,但Orientation不会改变,由于我们使用的图片预览器能够预处理图片,使其看起来与旋转后一致,但上传图片时,浏览器并不会预处理。所以导致图片旋转。
Orientation一共含有8个值,分别是:1、2、3、4、5、6、7、8。
这8个值对应的意思是:

Orientation 释义
1 正常
2 正常镜像
3 顺时针旋转180°
4 顺时针旋转180°镜像
5 顺时针旋转270°镜像
6 顺时针旋转270°
7 顺时针旋转90°镜像
8 顺时针旋转90°
在这里插入图片描述
前端通过exif.js文件获取要上传图片的元数据信息Orientation,再通过canvas旋转图片,改变图片的方向再进行上传。
创建Web Uploader实例

// 初始化Web Uploader
var uploader = WebUploader.create({
    // 选完文件后,是否自动上传。
    auto: true,
    // swf文件路径
    swf: BASE_URL + '/js/Uploader.swf',
    // 文件接收服务端。
    server: 'http://webuploader.duapp.com/server/fileupload.php',
    // 选择文件的按钮。可选。
    // 内部根据当前运行是创建,可能是input元素,也可能是flash.
    pick: '#filePicker',
    // 只允许选择图片文件。
    accept: {
        title: 'Images',
        extensions: 'gif,jpg,jpeg,bmp,png',
        mimeTypes: 'image/*'
    }
});

在Web Uploader实例里添加onFileQueued事件

uploader.onFileQueued = function( file ) {

    fileCount++;
    fileSize += file.size;

    if ( fileCount === 1 ) {
        $placeHolder.addClass( 'element-invisible' );
        $statusBar.show();
    }
    var Orientation = 0;
    var fileExif = file.source.source;
    var fileName = fileExif.name;
    var newFile = null;
    //图片方向角
    var rFilter = /^(image\/jpeg|image\/png|image\/jpg|image\/gif|image\/jpe)$/i; // 检查图片格式
    if (rFilter.test(file.type) && file.source.source !== undefined) {
        console.log("旋转开始");
        EXIF.getData(file.source.source, function() {
            Orientation = EXIF.getTag(this, 'Orientation');
            if (fileExif && Orientation > 1) {
                //获取照片方向角属性,用户旋转控制
                console.log(Orientation);
                var oReader = new FileReader();
                oReader.readAsDataURL(fileExif);

                oReader.onload = function(e) {
                    var image = new Image();
                    image.src = e.target.result;
                    image.onload = function() {
                        var expectWidth = this.naturalWidth;
                        var expectHeight = this.naturalHeight;

                        var canvas = document.createElement("canvas");
                        var ctx = canvas.getContext("2d");
                        canvas.width = expectWidth;
                        canvas.height = expectHeight;
                        ctx.drawImage(this, 0, 0, expectWidth, expectHeight);
                        var base64 = null;
                        //修复ios
                        if (navigator.userAgent.match(/iphone/i)) {
                            console.log('iphone');
                            if(Orientation != "" && Orientation != 1){
                                switch(Orientation){
                                    case 6:
                                        rotateImg(this,'left',canvas);
                                        break;
                                    case 8:
                                        rotateImg(this,'right',canvas);
                                        break;
                                    case 3:
                                        rotateImg(this,'right',canvas);//转两次
                                        rotateImg(this,'right',canvas);
                                        break;
                                }
                            }
                            base64 = canvas.toDataURL(fileExif.type, 1);
                        }else if (navigator.userAgent.match(/Android/i)) {// 修复android
                            var encoder = new JPEGEncoder();
                            base64 = encoder.encode(ctx.getImageData(0, 0, expectWidth, expectHeight), 80);
                        }else{
                            if(Orientation != "" && Orientation != 1){
                                switch(Orientation){
                                    case 6:
                                        rotateImg(this,'left',canvas);
                                        break;
                                    case 8:
                                        rotateImg(this,'right',canvas);
                                        break;
                                    case 3:
                                        rotateImg(this,'right',canvas);//转两次
                                        rotateImg(this,'right',canvas);
                                        break;
                                }
                            }
                            base64 = canvas.toDataURL(fileExif.type, 1);
                        }
                        var baseFile = dataURLtoFile(base64, fileName);
                        newFile = baseFile;
                        file.source.source = newFile;
                        addFile(file);
                        setState('ready');
                        updateTotalProgress();
                    };
                };
            }else {
                addFile( file );
                setState( 'ready' );
                updateTotalProgress();
            }
        });
    } else {
        addFile( file );
        setState( 'ready' );
        updateTotalProgress();
    }

    function dataURLtoFile(dataurl, filename) { //将base64转换为文件
        var arr = dataurl.split(','),
            mime = arr[0].match(/:(.*?);/)[1],
            bstr = atob(arr[1]),
            n = bstr.length,
            u8arr = new Uint8Array(n);
        while (n--) {
            u8arr[n] = bstr.charCodeAt(n);
        }
        return new File([u8arr], filename,{
            type: mime
        });
    }

    function rotateImg(img, direction,canvas) {
        //alert(img);
        //最小与最大旋转方向,图片旋转4次后回到原方向
        var min_step = 0;
        var max_step = 3;
        //var img = document.getElementById(pid);
        if (img == null)return;
        //img的高度和宽度不能在img元素隐藏后获取,否则会出错
        var height = img.height;
        var width = img.width;
        //var step = img.getAttribute('step');
        var step = 2;
        if (step == null) {
            step = min_step;
        }
        if (direction == 'right') {
            step++;
            //旋转到原位置,即超过最大值
            step > max_step && (step = min_step);
        } else {
            step--;
            step < min_step && (step = max_step);
        }
        //旋转角度以弧度值为参数
        var degree = step * 90 * Math.PI / 180;
        var ctx = canvas.getContext('2d');
        switch (step) {
            case 0:
                canvas.width = width;
                canvas.height = height;
                ctx.drawImage(img, 0, 0);
                break;
            case 1:
                canvas.width = height;
                canvas.height = width;
                ctx.rotate(degree);
                ctx.drawImage(img, 0, -height);
                break;
            case 2:
                canvas.width = width;
                canvas.height = height;
                ctx.rotate(degree);
                ctx.drawImage(img, -width, -height);
                break;
            case 3:
                canvas.width = height;
                canvas.height = width;
                ctx.rotate(degree);
                ctx.drawImage(img, -width, 0);
                break;
        }
    }

};

这样上传到后端服务器的图片的Orientation就全部为1啦,预览时,图片就不会被旋转。

评论 4
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值