简体   繁体   中英

create a copy of template presentation “.potx” to a new “.pptx” using openXML

I have a powerpoint template with .potx extension, i need to create a copy of the template file, but the created file does not have any content present in it, it is a blank presentation, below is the function i am using to create a destination file using template file.

    /// <summary>
    /// Creates a copy of the source template file
    /// </summary>
    /// <param name="sourceFile">sourcce file which has to be copied</param>
    /// <param name="destinationFile">destination file where the new file has to be placed.</param>
       public static void CreateFileFromTemplate(this string sourceFile, string destinationFile)
    {
        try
        {
            //File.Copy(sourceFile, destinationFile, true);
            if (System.IO.Path.GetExtension(sourceFile) == ".potx")
            {
                if (System.IO.Path.GetExtension(destinationFile) == ".potx")
                {
                    PresentationDocument destinationDoc = PresentationDocument.Create(destinationFile, PresentationDocumentType.Presentation);
                    PresentationPart presentationPart = destinationDoc.AddPresentationPart();
                    presentationPart.Presentation = new Presentation();
                    presentationPart.Presentation.Save();
                    destinationDoc.Close();
                    //Package destinationPackage = Package.Open(destinationFile, FileMode.Open, FileAccess.ReadWrite);
                    using (destinationDoc = PresentationDocument.Open(destinationFile, true))
                    {
                        Package templatePackage = Package.Open(sourceFile, FileMode.Open);
                        using (PresentationDocument templateDocument = PresentationDocument.Open(templatePackage))
                        {
                            PresentationPart sourcePresPart = templateDocument.PresentationPart;
                            PresentationPart destinationPresrPart = destinationDoc.PresentationPart;
                            //var templateSlideCount = templateDocument.CountSlides();
                            //for (int slides = 1; slides <= templateSlideCount; slides++)
                            //{

                            //}
                            SlidePart sourceSlidePart;
                            SlidePart destinationSlidePart;
                            foreach (SlideId slideId in sourcePresPart.Presentation.SlideIdList)
                            {
                                //int i=0;

                                sourceSlidePart = (SlidePart)sourcePresPart.GetPartById(slideId.RelationshipId);
                                destinationSlidePart = sourceSlidePart.Clone();
                                SlideIdList slideIdList = destinationPresrPart.Presentation.SlideIdList;

                                destinationPresrPart.AddPart(destinationSlidePart);
                                // Save the modified presentation.
                                destinationPresrPart.Presentation.Save();
                            }
                        }
                    }
                }
                else
                {
                    throw new FileFormatException("Invalid destination file format, Valid file should have .pptx as extension");
                }
            }
            else
            {
                throw new FileFormatException("Invalid file format, Valid file should have .potx as extension");
            }
        }
        catch (Exception ex)
        {
            throw;
        }
    }

Extension method used to clone a slide

    /// <summary>
    /// Clones the specified slide.
    /// </summary>
    /// <param name="sourceSlide">The slide to clone.</param>
    /// <returns>Cloned slide.</returns>
    public static SlidePart Clone(this SlidePart sourceSlide)
    {
        // find the presentationPart: makes the API more fluent
        var presentationPart = sourceSlide.GetParentParts()
            .OfType<PresentationPart>()
            .Single();

        // clone slide contents
        Slide currentSlide = (Slide)sourceSlide.Slide.CloneNode(true);
        var slidePartClone = presentationPart.AddNewPart<SlidePart>();

        currentSlide.Save(slidePartClone);

        // copy layout part
        slidePartClone.AddPart(sourceSlide.SlideLayoutPart);

        //copy all embedded elements
        foreach (ChartPart part in sourceSlide.ChartParts)
        {
            ChartPart newpart = slidePartClone.AddNewPart<ChartPart>(part.ContentType, sourceSlide.GetIdOfPart(part));
            newpart.FeedData(part.GetStream());
            newpart.AddNewPart<EmbeddedPackagePart>(part.EmbeddedPackagePart.ContentType, part.GetIdOfPart(part.EmbeddedPackagePart));
            newpart.EmbeddedPackagePart.FeedData(part.EmbeddedPackagePart.GetStream());
        }
        foreach (EmbeddedObjectPart part in sourceSlide.EmbeddedObjectParts)
        {
            EmbeddedObjectPart newpart = slidePartClone.AddNewPart<EmbeddedObjectPart>(part.ContentType, sourceSlide.GetIdOfPart(part));
            newpart.FeedData(part.GetStream());
        }
        foreach (EmbeddedPackagePart part in sourceSlide.EmbeddedPackageParts)
        {
            EmbeddedPackagePart newpart = slidePartClone.AddNewPart<EmbeddedPackagePart>(part.ContentType, sourceSlide.GetIdOfPart(part));
            newpart.FeedData(part.GetStream());
        }
        foreach (ImagePart part in sourceSlide.ImageParts)
        {
            ImagePart newpart = slidePartClone.AddNewPart<ImagePart>(part.ContentType, sourceSlide.GetIdOfPart(part));
            newpart.FeedData(part.GetStream());
        }
        foreach (VmlDrawingPart part in sourceSlide.VmlDrawingParts)
        {
            VmlDrawingPart newpart = slidePartClone.AddNewPart<VmlDrawingPart>(part.ContentType, sourceSlide.GetIdOfPart(part));
            newpart.FeedData(part.GetStream());
        }
        foreach (UserDefinedTagsPart part in sourceSlide.UserDefinedTagsParts)
        {
            UserDefinedTagsPart newpart = slidePartClone.AddNewPart<UserDefinedTagsPart>(part.ContentType, sourceSlide.GetIdOfPart(part));
            newpart.FeedData(part.GetStream());
        }
        return slidePartClone;
    }

in my main method i have below code which calls these functions to create the ppt

 string sourceFilePath =@"C:\TempFolder\template.potx";
 string destinationFilePath = @"C:\TempFolder\ClonedFile.potx";
 sourceFilePath.CreateFileFromTemplate(destinationFilePath);

but the final created ppt will not have any slides in it,

any help would be appreciated

I posted a similar answer before on saving an excel template to an actual excel document here and you should be able to apply the same logic with a power point template. Instead of the SpreadsheetDocument you will want to use the PresentationDocument and call ChangeDocumentType on it. Something along these lines:

byte[] byteArray = File.ReadAllBytes("C:\\temp\\sa123.potx");
using (MemoryStream stream = new MemoryStream())
{
    stream.Write(byteArray, 0, (int)byteArray.Length);
    using (PresentationDocument presentationDoc = PresentationDocument.Open(stream, true))
    {
       // Change from template type to presentation type
       presentationDoc.ChangeDocumentType(PresentationDocumentType.Presentation);
    }
    File.WriteAllBytes("C:\\temp\\sa123.pptx", stream.ToArray()); 
}

You can then reopen that saved file and do whatever extra stuff you want to it without touching the template file.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM