【问题标题】:Understanding ImageMagick's convert and translating to Ruby RMagick了解 ImageMagick 的转换和翻译为 Ruby RMagick
【发布时间】:2010-11-09 10:44:17
【问题描述】:

我未能将以下 PHP/ImageMagick 代码翻译成 Ruby RMagick(以使其对未来的用户更易于管理并了解它的实际作用):

$output = array();
$returnValue = 0;
$pngFiles = $myDir->find("/.png$/i");
foreach($pngFiles as $pngFile) {
   $cmd = 'convert '.$pngFile->path.' -resize 1x1 -alpha on -channel o -format "%[fx:u.a]" info:'
   exec($cmd, $output, $returnValue);
   if($output[0] != 1) {
      logMessage("PNG file contains some alpha transparency and will not be modified");
   }
}

By now 我以为我或多或少地理解了 convert-command 的作用,但是将它翻译成 RMagick 让我重新思考。

例如:为什么$output[0] != 1 有时 true$myDir 的PNG 上,而RMagick 的Image.alpha? 在@ 的PNG 上总是 true 987654330@?我错过了什么吗?

我认为让我回到正轨的最好方法是,如果有人可以向我解释 convert-command 到底在做什么(包括表达式 %[fx:u.a])。

更新:与此同时,我已经编写了我需要此信息的脚本。如果对你有帮助,可以check it out at Github

【问题讨论】:

  • 我认为 - Image.alpha 可能正在检查图像是否具有 alpha 层,PNG 就是这样做的。而这是检查单个像素的透明度级别。请参阅下面的答案。

标签: php ruby imagemagick rmagick


【解决方案1】:

代码检查特定图像是否包含透明度。

-format '%[fx:u.a]' info:

这指示图像魔法检查第一张图像ua 的 alpha 通道并在其上输出信息,如果左上角像素是透明的,它将返回 0,如果不是,则返回非零.这就是将图像调整为 1x1 的原因,因此只需要参考一个像素。 -channel o 是不透明通道。

因此,英文代码将读取,循环浏览所有 PNG 文件,仅查看 alpha 通道(不透明度),调整大小为单个像素并查看它是否透明。因此回显消息。

不幸的是,我不知道 Ruby 或 RMagick,但快速查看 API 似乎建议使用 image.channel(AlphaChannel) 获取 alpha 通道(AlphaChannelChannelType 值,不确定是否必须指定ChannelType.AlphaChannel),然后跟随 .resize(1,1) 以减小大小,并以 .pixel_color(0,0).get_pixels(0,0,1,1) 结束以取回 Pixel 对象(get_pixels() 返回一个数组),我相信它有一个opacity 属性。但是,channel() 命令将 RGB 值更改为所选通道的值,我不确定它是否保留了不透明度通道,因此您可能只需要查看红色示例,或者完全省略 .channel() 调用 -虽然我不知道这是否会破坏结果。

也许 Ruby 支持体面的函数式编程方法。

image.channel(AlphaChannel).resize(1,1).pixel_color(0,0).red

或者如果pixel_color()由于某种原因没有返回不透明度

image.channel(AlphaChannel).resize(1,1).get_pixels(0,0,1,1)[0].red

如果没有 channel() 调用,它将是:

image.resize(1,1).pixel_color(0,0).opacity

image.resize(1,1).get_pixels(0,0,1,1)[0].opacity

同样,我的 Ruby 不存在,因此您可能需要重新排列它们,但原语就在那里。

参考文献

  1. RMagick Documentation
  2. ImageMagick 'fx' escapes
  3. ImageMagick -channel options

【讨论】:

    【解决方案2】:

    为仍在寻找解决方案的任何人发布此内容,有一种方法可以使用此处描述的 rmagick gem 在 ruby​​ 中执行此操作 https://stackoverflow.com/a/41282162/1975112

    【讨论】:

      【解决方案3】:

      您显示的 php 代码(实际上只是将工作发送到 shell 中进行转换)不会检查图像是否具有 alpha 通道,它只是获取给定的任何文件并将其打开。如果它已经有一个,则不会更改文件,但不会要求 convert 根据状态做出任何决定,只需继续添加频道即可。

      【讨论】:

      • 对不起,我忘了添加整个 PHP 代码。请检查我编辑的问题。如果 convert-command 不检查现有的 alpha 值,为什么要检查和解释 convert-return-value?
      【解决方案4】:

      你为什么不只复制命令并用系统调用它?

      不需要 gem ... 没有问题,代码应该看起来几乎一样。

      编辑:RMagic 只包装 imagemagic,所以如果你已经有 imagmagic 命令字符串,为什么还要打扰 rmagic。

      【讨论】:

      • 我刚刚编辑了我的问题,希望我的问题现在更清楚了。只要我不明白 convert-command 到底在做什么,我用 system 调用那个东西还是用 RMagick 包装它并不重要。我不想使用我不完全理解的代码。
      【解决方案5】:

      我从未编写过任何 Ruby 代码,但这里是 PHP 脚本的部分改版:

      require 'find'
      
      pngFiles = Dir.glob("*.png")
      
      Find.find('./') do |f|
        if system 'convert ' + f + ' -resize 1x1 -alpha on -channel o -format "%[fx:u.a]" info' do
          print "PNG file contains some alpha transparency and will not be modified"
      

      我认为您需要检查的只是一个 Alpha 通道,而不是所有那些复杂的东西。查看此页面了解更多信息:http://www.imagemagick.org/script/escape.php。它有一个%A 运算符,可以输出一些关于 alpha 通道的信息。

      【讨论】:

      • 谢谢,但这并不能真正回答我的问题。我没有尝试重构 PHP 脚本,我仍然不知道 convert 命令到底在做什么。所有“复杂的东西”都已经在一个工作的 PHP 脚本中以这种方式实现了。
      猜你喜欢
      • 2012-05-28
      • 2015-04-05
      • 2016-08-10
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-08-29
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多