- PR -

CrystalReportsにうまく出力されない

1
投稿者投稿内容
ミユキ
会議室デビュー日: 2007/06/07
投稿数: 7
投稿日時: 2007-06-07 11:39
CrystalReportsを使って帳票を出そうとしている初心者です。
VB2005でwindowsアプリを作っています。VB2005に入っていたCrystalReports
を使っています。


下のコードはデータベースからデータを抽出し、「tmpTable」に展開しています。
「rptManageMilKihonStandard」はcrystalレポートです。rptのデータソースにtmpTable
を指定して出力します。

 Dim dbtMilKihon As New taskMilKihon(dbCtrl) '★
Dim objMilKihon As New modelMilKihon
Dim objrow(6) As Object
Dim aryMilKihon As modelMilKihon()
Dim i As Integer
Dim tmpTable As DataTable = Me.DsManageMilKihon1.dtManageMilKihon

whereString = Nothing
whereString = whereString & " mil_kubun ='" & cboKubun.Text & "'"
whereString = whereString & " AND "
whereString = whereString & " mil_siwake ='" & cboSiwake.Text & "'"
whereString = whereString & " AND "
whereString = whereString & " mil_varie ='" & txtMilVarie.Text & "'"

aryMilKihon = dbtMilKihon.getMilKihonArray(whereString) '★

If IsNothing(aryMilKihon) Then
Beep()
MessageBox.Show("該当するデータがありません。")
Exit Sub
End If

With tmpTable
For i = 0 To UBound(aryMilKihon)
objrow(0) = aryMilKihon(i).MilKihonId
objrow(1) = aryMilKihon(i).MilGrade
objrow(2) = aryMilKihon(i).MilVarie
objrow(3) = aryMilKihon(i).MilYotei
objrow(4) = aryMilKihon(i).MilNouki
objrow(5) = aryMilKihon(i).MilDenpyoNo
objrow(6) = aryMilKihon(i).MilTani
Next
End With

Dim rpt As New rptManageMilKihonStandard

rpt.SetDataSource(tmpTable)

rpt.PrintToPrinter(1, False, 0, 1)


「rptManageMilKihonStandard」には、対象となるテーブルのフィールドが左から順番に
mil_kihon_id
mil_grade
mil_varie
mil_yotei
mil_nouki
mil_denpyo_no
mil_tani
と置かれています。

このプログラムを実行すると、抽出はうまく行っていますが、crystalレポートへの出力に
問題があります。
フィールド名と内容がバラバラに出力されます。具体的には

指定された
フィールド名   出力された内容
============================================
mil_kihon_id ⇒ MilKihonId  (○)
mil_grade  ⇒ MilNouki  (×)
mil_varie  ⇒ MilYotei  (×)
mil_yotei  ⇒ MilDenpyoNo  (×)
mil_nouki  ⇒ MilTani  (×)
mil_denpyo_no ⇒ 何も表示しない (×)
mil_tani  ⇒ 何も表示しない (×)

こんな感じになり、rpt上のフィールド名の位置を変えても変わりません。
コードを見るとobjrowとrpt上のフィールド名をつなぎ合わせる記述がないの
が原因かと思いますが、そのやり方がわかりません。
また、コードでrpt上のオブジェクトをどのようにハンドルしたらいいのかも
わからない状態です。
コードのどこが悪いのか、アプローチ自体がおかしいのか、指摘していただきたく
お願いします。

さかもと
ぬし
会議室デビュー日: 2004/05/14
投稿数: 586
投稿日時: 2007-06-07 11:54
さかもとと申します。

Me.DsManageMilKihon1.dtManageMilKihon
のカラム名を
mil_kihon_id
mil_grade
mil_varie
mil_yotei
mil_nouki
mil_denpyo_no
mil_tani
に変えてしまうか、SQL分で
SELECT hoge AS mil_kihon_id
hoge2 AS mil_grade
・・・・

と名前を合わせてあげてもだめでしょうか?
ミユキ
会議室デビュー日: 2007/06/07
投稿数: 7
投稿日時: 2007-06-07 12:42
さかもと さん、回答ありがとうございます。

私の説明が悪くて申し訳ありません。
対象となるテーブルのカラム名は
mil_kihon_id
mil_grade
mil_varie
mil_yotei
mil_nouki
mil_denpyo_no
mil_tani
です。

ですので、Me.DsManageMilKihon1.dtManageMilKihonの
カラム名も
mil_kihon_id
mil_grade
mil_varie
mil_yotei
mil_nouki
mil_denpyo_no
mil_tani
となっています。

ですから、rpt上のカラム名と出力された関係は以下は表現を変えると
以下のようになります。

指定された
フィールド名   出力された内容
============================================
mil_kihon_id ⇒ mil_kihon_id  (○)
mil_grade  ⇒ mil_nouki  (×)
mil_varie  ⇒ mil_yotei  (×)
mil_yotei  ⇒ mil_denpyo_no  (×)
mil_nouki  ⇒ mil_tani  (×)
mil_denpyo_no ⇒ 何も表示しない (×)
mil_tani  ⇒ 何も表示しない  (×)

objrowが順番にrpt上のmil_kihon_id,mil_grade・・・に割り振られれば
いいのですが・・・

じゃんぬねっと
ぬし
会議室デビュー日: 2004/12/22
投稿数: 7811
お住まい・勤務地: 愛知県名古屋市
投稿日時: 2007-06-07 14:57
引用:

ミユキさんの書き込み (2007-06-07 11:39) より:

コード:


    With tmpTable
        For i = 0 To UBound(aryMilKihon)
            objrow(0) = aryMilKihon(i).MilKihonId
            objrow(1) = aryMilKihon(i).MilGrade
            objrow(2) = aryMilKihon(i).MilVarie
            objrow(3) = aryMilKihon(i).MilYotei
            objrow(4) = aryMilKihon(i).MilNouki
            objrow(5) = aryMilKihon(i).MilDenpyoNo
            objrow(6) = aryMilKihon(i).MilTani
        Next
    End With




この部分に何の意味があるのですか? 'tmpTable' とまったく関係がない記述なのもそうですが、objrow[] とデータソースたる tmpTable に関連が設けられていません。これで正しく表示されることを期待する方が無茶というものではないでしょうか?

_________________
C# と VB.NET の入門サイト
じゃんぬねっと日誌
ミユキ
会議室デビュー日: 2007/06/07
投稿数: 7
投稿日時: 2007-06-07 16:43
じゃんぬねっとさん、ご指摘ありがとうございました。

With tmpTable
 For i = 0 To UBound(aryMilKihon)
  objrow(0) = aryMilKihon(i).MilKihonId
  objrow(1) = aryMilKihon(i).MilGrade
  objrow(2) = aryMilKihon(i).MilVarie
  objrow(3) = aryMilKihon(i).MilYotei
  objrow(4) = aryMilKihon(i).MilNouki
  objrow(5) = aryMilKihon(i).MilDenpyoNo
  objrow(6) = aryMilKihon(i).MilTani
 Next
End With

の後ろに
dataGrid1.DataSource = tmpTable

とやって、いつもDataGridViewに出しているので、そのワンパターンで
あまり深く考えないでCrystalReportsにも当てはめてコードを
書いてしまいました。お恥ずかしい。

ご指摘のとおりobjrow()とtmpTableの関連付け方がよくわかりません。
具体的に教えて頂けないでしょうか?
よろしくお願い致します。


じゃんぬねっと
ぬし
会議室デビュー日: 2004/12/22
投稿数: 7811
お住まい・勤務地: 愛知県名古屋市
投稿日時: 2007-06-07 19:51
引用:

ミユキさんの書き込み (2007-06-07 16:43) より:

とやって、いつもDataGridViewに出しているので、そのワンパターンであまり深く考えないでCrystalReportsにも当てはめてコードを書いてしまいました。お恥ずかしい。
ご指摘のとおりobjrow()とtmpTableの関連付け方がよくわかりません。
具体的に教えて頂けないでしょうか?


dbtMilKihon.getMilKihonArray メソッドの仕様がわかりませんからね。今の情報からですと最適な方法はわかりかねます。大雑把に言えば、ひとつの DataSource にまとめてしまえば良いわけです。

_________________
C# と VB.NET の入門サイト
じゃんぬねっと日誌
ミユキ
会議室デビュー日: 2007/06/07
投稿数: 7
投稿日時: 2007-06-07 20:32
じゃんぬねっとさん、ありがとうございます。

dbtMilKihon.getMilKihonArray
は別クラスを呼んでいるんですけど、以下のようなSQL文です。

Public Function getMilKihonArray(ByVal whereString As String) As modelMilKihon()
Dim aryMilKihon() As modelMilKihon
Dim objMilKihon As modelMilKihon '行
Dim objRow As DataRow 'データ行
Dim sql As String
Dim dtTbl As DataTable
Dim i As Integer

sql = ""
sql = sql & " SELECT "
sql = sql & " mil_kihon_id"
sql = sql & ", mil_grade "
sql = sql & ", mil_varie"
sql = sql & ", mil_yotei"
sql = sql & ", mil_nouki"
sql = sql & ", mil_denpyo_no"
sql = sql & ", mil_tani"
sql = sql & " FROM"
sql = sql & " tbl_m_mil_kihon "
sql = sql & " WHERE " & whereString
sql = sql & " ORDER BY "
sql = sql & " mil_grade "
sql = sql & ", mil_kihon_id "

dtTbl = DbCtrl.getDataTable(sql) '★

If dtTbl.Rows.Count > 0 Then

ReDim aryMilKihon(dtTbl.Rows.Count - 1) 'aryMilKihon:行の配列化
i = 0
For Each objRow In dtTbl.Rows 'データ行
objMilKihon = makeMilKihonFromRow(objRow) '★
aryMilKihon(i) = objMilKihon
i = i + 1
objMilKihon = Nothing
Next
Return aryMilKihon
Else
Return Nothing
End If
End Function



「大雑把に言えば、ひとつの DataSource にまとめてしまえば良いわけです。」
と、おしえていただいた点ですけど、なんとなくわかるような気もするんですけど、
よくわかりません。

tmpTableはひとかたまりのデータセットですが、objrowは配列化されたひとつのrow
ですし・・・
ほんとうは、データセットをダイレクトにrpt上のフィールドに関連つければよいので
しょうが、SQLで絞りこんだデータはaryMilKihonですし・・・

どうやったらいいでしょうか?
よろしくお願いいたします。




じゃんぬねっと
ぬし
会議室デビュー日: 2004/12/22
投稿数: 7811
お住まい・勤務地: 愛知県名古屋市
投稿日時: 2007-06-07 21:31
引用:

ミユキさんの書き込み (2007-06-07 20:32) より:

どうやったらいいでしょうか?


まだわかりません。ごめんなさい。

その 2 つのデータの固まりの関係がわかるのは私ではなく貴方です。私には、この 2 つのデータの固まりを結合すべきかどうかすらわかりません。

結合すべきだとして、容易に結合できる関係にあるのか PL/SQL を駆使するほどのものなのかもわかりません。結合すべきでないとして、FieldObject から直接値を表示して良い (レコードごとに値が変わるものでないか) どうかもわかりません。

それをわからなくしている要因は下記の引用にあります。

引用:

With tmpTable
 For i = 0 To UBound(aryMilKihon)
  objrow(0) = aryMilKihon(i).MilKihonId
  objrow(1) = aryMilKihon(i).MilGrade
  objrow(2) = aryMilKihon(i).MilVarie
  objrow(3) = aryMilKihon(i).MilYotei
  objrow(4) = aryMilKihon(i).MilNouki
  objrow(5) = aryMilKihon(i).MilDenpyoNo
  objrow(6) = aryMilKihon(i).MilTani
 Next
End With


これは aryMilKihon の '最後の要素しか' 取得できていないことは理解しているでしょうか? 理解できているならば、For ステートメントを使わないと思いますので理解していないと見ています。

仮に本当に最後の要素しか考慮しないのであれば、FieldObject に値を直接渡すべきです。このように仕様によって、すべき対応策が異なるのはご理解頂けるでしょうか。

_________________
C# と VB.NET の入門サイト
じゃんぬねっと日誌
1

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