Apache POI 可以应用 Top 10 条件格式吗?

Can Apache POI apply Top 10 conditional formatting?

我已经创建了 excel 文件,例如 createConditionalFormattingRule 具有不同的类型,例如如果单元格值等于另一个:

XSSFConditionalFormattingRule my_rule1 = ContedFormat.createConditionalFormattingRule(ComparisonOperator.EQUAL, "$M$" + (CountRower + 1));

但我的问题是,有一种条件格式用于 select 喜欢反悔的前 10 个值。

Apache POI 可以创建这种吗?

编辑:我发现类似的东西:

CTConditionalFormatting TopScall = 
sheet.getCTWorksheet().addNewConditionalFormatting();
TopScall.setSqref(my_range);

CTCfRule myCFRule = TopScall.addNewCfRule();
myCFRule.setType(STCfType.TOP_10);
myCFRule.setPriority(1);

我试过添加 Formily 卷,但没有格式,值为 0

这是关于 Conditional Formatting Color Scale 的示例,我想做的是类似的事情,但我需要前 10 个

而不是色阶

当前 Apache poi 5.0.0 SheetConditionalFormatting 没有为前 10 名创建 ConditionalFormattingRule 的方法。但它有 SheetConditionalFormatting.createConditionalFormattingColorScaleRule()。因此,您使用基础 org.openxmlformats.schemas.spreadsheetml.x2006.main.* 类 创建色阶规则的链接示例已过时。

但是top 10的规则设置比色阶规则设置要复杂的多。对于色阶规则,所有设置都在 sheet 的 CTConditionalFormatting 中。对于前 10 条规则,需要使用填充模式格式。该模式格式链接到工作簿的样式部分。

所以最好的方法是为前 10 名创建一个 XSSFConditionalFormattingRule,它设置类型 STCfType.TOP_10 和排名。 ConditionalFormattingRule 已经提供了一种创建模式格式的方法。

不幸的是 XSSFConditionalFormattingRule 的构造函数不是 public 以及获取 CTCfRule 的方法。所以需要用到反射。

以下完整示例提供 XSSFConditionalFormattingRule createConditionalFormattingRuleTop10(XSSFSheetConditionalFormatting sheetCF, int rank) 为前 10 名创建 XSSFConditionalFormattingRule 给定特殊排名。所有其他内容就像 Busy Developers' Guide to HSSF and XSSF Features - Conditional Formatting.

中描述的用于创建条件格式的默认内容
import org.apache.poi.ss.usermodel.*;
import org.apache.poi.xssf.usermodel.*;

import org.apache.poi.ss.util.CellRangeAddress;

import org.openxmlformats.schemas.spreadsheetml.x2006.main.*;

import java.lang.reflect.Field;
import java.lang.reflect.Constructor;

import java.io.FileOutputStream;

public class CreateXSSFConditionalFormattingTop10 {

 static XSSFConditionalFormattingRule createConditionalFormattingRuleTop10(XSSFSheetConditionalFormatting sheetCF, int rank) throws Exception {
  Field _sheet = XSSFSheetConditionalFormatting.class.getDeclaredField("_sheet");
  _sheet.setAccessible(true);
  XSSFSheet sheet = (XSSFSheet)_sheet.get(sheetCF);
  Constructor constructor = XSSFConditionalFormattingRule.class.getDeclaredConstructor(XSSFSheet.class);
  constructor.setAccessible(true);
  XSSFConditionalFormattingRule rule = (XSSFConditionalFormattingRule)constructor.newInstance(sheet);
  Field _cfRule = XSSFConditionalFormattingRule.class.getDeclaredField("_cfRule");
  _cfRule.setAccessible(true);
  CTCfRule cfRule = (CTCfRule)_cfRule.get(rule);
  cfRule.setType(STCfType.TOP_10);
  cfRule.setRank(rank);
  return rule;
 }

 public static void main(String[] args) throws Exception {
  Workbook workbook = new XSSFWorkbook(); String filePath = "./CreateXSSFConditionalFormattingTop10.xlsx";

  Sheet sheet = workbook.createSheet();

  java.util.Random random = new java.util.Random();
  for (int r = 0; r < 100; r++) {
   sheet.createRow(r).createCell(0).setCellValue(random.nextInt(100)+r);
  }

  SheetConditionalFormatting sheetCF = sheet.getSheetConditionalFormatting();
  if (sheetCF instanceof XSSFSheetConditionalFormatting) {
   XSSFConditionalFormattingRule rule = createConditionalFormattingRuleTop10((XSSFSheetConditionalFormatting)sheetCF, 10);
   XSSFPatternFormatting fill = rule.createPatternFormatting();
   fill.setFillBackgroundColor(IndexedColors.LIGHT_GREEN.index);
   fill.setFillPattern(PatternFormatting.SOLID_FOREGROUND);

   XSSFConditionalFormattingRule[] cfRules = new XSSFConditionalFormattingRule[]{rule};

   CellRangeAddress[] regions = new CellRangeAddress[]{CellRangeAddress.valueOf("A1:A100")};

   sheetCF.addConditionalFormatting(regions, cfRules);
  }

  FileOutputStream out = new FileOutputStream(filePath);
  workbook.write(out);
  out.close();
  workbook.close();

 }
}