You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用PHP提取DOCX中全部加粗文本?现有方法仅提取到一个

解决PHP提取DOCX所有加粗文本的问题

问题根源

你遇到的问题是因为Word生成的document.xml中,加粗格式的标记不止<w:b/>这一种:

  • 除了空标签<w:b/>,还会生成带属性的<w:b w:val="true"/>
  • 部分加粗文本是通过字符样式/段落样式实现的(比如引用名为Bold的样式),这类文本不会直接包含<w:b>标签,而是通过<w:rStyle>引用样式定义

你的原代码仅用strstr($node,'<w:b/>')匹配空标签,自然会漏掉其他标记的加粗内容。

修正后的提取代码

使用DOMDocument+XPath解析,可以更精准识别所有加粗文本:

<?php
$folder = "sample";
$xmlFile = $folder . "/word/document.xml";

// 加载XML并忽略解析警告
$dom = new DOMDocument();
libxml_use_internal_errors(true);
$dom->load($xmlFile);
libxml_clear_errors();

// 注册DOCX的命名空间(必须,否则XPath无法找到节点)
$xpath = new DOMXPath($dom);
$xpath->registerNamespace('w', 'http://schemas.openxmlformats.org/wordprocessingml/2006/main');

$boldWords = [];

// 匹配两种加粗情况的字符块(w:r):
// 1. 直接包含有效加粗标签的run
// 2. 引用了含Bold字样样式的run
$rNodes = $xpath->query('//w:r[w:b[not(@w:val) or @w:val="true"] or w:rStyle[contains(@w:val, "Bold")]]');

foreach ($rNodes as $rNode) {
    // 提取当前run下所有文本节点内容
    $textNodes = $xpath->query('.//w:t', $rNode);
    $text = '';
    foreach ($textNodes as $tNode) {
        $text .= $tNode->nodeValue;
    }
    $trimmedText = trim($text);
    if (!empty($trimmedText)) {
        $boldWords[] = $trimmedText;
    }
}

echo "<pre>";
var_dump($boldWords);
echo "</pre>";
?>

代码说明

  1. 命名空间注册:DOCX的XML标签都属于http://schemas.openxmlformats.org/wordprocessingml/2006/main命名空间,必须注册后XPath才能正确定位节点
  2. XPath查询逻辑:
    • 匹配直接带有效加粗标签的run:<w:b>无属性(默认加粗)或w:val="true"
    • 匹配引用加粗样式的run:样式名称包含Bold(Word默认加粗样式名)
  3. 文本提取:每个加粗的字符块(w:r)可能包含多个<w:t>文本节点,需要拼接成完整文本

进阶补充(可选)

如果文档中使用了自定义加粗样式(名称不含Bold),需要额外解析word/styles.xml,提取样式的加粗属性,再关联到对应的run。示例逻辑:

  1. 加载styles.xml,解析所有包含<w:b w:val="true"/>的样式ID
  2. 在document.xml的XPath查询中,加入匹配这些样式ID的w:rStyle

内容的提问来源于stack exchange,提问作者Premlatha

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.22 02:09:09