【问题标题】:convert binary data to image using php [duplicate]使用php将二进制数据转换为图像[重复]
【发布时间】:2013-07-11 09:46:46
【问题描述】:

我的旧数据库中保存了二进制图像数据,它是由我的旧开发人员保存的,现在我想使用 PHP 显示来自该数据库的图像,但我不能。

我试过imagecreatefromstring,但它返回FALSE

二进制示例数据:http://freezinfo.com/gg.php

【问题讨论】:

  • 那不是二进制,是十六进制。
  • ok,不过是存入数据库的图片数据
  • 也许这可以帮助你stackoverflow.com/questions/13274691/…。如果您可以访问它,请尝试查找图像保存在数据库中的代码。
  • 收到警告Warning: pack() [function.pack]: Type H: illegal hex digit
  • 格式未知,需要联系老开发者提供规范。否则,您的问题只是邀请在这里进行一些猜测。如果您真的对答案感兴趣,请先提供一个示例代码,以便重现您的问题。还要添加规范。什么告诉了材料的老开发者?您当前形式的问题只是发布了一个(非常)不具体的要求。仅 “但不工作” 不符合编程问题。

标签: php binary php-imagine


【解决方案1】:

您尝试检索的数据包含 HTML 及其 HEX 格式,但图像已损坏或无效。

要获取数据:

// $url = "log.txt";
$url = "http://freezinfo.com/gg.php";

// Load Data from URL
$data = file_get_contents($url);
// Remove ALL HTML Tags
$data = strip_tags($data);

错误

现在让我们检查标题

 echo substr($data, 0, 4); // returns FF00

FF00 不是有效的 jpeg 前缀 它应该以 FFD8FfD9 开头

我怎么知道它是一个 JPEG 文件并且它是无效的?

 echo pack("H*", substr($data, 0, 60));

输出

����JFIF

它显然引用了 JFIF,即 JPEG File Interchange Format

如何解决?

快速图像验证imagecreatefromstring

$data = pack("H*", $data); // Convert from hex
$im = @imagecreatefromstring($data);
var_dump($im); // returns false 

再次查看图像标题$data .. 我可以看到一个模式

FF00D800FF00E000000010004A00460049
  ^^  ^^  ^^  ^^  ^^  ^^  ^^  ^^

我注意到00 被插入,所以删除它实际上会给我们一个有效的图像标题FFD8

你可以用一个简单的循环来解决这个问题

// Trim all Spaces
$data = trim($data);

$newData = "";
for($i = 0; $i < strlen($data); $i += 4) {
    $newData .= $data{$i} . $data{$i + 1};
}

$newData = pack("H*", $newData);
$im = imagecreatefromstring($newData);
var_dump($im); // resource(6, gd)

输出

resource(6, gd)

结论

您确实需要检查将图像转换为十六进制的方式,这里看起来很混乱

【讨论】:

  • 但是,它仍然没有显示图像。 .错在哪里?
  • 好的..没关系。谢谢
【解决方案2】:

鉴于字符串显示为文本 (extactly this sequence),它是一组十六进制数字。

在 Jpeg 中,此类文件的幻数是 FF D8 作为前两个字节,FF D9 作为最后两个字节(与 How to identify contents of a byte[] is a jpeg? 相比)。

这些十六进制(简称十六进制)数字也可以在序列的开头和结尾找到:

FF00D800FF00 ... 1F00FF00D9000
##  ##               ##  ##

寻找这些神奇的数字还会发现十六进制值总是附加00。它还表明在最后找到了一个额外的0

所以四个字符总是形成一个值。十六进制编码,这看起来像 16 位值,但该值永远不会超过 8 位范围 (0-255),因此总是有 00 可见。

仅凭此信息,就可以尝试将其转换为 PHP 的 imagecreatefromstring 可以处理的二进制字符串:

$string = implode('',         // map array of binary strings to binary string
    array_map('chr',          // map ord integer value to character
        unpack('v*',          // unsigned short (always 16 bit, little endian byte order)
            pack("H*", $data) // hex to binary (high nibble first)
)));

使用这样的字符串然后在

$result = imagecreatefromstring($string);
imagejpeg($result, 'test.jpg');

显示以下 PHP 错误通知:

imagecreatefromstring(): gd-jpeg, libjpeg: 可恢复的错误:损坏的 JPEG 数据:错误的 Huffman 代码

以及以下图片:

这看起来非常糟糕。所以你可能在这里面临一个额外的编码问题。最后一个NUL 字节表明我们已经完成了更多工作,而且数据存储为 16 位十六进制值,而不仅仅是二进制数据 (blob),因为数据库对此提供了支持,这一定是有原因的。

但不要浪费太多时间,因为过去使用的软件和配置存在缺陷,这可能只是数据丢失,所以您所能做的就是从备份中恢复。

【讨论】:

    猜你喜欢
    • 2013-02-10
    • 2011-07-22
    • 1970-01-01
    • 2014-11-12
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2019-10-26
    • 1970-01-01
    相关资源
    最近更新 更多