C# 如何在.NET中将Twips转换为像素?

C# 如何在.NET中将Twips转换为像素?,c#,graphics,vb6-migration,screen-resolution,C#,Graphics,Vb6 Migration,Screen Resolution,我正在做一个迁移项目,在这个项目中,数据库实际上以twips的形式存储显示大小。 由于我不能使用twips为WPF或Winforms控件分配大小,我想知道.NET是否有一个在运行时可用的转换方法?结果是迁移工具有一些功能,但在运行时它没有任何用处。下面是我所做的(如果扩展方法中的硬编码值更改为每英寸点数的值,它也可以用作点转换器): 1 Twip=1/1440英寸。 .NETGraphics对象有一个方法DpiX和DpiY,可用于确定一英寸中有多少像素。 使用这些测量值,我为图形创建了以下扩展方

我正在做一个迁移项目,在这个项目中,数据库实际上以twips的形式存储显示大小。
由于我不能使用twips为WPF或Winforms控件分配大小,我想知道.NET是否有一个在运行时可用的转换方法?

结果是迁移工具有一些功能,但在运行时它没有任何用处。下面是我所做的(如果扩展方法中的硬编码值更改为每英寸点数的值,它也可以用作点转换器):

1 Twip=1/1440英寸。 .NET
Graphics
对象有一个方法
DpiX
DpiY
,可用于确定一英寸中有多少像素。 使用这些测量值,我为
图形创建了以下扩展方法:

using System.Drawing;

static class Extensions
{
    /// <summary>
    /// Converts an integer value in twips to the corresponding integer value
    /// in pixels on the x-axis.
    /// </summary>
    /// <param name="source">The Graphics context to use</param>
    /// <param name="inTwips">The number of twips to be converted</param>
    /// <returns>The number of pixels in that many twips</returns>
    public static int ConvertTwipsToXPixels(this Graphics source, int twips)
    {
        return (int)(((double)twips) * (1.0 / 1440.0) * source.DpiX);
    }

    /// <summary>
    /// Converts an integer value in twips to the corresponding integer value
    /// in pixels on the y-axis.
    /// </summary>
    /// <param name="source">The Graphics context to use</param>
    /// <param name="inTwips">The number of twips to be converted</param>
    /// <returns>The number of pixels in that many twips</returns>
    public static int ConvertTwipsToYPixels(this Graphics source, int twips)
    {
        return (int)(((double)twips) * (1.0 / 1440.0) * source.DpiY);
    }
}
有关获取图形对象的方法列表,请参见中的“备注”部分。教程中提供了更完整的文档

简单总结一下最简单的方法:

  • Control.CreateGraphics
  • 绘制事件的
    PaintEventArgs
    在其
    Graphics
    属性中有一个
    Graphics
  • Hand
    Graphics.FromImage
    一个图像,它将返回一个可以在该图像上绘制的
    Graphics
    对象。(注意:您不太可能希望对实际图像使用twips)
参考另一个C#版本,使用Win32 API而不需要
图形
对象:

using System.Runtime.InteropServices;

static class SomeUtils {

  public static int ConvertTwipsToPixels(int twips, MeasureDirection direction) {
    return (int)(((double)twips)*((double)GetPixperinch(direction))/1440.0);
  }

  public static int ConvertPixelsToTwips(int pixels, MeasureDirection direction) {
    return (int)((((double)pixels)*1440.0)/((double)GetPixperinch(direction)));
  }

  public static int GetPPI(MeasureDirection direction) {
    int ppi;
    IntPtr dc = GetDC(IntPtr.Zero);

    if (direction == MeasureDirection.Horizontal)
      ppi = GetDeviceCaps(dc, 88); //DEVICECAP LOGPIXELSX
    else
      ppi = GetDeviceCaps(dc, 90); //DEVICECAP LOGPIXELSY

    ReleaseDC(IntPtr.Zero, dc);
    return ppi;
  }

  [DllImport("user32.dll")]
  static extern IntPtr GetDC(IntPtr hWnd);

  [DllImport("user32.dll")]
  static extern bool ReleaseDC(IntPtr hWnd, IntPtr hDC);

  [DllImport("gdi32.dll")]
  static extern int GetDeviceCaps(IntPtr hdc, int devCap);
}

public enum MeasureDirection {
  Horizontal,
  Vertical
}
应该指定
MeasureDirection
,因为不能保证像素总是正方形(根据kb)


参考资料:

对于迁移项目,我们可以使用内置的会话支持功能

microsoft.visualbasic.compatibility.vb6.twipsperpixelx
microsoft.visualbasic.compatibility.vb6.twipsperpixely

我知道这是一篇旧帖子,但这里有一份供参考的材料和上面1440个答案的数学

twip不仅仅是
1/1440
th英寸。twip是点的
1/20

您在可打印文档中使用的点通常是postscript 72dpi:

72dpi*20Twips/点=1440twips

因此,在处理水晶报告时,twips宽度为15840(边距为0 twips), 宽度为
11英寸(15840/(72*20))

基于96 dpi的屏幕密度,报告将在以下位置发布到屏幕:


1056px宽(96dpi*11in=1056px)

代码中有一个小错误。在ConvertTwipsToYPixles中,您可以使用DipX而不是DPIy。谢谢,我还有一个问题。您说过CreateGraphics返回一个Drawing.Graphics对象。它返回什么样的图形?你能举一个CreateGraphics方法的例子吗?
CreateGraphics
控件的成员。看
Graphics
是一个抽象的密封类,它将图形封装到屏幕上。如果你用这个,你不需要知道任何关于它的事情。只需使用任何控件(窗体、按钮等)并调用它即可。如果您的类继承自控件,您可以像我一样使用它(使用隐含的
this
)。表示1像素=15 twips==>1 twips=1/15像素仅对于使用基础设施的所有信息,1英寸等于1440 twips(桌面点的二十分之一)。一英寸等于72个桌面点。资料来源:
microsoft.visualbasic.compatibility.vb6.twipsperpixelx
microsoft.visualbasic.compatibility.vb6.twipsperpixely