此功能只有在浏览器停止发送下一批数据(如果已经发送了足够的数据以在用户屏幕上显示)之后才会变得很棒,因为它具有各种可能性,并且发送更多像素毫无意义。这是 JPEG 渐进式显示的当前目的,但尚未实现。之后,您无需为不同屏幕密度创建多个图片版本,这将节省大量工作。
(PHP 4, PHP 5, PHP 7, PHP 8)
imageinterlace — 启用或禁用隔行扫描
imageinterlace() 打开或关闭隔行扫描位。
如果设置了隔行扫描位,并且图像用作 JPEG 图像,则图像将创建为渐进式 JPEG。
image
一个 GdImage 对象,由图像创建函数之一返回,例如 imagecreatetruecolor()。
interlace
如果为 true
,则图像将被隔行扫描,如果为 false
,则隔行扫描位将被关闭。传递 null
将导致隔行扫描行为不会更改。
版本 | 描述 |
---|---|
8.0.5 | imageinterlace() 现在返回 bool;以前它返回 int(隔行扫描图像为非零,否则为零)。 |
8.0.0 |
image 现在期望一个 GdImage 实例;以前,期望一个有效的 gd resource。 |
8.0.0 |
enable 现在期望一个 bool;以前它期望一个 int。 |
示例 #1 使用 imageinterlace() 打开隔行扫描
<?php
// 创建一个图像实例
$im = imagecreatefromgif('php.gif');
// 启用隔行扫描
imageinterlace($im, true);
// 保存隔行扫描的图像
imagegif($im, './php_interlaced.gif');
imagedestroy($im);
?>
此功能只有在浏览器停止发送下一批数据(如果已经发送了足够的数据以在用户屏幕上显示)之后才会变得很棒,因为它具有各种可能性,并且发送更多像素毫无意义。这是 JPEG 渐进式显示的当前目的,但尚未实现。之后,您无需为不同屏幕密度创建多个图片版本,这将节省大量工作。
这个功能真的救了我的命!!!
好吧,为了测试,我应该上传几个 jpg,其中一些是 jfif 编码,
所以当我将它们包含在 fpdf 和 tcpdf 中时,一些颜色会丢失(我尝试了 2 个开源项目以最大限度地减少错误以了解问题所在)。
我现在使用的缩略图函数(已修复)是
public static function jpgtofilethumb($file,$thumb,$lun,$quality){
// 来自 php.net
list ($x, $y) = @getimagesize ($file);
$img = @imagecreatefromjpeg ($file);
if ($x > $y) {
$tx = $lun;
$ty = round($lun / $x * $y);
} else {
$tx = round($lun / $y * $x);
$ty = $lun;
}
$thb = imagecreatetruecolor ($tx, $ty);
// 启用隔行扫描
if(imageistruecolor($thb)) imageinterlace($thb, true);
imagecopyresampled ($thb,$img, 0,0, 0,0, $tx,$ty, $x,$y);
imagejpeg ($thb, $thumb, $quality);
imagedestroy ($thb);
imagedestroy ($img);
}
有人建议可以使用此函数检索存储在文件中的图像的隔行扫描位。事实并非如此。
虽然 imageinterlace() 在传递有效的 Image 资源时返回 0 或 1,但将文件名作为字符串传递会导致 PHP 警告,并且返回值既不是 0 也不是 1。
dr_snapid 的评论“服务器发送每 N 行”并不完全正确。Web 服务器不需要了解它正在发送的文件的内容;它的工作仅仅是发送数据。相反,图像的创建方式是,对应于“每 N 行”的数据出现在文件的开头,随着浏览器接收更多文件,细节能够被填充。在 PHP 的情况下,数据可能是动态生成的,而不是从文件中拉取,但这并不改变数据本身是不同的,而不是发送方式的事实。*
实际上,对于 JPEG 来说,它不太可能是“每 N 行”,而更像是“每 N 像素”,其中 N 逐渐减小,从而导致随着接收数据的增加,网格变得越来越细致(因此低分辨率图像的外观变得更加详细)。浏览器基本上会估计像素之间的间隙中填充的内容,可能是通过简单地将颜色混合在一起,而“真实”数据会继续到达。这与非渐进式 JPEG 编码数据的根本不同方法,并且与该格式的其他压缩技术相结合,确实可能导致不同的文件大小。
*你能想象如果服务器被期望使用不同的算法发送不同的文件类型,而浏览器被期望能够接收其中每一个,那么 Web 会出现多少个错误?*
如果您需要在 Flash 中加载生成的图像,请将 imageinterlace() 设置为 0。Flash 不支持渐进式 JPEG。
此函数在使用 Ming 时非常有用,因为 SWFBitmap 构造函数将使用非隔行扫描 JPEG 文件,因此您必须使用 imageinterlace(0);
只是为了补充我对 JPEG 渐进式原理的看法:JPEG 中没有存储几个低分辨率图像以及原始图像,唯一改变的是“像素”的顺序。在 JPEG 中,图像被划分为 8x8 像素的区域,因此,而不是像素的线性顺序(逐行),首先是每个 8x8 区域的一个像素包含在图像数据流的开头,因此当浏览器接收到所有 8x8 区域的像素时,它可以显示“像素化”图像,并且一旦它接收到更多数据,浏览器就可以添加更多像素并“锐化”图像。
关于 MichaelSoft 的注释“Imageinterlace($im, 1) 创建一个 JPG,它在显示任何内容之前先完全加载”
实际上,这并不完全正确。
这只会发生在 Internet Explorer(任何版本,目前为止)中,因为它似乎不支持渐进式显示,而是在完成加载后显示图像。其他浏览器(Mozilla、Mozilla Firefox、Opera、Konqueror 等)会按预期执行其工作:显示一个非常低分辨率的图像,然后叠加一个中等低分辨率的图像(在加载过程中),然后显示越来越多的细节。
微软 Internet Explorer 存在一个 bug(至少目前是这样),导致渐进式/交错式 JPEG 在加载时根本不会显示,只有当整个图片加载完毕后才会突然出现。而普通的非交错式/非渐进式 JPEG 会逐行加载,反而会给人一种加载速度更快的错觉。MSIE 在这方面真的反过来了!
这种行为在其他浏览器(如 Mozilla/FireFox)中并不明显 - 在这些浏览器中,图像会像预期的那样渐进式加载。
交错式并不存储另一张图片,它只是简单地改变了图片行发送和渲染的顺序。服务器会发送每 N 行,到达末尾后,再回到开头,读取中间的行。
每次传递后,浏览器都会显示已下载的行,并将未接收到的行用相同的方式填充,但随着每次传递,未填充的间隙会越来越小,图片也会变得越来越清晰。经过几次传递后,所有行都已读取,浏览器会以完整的细节渲染图像。
希望这说得通,这确实解释了为什么文件大小不应该有太大区别,所以我无法解释为什么有些人观察到了文件大小的差异。
据我所知,文件中只有一个位表示它是交错的还是非交错的,服务器和客户端(浏览器)如果设置为 1,就会以不同的方式处理它。