web中图片被自动旋转了,怎么解决

先看个案例:
web站上图片被旋转90度
打开图片连接可以查看到原图是横向的

很多人会遇到这样的问题,一张背景图片或者img标签图片没有任何角度相关的样式,图片却被旋转了90度或者180度,然后疯狂查看代码依然找不到原因,其实这是部分图片由于拍摄时候保存了exif信息。

什么是EXIF

简单来说,Exif 信息就是由数码相机在拍摄过程中采集一系列的信息,然后把信息放置在我们熟知的 JPEG/TIFF 文件的头部,也就是说 Exif信息是镶嵌在 JPEG/TIFF 图像文件格式内的一组拍摄参数,它就好像是傻瓜相机的日期打印功能一样,只不过 Exif信息所记录的资讯更为详尽和完备。Exif 所记录的元数据信息非常丰富,主要包含了以下几类信息:

  • 拍摄日期
  • 摄器材(机身、镜头、闪光灯等
  • 拍摄参数(快门速度、光圈F值、ISO速度、焦距、测光模式等
  • 图像处理参数(锐化、对比度、饱和度、白平衡等)
  • 图像描述及版权信息
  • GPS定位数据
  • 缩略图

这里面就包含了图片的角度信息,就是说你用手机拍照时是不是倒着拍还是侧着拍,这些都是有记录的。

有几种方式去解决这个问题:

一、后端可以利用php的exif扩展中的函数exif_read_data()去做,具体操作可以只行百度,不做详细描写。
二、js
// 这里的获取exif要将图片转ArrayBuffer对象,这里假设获取了图片的baes64
// 步骤一
// base64转ArrayBuffer对象
  function base64ToArrayBuffer(base64) {
    base64 = base64.replace(/^data\:([^\;]+)\;base64,/gmi, '');
    var binary = atob(base64);
    var len = binary.length;
    var buffer = new ArrayBuffer(len);
    var view = new Uint8Array(buffer);
    for (var i = 0; i < len; i++) {
      view[i] = binary.charCodeAt(i);
    }
    return buffer;
  }
// 步骤二,Unicode码转字符串
// ArrayBuffer对象 Unicode码转字符串
  function getStringFromCharCode(dataView, start, length) {
    var str = '';
    var i;
    for (i = start, length += start; i < length; i++) {
      str += fromCharCode(dataView.getUint8(i));
    }
    return str;
  }
 
// 步骤三,获取jpg图片的exif的角度(在ios体现最明显)
  function getOrientation(arrayBuffer) {
    var dataView = new DataView(arrayBuffer);
    var length = dataView.byteLength;
    var orientation;
    var exifIDCode;
    var tiffOffset;
    var firstIFDOffset;
    var littleEndian;
    var endianness;
    var app1Start;
    var ifdStart;
    var offset;
    var i;
    // Only handle JPEG image (start by 0xFFD8)
    if (dataView.getUint8(0) === 0xFF && dataView.getUint8(1) === 0xD8) {
      offset = 2;
      while (offset < length) {
        if (dataView.getUint8(offset) === 0xFF && dataView.getUint8(offset + 1) === 0xE1) {
          app1Start = offset;
          break;
        }
        offset++;
      }
    }
    if (app1Start) {
      exifIDCode = app1Start + 4;
      tiffOffset = app1Start + 10;
      if (getStringFromCharCode(dataView, exifIDCode, 4) === 'Exif') {
        endianness = dataView.getUint16(tiffOffset);
        littleEndian = endianness === 0x4949;
 
        if (littleEndian || endianness === 0x4D4D /* bigEndian */) {
          if (dataView.getUint16(tiffOffset + 2, littleEndian) === 0x002A) {
            firstIFDOffset = dataView.getUint32(tiffOffset + 4, littleEndian);
 
            if (firstIFDOffset >= 0x00000008) {
              ifdStart = tiffOffset + firstIFDOffset;
            }
          }
        }
      }
    }
    if (ifdStart) {
      length = dataView.getUint16(ifdStart, littleEndian);
 
      for (i = 0; i < length; i++) {
        offset = ifdStart + i * 12 + 2;
        if (dataView.getUint16(offset, littleEndian) === 0x0112 /* Orientation */) {
 
          // 8 is the offset of the current tag's value
          offset += 8;
 
          // Get the original orientation value
          orientation = dataView.getUint16(offset, littleEndian);
 
          // Override the orientation with its default value for Safari (#120)
          if (IS_SAFARI_OR_UIWEBVIEW) {
            dataView.setUint16(offset, 1, littleEndian);
          }
          break;
        }
      }
    }
    return orientation;
  }

方法getStringFromCharCode(arrayBuffer)返回的orientation就是图片的方向也就是旋转的值,再对应下面的表,对图片进行处理

orientation值表:

orientation值 / 旋转角度:
1 / 0
3 / 180度
6 / 顺时针90度
8 / 逆时针90度

大家可以先判断图片Exif的orientation值再根据上表对应的旋转值,在canvas上对图片进行反方向旋转消除影响

三、Photoshop另存图片

如果图片是单独的一张或者是固定的又或者不是后台返回的,可以通过photoshop重新保存,保存的时候去掉exif信息

四、vue中安装exif插件就可以获取Orientation参数然后做调整就可以了

这里有我自己项目上传照片时的处理代码:

import EXIF from 'exif-js'
selectPhoto(e) {
            this.uploadImgClass = '';
            if (e.target.files[0].type.indexOf('image/') != 0) {
                this.showTopTip('error', this.language.unify_errorFormatImgTip);
                return false;
            }
            this.dialogData = {};
            let tthis = this,
                reader = new FileReader();
            EXIF.getData(e.target.files[0], function() {
                let Orientation = EXIF.getTag(this, 'Orientation');
                if (Unit.inArray(Orientation, [3, 6, 8]) != -1) {
                    tthis.uploadImgClass = 'img rotate' + Orientation;
                } else {
                    tthis.uploadImgClass = 'img';
                }
            });
            if (e.target.files[0]) {
                this.file = e.target.files[0];
                e.target.value = ''; //clear file
                reader.readAsDataURL(this.file);
                reader.onload = function(e) {
                    tthis.uploadImg = this.result;
                    // tthis.text = tthis.language.unify_upload;
                    tthis.btn = true;
                    //get width&height
                    let img = new Image();
                    img.src = tthis.uploadImg;
                    img.onload = function() {
                        tthis.width = img.naturalWidth;
                        tthis.height = img.naturalHeight;
                    };

                }
            }
        },

我是定义了类名根据Orientation的值做了相应旋转

这里的exif插件不只是可以用来获取信息还可以用来做摄像头实时拍照等功能,总的说来是很方便的

阅读终点,创作起航,您可以撰写心得或摘录文章要点写篇博文。去创作
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论
伊曼基照片管理软件是一款专业、好用的照片(图片)管理系统。它没有花哨的界面,但是有实用的功能。它适合于用来管理各种数码照片,业务图片等。 伊曼基照片管理软件特点: 1.自动识别重复的文件;在集存放的基础上,利用我们既有的产品--“重复文件查找王”--所使用的先进识别技术,一旦发现新加入的照片(A)在本系统已经存在了(B),那么这个加入动作将不会真正地重复加入这个照片A,而是建立一个对本系统照片B的一个引用而已。 2.虚拟相册功能;比如一张照片,是你和你的爱人2009年10月去上海旅游拍摄的合影照,那么,你就可以把该照片分别归入4个相册:(1)2009年10月的照片合集;(2)上海旅游的照片合集;(3)爱人照片专用相册;(4)和爱人的合影相册。怎么样?够灵活吧?!这个照片被利用了4次,但是在本系统,仅仅存放了一次而已。 3.添加任意多的备注、说明文字;针对某个相册或者某个照片,都可以添加任意多的备注、说明文字。如果年轻的父母们,想针对自己宝宝的某一个照片写上若干段记事文字,那么就应该使用本系统(这个是本系统的特色功能, 独此一家,是你在其它的类似系统见不到的)。这样,日积月累,就可以形成完整的宝宝成长日记,详细记录宝宝成长的足迹,以及生活的点点滴滴。 其它的一些特点: 照片评分(5分制);可以从网络或者剪贴板获取新的图像;两张图片同屏对比;批量导出;批量导出时自动命名、调整大小、添加水印文字;强大的搜索功能按评分,文件名称,文件高度、宽度等信息来搜索。 版本历史:   1.5 的改进:   用户可以自己定义缩略图区域的背景颜色   在看大图时,提供放大镜功能,放大倍数提供若干预选项,包括“放大到实际大小”   高级搜索图片名称和备注文字,可以支持组合条件搜索,条件之间用空格隔开即可   看大图时,图片四周可以添加一个框线,这样就可以把黑色的图片和显示背景区分开来   修正了修改单个图片的名称,总是提示“是否也一并修改链接的图片”,而实际上该图片并没有被链接到别的地方的问题   专业版以及专业U盾版,支持众多品牌数码相机的RAW格式照片(包括Canon、Nikon、Sony、Panasonic、Olympus、Samsung等品牌)   在“文件”菜单,增加了“打印”菜单,提供了较简单的图片打印功能 (专业版以及U盾版适用)   优化了给图片加边框的绘制,避免了给很大的图片加边框,边框显示不清楚的问题   解决了超大图片无法进行幻灯片播放的问题   解决了少数时候,从文件夹直接导入图片,生成的缩略图不完整的问题   修正了主界面工具栏上,当缩小了窗口,然后再逐渐拉大后,快捷搜索栏不能重新出现的问题   增加了节点控制选项和备注控制选项功能,具体请使用主界面工具栏上新增加的“选项设置”按钮来查看和设置这些选项   缩略图的右键菜单,也同时显示在了主菜单,以方便不习惯使用右键菜单的用户   节点和图片的备注文字,全部更改为HTML格式,支持在其加入本地文件或者图片的链接,也支持对文字进行格式定义了,具体的操作方法:在编辑备注时使用右键菜单   以及其它的一些改进   1.4的改进:   实现三种方式的节点排序功能:节点窗口工具栏的“向上”和“向下”按钮,节点右键菜单的“下级节点自动排序”,以及点击节点窗口的标题栏排序;   快捷搜索,支持在已有结果继续搜索,从而实现组合条件的复杂搜索效果;   用户可以决定是否显示图片评分;   看大图时,大图和缩略图选情况同步;   看大图时,只需要鼠标单击缩略图即可切换大图,以前需要双击;   看大图时,可以用鼠标滚轮滚动,也可以用键盘(空格键、上下左右方向键、Home键、End键等)操作,实现上一张、下一张等的切换;   对选图片可以统一重命名(缩略图右键菜单);   对选图片可以统一添加备注(缩略图右键菜单);   把"当前图片旋转"更改为"已选图片统一旋转"(缩略图右键菜单);   当导入过程缩略图生成不正确时,允许在主界面重新生成一个图片的缩略图数据(缩略图右键菜单);   修改图片名称、评分或者添加备注时,可以针对该图片在其它节点下的链接图片,进行统一更改,当然也可以不统一更改;   允许节点标题就地编辑,类似于Windows 资源管理器一样,通过在已经获取焦点的节点上再点击一下就开始手工编辑;   高级搜索结果,也支持幻灯片播放;   主界面上的图片,不一定需要选才能进行幻灯播放,F5快捷键默认是针对所有的图片进行幻灯播放;   用过一次后,“图片链接到”的窗口,默认是前面用过的节点列表,便于快速使用常用的节点作为目标节点;   缩略图序号数字,输出更清晰;   图片属性窗口,列出该图片已经被链接到了的所有地方/节点路径;   从Internet获取图片的界面,增加了“自动监视剪贴板WEB地址”和“添加URL到备注文字”的选项;   节点图标自由设置,可从16个预设图标选择一个;   删除了当前的一张缩略图后,缩略图显示后续的一张,而不是回到第一张。   修正了节点文字长度过长时导致的错误;   修正了对孤立节点,重新链接时出现的错误;   修正了幻灯片播放时,图片没有按照设置进行角度旋转的问题;   修正了缩略图在旋转后,较原图模糊的问题;   其它的一些修正和改进。   1.3 的改进:   1,解决了1.2版本引入的一个BUG:如果图片库超过2G,将不能再继续正确地导入新的图片。   2,节点右键菜单,增加了按照节点的目录结构,原样导出图片的菜单项。   3,节点右键菜单,增加了查看该节点(以及下级节点)下所有图片的菜单项。   4,缩略图右键菜单,增加了“全屏播放已选图片”的功能(幻灯片的播放方式)。   5,解决了偶尔导致备注文字丢失的问题。   6,解决了当一条备注文字较长时,无法看到全部文字的问题。   7,解决了在复制图片时,未能同步复制其备注文字的问题。   8,导出图片,在存在同名文件时,增加了“跳过”选项。   9,切换节点时,自动在大图区域显示第一幅图片(以前是不显示任何图片)。   10,在窗口底部的状态栏,显示当前缩略图的节点路径。   11,大幅度地提高了插入、删除图片的操作速度。   12,高级搜索结果,也可以鼠标双击缩略图,查看其大图。   13,图片排序,新增加了“按节点路径排序”选项;这个如果在快捷搜索或者“查看节点下所有图片”,导致缩略图区域内的图片来源节点很多时,可能有用。   其它的一些改进。
iSlider 是个非常平滑的滑块,支持移动端 WebApp,HTML5App 和混合型的 App。 iSlider是移动端的滑动组件的最佳解决方案。他和普通的web 端的滑动插件有很大不同,面向的用户和解决的问题也有很大差别,iSlider 的出现,解决的根本问题是内容的分屏显示,通过滑动操作来表示上一页内容或是下一页内容。而iSlider 是用最优雅的方式去解决,尽可能的节省内存,提高性能。在功能上iSlider 支持: 图片和dom 两种类型滑动,图片的类型很适合读图类的app,dom 类型则可以根据需要配置成各式各样的webapp 自定义的事件回调,你可以在滑动,滑动结束,或是滑动开始绑定自己的事件回调 可配置的滑动动画,在获得高性能的同时,你仍然可以指定一些特殊的高级的动画效果来完成你的app,iSlider 提供default,flip,depth,flow, rotate, w等动画方式来丰富你的滑动效果。 iSlider 会帮你处理好屏幕旋转事件,你只要考虑的是,屏幕旋转后,你的dom 或是 图片改如何显示。 iSlider 还有一些小功能,比如滑动边界递减,自动滑动,垂直水平滑动可配置。 而使用iSlider也非常容易上手,你只需要准备一个dom节点用来存放你的slider: var data = [{     height: 414,     width: 300,     content: "imgs/1.jpg", },{     height: 414,     width: 300,     content: "imgs/2.jpg", },{     height: 414,     width: 300,     content: "imgs/3.jpg", }]; 然后你需要准备展示的数据,这里展示的数据分两种类型,拿图片类型的slider 举例,你只需要准备好的是图片的json 数据,数据格式如下: var data = [{     'height' : '100%',     'width' : '100%',     'content' : '<div><h1>Home</h1><h2>This is home page</h2><p>home is pretty awsome</p><div>' },{     'height' : '100%',     'width' : '100%',     'content' : '<div><h1>Page1</h1><h2>This is page1</h2><p>page1 is pretty awsome</p><div>' },{     'height' : '100%',     'width' : '100%',     'content' : '<div><h1>Page2</h1><h2>This is Page2</h2><p>Page2 is pretty awsome</p><div>' }]; 调用时候,需要对iSlider 实例化: [removed]     var islider = new iSlider({         dom : document.getElementById('iSlider-wrapper'),         data : data,         duration: 2000,         isVertical: true,         isLooping: true,         isDebug: true,         isAutoplay: true     }); [removed] 这样就可以运行一个iSlider 的实例了,关于上面一些参数的意义,可以在官网看到: http://be-fe.github.io/iSlider/ iSlider 的依赖:iSlider 不依赖任何库或是框架,你可以很轻松的把他用在自己的项目,不会和zepto 或是jqmobi 冲突。 体积大小:iSlider 压缩后代码2kb,你可以很随意的打包在你的项目。 性能上:iSlider借助了手机硬件加速,所有的动画都尽可能重用dom ,并且使用尽可能少dom 来完成整个渲染,支持无尽的滚动,并且在手指快速滑动也达到流畅的体验。 未来: iSlider 还会持续开发,预计会更丰富对dom 类型的支持,方便开发者用iSlider 来build 自己的 app。对图形类型也将支持放大缩小。iSlider目前的版本是 1.0-beta ,预计这些功能会在下一个版本加上。 标签:iSlider

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

摩登开发者Oliver

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值