创建ppt幻灯片缩略图而不导出到文件

时间:2013-01-24 03:36:48

标签: c# add-in powerpoint

我在powerpoint窗口上开发了侧面板形式的ppt添加 我需要的是自定义幻灯片缩略图,到目前为止我所做的我使用Export()方法将所有幻灯片转换为临时图像并显示它们。 但这种方法太慢,因为我需要从磁盘保存/加载,我的要求是以交互方式显示它们(需要足够快)

我想知道是否有办法在内存中导出幻灯片缩略图......

2 个答案:

答案 0 :(得分:1)

一种可能的方法:

ActivePresentation.Slides(x).Copy

这会将幻灯片以多种格式放在Windows剪贴板上,包括位图,PNG,JPG等。

如果您有办法将剪贴板中的图像加载到您正在做的任何事情中,那么您就可以了。

答案 1 :(得分:0)

感谢Steve使用剪贴板的想法,

修改 它工作但仍然很慢,当我生成70张幻灯片时需要4-5秒 似乎Copy()方法非常慢,因此开销不在剪贴板的位图图像中......

这就是我所做的

slide.Copy();
if (Clipboard.GetDataObject().GetDataPresent(DataFormats.Bitmap))
{
    ImageSource imgSource = BinaryStructConverter.ImageFromClipboardDib();
}

对于BinaryStructConverter,我从这里得到了一个很好的代码: http://www.thomaslevesque.com/2009/02/05/wpf-paste-an-image-from-the-clipboard/ (不知怎的,我们需要转换它,因为如果你只是直接从剪贴板复制它,位图图像格式可能会搞砸了)

[StructLayout(LayoutKind.Sequential, Pack = 2)]
public struct BITMAPFILEHEADER
{
    public static readonly short BM = 0x4d42; // BM

    public short bfType;
    public int bfSize;
    public short bfReserved1;
    public short bfReserved2;
    public int bfOffBits;
}

[StructLayout(LayoutKind.Sequential)]
public struct BITMAPINFOHEADER
{
    public int biSize;
    public int biWidth;
    public int biHeight;
    public short biPlanes;
    public short biBitCount;
    public int biCompression;
    public int biSizeImage;
    public int biXPelsPerMeter;
    public int biYPelsPerMeter;
    public int biClrUsed;
    public int biClrImportant;
}

public static class BinaryStructConverter
{
    public static ImageSource ImageFromClipboardDib()
    {
        MemoryStream ms = Clipboard.GetData("DeviceIndependentBitmap") as MemoryStream;
        if (ms != null)
        {
            byte[] dibBuffer = new byte[ms.Length];
            ms.Read(dibBuffer, 0, dibBuffer.Length);

            BITMAPINFOHEADER infoHeader =
                BinaryStructConverter.FromByteArray<BITMAPINFOHEADER>(dibBuffer);

            int fileHeaderSize = Marshal.SizeOf(typeof(BITMAPFILEHEADER));
            int infoHeaderSize = infoHeader.biSize;
            int fileSize = fileHeaderSize + infoHeader.biSize + infoHeader.biSizeImage;

            BITMAPFILEHEADER fileHeader = new BITMAPFILEHEADER();
            fileHeader.bfType = BITMAPFILEHEADER.BM;
            fileHeader.bfSize = fileSize;
            fileHeader.bfReserved1 = 0;
            fileHeader.bfReserved2 = 0;
            fileHeader.bfOffBits = fileHeaderSize + infoHeaderSize + infoHeader.biClrUsed * 4;

            byte[] fileHeaderBytes =
                BinaryStructConverter.ToByteArray<BITMAPFILEHEADER>(fileHeader);

            MemoryStream msBitmap = new MemoryStream();
            msBitmap.Write(fileHeaderBytes, 0, fileHeaderSize);
            msBitmap.Write(dibBuffer, 0, dibBuffer.Length);
            msBitmap.Seek(0, SeekOrigin.Begin);

            return BitmapFrame.Create(msBitmap);
        }
        return null;
    }

    public static T FromByteArray<T>(byte[] bytes) where T : struct
    {
        IntPtr ptr = IntPtr.Zero;
        try
        {
            int size = Marshal.SizeOf(typeof(T));
            ptr = Marshal.AllocHGlobal(size);
            Marshal.Copy(bytes, 0, ptr, size);
            object obj = Marshal.PtrToStructure(ptr, typeof(T));
            return (T)obj;
        }
        finally
        {
            if (ptr != IntPtr.Zero)
                Marshal.FreeHGlobal(ptr);
        }
    }

    public static byte[] ToByteArray<T>(T obj) where T : struct
    {
        IntPtr ptr = IntPtr.Zero;
        try
        {
            int size = Marshal.SizeOf(typeof(T));
            ptr = Marshal.AllocHGlobal(size);
            Marshal.StructureToPtr(obj, ptr, true);
            byte[] bytes = new byte[size];
            Marshal.Copy(ptr, bytes, 0, size);
            return bytes;
        }
        finally
        {
            if (ptr != IntPtr.Zero)
                Marshal.FreeHGlobal(ptr);
        }
    }
}