0

如何沿圆圈重复图像?请注意,它也应该有点失真。我想要做到的是:我一直在研究一种 POV LED 设计,它可以拍摄图像并在整个旋转时沿着一串 LED 闪烁。当你看显示器时,图像有点扭曲,沿着圆圈的内部挤压并在外部拉伸一点。我想重新创建它。

红色圆圈仅供参考,大小始终相同。我可能也会将它留在生成的复合材料中。图像沿圆形路径重复的频率应该可以根据原始图像的实际宽度(以及我是否在每个副本之间添加中断)进行调整。例如,有些图像彼此相邻,没有休息,其他需要休息的。所以我需要一种方法来定义它。

使用黄色对角线,我不想在图像重复时出现中断。我将白色边缘留在顶部以显示它是如何变形的。

如何使用 Magick++ 完成此任务?最终,我将获取代码并将其合并到一个非常大的应用程序中,该应用程序使用 Magick++ 来处理用户为 POV LED 显示屏导入的图像。

谢谢!

重复图像

4

2 回答 2

2

是的,您可以使用Magick::Image.distort. 尽管由于您对 POV 项目有非常本地化的要求,因此会出现一些试验和错误。

沿圆圈重复图像

ArcDistortion示例同样适用于Magick++. 确保启用虚拟像素方法,并使用 360 度圆弧扭曲给定图像。我正在使用图像“pattern:CHECKERBOARD”,但您会使用“tile:image_source.png”。

Magick::Image MyArc;
MyArc.read("pattern:CHECKERBOARD");
MyArc.size("600x45");
MyArc.virtualPixelMethod(Magick::WhiteVirtualPixelMethod);
const double arcArgs[1] = {360};
MyArc.distort(Magick::ArcDistortion,1, arcArgs,Magick::MagickTrue);
MyArc.write("out.png");

这将为您提供沿圆圈重复的图像。

弧形畸变示例

保护者内圈

控制内外圆的大小。将第三和第四个参数应用于失真方法。

const double arcArgs[4] = {360,0,200,100};
MyArc.distort(Magick::ArcDistortion,4, arcArgs,Magick::MagickTrue);

给定圆周围的弧形变形示例

带有预处理的自定义图像

至于添加空白、填充、出血和调整图像重复。这些都需要在电弧变形之前进行预处理。

Magick::Image SourceImage;
SourceImage.read("me.png");
SourceImage.resize("45x45");
// Add whitespace between repeating image
SourceImage.extent(Magick::Geometry(100,45));

// Resize image to be "long" enough to bend around arc.
SourceImage.size("600x45");
// PrePrecess image to tile horizontally with Edge Virtual Pixel
SourceImage.virtualPixelMethod(Magick::HorizontalTileEdgeVirtualPixelMethod);
const double tileArgs[1] = {0};
SourceImage.distort(Magick::ScaleRotateTranslateDistortion,1,tileArgs,Magick::MagickTrue);

// Distort around circle
SourceImage.virtualPixelMethod(Magick::WhiteVirtualPixelMethod);
const double arcArgs[4] = {360,0,200,100};
SourceImage.distort(Magick::ArcDistortion,4, arcArgs,Magick::MagickTrue);
SourceImage.write("out.png");

具有自定义图像频率的弧形失真

如果 POV 问题可以通过有趣的数学来解决,请记住很多。

于 2014-04-02T11:38:16.130 回答
0

我想我想通了。所以这是我现在正在使用的代码片段:

Magick::Image srcImage;
srcImage.read("001.png");
srcImage.resize("x100");      // I want images at least 100 pixels high
Magick::Color color(0, 0, 0); // images should always be on a black background

// to add space beween a repeating image, add a value to .columns()
// for example:
// srcImage.extent(Magick::Geometry(srcImage.columns() + 10, 100), color);
// will add 10 pixels of space or padding after each image repeat
srcImage.extent(Magick::Geometry(srcImage.columns(), 100), color);

// preprocess
// .columns() is multiplied by the amount of times the image repeats in the circle
// for example, this repeats the image 8 times:
// srcImage.size(Magick::Geometry(srcImage.columns() * 8, 100));
srcImage.size(Magick::Geometry(srcImage.columns() * 8, 100));
srcImage.virtualPixelMethod(Magick::HorizontalTileEdgeVirtualPixelMethod);
const double tileArgs[1] = {0};
srcImage.distort(Magick::ScaleRotateTranslateDistortion, 1, tileArgs, Magick::MagickTrue);

// distort
srcImage.virtualPixelMethod(Magick::BlackVirtualPixelMethod);
const double arcArgs[4] = {360, 0, 98, 30};
srcImage.distort(Magick::ArcDistortion, 4, arcArgs, Magick::MagickTrue);
srcImage.write("001-out.png");
于 2014-04-03T06:21:59.680 回答