- PR -

Jtableの印刷

投稿者投稿内容
モンプチ
常連さん
会議室デビュー日: 2004/06/03
投稿数: 28
投稿日時: 2004-06-22 10:47
再び失礼します。
この掲示板で皆様から的確な御指導頂き、深く感謝しております。

印刷の件でわからない事があります。
JTABLEを表示した内容ごと印刷したいのですが、エラーになってしまいます。
ソースを以下に記述します。

public void printTable(Component comp) throws Exception
{
// 印刷要求属性のセットに対するインタフェース、
// つまり PrintRequestAttribute インタフェースを実装する印刷属性を指定
PrintRequestAttributeSet pras = new HashPrintRequestAttributeSet();
DocFlavor flavor = DocFlavor.SERVICE_FORMATTED.PRINTABLE;
PrintService printService[] = PrintServiceLookup.lookupPrintServices(flavor, pras);
PrintService defaultService = PrintServiceLookup.lookupDefaultPrintService();
PrintService service = ServiceUI.printDialog( null,
200,
200,
printService,
defaultService,
flavor,
pras );

if (service != null)
{ DocPrintJob job = service.createPrintJob();
DocAttributeSet das = new HashDocAttributeSet();
Doc doc = new SimpleDoc(comp, flavor, das);

try {
job.print(doc, pras);
}
catch (PrintException pe)
{
pe.printStackTrace();
}
}
}

上記メソッドに、jtableをコンポーネントとして渡すことで印刷できるのはないかと考えました。
が、以下のようなエラーになります。
java.lang.IllegalArgumentException: data is not of declared type

また、併せて教えて頂けると大変助かる事があります。
JTABBEDPANEの中に、JTABLEを仕込んでいるのですが、現在のTabを取得して、そのtabに表示されているものを印刷する、といった事は可能なのでしょうか?
それとも、tabの中に表示されるJTABLEを取得して、印刷するべきなのでしょうか?

大変申し訳ないのですが、御教授頂ける様御願い申し上げます。
以上、よろしく御願い致します。
シュン
ぬし
会議室デビュー日: 2004/01/06
投稿数: 328
お住まい・勤務地: 東京都
投稿日時: 2004-06-22 11:14
SimpleDocのコンストラクタの第一引数(要求する型はObjectなのですね)が何なのかを示し
ているのが第二引数のようですが、それが矛盾している、というエラーだと読み取れますね。

印刷のターゲットとして渡しているComponentオブジェクトが、SimpleDocコンストラクタに
渡している第二引数の宣言に反して、java.awt.print.Printableインタフェースを実装して
いないからではないでしょうか。

コード:
class MyPrintable implements java.awt.print.Printable{
  private Component c;
  public MyPrintable(Component c){this.c = c;}
  public int print(Graphics graphics, PageFormat pageFormat, int pageIndex)
  {/*graphicsにcをドローする作業を自力で実装*/}
}



例えばこのようなラッパクラスを作って、SimpleDocコンストラクタの第一引数に渡して
やってみてください。
モンプチ
常連さん
会議室デビュー日: 2004/06/03
投稿数: 28
投稿日時: 2004-06-22 14:46
「シュン」様、御返事有難う御座います。

その案も考えました。
しかし、Graphicsクラスのメソッドでcompornentを扱うものがないので、却下しました。

でも、このようなアドバイスを頂けるという事は、compornent → Graphics に変換(正確には描画でしょうか)できるんですね。

再度考えてみます。
アドバイス有難う御座いました。
完了後、再度御礼申し上げます。
シュン
ぬし
会議室デビュー日: 2004/01/06
投稿数: 328
お住まい・勤務地: 東京都
投稿日時: 2004-06-22 15:09
引用:

モンプチさんの書き込み (2004-06-22 14:46) より:
「シュン」様、御返事有難う御座います。

その案も考えました。
しかし、Graphicsクラスのメソッドでcompornentを扱うものがないので、却下しました。

でも、このようなアドバイスを頂けるという事は、compornent → Graphics に変換(正確には描画でしょうか)できるんですね。

再度考えてみます。
アドバイス有難う御座いました。
完了後、再度御礼申し上げます。



Printable#print()が引数として受け取るGraphicsクラス(このGrahicsオブジェクトは、Graphics2D型へのキャストが可能です)オブジェクトに対して、書き込みを行うdrawXXX()メソッドや、拡大縮小、原点移動等を行うさまざまなメソッドを駆使して、Graphicsにあなたの望む帳票を描画する責任は、あなたにあります。あなたの望むデザインをコードに落としてください。
…というのがJavaコアAPIの思想のようです。

画面への描画と同等の描画を印刷用Graphicsオブジェクトへ簡単に行う簡易メソッドとして、Component#print(Graphics) Component#printAll(Graphics)というメソッドが準備
されています。画面上のコンポーネントの単純なハードコピーが欲しいなら、これを呼び
出すだけですみます。このあたりを駆使してがんばってください。


チュートリアルを読んだほうが早いかも^^;
http://java.sun.com/docs/books/tutorial/2d/printing/index.html


[ メッセージ編集済み 編集者: シュン 編集日時 2004-06-22 15:11 ]
モンプチ
常連さん
会議室デビュー日: 2004/06/03
投稿数: 28
投稿日時: 2004-06-22 20:26
「シュン」様、何度も御迷惑お掛けしてます。
御返事有難う御座います。

とりあえず印刷できました。
Graphicsのヘルプばかり見て、Compornentのヘルプをよく見てませんでした。
ごめんなさい。

明日はサイズの調整を試みます。
こちらはなんとかできそうです。

前回の質問時もお助け頂き大変助かりました。
頭は上がりませんが、腕は上げていきますので、今後ともよろしくお願い致します。

有難う御座いました。
モンプチ
常連さん
会議室デビュー日: 2004/06/03
投稿数: 28
投稿日時: 2004-06-24 11:10
再度失礼します。

印刷が白紙となります。
Component→graphic変換に問題があると思い、試しに画像ファイルを読み込んでテストしました。
しかしこれも、処理自体が完了はするのですが、印刷は白紙となります。
ソースを以下に記述します。

class Printer
{

static class Mycomponent extends JPanel implements Printable
{
Image im = null;

public Mycomponent()
{
Toolkit toolkit = Toolkit.getDefaultToolkit();
//Imageオブジェクトの生成
im = toolkit.getImage("E:\\test.bmp");
}

public void paint(Graphics g)
{
super.paint(g);
System.out.println("paint");
g.drawImage(im,50,50,300,200,this);
}

public int print(Graphics g, PageFormat pageFormat, int pageIndex)
{
int x = (int)pageFormat.getImageableX();
int y = (int)pageFormat.getImageableY();
g.translate(x, y);

if (pageIndex == 0)
{
paint(g);
return Printable.PAGE_EXISTS;
}
return Printable.NO_SUCH_PAGE;
}
}

//印刷メソッド
public static void printTable()
{
try {

// 印刷要求属性のセットに対するインタフェース、
// つまり PrintRequestAttribute インタフェースを実装する印刷属性を指定
PrintRequestAttributeSet pras = new HashPrintRequestAttributeSet();
DocFlavor flavor = DocFlavor.SERVICE_FORMATTED.PRINTABLE;
PrintService printService[] = PrintServiceLookup.lookupPrintServices(flavor, pras);
PrintService defaultService = PrintServiceLookup.lookupDefaultPrintService();
PrintService service = ServiceUI.printDialog( null,
200,
200,
printService,
defaultService,
flavor,
pras );

// 印刷対象の取得
final Mycomponent test = new Mycomponent();

if (service != null)
{
DocPrintJob job = service.createPrintJob();
DocAttributeSet das = new HashDocAttributeSet();
Doc doc = new SimpleDoc(test, flavor, das); //
job.print(doc, pras);
}

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

}
}

2日間作業しましたが、すいません、原因がわかりません。
エラーにもならず、処理自体も成功しているのですが。。

再度、御教授願います。
よろしく御願い致します。
シュン
ぬし
会議室デビュー日: 2004/01/06
投稿数: 328
お住まい・勤務地: 東京都
投稿日時: 2004-06-24 11:21
いまわかる範囲ですと、Toolkit#getImage()を非同期API(画面イメージのロードが完了する前にリターンしてしまう)で実装しているVMがあったような。描画しようとした時点でImageは対象ファイルのロードを完了していないかもしれません。
画像のロード完了に対する同期をとるために、MediaTrackerを使用するか、新しいJDKをお使いならImageI/O APIを使用するのが良いですよ。



APIドキュメントを見たところ、Toolkit#getImage()はBMPに対応していないようですね… orzガックリ

BMPをJavaからロードしたい場合は、新しいImageI/O APIの実装(BMPのロードが可能になっているもの)をインストールしてやらなければいけないかな?


[ メッセージ編集済み 編集者: シュン 編集日時 2004-06-24 11:25 ]
モンプチ
常連さん
会議室デビュー日: 2004/06/03
投稿数: 28
投稿日時: 2004-06-24 12:41
シュン様、御返事有難う御座います。
シュン様には御忙しい中で何度も御返事頂いている事を感謝しております。

原因は、Toolkit#getImage()がBMPに対応してなかったためなんですね。
確かにGIFで試してみたら成功しました。
あと紙が無駄になると思い、PDFWriter形式で出力して、画像の有無をチェックしてたのですが、pdfファイルは空でも、印刷したらきちんと印刷されていました。

あぁ、よかった。
じゃぁ、Componentでもきちんと印刷されるだろう、と思い

// Component = c
im = c.createImage( c.getWidth() , c.getHeight() );

で渡して、同じように実行したのですが、これは白紙になってしまいます。
ソースを以下に記述します。

class Printer
{

static private Component c; // 印刷コンポーネント
Image im = null; // image変換用

// コンストラクタ
public Printer(Component comp)
{
c = comp;
// compornent → image
im = c.createImage( c.getWidth() , c.getHeight() );

}

class MyComponent extends Component implements Printable
{
public int print(Graphics g, PageFormat pageFormat, int pageIndex)
{
int x = (int)pageFormat.getImageableX();
int y = (int)pageFormat.getImageableY();
g.translate(x, y);

if (pageIndex == 0)
{

//c.printAll(g); // こちらは印刷可能

// 用紙サイズの取得
int xsize = (int)pageFormat.getWidth();
int ysize = (int)pageFormat.getHeight();
//用紙サイズにあわせて拡大・縮小して描画
g.drawImage( im,
x,
y,
xsize,
ysize,
Color.black,
this );

System.out.println(x);
System.out.println(y);
System.out.println(im.getWidth());
System.out.println(im.getHeight());
System.out.println(xsize);
System.out.println(ysize);
System.out.println(im); // サイズ的には正しい

return Printable.PAGE_EXISTS;
}
return Printable.NO_SUCH_PAGE;
}
}

// 印刷メソッド
public void printTable()
{
try {

// 印刷要求属性のセットに対するインタフェース、
// つまり PrintRequestAttribute インタフェースを実装する印刷属性を指定
PrintRequestAttributeSet pras = new HashPrintRequestAttributeSet();
DocFlavor flavor = DocFlavor.SERVICE_FORMATTED.PRINTABLE;
PrintService printService[] = PrintServiceLookup.lookupPrintServices(flavor, pras);
PrintService defaultService = PrintServiceLookup.lookupDefaultPrintService();
PrintService service = ServiceUI.printDialog( null,
200,
200,
printService,
defaultService,
flavor,
pras );

// 印刷対象の取得
final Component test = new MyComponent();

if (service != null)
{
DocPrintJob job = service.createPrintJob();

// インターフェイス
PrintJobListener pjlistener = new PrintJobAdapter()
{
public void printDataTransferCompleted(PrintJobEvent e)
{
System.out.println("Good-bye");

}
};

job.addPrintJobListener(pjlistener);

DocAttributeSet das = new HashDocAttributeSet();
Doc doc = new SimpleDoc(test, flavor, das); //
job.print(doc, pras);
}

}
catch (Exception ex)
{
// エラー内容の取得
ex.printStackTrace();
}

}
}

printメソッドの中でdrawしてるのが問題なのでしょうか?
結局対処方法が思いつきません。
あと気になるのが、たとえdrawできるようになっても、printAllでは印刷できていた内部componentが描画されるのかです。

申し訳ありません、再度御教願います。
よろしく御願い致します。

スキルアップ/キャリアアップ(JOB@IT)