首页
学习
活动
专区
圈层
工具
发布
社区首页 >问答首页 >为什么我的图元文件“丢失”了一个位图?

为什么我的图元文件“丢失”了一个位图?
EN

Stack Overflow用户
提问于 2011-01-27 19:11:54
回答 1查看 995关注 0票数 0

最近,我在使用图元文件绘制东西时发现了一个bug。现在,我不确定是我做错了什么,还是在图元文件本身的绘图中有一个bug:

当我在一个图元文件上绘制图像,而这个图元文件是由PlayEnhMetafile自己绘制在另一个图元文件上时,我丢失了图像的最下方或最右边。我猜这与屏幕坐标有关(我运行双屏幕1280*1024,所以运行2560*1024),因为图像开始消失的底部通道大约是500。

下面是一些示例代码,我创建这些代码是为了更具体地向您展示问题。(你可以用下面的代码替换一个新创建的Windows C#项目的Form1.cs,然后在上面放一个按钮)

代码语言:javascript
复制
using System;
using System.Drawing;
using System.Windows.Forms;
using System.Drawing.Imaging;
using System.IO;
using System.Runtime.InteropServices;

namespace MetaFileDrawing
{ 
 public partial class Form1
  : Form
 { 
  [DllImport("gdi32.dll", SetLastError = true)]
  private static extern bool PlayEnhMetaFile(IntPtr hdc, IntPtr hEmf, ref Rectangle rectangle);

  [DllImport("gdi32.dll", SetLastError = true)]
  public static extern bool DeleteObject(IntPtr hGdiObj);

  public Form1()
  {
   InitializeComponent();
  }

  /// <summary>
  /// Creates the sub-metafile where the actual drawing is done (and the problems occur).
  /// </summary>
  private Metafile GetSubMetafile()
  {
   Metafile metafile = null;
   using(Graphics controlGraphics = this.CreateGraphics())
   {
    using(MemoryStream memoryStream = new MemoryStream())
    {
     metafile = new Metafile(memoryStream, controlGraphics.GetHdc(), EmfType.EmfOnly, string.Empty);

     using(Graphics metafileGraphics = Graphics.FromImage(metafile))
     {
      Bitmap bitmap = new Bitmap("Fibonacci.png");
      // Draw the image 3 times... if pushed to far down, it wont show up?
      metafileGraphics.DrawRectangle(Pens.Yellow, new Rectangle(0, 0, 40, 1200));
      metafileGraphics.DrawImage(bitmap, new Point(0, 0));
      metafileGraphics.DrawImage(bitmap, new Point(10, 950));
      metafileGraphics.DrawImage(bitmap, new Point(20, 1150));
     }
    }
    controlGraphics.ReleaseHdc();
   }
   return metafile;
  }

  /// <summary>
  /// Creates and draws the metafile.
  /// </summary>
  private void DrawMetafile()
  {
   using(Graphics controlGraphics = this.CreateGraphics())
   {    
    using(MemoryStream memoryStream = new MemoryStream())
    {
     // EmfType.EmfOnly is a restriction defined by my project limitations
     Metafile metafile = new Metafile(memoryStream, controlGraphics.GetHdc(), EmfType.EmfOnly, string.Empty);

     using(Graphics metafileGraphics = Graphics.FromImage(metafile))
     {
      // A large red rect for orientation
      metafileGraphics.DrawRectangle(Pens.Red, new Rectangle(0, 0, 4000, 4000));

      // Create the sub metafile
      Metafile subMetafile = GetSubMetafile();

      // To check, draw the subMetafile with DrawImage (works fine, the inlined image is drawn 3 times)
      metafileGraphics.DrawImage(subMetafile, new Point(10, 0));

      // On the right side, draw the sub metafile using PlayEnhMetaFile (dont work correctly, only 2 images)
      IntPtr hMetafile = subMetafile.GetHenhmetafile();
      Rectangle rectangle1 = new Rectangle(100, 0, 170, 1230);
      PlayEnhMetaFile(metafileGraphics.GetHdc(), hMetafile, ref rectangle1);
      metafileGraphics.ReleaseHdc();
      DeleteObject(hMetafile);
     }

     metafile.Save("Output.emf");
    }
    controlGraphics.ReleaseHdc();
   }
  }

  private void button1_Click(object sender, EventArgs e)
  {
   DrawMetafile();
  }
 }
}

正如您所看到的,使用PlayEnhMetaFile函数会导致我丢失三个图像中的一个。有什么想法吗?

EN

回答 1

Stack Overflow用户

发布于 2011-05-13 19:46:59

我在使用C++时遇到了同样的问题,并找到了两种变通方法。我可以使用GDI+附加到图元文件并播放它,但坐标稍有偏差。我目前使用的更复杂的替代方法是使用EnumEnhMetaFile,并手动执行bitblt/stretchblt/stretchdibits调用,这似乎是可行的。如果你找到了更好的解决方案,请告诉我。

票数 0
EN
页面原文内容由Stack Overflow提供。腾讯云小微IT领域专用引擎提供翻译支持
原文链接:

https://stackoverflow.com/questions/4815586

复制
相关文章

相似问题

领券
问题归档专栏文章快讯文章归档关键词归档开发者手册归档开发者手册 Section 归档