【问题标题】:Tiling Text Over Image at an Angle以一定角度将文本平铺在图像上
【发布时间】:2016-12-04 00:57:43
【问题描述】:

我使用下面的代码在图像的中心绘制一个角度的文本

Bitmap bmp = new Bitmap(pictureBox1.Image);
using (Graphics g = Graphics.FromImage(bmp)) {
  g.TranslateTransform(bmp.Width / 2, bmp.Height / 2);
  g.RotateTransform(30);
  SizeF textSize = g.MeasureString("hi", font);
  g.DrawString("hi", font, Brushes.Red, -(textSize.Width / 2), -(textSize.Height / 2));
}

我需要像这样将文字平铺在图像上

我知道我可以增加坐标并使用循环。我有

Bitmap bmp = new Bitmap(pictureBox1.Image);
            for (int i = 0; i < bmp.Width; i += 20)
            {
                for (int y = 0; y < bmp.Height; y += 20)
                {
                    using (Graphics g = Graphics.FromImage(bmp))
                    {
                        g.TranslateTransform(bmp.Width / 2, bmp.Height / 2);                      
                        g.RotateTransform(30);
                        SizeF textSize = g.MeasureString("my test image", DefaultFont);
                        g.DrawString("my test image", DefaultFont, Brushes.Yellow, i, y);
                       
                    }
                }
            }
            pictureBox1.Image = bmp;

这会产生以下结果

如何通过正确测量绘制区域来正确放置文本。可能是更好更快的方法。

【问题讨论】:

  • 您是每次都添加相同的文本还是完全是动态的?

标签: c# .net bitmap gdi+ system.drawing


【解决方案1】:

您在页面中心插入文本。
这意味着您的图像 0,0 坐标位于其他图像的 50%,50%

如果您想获得您想要的结果,我建议您将图像宽度划分为 25% 的块,以获得建议的 16 个块。然后在每个块的中心添加其中一个文本图像。

请记住,当您添加图像并且您希望图像从点而不是从点 0,0(这就是您的情况发生的情况)开始旋转时,您需要明确说明它,认为命令是 rotateorigan或者那一行的东西,

【讨论】:

  • 你能发布实现吗?
【解决方案2】:

另外调用TranslateTransform 将文本移动到您想要的位置,然后在 (0, 0) 坐标处使用DrawString 绘制文本。这将使每个文本围绕其自己的中心旋转,而不是围绕段落中心旋转文本。

Bitmap bmp = new Bitmap(pictureBox1.Image);
Graphics g = Graphics.FromImage(bmp);
String text = "TextTile";

Font font = new Font(DefaultFont.Name, 20);
SizeF size = g.MeasureString(text, font);
int textwidth = size.ToSize().Width;
int textheight = size.ToSize().Height;

int y_offset = (int)(textwidth * Math.Sin(45 * Math.PI / 180.0));

//the sin of the angle may return zero or negative value, 
//it won't work with this formula
if (y_offset >= 0)
{
    for (int x = 0; x < bmp.Width; x += textwidth)
    {
        for (int y = 0; y < bmp.Height; y += y_offset)
        {
            //move to this position
            g.TranslateTransform(x, y);

            //draw text rotated around its center
            g.TranslateTransform(textwidth, textheight);
            g.RotateTransform(-45);
            g.TranslateTransform(-textwidth, -textheight);
            g.DrawString(text, font, Brushes.Yellow, 0, 0);

            //reset
            g.ResetTransform();
        }
    }
}

pictureBox1.Image = bmp;

上面的例子使用了更大的字体,大小为 20。您可以将其重新设置为使用DefaultFont.size。它使用45度角。

【讨论】:

  • 非常感谢,它工作正常。我想知道如果图像尺寸很大,这种方法的性能。在位图上绘制文本并在整个图像上绘制位图会更好方法?
  • 你应该自动有双缓冲。上面的代码应该在内存中准备图像并且只在屏幕上绘制一次。主要瓶颈是在屏幕上绘制图像时,或在屏幕上更改像素时。顺便说一句,最后一行不是必须的:pictureBox1.Image = bmp; 或者,您可以将picturebox图像保留为none,然后在运行时加载图像并在其上绘制,最后在最后设置pictureBox1.Image = bmp;
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2011-02-19
  • 2022-12-29
  • 2021-11-27
相关资源
最近更新 更多