无法使用 openxml 在 PPT 报告中生成第二个表

2024-04-27

我有这个代码。我能够完美地生成带有文本数据的 pptx 报告。我在这份报告中还有 4 个表格,其中包含动态数据。我可以在 PPT 中生成一张表格,但无法生成多个表格。

Requirement: On the right I have 4 tables. enter image description here

Expectation: I am able to get the 1st table. enter image description here

在下面的代码中我添加了P.GraphicFrame graphicFrame2 in AddNewSlide假设它会创建另一个表格框架,我可以在其中填充数据并将其放置在 PPT 上。但这不起作用。请帮忙。

using (PresentationDocument presentationDocument = PresentationDocument.Open(slideName, true))
            {
                //Get the first slide from presentation
                SlidePart intitalSlide = presentationDocument.PresentationPart.SlideParts.First();
                AddNewSlide(presentationDocument, intitalSlide, projectID, reportType);
            }

 #region Powerpoint Reports


    private System.Data.DataTable GetValueForPPTReport(int projectID)
    {
        System.Data.DataTable dt = new System.Data.DataTable();
        SqlCommand cmd = new SqlCommand();
        cmd.CommandType = CommandType.Text;
        cmd.CommandText = "select convert(varchar(10),proj_id) + ' : ' + proj_name as projName,proj_type, proj_problem_state, proj_goal_obj, proj_in_scope, proj_out_scope , proj_who_customer, proj_what_defect,proj_critical_to_qlty from tbl_proj_details where proj_id = @proj_id";
        cmd.Parameters.Add("@proj_id", SqlDbType.Int).Value = projectID;
        dt = (new Bussiness()).Execute(cmd);
        return dt;
    }
    private System.Data.DataTable GetValueForPPTReportBenefit(int projectID)
    {
        System.Data.DataTable dt = new System.Data.DataTable();
        SqlCommand cmd = new SqlCommand();
        cmd.CommandType = CommandType.Text;
        cmd.CommandText = "select [proj_ben_type] as [Benefit Type], [proj_ben_year] as Year ,[proj_ben_fcst] as Forecast,[proj_ben_act] as Actual  from [tbl_proj_benefits_detail]  where proj_id = @proj_id";
        cmd.Parameters.Add("@proj_id", SqlDbType.Int).Value = projectID;
        dt = (new Bussiness()).Execute(cmd);
        return dt;
    }
    private void AddNewSlide(PresentationDocument presentationDocument, SlidePart _slideTemplate, int projectID, string reportType)
    {
        PresentationPart parent = presentationDocument.PresentationPart;
        var newSlidePart = parent.AddNewPart<SlidePart>("newSlide1");

        if (reportType == "Charter")
        {
            System.Data.DataTable dt = GetValueForPPTReport(projectID);

            //copy the contents of the template slide to the new slide and attach the appropriate layout
            newSlidePart.FeedData(_slideTemplate.GetStream(FileMode.Open));
            newSlidePart.AddPart(_slideTemplate.SlideLayoutPart, _slideTemplate.GetIdOfPart(_slideTemplate.SlideLayoutPart));

            //Alter the placeholder text in new slide
            SetPlaceholder(newSlidePart, "txtProjectIDName", dt.Rows[0]["projName"].ToString());
            SetPlaceholder(newSlidePart, "txtProjType", dt.Rows[0]["proj_type"].ToString());
            SetPlaceholder(newSlidePart, "txtProbSt", dt.Rows[0]["proj_problem_state"].ToString());
            SetPlaceholder(newSlidePart, "txtGoal", dt.Rows[0]["proj_goal_obj"].ToString());
            SetPlaceholder(newSlidePart, "txtDate", System.DateTime.Now.ToString("MM/dd/yyyy HH:mm"));
        }


        //Add dynamic Tables here

        ////List<OpenXmlElement> elements = new List<OpenXmlElement>();
        ////elements.Add(new P.NonVisualGraphicFrameProperties
        ////    (new P.NonVisualDrawingProperties() { Id = 1, Name = "xyz" }, new P.NonVisualGraphicFrameDrawingProperties(), new ApplicationNonVisualDrawingProperties()));

        // Declare and instantiate the graphic Frame of the new slide 
        P.GraphicFrame graphicFrame = newSlidePart.Slide.CommonSlideData.ShapeTree.AppendChild(new P.GraphicFrame());
        P.GraphicFrame graphicFrame2 = newSlidePart.Slide.CommonSlideData.ShapeTree.AppendChild(new P.GraphicFrame());

        // Specify the required Frame properties of the graphicFrame 
        ApplicationNonVisualDrawingPropertiesExtension applicationNonVisualDrawingPropertiesExtension = new ApplicationNonVisualDrawingPropertiesExtension() { Uri = "{D42A27DB-BD31-4B8C-83A1-F6EECF244321}" };
        P14.ModificationId modificationId1 = new P14.ModificationId() { Val = 3229994563U };
        modificationId1.AddNamespaceDeclaration("p14", "http://schemas.microsoft.com/office/powerpoint/2010/main");
        applicationNonVisualDrawingPropertiesExtension.Append(modificationId1);

        ApplicationNonVisualDrawingPropertiesExtension applicationNonVisualDrawingPropertiesExtension2 = new ApplicationNonVisualDrawingPropertiesExtension() { Uri = "{D42A27DB-BD31-4B8C-83A1-F6EECF244321}" };
        P14.ModificationId modificationId2 = new P14.ModificationId() { Val = 3229994564U };
        modificationId2.AddNamespaceDeclaration("p14", "http://schemas.microsoft.com/office/powerpoint/2010/main");
        applicationNonVisualDrawingPropertiesExtension.Append(modificationId2);

        graphicFrame.NonVisualGraphicFrameProperties = new P.NonVisualGraphicFrameProperties
        (new D.NonVisualDrawingProperties() { Id = 1, Name = "table1" },
        new D.NonVisualGraphicFrameDrawingProperties(new D.GraphicFrameLocks() { NoGrouping = true }),
        new ApplicationNonVisualDrawingProperties(new ApplicationNonVisualDrawingPropertiesExtensionList(applicationNonVisualDrawingPropertiesExtension)));

        graphicFrame2.NonVisualGraphicFrameProperties = new P.NonVisualGraphicFrameProperties
        (new D.NonVisualDrawingProperties() { Id = 2, Name = "table2" },
        new D.NonVisualGraphicFrameDrawingProperties(new D.GraphicFrameLocks() { NoGrouping = true }),
        new ApplicationNonVisualDrawingProperties(new ApplicationNonVisualDrawingPropertiesExtensionList(applicationNonVisualDrawingPropertiesExtension2)));

        if (true)
        {
            graphicFrame.Transform = new Transform(new D.Offset() { X = 5050609L, Y = 883400L }, new D.Extents() { Cx = 0, Cy = 0 });
            // Specify the Griaphic of the graphic Frame 
            graphicFrame.Graphic = new D.Graphic(new D.GraphicData(GenerateTable(projectID, reportType)) { Uri = "http://schemas.openxmlformats.org/drawingml/2006/table" });

            graphicFrame2.Transform = new Transform(new D.Offset() { X = 5050609L, Y = 983400L }, new D.Extents() { Cx = 0, Cy = 0 });
            // Specify the Griaphic of the graphic Frame 
            graphicFrame2.Graphic = new D.Graphic(new D.GraphicData(GenerateTable(projectID, reportType)) { Uri = "http://schemas.openxmlformats.org/drawingml/2006/table" });
        }
        //save the changes to the slide
        newSlidePart.Slide.Save();

        //need to assign an id to the new slide and add it to the slideIdList
        //first figure out the largest existing id
        DocumentFormat.OpenXml.Presentation.SlideIdList slideIdList = parent.Presentation.SlideIdList;
        uint maxSlideId = 1;

        foreach (DocumentFormat.OpenXml.Presentation.SlideId slideId in slideIdList.ChildElements)
        {
            if (slideId.Id > maxSlideId) maxSlideId = slideId.Id;
        }

        //assign an id and add the new slide at the end of the list
        DocumentFormat.OpenXml.Presentation.SlideId newSlideId = new DocumentFormat.OpenXml.Presentation.SlideId { Id = ++maxSlideId, RelationshipId = parent.GetIdOfPart(newSlidePart) };
        slideIdList.Append(newSlideId);

        //Delete first template slide 
        SlideId tempSlideId = slideIdList.ChildElements[0] as SlideId;
        slideIdList.RemoveChild(tempSlideId);
    }
    private void SetPlaceholder(SlidePart slidePart, string placeholder, string value)
    {
        List<D.Text> textListExif1 = slidePart.Slide.Descendants<D.Text>().Where(t => t.Text.Equals(placeholder)).ToList();
        foreach (D.Text text in textListExif1)
        {
            text.Text = value;
        }
    }

    #region tables

    /// <summary> 
    /// Generate Table as below order: 
    /// a:tbl(Table) ->a:tr(TableRow)->a:tc(TableCell) 
    /// We can return TableCell object with CreateTextCell method 
    /// and Append the TableCell object to TableRow  
    /// </summary> 
    /// <returns>Table Object</returns> 
    private D.Table GenerateTable(int projectID, string reportType)
    {
        // Declare and instantiate table  
        D.Table table = new D.Table();

        // Specify the required table properties for the table 
        D.TableProperties tableProperties = new D.TableProperties() { FirstRow = true, BandRow = false };
        D.TableStyleId tableStyleId = new D.TableStyleId();
        tableStyleId.Text = "{5C22544A-7EE6-4342-B048-85BDC9FD1C3A}";

        tableProperties.Append(tableStyleId);
        D.TableGrid tableGrid1 = new D.TableGrid();
        System.Data.DataTable dtData = new System.Data.DataTable();
        if (reportType == "Charter")
        {
            //tblXBenefit
            dtData = GetValueForPPTReportBenefit(projectID);

            // Declare and instantiate tablegrid and colums 
            //D.TableGrid tableGrid1 = new D.TableGrid();
            D.GridColumn gridColumn1 = new D.GridColumn() { Width = 1848000L };
            D.GridColumn gridColumn2 = new D.GridColumn() { Width = 648000L };
            D.GridColumn gridColumn3 = new D.GridColumn() { Width = 648000L };
            D.GridColumn gridColumn4 = new D.GridColumn() { Width = 648000L };

            tableGrid1.Append(gridColumn1);
            tableGrid1.Append(gridColumn2);
            tableGrid1.Append(gridColumn3);
            tableGrid1.Append(gridColumn4);
        }
        table.Append(tableProperties);
        table.Append(tableGrid1);

        // Instantiate the table header row 
        D.TableRow tableHRow = new D.TableRow() { Height = 0L };
        for (int column = 0; column < dtData.Columns.Count; column++)
        {
            tableHRow.Append(CreateTextCell(dtData.Columns[column].ToString()));
        }
        table.Append(tableHRow);

        // Instantiate the table data row 
        for (int row = 0; row < dtData.Rows.Count; row++)
        {
            // Instantiate the table row 
            D.TableRow tableRow = new D.TableRow() { Height = 0L };
            for (int column = 0; column < dtData.Columns.Count; column++)
            {
                tableRow.Append(CreateTextCell(dtData.Rows[row][column].ToString()));
            }
            table.Append(tableRow);
        }
        return table;
    }

    /// <summary> 
    /// Create table cell with the below order: 
    /// a:tc(TableCell)->a:txbody(TextBody)->a:p(Paragraph)->a:r(Run)->a:t(Text) 
    /// </summary> 
    /// <param name="text">Inserted Text in Cell</param> 
    /// <returns>Return TableCell object</returns> 
    private D.TableCell CreateTextCell(string text)
    {
        if (string.IsNullOrEmpty(text))
        {
            text = string.Empty;
        }

        // Declare and instantiate the table cell  
        // Create table cell with the below order: 
        // a:tc(TableCell)->a:txbody(TextBody)->a:p(Paragraph)->a:r(Run)->a:t(Text) 
        D.TableCell tableCell = new D.TableCell();

        //  Declare and instantiate the text body 
        D.TextBody textBody = new D.TextBody();
        D.BodyProperties bodyProperties = new D.BodyProperties();
        D.ListStyle listStyle = new D.ListStyle();

        D.Paragraph paragraph = new D.Paragraph();
        D.Run run = new D.Run();
        D.RunProperties runProperties = new D.RunProperties() { Language = "en-US", Dirty = false, FontSize = 800 };
        D.Text text2 = new D.Text();
        text2.Text = text;

        run.Append(runProperties);
        run.Append(text2);
        D.EndParagraphRunProperties endParagraphRunProperties = new D.EndParagraphRunProperties() { Language = "en-US", Dirty = false, FontSize = 700 };

        paragraph.Append(run);
        paragraph.Append(endParagraphRunProperties);
        textBody.Append(bodyProperties);
        textBody.Append(listStyle);
        textBody.Append(paragraph);

        D.TableCellProperties tableCellProperties = new D.TableCellProperties();
        tableCell.Append(textBody);
        tableCell.Append(tableCellProperties);

        return tableCell;
    }

    #endregion

    #endregion

好吧,所以我找不到生成多个表的方法。我所做的是将占位符放在 tempaltes 表中,并将占位符替换为中的值

SlidePart.Slide.InnerXml
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

无法使用 openxml 在 PPT 报告中生成第二个表 的相关文章

  • 更改文本框中文本的前景色和背景色

    我正在使用 VB NET 制作 C 代码编辑器应用程序 我想在用户键入关键字时更改关键字的颜色 另外 我正在寻找一种方法来突出显示某些代码行 有没有办法更改文本框或富文本框中一段文本的前景色和背景色 我真的不知道你想做什么 所以这里有一些选
  • 如何通过MFC将应用程序设置保存到注册表中?

    我有一个由 MFC 项目向导创建的 MFC 应用程序 我想在注册表中保存 读取应用程序设置 所以问了这个question https stackoverflow com questions 1880275 good c registry w
  • 如何让 CMake 为目标安装 PDB 文件

    如何让 CMake 安装调试 Visual Studio 生成的 DLL 文件和 EXE 文件所需的配套 PDB 文件 我已经挣扎了一段时间 试图找到这个问题的一个好的答案 我现在认为我找到了一个 使用安装文件命令
  • SIGKILL 和 SIGSTOP 信号无法被捕获、阻止或忽略,为什么?

    我想知道为什么这两个信号在一个进程中不能被捕获 阻止或忽略 可以使用 signal 更改其余信号的操作 这两个信号和其余信号有什么区别 如果您谈论它们被阻止的原因 那么原因已经提到了 Adam B https stackoverflow c
  • 为什么 C++ Concepts TS 中同时存在变量和函数概念?

    我一直在看 C 1zN4377 http www open std org jtc1 sc22 wg21 docs papers 2015 n4377 pdfGCC 6 中正在实现的概念 TS 草案 我不明白拥有两种不同概念的目的 变量概念
  • 如何从头开始重复C程序并清理屏幕和第一个输入值?

    我是编程新手 我写了一个简单的程序 我想一次又一次地重复该程序 并且只有当用户想要退出时它才能退出 这是我的程序 include
  • 当 TestCase 包含数组时,NUnit 无法识别该 TestCase

    这是我在 NUnit 中遇到的非常简单但烦人的行为 我有一些这样的测试 Test TestCase 1 2 hello TestCase 3 5 goodbye public void MyClass MyMethod int a int
  • DPI 图形屏幕分辨率像素 WinForm PrintPageEventArgs

    对于运行我的应用程序的任何显示器 Dpi 点与像素有何关系 int points Screen primary public Form1 InitializeComponent points 1 primary null void OnPa
  • Mono 和 WebRequest 速度 - 测试

    在 mono 4 6 2 linux 中 我注意到 wget 下载文件的速度与webclient DownloadString 所以我做了一个小测试来调查 为什么 wget 明显比 C 快 根据我自己的实验 使用 wget 下载 手动读取文
  • ReportViewer“缺少 URL 参数:名称”

    在一个网络应用程序中 我正在处理 ReportViewer 时不断出现错误 缺少 URL 参数 名称 我找到了原因 但没有找到解决方案 导致报告查看器出现异常的 url Reserved ReportViewerWebControl axd
  • WinForms TreeView - 如何手动“突出显示”节点(就像被单击一样)

    我需要知道如何让以编程方式选择的节点以图形方式处于 选定 状态 就像用户单击它一样 SelectedNode 仅使这一节点在内部被选中 非常感谢 它没有显示为突出显示的原因是由于树视图没有焦点 这是我的测试表单上的按钮单击事件 TreeVi
  • VBA Office2010 Shapes.PasteSpecial 失败

    我在将 VBA 代码从 Office2003 迁移到 Office2010 时遇到问题 我想将单元格 Excel 的文本复制到Powerpoint Office2003生成了一个新的文本框 文本样式与Excel中相同 现在我的代码在 Off
  • 弹出窗口或弹出窗口显示附加信息

    我想在我的应用程序顶部显示带有附加信息的弹出窗口 我的信息是Listview大约 500 个项目我都尝试过 有问题flyout gt 它里面可能有scrollViewer 所以我的列表视图不能正确虚拟化 其他一切都可以 有我的代码 Flyo
  • 如何在 Datagridview 中为图像列提供超链接

    如何在winforms中超链接到DataGridViewImageColumn OP 评论中的代码示例 DataGridView dgv new DataGridView dgv Name dgv i dgv DataSource dsMa
  • 最佳实践:从属性中抛出异常

    什么时候适合从属性 getter 或 setter 中抛出异常 什么时候不合适呢 为什么 关于这个主题的外部文档的链接会很有帮助 谷歌搜索结果出奇的少 Microsoft 在以下位置提供了有关如何设计属性的建议 http msdn micr
  • STL(标准模板库)中使用的设计模式

    我正在学习STL和设计模式 我想知道是否有任何文档或链接可以解释如何在 STL 中实现设计模式 我做了谷歌但无法获得太多数据 我希望你的意思是 哪些设计模式可以在STL中识别 STL 堆栈是一个容器适配器 适配器是一种设计模式 迭代器也是一
  • 在 C 或 C++ 中使用逗号作为宏名称

    我想做这样的事情 define define MAX 10 000 000 undef 有什么技巧可以做到吗 编辑 我知道 C 14 中的数字分隔符 我正在寻找一种技巧来对不兼容的编译器执行相同的操作 EDIT2 请考虑Variadic M
  • 使用 CryptUnprotectData 解密 WEP wlan 配置文件密钥

    我正在尝试使用解密 WEP 配置文件的密钥加密解除数据保护 http msdn microsoft com en us library windows desktop aa380882 28v vs 85 29 aspx 我获取配置文件密钥
  • C# 中 WinForm TextBox 中数字的按键事件

    我想限制用户在文本框中仅输入数字 我在按键事件中添加此代码 private void txtPartID KeyPress object sender KeyPressEventArgs e if e KeyChar gt 0 e KeyC
  • 提高批量请求的野兽内存使用率

    我运行这个boost beast 客户端 异步 ssl http www boost org doc libs develop libs beast example http client async ssl http client asy

随机推荐

  • 在 Linux 上的 makefile 和 Makefile 之间进行选择

    我想在一个目录中同时使用 Makefile 和 makefile 进行 make 默认情况下 它将执行makefile 我可以选择执行 Makefile 吗 提前致谢 最简单的选择是使用 f make f Makefile From man
  • 如何在 github 提交中设置用户名别名?

    我刚刚在大学读完一个学期 决定将我的所有项目从 bitbucket 我的课程所需 导入到 github 我所有其他项目都在其中 我成功导入了它们 不幸的是 当我从事这些项目时 我在三台不同的计算机之间切换 因此 提交历史记录中有许多我自己所
  • 在 Cygwin 中启用 Postgresql

    我安装了Cygwin与 Perl 和Postgresql已启用软件包 然后输入 usr bin cygserver config This will install the service 然后输入 net start cygserver
  • set()是如何实现的?

    我见过有人这么说setpython 中的对象具有 O 1 成员资格检查 他们如何在内部实施以实现这一点 它使用什么类型的数据结构 该实施还有哪些其他影响 这里的每个答案都非常有启发性 但我只能接受一个 所以我将选择最接近我原来问题的答案 谢
  • 您能否推荐一个 JQuery 插件来组成一组可映射到 SQL 查询的条件? [关闭]

    Closed 此问题正在寻求书籍 工具 软件库等的推荐 不满足堆栈溢出指南 help closed questions 目前不接受答案 我发现了http redquerybuilder appspot com http redquerybu
  • 在内存无法容纳的大文件中查找“n”个最重复的单词/字符串

    我想验证我的伪代码 建议优化和更好的方法 最重复的单词 按排名 此处的排名定义了您要选择的排名 即前 X 个最重复的单词 外部按字母顺序对所有文件进行排序 下列的这里提到的算法 http www tcs fudan edu cn rudol
  • Javascript 已禁用,简短的问题

    只是一些关于 javascript 和网站的简短问题 1 通过启用 javascript 是否意味着在浏览器设置中安装并启用了 sun java 或者每个浏览器都始终启用 JavaScript 吗 2 如果禁用 javascript 我的网
  • PL/SQL 中的 BEGIN - END 块原子事务

    这些信息应该很容易找到 但我没有任何运气 当我有一个BEGIN ENDPL SQL 中的块 它是否表现为原子事务 它将尝试在命中时提交END阻止 如果出现问题会回滚更改吗 如果不是 我如何确保 BEGIN END 块内的代码的行为类似于原子
  • 删除记录时出现SystemStackError(堆栈级别太深)

    删除记录时出现 Stack Overflow 错误 SystemStackError 堆栈级别太深 应用程序 控制器 orders controller rb 18 在 销毁 中 我发现了另一个与 ruby 相关的系统堆栈错误 但我没有完全
  • .NET中的文档管理系统[关闭]

    Closed 这个问题正在寻求书籍 工具 软件库等的推荐 不满足堆栈溢出指南 help closed questions 目前不接受答案 有谁知道可以与 NET集成的文档管理系统 或模块 Thanks 以下是当今企业中一些最常见的 DMS
  • CentOs Php 和 MySql 配置

    我已经安装了 php 并运行了一段时间 但我开始从事一个连接到数据库 即 mysql 的项目 所以我安装了 mysql 5 1 73 现在当我使用它连接到数据库时线 dbhandle mysql connect hostname usern
  • 作用域类型变量需要显式 foralls。为什么?

    如果你想使用 GHC词法作用域类型变量 http www haskell org ghc docs 7 6 2 html users guide other type extensions html scoped type variable
  • Spring Data JPA 中使用 @Query 进行动态查询?

    我在 Spring Boot 应用程序中使用规范 可以通过不同的过滤器选项过滤结果 但是 我需要使用特殊的过滤器 Query在我的存储库方法中 据我所知 我无法在此查询中构建动态 WHERE 子句 还有 QueryDSL 和 Criteri
  • Swift 计算属性上的 KVO

    Swift 中计算属性上的 KVO 可行吗 var width 0 var height 0 private var area Double get return with height self addOberser self forKe
  • 如何从 netbeans 远程调试 jar

    我正在尝试弄清楚如何调试远程运行的 jar 这是我的场景 我的 jar 将从 VPS 运行 这个jar基本上运行一个服务器 对于游戏 所以它还连接到 mysql 数据库 我使用 3 个 bat 文件启动服务器 如下所示 设置 CLASSPA
  • Python:Pycharm 运行时

    我目睹了 PyCharm 的一些奇怪的运行时问题 解释如下 该代码已在具有 20 个内核和 256 GB RAM 的机器上运行 并且有足够的空闲内存 我没有展示任何实际功能 因为它是一个相当大的项目 但我非常乐意根据要求添加详细信息 简而言
  • 为什么不建议将常量存储在单独的类中?

    有人告诉我 我在其他一些地方也看到过这种说法 不建议将常量存储在 Java 中的单独类中 以便在其他类中使用它们 但我没有看到任何地方为什么会这样 我不应该将它们存储在自己的接口 类中的原因是什么 我从 C 转到 Java 在 C 中我只想
  • 将图像上传到服务器 PHP Android

    我现在迷失了尝试将图像上传到我的服务器 我可以在 Android 设备上拍照并获取我的位置 我有以下代码将文件上传到服务器 public Boolean postFunction File image String tag postFunc
  • Javascript/jQuery/等中测量经过时间/一段时间后触发事件的方法

    我正在尝试使用 HTML5 Javascript 制作一个简单的游戏 我想对活动施加时间限制 例如 当玩家进入一个屋顶正在向他们逼近的房间时 我想给他们一些时间来做出决定 然后自动发生其他事件 但是 如果他们做出决定 我根本不希望触发定时功
  • 无法使用 openxml 在 PPT 报告中生成第二个表

    我有这个代码 我能够完美地生成带有文本数据的 pptx 报告 我在这份报告中还有 4 个表格 其中包含动态数据 我可以在 PPT 中生成一张表格 但无法生成多个表格 Requirement On the right I have 4 tab