目錄 (TOC) 是 Word 文檔的重要組成部分。它提供了文檔內容的概覽,並允許您快速導航到所需的部分。您可能會發現自己處於需要以編程方式從 Word 文檔中添加、提取、更新或刪除目錄的情況。為此,本文將教您如何使用 C++ 處理 Word 文件中的目錄。

用於在 Word 文檔中處理目錄的 C++ API

Aspose.Words for C++ 是一個本地 C++ 庫,允許您創建、讀取、修改和轉換 Microsoft Word 文檔。此外,它還支持使用 Word 文件中的目錄。您可以通過 NuGet 安裝 API 或直接從 下載 部分下載。

PM> Install-Package Aspose.Words.Cpp

在 Word 文檔中添加目錄

以下是在 Word 文檔中添加目錄的步驟。

以下示例代碼顯示瞭如何使用 C++ 在 Word 文檔中添加目錄。

// 源和輸出目錄路徑。
System::String sourceDataDir = u"SourceDirectory\\";
System::String outputDataDir = u"OutputDirectory\\";

// 加載Word文件
System::SharedPtr<Document> doc = System::MakeObject<Document>(sourceDataDir + u"Sample 5.docx");

// 創建 DocumentBuilder 類的實例
System::SharedPtr<DocumentBuilder> builder = System::MakeObject<DocumentBuilder>(doc);

// 在文檔的開頭插入目錄。
builder->InsertTableOfContents(u"\\o \"1-3\" \\h \\z \\u");

// 新插入的目錄最初是空的。
// 它需要通過更新文檔中的字段來填充。
doc->UpdateFields();

// 輸出文件路徑
System::String outputPath = outputDataDir + u"AddTOC.docx";

// 保存 Word 文件
doc->Save(outputPath);
包含目錄的輸出 Word 文件

包含目錄的輸出 Word 文件

從 Word 文檔中提取目錄

以下是從 Word 文檔中提取目錄的步驟。

以下示例代碼演示瞭如何使用 C++ 從 Word 文檔中提取目錄。

// 源目錄
System::String inputDataDir = u"SourceDirectory\\";

// 加載Word文件
System::SharedPtr<Document> doc = System::MakeObject<Document>(inputDataDir + u"SampleTOC.docx");

// 遍歷字段
for (System::SharedPtr<Field> field : System::IterateOver(doc->get_Range()->get_Fields()))
{
	// 獲取 FieldHyperlink 字段
	if (field->get_Type() == FieldType::FieldHyperlink)
	{
		System::SharedPtr<FieldHyperlink> hyperlink = System::DynamicCast<FieldHyperlink>(field);

		// 檢查字段是否屬於目錄
		if (hyperlink->get_SubAddress() != nullptr && hyperlink->get_SubAddress().StartsWith(u"_Toc"))
		{
			System::SharedPtr<Paragraph> tocItem = System::DynamicCast<Paragraph>(field->get_FieldStart()->GetAncestor(NodeType::Paragraph));
			std::cout << System::StaticCast<Node>(tocItem)->ToString(SaveFormat::Text).Trim().ToUtf8String() << std::endl;
			std::cout << "------------------" << std::endl;
			if (tocItem != nullptr)
			{
				System::SharedPtr<Bookmark> bm = doc->get_Range()->get_Bookmarks()->idx_get(hyperlink->get_SubAddress());

				// 獲取此目錄項指向的位置
				System::SharedPtr<Paragraph> pointer = System::DynamicCast<Paragraph>(bm->get_BookmarkStart()->GetAncestor(NodeType::Paragraph));
				std::cout << System::StaticCast<Node>(pointer)->ToString(SaveFormat::Text).ToUtf8String() << std::endl;
			}
		}
	}
}

更新 Word 文檔中的目錄

如果文檔的內容已更新,並且您需要在目錄中反映這些更改,您只需加載 Word 文件並調用 Document->UpdateFields() 方法即可。該方法會根據修改後的內容更新目錄。在此之後,保存更新的 Word 文檔。

從 Word 文檔中刪除目錄

以下是從 Word 文檔中刪除目錄的步驟。

以下示例代碼顯示如何使用 C++ 從 Word 文檔中刪除目錄。

void RemoveTableOfContents(const System::SharedPtr<Document>& doc, int32_t index)
{
	// 將 TOC 字段的 FieldStart 節點存儲在文檔中以便快速訪問。
	std::vector<System::SharedPtr<FieldStart>> fieldStarts;
	// 這是一個列表,用於存儲在指定目錄中找到的節點。他們將被刪除
	// 在這個方法的最後。
	std::vector<System::SharedPtr<Node>> nodeList;

	for (System::SharedPtr<FieldStart> start : System::IterateOver<System::SharedPtr<FieldStart>>(doc->GetChildNodes(NodeType::FieldStart, true)))
	{
		if (start->get_FieldType() == FieldType::FieldTOC)
		{
			// 添加所有類型為 FieldTOC 的 FieldStarts。
			fieldStarts.push_back(start);
		}
	}

	// 確保傳遞的索引指定的 TOC 存在。
	if (index > fieldStarts.size() - 1)
	{
		throw System::ArgumentOutOfRangeException(u"TOC index is out of range");
	}

	bool isRemoving = true;

	// 獲取指定 TOC 的 FieldStart。
	System::SharedPtr<Node> currentNode = fieldStarts[index];

	while (isRemoving)
	{
		// 將這些節點存儲起來,以後一次性全部刪除比較安全。
		nodeList.push_back(currentNode);
		currentNode = currentNode->NextPreOrder(doc);

		// 一旦我們遇到 FieldTOC 類型的 FieldEnd 節點,我們就知道我們到了最後
		// 當前的 TOC,我們可以在這裡停止。
		if (currentNode->get_NodeType() == NodeType::FieldEnd)
		{
			System::SharedPtr<FieldEnd> fieldEnd = System::DynamicCast<FieldEnd>(currentNode);
			if (fieldEnd->get_FieldType() == FieldType::FieldTOC)
			{
				isRemoving = false;
			}
		}
	}

	// 刪除在指定目錄中找到的所有節點。
	for (System::SharedPtr<Node> node : nodeList)
	{
		node->Remove();
	}
}

int main()
{
	// 源和輸出目錄路徑。
	System::String sourceDataDir = u"SourceDirectory\\";
	System::String outputDataDir = u"OutputDirectory\\";

	// 打開 Word 文檔
	System::SharedPtr<Document> doc = System::MakeObject<Document>(sourceDataDir + u"SampleTOC.docx");

	// 從文檔中刪除第一個目錄。
	RemoveTableOfContents(doc, 0);

	// 輸出文件路徑
	System::String outputPath = outputDataDir + u"RemoveTOC.docx";

	// 保存 Word 文件
	doc->Save(outputPath);
}

獲得免費許可證

您可以通過申請 免費的臨時許可證 來試用沒有評估限制的 API。

結論

在本文中,您了解瞭如何使用 C++ 使用 Word 文檔中的目錄。您已經看到了從 Word 文檔中添加、提取、更新和刪除目錄所需的步驟和示例代碼。 Aspose.Words for C++ 提供了許多用於處理 Word 文件的附加功能。您可以通過訪問 官方文檔 來詳細探索 API。如有任何疑問,請隨時通過我們的 免費支持論壇 與我們聯繫。

也可以看看