Insertar una imagen en un documento de procesamiento de texto
En este tema se muestra cómo usar las clases del SDK de Open XML para Office para agregar mediante programación una imagen a un documento de procesamiento de texto.
Abrir un documento existente para su edición
Para abrir un documento existente, cree una instancia de la clase WordprocessingDocument como se muestra en la siguiente instrucción using. En la misma instrucción, abra el archivo de procesamiento de texto en la ruta de acceso especificada usando el método Open(String, Boolean), con el parámetro booleano establecido en verdadero para habilitar la edición del documento.
using (WordprocessingDocument wordprocessingDocument =
WordprocessingDocument.Open(filepath, true))
{
// Insert other code here.
}
La instrucción using proporciona una alternativa recomendada a la típica secuencia .Create, .Save, .Close. Asegura que se llamará automáticamente al método Dispose (método interno usado por Open XML SDK para limpiar recursos) cuando se llegue a la llave de cierre. El bloque que sigue a la instrucción using establece un ámbito para el objeto que se crea o se nombra en la instrucción using, en este caso wordprocessingDocument. Dado que la clase WordprocessingDocument en Open XML SDK guarda y cierra el objeto automáticamente como parte de su implementación System.IDisposable y que se llama automáticamente a Dispose cuando sale del bloque, no necesita llamar explícitamente a Save y Close, siempre que use using.
La representación XML del objeto gráfico
El siguiente texto de la especificación ISO/IEC 29500 presenta el elemento de datos de objeto gráfico.
Este elemento especifica la referencia a un objeto gráfico en el documento. Este objeto gráfico lo proporcionan en su totalidad los autores del documento que desean conservar estos datos en el documento.
[Nota: según el tipo de objeto gráfico que se usa, es posible que no todas las aplicaciones de generación compatibles con el marco OOXML tengan la posibilidad de representar el objeto gráfico. Fin de la nota]
© ISO/IEC29500: 2008.
El siguiente fragmento de esquema XML define el contenido de este elemento
<complexType name="CT_GraphicalObjectData">
<sequence>
<any minOccurs="0" maxOccurs="unbounded" processContents="strict"/>
</sequence>
<attribute name="uri" type="xsd:token"/>
</complexType>
Funcionamiento del código de ejemplo
Después de abrir el documento, agregue el objeto ImagePart al objetoMainDocumentPart mediante una secuencia de archivos, como se muestra en el segmento de código siguiente.
MainDocumentPart mainPart = wordprocessingDocument.MainDocumentPart;
ImagePart imagePart = mainPart.AddImagePart(ImagePartType.Jpeg);
using (FileStream stream = new FileStream(fileName, FileMode.Open))
{
imagePart.FeedData(stream);
}
AddImageToBody(wordprocessingDocument, mainPart.GetIdOfPart(imagePart));
Para agregar la imagen al cuerpo, primero debe definir la referencia de la imagen. A continuación, anexe la referencia en el cuerpo. El elemento debe estar en una Ejecución.
// Define the reference of the image.
var element =
new Drawing(
new DW.Inline(
new DW.Extent() { Cx = 990000L, Cy = 792000L },
new DW.EffectExtent()
{
LeftEdge = 0L,
TopEdge = 0L,
RightEdge = 0L,
BottomEdge = 0L
},
new DW.DocProperties()
{
Id = (UInt32Value)1U,
Name = "Picture 1"
},
new DW.NonVisualGraphicFrameDrawingProperties(
new A.GraphicFrameLocks() { NoChangeAspect = true }),
new A.Graphic(
new A.GraphicData(
new PIC.Picture(
new PIC.NonVisualPictureProperties(
new PIC.NonVisualDrawingProperties()
{
Id = (UInt32Value)0U,
Name = "New Bitmap Image.jpg"
},
new PIC.NonVisualPictureDrawingProperties()),
new PIC.BlipFill(
new A.Blip(
new A.BlipExtensionList(
new A.BlipExtension()
{
Uri =
"{28A0092B-C50C-407E-A947-70E740481C1C}"
})
)
{
Embed = relationshipId,
CompressionState =
A.BlipCompressionValues.Print
},
new A.Stretch(
new A.FillRectangle())),
new PIC.ShapeProperties(
new A.Transform2D(
new A.Offset() { X = 0L, Y = 0L },
new A.Extents() { Cx = 990000L, Cy = 792000L }),
new A.PresetGeometry(
new A.AdjustValueList()
) { Preset = A.ShapeTypeValues.Rectangle }))
) { Uri = "http://schemas.openxmlformats.org/drawingml/2006/picture" })
)
{
DistanceFromTop = (UInt32Value)0U,
DistanceFromBottom = (UInt32Value)0U,
DistanceFromLeft = (UInt32Value)0U,
DistanceFromRight = (UInt32Value)0U,
EditId = "50D07946"
});
// Append the reference to the body. The element should be in
// a DocumentFormat.OpenXml.Wordprocessing.Run.
wordDoc.MainDocumentPart.Document.Body.AppendChild(new Paragraph(new Run(element)));
Código de ejemplo
En el ejemplo de código siguiente se agrega una imagen a un documento de Word existente. En el código, se puede llamar al método InsertAPicture pasando la ruta de acceso del documento de Word y la ruta de acceso del archivo que contiene la imagen. Por ejemplo, la siguiente llamada inserta la imagen "MyPic.jpg" en el archivo "Word9.docx", que se encuentra en las rutas de acceso especificadas.
string document = @"C:\Users\Public\Documents\Word9.docx";
string fileName = @"C:\Users\Public\Documents\MyPic.jpg";
InsertAPicture(document, fileName);
Después de ejecutar el código, compruebe el archivo "Word9.docx" para ver la imagen insertada.
A continuación se incluye el código de ejemplo completo en C# y Visual Basic.
using DocumentFormat.OpenXml;
using DocumentFormat.OpenXml.Packaging;
using DocumentFormat.OpenXml.Wordprocessing;
using System;
using System.IO;
using A = DocumentFormat.OpenXml.Drawing;
using DW = DocumentFormat.OpenXml.Drawing.Wordprocessing;
using PIC = DocumentFormat.OpenXml.Drawing.Pictures;
InsertAPicture(args[0], args[1]);
static void InsertAPicture(string document, string fileName)
{
using (WordprocessingDocument wordprocessingDocument = WordprocessingDocument.Open(document, true))
{
if (wordprocessingDocument.MainDocumentPart is null)
{
throw new ArgumentNullException("MainDocumentPart is null.");
}
MainDocumentPart mainPart = wordprocessingDocument.MainDocumentPart;
ImagePart imagePart = mainPart.AddImagePart(ImagePartType.Jpeg);
using (FileStream stream = new FileStream(fileName, FileMode.Open))
{
imagePart.FeedData(stream);
}
AddImageToBody(wordprocessingDocument, mainPart.GetIdOfPart(imagePart));
}
}
static void AddImageToBody(WordprocessingDocument wordDoc, string relationshipId)
{
// Define the reference of the image.
var element =
new Drawing(
new DW.Inline(
new DW.Extent() { Cx = 990000L, Cy = 792000L },
new DW.EffectExtent()
{
LeftEdge = 0L,
TopEdge = 0L,
RightEdge = 0L,
BottomEdge = 0L
},
new DW.DocProperties()
{
Id = (UInt32Value)1U,
Name = "Picture 1"
},
new DW.NonVisualGraphicFrameDrawingProperties(
new A.GraphicFrameLocks() { NoChangeAspect = true }),
new A.Graphic(
new A.GraphicData(
new PIC.Picture(
new PIC.NonVisualPictureProperties(
new PIC.NonVisualDrawingProperties()
{
Id = (UInt32Value)0U,
Name = "New Bitmap Image.jpg"
},
new PIC.NonVisualPictureDrawingProperties()),
new PIC.BlipFill(
new A.Blip(
new A.BlipExtensionList(
new A.BlipExtension()
{
Uri =
"{28A0092B-C50C-407E-A947-70E740481C1C}"
})
)
{
Embed = relationshipId,
CompressionState =
A.BlipCompressionValues.Print
},
new A.Stretch(
new A.FillRectangle())),
new PIC.ShapeProperties(
new A.Transform2D(
new A.Offset() { X = 0L, Y = 0L },
new A.Extents() { Cx = 990000L, Cy = 792000L }),
new A.PresetGeometry(
new A.AdjustValueList()
)
{ Preset = A.ShapeTypeValues.Rectangle }))
)
{ Uri = "http://schemas.openxmlformats.org/drawingml/2006/picture" })
)
{
DistanceFromTop = (UInt32Value)0U,
DistanceFromBottom = (UInt32Value)0U,
DistanceFromLeft = (UInt32Value)0U,
DistanceFromRight = (UInt32Value)0U,
EditId = "50D07946"
});
if (wordDoc.MainDocumentPart is null || wordDoc.MainDocumentPart.Document.Body is null)
{
throw new ArgumentNullException("MainDocumentPart and/or Body is null.");
}
// Append the reference to body, the element should be in a Run.
wordDoc.MainDocumentPart.Document.Body.AppendChild(new Paragraph(new Run(element)));
}