我正在尝试使用SDL加载PNG图像,但该程序不起作用,此错误出现在控制台中
libpng警告:iCCP:已知错误的sRGB配置文件
为什么会出现此警告?我该怎么做才能解决这个问题?
答案 0 :(得分:142)
对于检查ICC配置文件,Libpng-1.6比以前的版本更严格。您可以忽略该警告。要摆脱它,请从PNG图像中删除iCCP块。
有些应用将警告视为错误;如果您使用这样的应用程序,则必须删除该块。您可以使用各种PNG编辑器(如ImageMagick的
)来实现convert in.png out.png
要从文件夹(目录)中的所有PNG文件中删除无效的iCCP块,可以使用ImageMagick中的mogrify
:
mogrify *.png
这要求您的ImageMagick是使用libpng16构建的。您可以通过运行来轻松检查:
convert -list format | grep PNG
如果你想找出哪些文件需要修复而不是盲目处理所有文件,你可以运行
pngcrush -n -q *.png
其中-n
表示不重写文件,-q
表示除了警告外,抑制大部分输出。对不起,除了警告之外,pngcrush还没有任何选项来禁止所有内容。
ImageMagick的二进制版本为here
对于Android项目(Android Studio),请导航至res
文件夹。
例如:
C:\{your_project_folder}\app\src\main\res\drawable-hdpi\mogrify *.png
答案 1 :(得分:65)
使用pngcrush
从png文件中删除不正确的sRGB配置文件:
pngcrush -ow -rem allb -reduce file.png
-ow
将覆盖输入文件-rem allb
将删除除tRNS和gAMA之外的所有辅助组块-reduce
执行无损颜色类型或位深度缩减在控制台输出中,您应该看到Removed the sRGB chunk
,以及可能有关于块删除的更多消息。您将获得一个较小的优化PNG文件。由于该命令将覆盖原始文件,因此请确保创建备份或使用版本控制。
答案 2 :(得分:17)
错误的个人资料可以通过以下方式解决:
注意:此解决方案使用Qt Library。
这是我用C ++编写的一个最小例子,用于演示如何实现所提出的解决方案:
<configuration>
<system.web>
<machineKey decryptionKey="0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF0" validationKey="0123456789ABCDEF0123456789ABCDEF0123456789ABCDEF00123456789ABCDEF0123456789ABCDEF0123456789ABCDEF00123456789ABCDEF0123456789ABCD" />
</system.web>
</configuration>
GitHub上提供了基于此示例的GUI应用程序的完整源代码。
答案 3 :(得分:10)
你也可以在photoshop中解决这个问题...我已经有了CC2015,但我确信这对所有版本都是一样的。
答案 4 :(得分:7)
为了补充格伦的好答案,我在这里找到了哪些文件有问题:
find . -name "*.png" -type f -print0 | xargs \
-0 pngcrush_1_8_8_w64.exe -n -q > pngError.txt 2>&1
我使用了find和xargs,因为pngcrush无法处理很多参数(由**/*.png
返回)。处理包含空格的文件名需要-print0
和-0
。
然后在输出中搜索这些行:iCCP: Not recognizing known sRGB profile that has been edited
。
./Installer/Images/installer_background.png:
Total length of data found in critical chunks = 11286
pngcrush: iCCP: Not recognizing known sRGB profile that has been edited
对于每一个,在它上面运行mogrify来修复它们。
mogrify ./Installer/Images/installer_background.png
执行此操作可防止在只有少数实际修改过的情况下更改存储库中每个png文件的提交。此外,它还可以准确显示哪些文件有问题。
我在Windows上使用Cygwin console和zsh shell对此进行了测试。再次感谢上述大部分内容的Glenn,我只是添加一个答案,因为它通常比评论更容易找到:)
答案 5 :(得分:6)
感谢fantastic answer中的Glenn,我使用了ImageMagik的“mogrify * .png”功能。但是,我将图像隐藏在子文件夹中,因此我使用这个简单的Python脚本将其应用于所有子文件夹中的所有图像,并认为它可以帮助其他人:
import os
import subprocess
def system_call(args, cwd="."):
print("Running '{}' in '{}'".format(str(args), cwd))
subprocess.call(args, cwd=cwd)
pass
def fix_image_files(root=os.curdir):
for path, dirs, files in os.walk(os.path.abspath(root)):
# sys.stdout.write('.')
for dir in dirs:
system_call("mogrify *.png", "{}".format(os.path.join(path, dir)))
fix_image_files(os.curdir)
答案 6 :(得分:5)
使用Mac OS和Homebrew可以更轻松地解决此问题:
安装自制软件(如果尚未安装)
$brew install libpng
$pngfix --strip=color --out=file2.png file.png
或者对当前目录中的每个文件执行此操作:
mkdir tmp; for f in ./*.png; do pngfix --strip=color --out=tmp/"$f" "$f"; done
它将为当前目录中的每个png文件创建一个固定副本,并将其放在tmp子目录中。之后,如果一切正常,您只需要覆盖原始文件。
另一个提示是使用Keynote和Preview应用程序来创建图标。我使用Keynote绘制它们,大小约为120x120像素,在带有白色背景的幻灯片上(使多边形可编辑的选项很棒!)。在导出到预览之前,我在图标周围绘制一个矩形(没有任何填充或阴影,只有轮廓,大小约为135x135)并将所有内容复制到剪贴板。之后,你只需要使用预览工具打开它,使用&#34;剪贴板中的新功能&#34;,选择图标周围的128x128像素区域,复制,使用&#34;剪贴板中的新功能&#34;再次,并将其导出到PNG。您不需要运行pngfix工具。
答案 7 :(得分:4)
关于此的一些背景信息:
libpng 1.6+版中的一些更改会导致它发出警告或 甚至无法正常使用原始HP / MS sRGB配置文件 到以下stderr:libpng警告:iCCP:已知错误的sRGB 配置文件旧配置文件使用D50白点,其中D65是标准配置。 尽管如此,Adobe Photoshop使用此配置文件并不罕见 它默认没有嵌入到图像中。
(来源:https://wiki.archlinux.org/index.php/Libpng_errors)
某些块中的错误检测已得到改善;尤其是iCCP 块读取器现在可以对基本格式进行相当完整的验证。 以前接受的一些不良配置文件现在被拒绝了 特别是破旧的Microsoft / HP sRGB配置文件。 PNG规范 要求只有灰度配置文件可能出现在图像中 颜色类型0或4,即使图像只包含灰色 像素,只有RGB配置文件可能出现在颜色类型为2,3的图像中, 或6,现在执行。允许sRGB块出现在图像中 任何颜色类型。
答案 8 :(得分:3)
在Windows中使用IrfanView图像查看器,我只是重新保存了PNG图像并更正了问题。
答案 9 :(得分:3)
在尝试了此页面上的一些建议后,我最终使用了pngcrush解决方案。您可以使用下面的bash脚本递归检测并修复错误的png配置文件。只需将它的完整路径传递给您要搜索png文件的目录。
fixpng "/path/to/png/folder"
剧本:
#!/bin/bash
FILES=$(find "$1" -type f -iname '*.png')
FIXED=0
for f in $FILES; do
WARN=$(pngcrush -n -warn "$f" 2>&1)
if [[ "$WARN" == *"PCS illuminant is not D50"* ]] || [[ "$WARN" == *"known incorrect sRGB profile"* ]]; then
pngcrush -s -ow -rem allb -reduce "$f"
FIXED=$((FIXED + 1))
fi
done
echo "$FIXED errors fixed"
答案 10 :(得分:1)
扩展friederbluemle解决方案,下载pngcrush,然后在多个png文件上运行时使用类似的代码
path =r"C:\\project\\project\\images" # path to all .png images
import os
png_files =[]
for dirpath, subdirs, files in os.walk(path):
for x in files:
if x.endswith(".png"):
png_files.append(os.path.join(dirpath, x))
file =r'C:\\Users\\user\\Downloads\\pngcrush_1_8_9_w64.exe' #pngcrush file
for name in png_files:
cmd = r'{} -ow -rem allb -reduce {}'.format(file,name)
os.system(cmd)
此处与项目相关的所有png文件都位于1个文件夹中。
答案 11 :(得分:1)
一些建议的答案将 pngcrush
与 -rem allb
选项结合使用,文档说这就像“用电锯进行手术”。该选项会删除许多块。为了防止出现“iCCP:已知不正确的 sRGB 配置文件”警告,删除 iCCP
块就足够了,如下所示:
pngcrush -ow -rem iCCP filename.png
答案 12 :(得分:0)
我在项目的根目录及其固定版本中运行了这两个命令。
基本上将“ find”命令的输出重定向到文本文件,以用作要处理的文件列表。然后,您可以使用“ @”标志将该文本文件读为“ mogrify”:
找到* .png -mtime -1> list.txt
mogrify -resize 50%@ list.txt
这将使用“查找”来获取所有比1天更新的* .png图像,并将它们打印到名为“ list.txt”的文件中。然后,“ mogrify”读取该列表,处理图像,并使用调整后的版本覆盖原始文档。从一个系统到另一个系统的“查找”行为可能会有细微的差异,因此您必须检查手册页以了解确切的用法。
答案 13 :(得分:-2)
这是一个荒谬的暴力回答:
我修改了gradlew脚本。这是我在
文件末尾的新exec命令exec "$JAVACMD" "${JVM_OPTS[@]}" -classpath "$CLASSPATH" org.gradle.wrapper.GradleWrapperMain "$@" **| grep -v "libpng warning:"**