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

如何在JavaScript中结合querySelectorAll与switch处理自定义data属性?

解决根据自定义data属性用switch处理元素的问题

你的核心问题是:之前用element.tagName.toLowerCase()拿的是元素的标签名(比如h2、div),但你要匹配的是data-printpdf-*这类自定义属性的后缀,两者完全不搭,所以switch分支根本触发不了。同时,表单元素(input、textarea)不能用textContent取内容,得用value,这也是你拿不到文本的原因。

下面是具体的修正方案:

1. 写个辅助函数,精准获取printpdf属性类型

遍历元素的所有属性,找到以data-printpdf-开头的那个,提取后面的部分作为switch的判断依据:

function getPrintPdfElementType(element) {
  for (const attr of element.attributes) {
    if (attr.name.startsWith('data-printpdf-')) {
      return attr.name.replace('data-printpdf-', '');
    }
  }
  return null; // 没找到匹配属性就跳过
}

2. 改写循环和switch逻辑

替换原来的elementType赋值,用上面的函数拿到属性类型,然后对应分支处理:

var elementsToPrint = document.querySelectorAll(
  '[data-printpdf-Cpv-response-div="true"], [data-printpdf-Cpv-div="true"], [data-printpdf-Cig-div="true"], [data-printpdf-h2="true"], [data-printpdf-span="true"], [data-printpdf-input="true"], [data-printpdf-textarea="true"], [data-printpdf-label="true"], [data-printpdf-div="true"], [data-printpdf-label-roleName-label="true"], [data-printpdf-label-procedure-label="true"], [data-printpdf-strong="true"]'
);

// 遍历元素生成PDF
for (var i = 0; i < elementsToPrint.length; i++) {
  var element = elementsToPrint[i];
  var printType = getPrintPdfElementType(element);
  if (!printType) continue; // 无匹配属性直接跳过

  switch (printType) {
    case 'h2':
      // h2的PDF样式和文本处理
      doc.setFont("Verdana", "bold");
      doc.setFontSize(12);
      var textParts = doc.splitTextToSize(element.textContent, pageWidth - 2 * margin);
      textParts.forEach((part) => {
        if (currentY + 5 > pageHeight - margin) {
          doc.addPage();
          currentY = margin;
        }
        doc.text(part, leftMargin, currentY);
        currentY += 10;
      });
      break;

    case 'span':
    case 'strong':
      // 普通文本元素的处理
      doc.setFont("Verdana", "normal");
      doc.setFontSize(10);
      var textParts = doc.splitTextToSize(element.textContent, pageWidth - 2 * margin);
      textParts.forEach((part) => {
        if (currentY + 5 > pageHeight - margin) {
          doc.addPage();
          currentY = margin;
        }
        doc.text(part, leftMargin, currentY);
        currentY += 8;
      });
      break;

    case 'input':
    case 'textarea':
      // 表单元素要取value而非textContent
      doc.setFont("Verdana", "normal");
      doc.setFontSize(10);
      var content = element.value || '无输入内容';
      var textParts = doc.splitTextToSize(content, pageWidth - 2 * margin);
      textParts.forEach((part) => {
        if (currentY + 5 > pageHeight - margin) {
          doc.addPage();
          currentY = margin;
        }
        doc.text(part, leftMargin, currentY);
        currentY += 8;
      });
      break;

    case 'Cpv-response-div':
    case 'Cpv-div':
      // 自定义div的特殊处理
      doc.setFont("Verdana", "italic");
      doc.setFontSize(10);
      var textParts = doc.splitTextToSize(element.textContent, pageWidth - 2 * margin);
      textParts.forEach((part) => {
        if (currentY + 5 > pageHeight - margin) {
          doc.addPage();
          currentY = margin;
        }
        doc.text(part, leftMargin, currentY);
        currentY += 8;
      });
      break;

    // 其他属性类型的分支可以继续添加
    default:
      // 默认处理逻辑,兜底用
      doc.setFont("Verdana", "normal");
      doc.setFontSize(10);
      var content = element.textContent || element.value || '';
      var textParts = doc.splitTextToSize(content, pageWidth - 2 * margin);
      textParts.forEach((part) => {
        if (currentY + 5 > pageHeight - margin) {
          doc.addPage();
          currentY = margin;
        }
        doc.text(part, leftMargin, currentY);
        currentY += 8;
      });
  }
}

重点提醒

  • 表单元素(input、textarea)必须用element.value获取内容,textContent拿不到用户输入的值。
  • 如果一个元素同时有多个data-printpdf-*属性,上面的辅助函数会返回第一个匹配的;如果需要处理多属性,可以改成返回属性数组再逐个处理。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.05 22:14:53