トップ 差分 一覧 ソース 置換 検索 ヘルプ PDF RSS ログイン

JasperReports と iReport

http://www.ponpo.com/jrs/jpn/intoro.html
http://jasperforge.org/jaspersoft/opensource/business_intelligence/ireport/index.php
http://itextpdf.sourceforge.net/

iReportの起動オプション

-cp:p D:\data\Development_tools\java\JDBC\oracle\ojdbc6.jar

でクラスパスを指定して起動できる。

iReport & JasperReports で日本語を表示する方法

 フォントをPDFに埋め込まない方法

注意点

半角文字列の長さが正しく計算されないことがあるので注意。
個人的にはフォントをPDFに埋め込む方法を推奨する。

iTextAsian.jarを取得

http://itextpdf.sourceforge.net/
から iTextAsian.jar をダウンロード
※必要に応じて iTextAsianCmaps.jar もダウンロードする
iTextAsian.jar(806)
iTextAsianCmaps.jar(992)
コンパイルの時にクラスパスに追加するく

iReport で Pdf Font name を設定する

HeiseiKakuGo-W5 ゴシック
HeiseiMin-W3 明朝

のいずれか

iReport で Pdf Encoding の設定する

UniJIS-UCS2-H Adobe-Japan1のUnicodeエンコーディング
UniJIS-UCS2-V UniJIS-UCS2-Hの縦書きエンコーディング
UniJIS-UCS2-HW-H UniJIS-UCS2-Hと同じ、ただし英文字を半角に置き換える
UniJIS-UCS2-HW-V UniJIS-UCS2-HW-Hの縦書きエンコーディング

のいずれか

 PDF にフォントを埋め込む方法(Font extentionを使う)

説明

http://d.hatena.ne.jp/dojum/20121108
http://dev.classmethod.jp/server-side/java/jasperreports-tutorial/

PDFにフォントを埋め込む方法で現在推奨されている方法。
PDF font nameや Pdf encoding は非推奨になっている。

iReportへのフォント追加

  • ツール -> オプションを選択
  • iReport -> Fonts タブを選択


  • フォントを選択する


  • PDF用フォントの設定


ここで選んだフォントはiReportのディレクトリ以下のfontsディレクトリへコピーされる。

iReport でフォントを指定する


PDF Font NameやPDF Encoding はいじらなくてよい。

jasperreports Font extention の設定

以下の2つのファイルを作成する。
これらのファイルはiReportのfontsディレクトリに作成されているので、
自分で作成せずにコピーして編集しても良い。

jasperreports_extension.properties を作成して、
実行時のクラスパスが通ったパスへ配置する。
内容は、以下のとおり。
フォントを定義しているXMLのパスを指定する。

  • jasperreports_extension.properties
net.sf.jasperreports.extension.registry.factory.fonts=net.sf.jasperreports.engine.fonts.SimpleFontExtensionsRegistryFactory
net.sf.jasperreports.extension.simple.font.families.ireport=fonts/irfonts.xml

フォント定義のXMLを作成する。
記載内容は以下の通り。

  • irfonts.xml
 <?xml version="1.0" encoding="UTF-8"?>
 <fontFamilies>
    <fontFamily name="Consolas_Migu1M">
        <normal><![CDATA[Consolas_Migu1M-Regular.ttf]]></normal>
        <bold><![CDATA[Consolas_Migu1M-Bold.ttf]]></bold>
        <italic><![CDATA[Consolas_Migu1M-Italic.ttf]]></italic>
        <boldItalic><![CDATA[Consolas_Migu1M-BoldItalic.ttf]]></boldItalic>
        <pdfEncoding><![CDATA[Identity-H]]></pdfEncoding>
        <pdfEmbedded><![CDATA[true]]></pdfEmbedded>
    </fontFamily>
 
    <fontFamily name="IPA P明朝">
        <normal><![CDATA[ipamp.ttf]]></normal>
        <pdfEncoding><![CDATA[Identity-H]]></pdfEncoding>
        <pdfEmbedded><![CDATA[true]]></pdfEmbedded>
    </fontFamily>
 
 </fontFamilies>

jasperreports_extension.propertiesやフォント定義のXML、フォントファイルのパスはクラスパスから検索される。

 PDF にフォントを埋め込む方法(PDF Font Nameを直接指定する方法)

※推奨されていない

iReport で Pdf font name を設定する

フォントを埋め込む場合は、 Pdf font name に 埋め込むフォントのファイル名を書く

ipag.ttf

フルパスではなく、ファイル名(クラスパスからクラスローダが検索できるようなパス)を書く
フォントファイルがある場所はクラスパスに追加する

フォントは、クラスパスからクラスローダによって検索されるので
フォントのパスが

project/font/ipag.ttf

にあって、クラスパスが

project

に通っている場合、フォント名は

font/ipag.ttf

と指定する。

iReport で Pdf embedded を設定する

Pdf embeddedを

true

に設定する

iReport で Pdf encoding を設定する

Pdf encoding を
Identity-H 横書き
Identity-V 縦書き
に設定する

使い方

jasper_test.zip(1034) サンプル

新規レポートの設定

Expressionの記述言語を指定する。
もし、Expressionの記載言語をJavaにするには、レポートのプロパティのLanguageをJavaにする。


基本

  1. ソースからもらうパラメータ、フィールドを必要に応じて追加する
  2. 追加したパラメータ、フィールドを使ってTextFieldやサブフォーム、グラフを追加

※ソースコンパイル時にクラスが無いって表示されたときは、iReportのディレクトリ以下からjarファイルを探して、それっぽいjarファイルをクラスパスに追加。

  1. 罫線は、各TextFieldを右クリックして、borderを設定すると楽
    1. Lineを引いたり、rectangleで罫線を付けてもいいけど、borderのほうが楽

ソースからデータを渡す1

2次元配列からデータを出力するデータソースを作る

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
import java.util.HashMap;
import java.util.Map;

import net.sf.jasperreports.engine.JRField;
import net.sf.jasperreports.engine.JRRewindableDataSource;
import net.sf.jasperreports.engine.JRRuntimeException;

public class ArrayDataSource implements JRRewindableDataSource {
  private int currentRow;
  private Object[][] records;
  private Object[] currentRecord;
  private Map columnNamesMap = new HashMap();
  
  
  public ArrayDataSource(Object[][] records, String[] columnNames) {
    this.records = records;
    if (columnNames != null) {
      for (int i = 0; i < columnNames.length; i++) {
        columnNamesMap.put(columnNames[i], Integer.valueOf(i));
      }
    }
    currentRow = -1;
  }
  
  
  public boolean next() {
    currentRow++;
    
    return currentRow < records.length;
  }
  
  
  public Object getFieldValue(JRField jrField) {
    Integer fieldIndex = (Integer)columnNamesMap.get(jrField.getName());
    
    if (fieldIndex == null) {
      throw new JRRuntimeException("Field \"" + jrField.getName() + "\" not found in data source.");
    }
    
    return records[currentRow][fieldIndex.intValue()];
  }
  
  public void moveFirst() {
    currentRow = -1;
  }
 
  
}

出力する

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
import net.sf.jasperreports.engine.*;
import net.sf.jasperreports.engine.design.*;
import net.sf.jasperreports.view.JasperViewer;
import net.sf.jasperreports.engine.data.*;

import net.sf.jasperreports.engine.util.*; 
import net.sf.jasperreports.engine.xml.JRXmlLoader;
import java.util.*;
import java.io.*;

public class test2 {
  
  public static void main(String args[]){
    try{
      // JasperDesign jasperDesign = JRXmlLoader.load("report/report.jrxml");
      // JasperReport jasperReport = JasperCompileManager.compileReport(jasperDesign);
      JasperReport jasperReport = (JasperReport)JRLoader.loadObject("report/report.jasper");
      
      Map parameters = new HashMap();
      parameters.put("Title", "Basic JasperReport");
      parameters.put("MaxSalary", new Double(25000.00));
      
      
      String[] header = new String[] {"name","cost"};
      Object[][] data = new Object[3][2];
      data[0][0] = "test1";
      data[0][1] = "1000";
      data[1][0] = "test2";
      data[1][1] = "3000";
      data[2][0] = "てすと";
      data[2][1] = "4000";
      
      ArrayDataSource ds = new ArrayDataSource(data,header );
      JasperPrint jasperPrint = JasperFillManager.fillReport(jasperReport,
        parameters, ds);
      
      // You can use JasperPrint to create PDF
      JasperExportManager.exportReportToPdfFile(jasperPrint, "BasicReport.pdf");
      
    } catch (Exception e){
      e.printStackTrace();
    }
  }
}

ソースからデータを渡す2

3.7.6には ListOfArrayDataSource が追加された。

     String[] header = new String[] {"name","cost"};
     Vector vec = new Vector();
     vec.add(new Object[]{"test", "100"});
     vec.add(new Object[]{"test1","200"});
     vec.add(new Object[]{"あいうえお","200"});
     
     ListOfArrayDataSource ds = new ListOfArrayDataSource(vec,header );
     JasperPrint jasperPrint = JasperFillManager.fillReport(jasperReport,
       parameters, ds);

と言う風に使えるはず・・・。

ソースからデータを渡す3

Vector vec = new Vector();
HashMap map = new HashMap();
map.put("BU","001");
map.put("KA","A");
map.put("NAME","hoge");
map.put("COST",new Double(2));
vec.add(map);
     
map = new HashMap();
map.put("BU","001");
map.put("KA","A");
map.put("NAME","hoge2");
map.put("COST",new Double(2));
vec.add(map);

JRMapCollectionDataSource ds = new JRMapCollectionDataSource(vec);
JasperPrint jasperPrint = JasperFillManager.fillReport(jasperReport,
     parameters, ds);

※$F{BU} や $F{KA}などを使えるように、iReportでフィールドを追加する

サブレポート用のデータをソースから渡す

パラメータ用のMapに含めて渡してしまえばいい。

parameters.put("subdata",new JRMapCollectionDataSource(vec))

$P{subdata} を使えるように、iReportでパラメータを追加する

グラフの使い方

円グラフの場合はこんな感じ。

 vec = new Vector();
 map = new HashMap();
 map.put("項目","項目1");
 map.put("value",1);
 vec.add(map);
    
 map = new HashMap();
 map.put("項目","項目2");
 map.put("value",2);
 vec.add(map);

折れ線グラフの場合は

 vec = new Vector();
 map = new HashMap();
 map.put("項目","項目1");
 map.put("カテゴリ","カテゴリ1");
 map.put("value",1);
 vec.add(map);
 
 map = new HashMap();
 map.put("項目","項目1");
 map.put("カテゴリ","カテゴリ2");
 map.put("value",2);
 vec.add(map);
 
 map = new HashMap();
 map.put("項目","項目2");
 map.put("カテゴリ","カテゴリ1");
 map.put("value",1);
 vec.add(map);
 
 map = new HashMap();
 map.put("項目","項目2");
 map.put("カテゴリ","カテゴリ2");
 map.put("value",4);
 vec.add(map);

な感じでデータを送る。Series に項目nを設定すると、項目毎にグループ化を行って出力される。

プリンタ直印刷

     PrintRequestAttributeSet atts = new HashPrintRequestAttributeSet();
     atts.add(new NumberUp(2)); // Nアップの指定
     atts.add(new Copies(5)); // 部数の指定
     atts.add(MediaSizeName.ISO_A4); // サイズの指定
     atts.add(OrientationRequested.PORTRAIT); // 縦方向
     atts.add(SheetCollate.COLLATED); // ドキュメントを部単位で印刷コピー機でいうところのソート機能でしょうか?
     atts.add(Sides.DUPLEX); // 両面印刷
     
     PrintServiceAttributeSet atts2 = new HashPrintServiceAttributeSet();
     atts2.add(new PrinterName("PDF Printer",Locale.getDefault()));
     
     JRExporter exporter = new JRPrintServiceExporter();
     exporter.setParameter(JRExporterParameter.JASPER_PRINT, jasperPrint);
     exporter.setParameter(JRPrintServiceExporterParameter.PRINT_REQUEST_ATTRIBUTE_SET, atts);
     exporter.setParameter(JRPrintServiceExporterParameter.DISPLAY_PAGE_DIALOG, Boolean.FALSE);
     exporter.setParameter(JRPrintServiceExporterParameter.DISPLAY_PRINT_DIALOG, Boolean.TRUE);
     exporter.setParameter(JRPrintServiceExporterParameter.PRINT_SERVICE_ATTRIBUTE_SET, atts2);
     exporter.exportReport();

ページ数表示

http://74.125.153.132/search?q=cache:OrH57gRZFk4J:d.hatena.ne.jp/w650/20051101+jasperreports+%E3%83%9A%E3%83%BC%E3%82%B8%E6%95%B0&cd=1&hl=ja&ct=clnk&gl=jp
JasperReportにて各ページに“Page X of Y”(ex.1/2)みたいな記述を入れたい場合には、textField要素を二つ用意してそれぞれにPAGE_NUMBER変数を設定する。

そして現在ページ数のtextFieldには、evaluationTime="Now"とし、全体ページ数のtextFieldにはevaluationTime="Report"を指定する。

複数のレポ−トを1つレポ−トに結合する

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
  public static JasperPrint connectJasperPrint(List<JasperPrint> printList){
    JasperPrint basePrint = null;
    JasperPrint currentPrint = null;
    Iterator<JasperPrint> printIterator = printList.iterator();
    Iterator<JRPrintPage> pageIterator = null;
    
    while(printIterator.hasNext()){
      currentPrint = printIterator.next();
      if (basePrint == null){
        basePrint = currentPrint;
        continue;
      }
      
      pageIterator = currentPrint.getPages().iterator();
      while(pageIterator.hasNext()){
        basePrint.addPage(pageIterator.next());
      }
    }
    
    return basePrint;
  }

こんな感じで、ページを追加をする。
ただし、1ページ目のサイズに固定されるので注意。

サイズの違うレポートを1つのPDFに結合する

1
2
3
4
5
6
7
8
9
10
  public static byte[] connectJasperPrintToPDF(List<JasperPrint> printList) throws Exception {
    ByteArrayOutputStream outStream = new ByteArrayOutputStream();
    
    JRPdfExporter jrPdfExporter = new JRPdfExporter();
    jrPdfExporter.setParameter(JRExporterParameter.OUTPUT_STREAM, outStream);
    jrPdfExporter.setParameter(JRExporterParameter.JASPER_PRINT_LIST, printList);
    jrPdfExporter.exportReport();
    
    return outStream.toByteArray();
  }

http://gendosu.jp/redmine/projects/25/wiki/JasperReports-%E3%82%B5%E3%82%A4%E3%82%BA%E3%81%AE%E9%81%95%E3%81%86%E7%94%A8%E7%B4%99%E3%82%84%E3%80%81%E7%94%A8%E7%B4%99%E6%96%B9%E5%90%91%E3%81%AE%E9%81%95%E3%81%86%E7%89%A9%E3%82%92%E5%8D%98%E4%B8%80%E3%81%AEPDF%E3%81%A8%E3%81%97%E3%81%A6%E5%87%BA%E5%8A%9B%E3%81%99%E3%82%8B%E3%81%AB%E3%81%AF?version=2

テキストフィールドを自動的に折り返す

テキストフィールドでWordWrap機能を有効にすることができる。
http://stackoverflow.com/questions/10631806/jasperreport-wrap-text-to-show-long-text-in-textfield

Stretch With Overflow

を有効にすれば、自動的に折り返す。

また、枠(rectangle)に対しても stretchType を RelativeToBandHeight にすることで自動的に高さを変えることができる。

For rectangle :

       <rectangle>
           <reportElement stretchType="RelativeToBandHeight" ... />
       </rectangle>

For textField :

       <textField isStretchWithOverflow="true">
           ...
       </textField>


改行位置がずれる場合

http://kenichiro22.hatenablog.com/entry/20101208/1291779030
PDFを出力する際に、文字の改行位置がおかしくなることがある。
フォントやバージョンに左右されるような気がするが、詳しいことは不明。

解決策としてはJRPdfExporterのパラメータ"FORCE_LINEBREAK_POLICY"をtrueする。
(バージョンによってはパラメータの設定方法が変わっているかも)

JRExporter exporter = new JRPdfExporter();
exporter.setParameter(JRPdfExporterParameter.FORCE_LINEBREAK_POLICY, Boolean.TRUE);

または、jrxmlファイルにpropertyを追加します。

<property name="net.sf.jasperreports.export.pdf.force.linebreak.policy" value="true"/>




[カテゴリ: プログラミング言語 > Java]

[通知用URL]



  • Hatenaブックマークに追加
  • livedoorクリップに追加
  • del.icio.usに追加
  • FC2ブックマークに追加

最終更新時間:2017年04月27日 23時24分56秒