Partilhar via


Taking snapshots for part of a Word document - the new EnhMetaFileBits property

In Word 2003 object model a new property named EnhMetaFileBits for Range and Selection object is introduced. From the documentation, you'd see that it is supposed to help getting the picture representation for a portion of a Word document. Very interesting, isn't it? However the sample included with Word VBA help is too simple to make any real use of it. I searched the web a little and did not find anything helpful. So I decided to try it out myself to see how it works. And the result? Check out this nice little screenshot:

 

EnhMetaFileBits test screenshot

 

What I did was to create my favorite "rainbow" WordArt in Word, then use EnhMetaFileBits to get its EMF representation and draw that in the picture box on my windows form. The skeleton of my c# code is as following:

 

using Office = Microsoft.Office.Core;

using Word = Microsoft.Office.Interop.Word;

 

object missing = System.Reflection.Missing.Value;

 

// Get the Graphics object from the picture box

Graphics g = pictureBox1.CreateGraphics();

// Clear the picture box

g.Clear(pictureBox1.BackColor);

g.DrawString("Starting Microsoft Word, please wait...",this.Font,new SolidBrush(Color.Black),new PointF(0F,0F));

 

// Start a new Word instance if necessary

if (wdApp == null)

wdApp = new Word.ApplicationClass();

// Create a new document

Word.Document wdDoc = wdApp.Documents.Add(ref missing, ref missing, ref missing, ref missing);

 

// Add a WordArt with text from textBox1 to the new document

Word.Shape wdShape = wdDoc.Shapes.AddTextEffect(

    Office.MsoPresetTextEffect.msoTextEffect16, //the rainbow wordart

    this.textBox1.Text, "Arial Black", 16,

    Office.MsoTriState.msoFalse, Office.MsoTriState.msoFalse,

    0, 0, ref missing);

// Select the shape so that EnhMetaFileBits can be retrieved from the Selection object

// This is unnecessary if you have a Range object handy

wdShape.Select(ref missing);

 

// Create a meta file using the byte array returned from EnhMetaFileBits

byte[] emfData = (byte[])wdApp.Selection.EnhMetaFileBits;

System.IO.MemoryStream ms = new System.IO.MemoryStream(emfData);

Metafile mf = new Metafile(ms);

 

// Draw the meta file in the picture box

g.Clear(pictureBox1.BackColor);

g.DrawImageUnscaled(mf, 0, 0);

g.Dispose();

 

As you can see it is pretty easy and straigtforward. However, there is one caveat: the Metafile object created this way may be much wider than it should be: a very big extra white margin may appear to the right. That is why I am using the DrawImageUnscaled method to crop the image. I am still trying to figure out the cause. It might be something I did wrong because I know very little about System.Drawing namespace. Any GDI experts out there care to comment?

 

The sample VS.Net 2003 solution is available for download here.

Comments

  • Anonymous
    August 05, 2005
    Any possibility of using EnhMetaFileBits from VBA?

    RE: Whitespace
    I think this is a problem with Word itself. Try selecting text & use PasteSpecial to past it as an EMF. There is a lot of whitespace to the right.
  • Anonymous
    August 08, 2005
    Is this possible with a aspx page with GDI+

    Thanks
  • Anonymous
    August 08, 2005
    Michael: you should be able to call GDI related win32 APIs from VBA to manipulate the EMF bits as long as you are good enough with GDI. I can not help you with that though. Also thanks for the comments about extra spaces. I will look into that.

    CMDev: I think it is. But keep in mind that automating Microsoft Word (as well as most other Office client products) from a Web server is not supported by Microsoft.
  • Anonymous
    August 08, 2005
    The comment has been removed
  • Anonymous
    August 09, 2005
    I can not tell whether the web site you mentioned is using Word to create the signs or not. My guess is not though. Still you could do it using Word, as long as you know this kind of usage is not supported by Microsoft.

    To change the text of a WordArt on the fly, use InlineShape or Shape object's texteffect property. For example: Selection.InlineShapes(1).TextEffect.Text = "abc" would change the text to "abc".
  • Anonymous
    November 26, 2007
    PingBack from http://feeds.maxblog.eu/item_1395503.html