解决JPEG照片在windows无法打开 您所在的位置:网站首页 jpg格式为什么打印不出来 解决JPEG照片在windows无法打开

解决JPEG照片在windows无法打开

2023-11-23 19:25| 来源: 网络整理| 查看: 265

引言

今天,测试妹子拿个样机过来说:“手机拍出来的照片拷贝到windows电脑上无法打开”。查了一下代码,仅仅是一个bitmap.compress(Bitmap.CompressFormat.JPEG, 90, data),用过无数次的方法,无论如何不可能出问题。那么问题肯定出在电脑上了,百度一下,还真有解决方案,将windows颜色系统的默认值改为 “Agfa:Swop Standard”,可以正常显示了。本想告诉测试妹子解决方案,但却总隐约觉得不对劲,仔细排查一圈下来发现是JPEG图片的EXIF信息出了问题。

1. 问题现象

手机拍照后,将照片拷贝到windows电脑上,使用windows照片查看器无法打开照片,提示:

Windows 照片查看器无法显示此图片,因为计算机上的可用内存可能不足。请关闭一些目前没有使用的程序或者释放部分硬盘空间(如果硬盘几乎已满),然后重试。

windows打不开jpeg图片.jpg

但是同样的照片:

在手机上可以正常显示。 点击windows照片查看器的幻灯片放映也可以显示。 使用其它看图工具也可以显示。

此时,电脑内存或者磁盘空间是充足的。

2. 问题可能的原因

可能的原因一: 色彩空间不同,windows默认的色彩空间是sRGB,而很多相机、手机的色彩空间是Adobe RGB。

可能的原因二: JPEG图片的EXIF信息有问题。由于某些相机APP处理照片后,修改或者添加了某些EXIF信息。例如,修改了图片数据长度等,EXIF信息与实际图片数据不一致,windows照片查看器无法正常解析照片,导致无法打开照片。甚至华为P40也有用户反馈过类似的问题:照片传到电脑里总是说Windows照片查看器无法显示此图片。

什么是EXIF信息? EXIF信息是可交换图像文件的缩写,是专门为数码相机的照片设定的,可以记录数码照片的属性信息和拍摄数据。EXIF可以附加于JPEG、TIFF、RIFF等文件之中,为其增加有关数码相机拍摄信息的内容和索引图或图像处理软件的版本信息。

JPEG文件可包含实际的图像数据和Exif信息。Exif信息包括品牌、型号、光圈、曝光时间、ISO、焦距、闪光、白平衡、日期时间、位置信息、色彩空间等等各种信息。但不是所有JPEG文件都有Exif信息。

3. 解决方案 3.1 针对色彩空间不同,有两种解决方案:

方案一: 不使用windows默认的图片查看器,使用其它看图工具。

方案二: 修改windows颜色系统的默认值。打开windows “控制面板”,查看方式由 “类别” 修改为 “小图标”,打开 “颜色管理”,点击 “高级” 选项卡,将“设备配置文件(D): ”由“系统默认(sRGB IEC61966-2.1)” 改为 “Agfa:Swop Standard”。

Agfa.png 再次使用windows默认的图片查看器打开图片,就可以正常显示了。

3.2 针对JPEG图片EXIF信息有问题,也有两种解决方案:

方案一: 不使用windows默认的图片查看器,使用其它看图工具。一些第三方的图片查看器显示图片时,并不依赖EXIF信息,它们可以正常显示照片。

方案二: 下载一个 “jpg图片修复工具”,用它修复JPEG图片的EXIF信息。修复后windows默认的图片查看器就可以正常显示照片了。所谓的修复,其实就是重新生成与JPEG图像数据一致的EXIF信息。

4. 实际android项目上的问题分析及解决

我们回到引言中测试妹子报的那个bug,这个展锐平台的项目在Camera APP中集成了一个第三方算法库,大概的图像格式的转换流程为:

图像格式转换流程.png

如上图,JpegCallback中出来原JPEG图片时,还一起生成了图片的EXIF信息。

首先,我怀疑色彩空间不是sRGB。于是将bitmap的ColorSpace打印出来:

2021-01-25 10:10:32.125 31995-32126/com.android.camera2 D/CAM2: bitmap.getColorSpace():sRGB IEC61966-2.1 (id=0, model=RGB),

发现色彩空间确实是sRGB。

那么,问题就应该出在EXIF信息上了。再将EXIF信息打印出来,最终发现问题就出在JPEG图片的数据长度上。第三方算法输出RGB,所以必须利用Bitmap将RGB压缩成JPEG再保存,再次压缩后,新JPEG图片的数据长度与原JPEG图片的数据长度已经不同了,新JPEG图片的占用空间要比较原JPEG图片大一点点。日志证明了这一点:

2021-01-25 10:33:35.155 31995-32126/com.android.camera2 D/CAM2:jpegData.length:2431896 2021-01-25 10:33:35.812 31995-32126/com.android.camera2 D/CAM2: newJpegData.length:2904395

所以,问题的原因就是:图片的EXIF信息在JpegCallback中出来原JPEG图片时就生成了,后面图片数据改变了,却没有更新EXIF信息。

而windows默认图片查看器又可能比较蠢,查看图片时,按EXIF信息去分配内存,真正加载图片时发现内存不够,所以就报一个内存不足的提示,造成了难以理解的乌龙。

知道了问题的原因,解决起来也就很简单了,只需要更新一下EXIF信息中的数据长度:

exifInterface.setTagValue(ExifInterface.TAG_JPEG_LENGTH, newJpegData.length);

重新编译、验证,果然,拍出来的照片都可以正常用windows默认图片查看器打开显示了。

通过这个bug,我们可以知道,如果一张JPEG图片除图像数据外,还保存有EXIF信息,那么图像数据需要和EXIF信息能对应上,否则会出现一些奇怪的问题。如果对图像数据进行过编辑和处理,那么EXIF信息也要同步更新。

5. 参考

Windows照片查看器无法显示此图片,因为计算机上的可用内存可能不足。 EXIF信息



【本文地址】

公司简介

联系我们

今日新闻

    推荐新闻

    专题文章
      CopyRight 2018-2019 实验室设备网 版权所有