2017-01-06 41 views
0

私はPOIには初心者ですが、奇妙な問題に直面しています。デフォルト値のセルにHSSFRichTextStringスタイルが適用されていません

各セルのフォントがArial(Font-size:6.5)に設定されたテンプレートxlsがあります。 私のアプリケーションでは、上記のデフォルトテンプレートを使用して新しいExcelレポートを生成しています。

Workbook workbook = new HSSFWorkbook(InputStream s); 

結果、新しいExcelは、[マイテンプレートxls]で指定されたすべてのプロパティ(フォントスタイル)を取得しました。

ここで、HSSFRichTextStringを使用して特定のセルに書き込むと、そのスタイルは適用されません。 テキストを含むセルに記載してください& numberテキストをArial &としてターミナルとして作成します。例えば、SS 123: SS:Arial、123:Terminal。 しかし、セルのArialすべてがArial Onlyとして書かれているため、私のセルはデフォルトのフォントスタイルを持っています。 &を123のセルで検査すると、そのフォントはTerminalとして描写されますが、ion reality appliedフォントはArial Onlyです。

private static HSSFRichTextString formatNumbersOfCellText(String outputString,Font numberFont, Font strFont){ 
    HSSFRichTextString formattedString = null; 
    try{ 
     if(null != outputString &&    !outputString.trim().equalsIgnoreCase("")){ 
      int lstIndexCalculated=0; 
      int startIndex ; 
      int endIndex; 
      String[] splittedArr = outputString.split("\\s"); 
      if(null != splittedArr && splittedArr.length > 0){ 
       formattedString = new HSSFRichTextString(outputString); 
       for (int i = 0; i < splittedArr.length; i++) { 

         if(lstIndexCalculated == 0){ 
          startIndex =  outputString.indexOf(splittedArr[i]); 
         }else{ 
          startIndex = outputString.indexOf(splittedArr[i],lstIndexCalculated); 
          if(lstIndexCalculated < startIndex){ 
           formattedString.applyFont(lstIndexCalculated,startIndex ,numberFont); 
          } 
         } 
         endIndex = startIndex + (splittedArr[i].length()); 
         lstIndexCalculated = endIndex; 
         if(isNumericField(splittedArr[i])){ 
          formattedString.applyFont(startIndex,endIndex ,numberFont); 
         }else{ 
          formattedString.applyFont(startIndex,endIndex ,strFont); 
         } 
         startIndex = 0; 
         endIndex = 0; 

       } 
       if(lstIndexCalculated != 0){ 
        return formattedString; 
       } 
      } 
     } 
    }catch(Exception e){ 
     return null; 
    } 
    return null; 

} 

ここで、1つの部分文字列のみに書式設定すると、正常に動作します。

RichTextString richString = new HSSFRichTextString("SS 123 SS"); 
richString.applyFont(0, 3, font1); 
cell.setCellValue(richString); 

これはうまく動作しますが、あなたはそこにターミナルフォントのための第一のリンク(有効なスタイル)で見ることができるように、以下の場合には、複数回反復することは問題に

RichTextString richString = new HSSFRichTextString("SS 123 SS"); 
richString.applyFont(0, 3, font1); 
richString.applyFont(3, 6, font2); 
richString.applyFont(6, 9, font1); 
cell.setCellValue(richString); 

Valid style My incorrect xls style

を与える場所キャラクター '1'のストライキの下にあります。 しかし、Arialでは、文字 '1'に対してアンダーストライキはありません。これは期待される動作です。 しかし、213.27がTerminalフォントとしてリボンで表示されたとしても、私の場合は2番目のリンク(私の不正確なxlsスタイル)のように私はそうではありません。画像内の文字「1」の間のdiffを参照してください。 これは私が参照しているものです

助けてください。私はそれによって完全にブロックされています。 ありがとうございます。

+1

をあなたはどのようにコードを表示してくださいそれ。 Btw .: https://poi.apache.org/spreadsheet/quick-guide.html#RichText –

+0

formattedString.applyFont(startIndex、endIndex、strFont);どこの開始/終了インデックスは、特定のフォントを適用する必要がある部分文字列ですか。 –

+0

今後の分析の結果、MS Excelはそのスタイルをコンテンツに適用しないことがわかりました。しかし、私が印刷プレビューをするとき、私はリッチテキストスタイルがコンテンツに適用されているのを見ることができます。どんな具体的な理由? –

答えて

1

間違っていることがわかりません。このような

enter image description here

コード::このようなSource.xls仮に

import org.apache.poi.ss.usermodel.*; 
import org.apache.poi.hssf.usermodel.HSSFRichTextString; 

import java.io.InputStream; 
import java.io.FileInputStream; 
import java.io.FileOutputStream; 

class ReadAndWriteRichText { 

public static void main(String[] args) { 
    try { 

    InputStream inp = new FileInputStream("Source.xls"); 
    Workbook wb = WorkbookFactory.create(inp); 

    Sheet sheet = wb.getSheetAt(0); 
    Row row = sheet.getRow(0); 
    Cell cell = row.getCell(0); 

    Font font1 = wb.getFontAt(cell.getCellStyle().getFontIndex()); 
    System.out.println(font1); 

    Font font2 = wb.createFont(); 
    font2.setFontName("Terminal"); 
    font2.setFontHeightInPoints(font1.getFontHeightInPoints()); 
    System.out.println(font2); 

    RichTextString richString = new HSSFRichTextString("SS 123 SS"); 
                 //^0 ^3 ^6 ^9 
    richString.applyFont(0, 3, font1); 
    richString.applyFont(3, 6, font2); 
    richString.applyFont(6, 9, font1); 
    cell.setCellValue(richString); 

    FileOutputStream fileOut = new FileOutputStream("Target.xls"); 
    wb.write(fileOut); 
    wb.close(); 

    } catch (Exception ex) { 
    } 
} 
} 

は、このようなTarget.xlsになります:

enter image description here

あなたが見る通り、123はフォントTerminalです。


、私が望んでいたとして動作するはずのコードを提供し、あなたの更新質問よると:「今私はそのスタイルをHSSFRichTextString使用して特定のセルへの書き込み時には適用されません」

import org.apache.poi.ss.usermodel.*; 
import org.apache.poi.hssf.usermodel.HSSFRichTextString; 

import java.io.InputStream; 
import java.io.FileInputStream; 
import java.io.FileOutputStream; 

class ReadAndWriteRichText { 

private static boolean isNumeric(String string) { 
    try { 
    double d = Double.parseDouble(string); 
    } catch(NumberFormatException nfe) { 
    return false; 
    } 
    return true; 
} 

private static RichTextString formatNumbersOfCellText(String outputString, Font numberFont, Font strFont) { 

    RichTextString richString = new HSSFRichTextString(outputString); 

    String[] tokens = outputString.split("\\s"); // splits on a single space, so possibly empty strings are in the array 

    int start = 0; 
    int end = 0; 
    for (int i = 0; i < tokens.length; i++) { 
    String token = tokens[i]; 
    end = start + token.length(); 

    if (i < tokens.length - 1) { 
    end = end + 1; // if not the last token, then take one character more than the length because of formatting the split-delimiter-space after the token 
    } 

    if (isNumeric(token)) { 
    richString.applyFont(start, end, numberFont); 
    } else { 
    richString.applyFont(start, end, strFont); 
    } 
    start = end; 
    } 

    return richString; 
} 

public static void main(String[] args) { 
    try { 

    InputStream inp = new FileInputStream("Source.xls"); 
    Workbook wb = WorkbookFactory.create(inp); 

    Font font1 = wb.createFont(); 
    font1.setFontName("Arial"); 
    font1.setFontHeightInPoints((short)26); 

    Font font2 = wb.createFont(); 
    font2.setFontName("Terminal"); 
    font2.setFontHeightInPoints((short)26); 

    Sheet sheet = wb.getSheetAt(0); 

    for (Row row : sheet) { 
    for (Cell cell : row) { 
    String cellValue = cell.getStringCellValue(); // all cells must be text cells 
    RichTextString richString = formatNumbersOfCellText(cellValue, font2, font1); 
    cell.setCellValue(richString); 
    } 
    } 

    FileOutputStream fileOut = new FileOutputStream("Target.xls"); 
    wb.write(fileOut); 
    wb.close(); 

    } catch (Exception ex) { 
    ex.printStackTrace(); 
    } 
} 
} 
+0

サンプルコードはありがとうございました。上記の質問に自分のセルの内容にリッチテキストの書式を適用するためのコードを追加しました。 –

+0

私はやってみたが、まだ運がなかった。 text/numberを選択するとexcelはそれぞれのフォントが適用されていることを示しますが、実際にはARIALフォントのみが適用されます。私が印刷プレビューを行うとき、私は正しい書式を見ます。 –

+0

セル全体のフォント(セル全体を選択するとリボンに表示される)とリッチテキストのフォントがセル内で実行されます(セルを編集するときにリボンに表示され、依存するカーソル位置または部分的選択)。リッチテキストのフォントはそこにありますが、セル全体が選択されている場合は表示されません。 –

関連する問題