none
別フォームへのデータテーブルを作成して、その値を使って別フォームへ表示したい RRS feed

  • 質問

  • windowsフォーム5からwindowsフォーム2に会社データを表示する際に、windowsフォーム2用のデータテーブルを作成しその値を使ってフォーム2に表示するにはどうすれば良いでしょうか?

    使用環境はVS2010PRO、バンドル版のクリスタルレポート、アクセス2003です

    ・windowsフォーム5のtextboxで検索、データグリッドビューで表示

    Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
    Dim i As Integer
    For i = 0 To 9
    Next
    DataGridView1.AutoSizeColumnsMode = DataGridViewAutoSizeColumnsMode.AllCells
    DataGridView1.AutoSizeRowsMode = DataGridViewAutoSizeRowsMode.AllCells
    Dim OLEDBCon As OleDb.OleDbConnection = _
    New OleDb.OleDbConnection
    Dim OLEDA As OleDb.OleDbDataAdapter
    Dim OLEDS As DataSet = New DataSet("TABLEDATA")
    Dim strSQL As String
    OLEDBCon.ConnectionString = _
    "Provider=Microsoft.Jet.OLEDB.4.0;" & _
    "Data Source=" & Form1.TextBox1.Text & ";" & _
    "Persist Security Info=False"
    strSQL = "select 得意先コード, 郵便番号,住所1,住所2,得意先名 FROM 得意先T WHERE (((得意先T.得意先名) Like '%" & TextBox1.Text & "%'))"
    OLEDA = New OleDb.OleDbDataAdapter(strSQL, OLEDBCon)
    Try OLEDA.Fill(OLEDS, "得意先T")
    Me.DataGridView1.DataSource = OLEDS.Tables("得意先T")
    Catch ex As Exception
    MessageBox.Show(ex.Message)
    End Try

    End If

    End Sub

    ・windowsフォーム5でデータグリッドビューで表示されているセルをダブルクリック、windowsフォーム2のtextboxに表示

    Private Sub CellDoubleClick(ByVal sender As System.Object, ByVal e As System.Windows.Forms.DataGridViewCellEventArgs) Handles DataGridView1.CellDoubleClick
    Dim i As Integer
    For i = 0 To 9
    Next
    Dim dgr As System.Windows.Forms.DataGridViewRow = Me.DataGridView1.CurrentRow
    Form2.TextBox1.Text = Me.DataGridView1.SelectedRows(0).Cells(0).Value
    Form2.TextBox3.Text = Me.DataGridView1.SelectedRows(0).Cells(1).Value
    Form2.TextBox4.Text = Me.DataGridView1.SelectedRows(0).Cells(2).Value
    Form2.TextBox5.Text = Me.DataGridView1.SelectedRows(0).Cells(3).Value
    Form2.TextBox6.Text = Me.DataGridView1.SelectedRows(0).Cells(4).Value
    Form2.Show()                                                                                                                             end sub                           

    windowsフォーム5からwindowsフォーム2に表示する際に、windowsフォーム2用のデータテーブルを作成し、その値を使ってwindowsフォーム2に表示いたしたく思います

    宜しくお願いします

    2012年11月28日 2:04

回答

  • どの辺りがわからないのでしょうか? そこを教えていただけると的を得た回答が付きやすいです。
    とりあえず、OLEDBでのアクセスに替え、一通りコメントを付けました。この辺りはADO.NETの基礎になりますので、よく理解された方が良いと思います。以下の記事は古いですが、ADO.NETの基礎は学べると思います。現在は、ADO.NETを楽に使用できるTableAdapterが追加されていますので、次はそれについて学んでください。

    ADO.NET基礎講座
    http://www.atmarkit.co.jp/fdotnet/basics/adonet_index/index.html

    Dim dt = New DataTable
    
    '本当は、プロジェクトの「プロパティ」→「設定」タブで接続文字列を定義し、以下の様に指定すると一元管理できて便利です。
    'ここでは、接続文字列にdb1ConnectionStringという名前を付けています。
    'Using cn As New OleDbConnection(My.MySettings.Default.db1ConnectionString)
    '
    'Usingを使用すると、最後で必ず自動的にDisposeメソッドを実行してくれます。データベースへの接続は使用し終わったら直ちに解放する必要が
    'ありますので、すぐにDisposeメソッドを実行する必要があります。
    Using cn As New OleDbConnection("Provider=Microsoft.Jet.OLEDB.4.0;Data Source=|DataDirectory|\db1.mdb;Persist Security Info=False")
    
        'SQLを発行するOleDbCommandクラスのインスタンスを生成します。
        Using cmd As New OleDbCommand
    
            'OleDbCommandの設定をします。SQL文中でパラメーターを使っているところに注意して下さい。パラメーターは@で始まります。
            'パラメーターを使わずに文字列を連結するとSQLインジェクションが発生する可能性があり、大変危険です。調べてみて下さい。
            With cmd
                .Connection = cn
                .CommandType = CommandType.Text
                .CommandText = "select name from table1 where ID = @ID"
                .Parameters.AddWithValue("@ID", 3)
            End With
    
            'データセットを扱うOleDbDataAdapterクラスのインスタンスを生成します。
            Using da As New OleDbDataAdapter
                'SQLを発行するコマンドをセットします。
                da.SelectCommand = cmd
                'すぐ上でセットしたSQLを発行するコマンドを使用して、データベースからデータを取得し、データテーブルにセットします。
                da.Fill(dt)
            End Using
    
        End Using
    End Using
    
    'TextBox1のTextプロパティにデータテーブルをバインドします。テキストボックスにはデータテーブルのカレント行の値が表示されます。
    'ここではデータテーブルに1行しかないので、それがカレント行になります。
    TextBox1.DataBindings.Add("Text", dt, "name")
    
    '別の方法として、以下でも表示できます。これはデータテーブルの1行目のnameという列の値を、TextBox1のTextプロパティにセットしています。
    '上記のようにバインドしていないので常に1行目のデータしか表示できませんが、今回はデータテーブルに1行しかないのでこれでもかまいません。
    'TextBox1.Text = dt.Rows(0).Item("name").ToString

    ★良い回答には回答済みマークを付けよう! わんくま同盟 MVP - Visual C# http://d.hatena.ne.jp/trapemiya/


    2012年11月30日 1:11
    モデレータ

すべての返信

  • p>windowsフォーム5からwindowsフォーム2に表示する際に、windowsフォーム2用のデータテーブルを作成し、その値を使ってwindowsフォーム2に表示いたしたく思います

    単にデータテーブルを作りたいのであれば、以下のページに載っているコードが参考になると思います。

    DataRow クラス
    http://msdn.microsoft.com/ja-jp/library/system.data.datarow(v=vs.80).aspx?cs-save-lang=1&cs-lang=vb#code-snippet-4

    ところで、データテーブルを作りたいという理由は何でしょうか? それによってはもっと良い方法があるかもしれません。


    ★良い回答には回答済みマークを付けよう! わんくま同盟 MVP - Visual C# http://d.hatena.ne.jp/trapemiya/

    2012年11月28日 2:34
    モデレータ
  • trapemiya様

    ありがとうございます

    データテーブルを作って、クリスタルレポートに渡し印刷を致したく思います

    良い方法ありますでしょうか?

    2012年11月28日 2:43
  • 一般的には、フォーム5で選んだ際にID(主キー)を取得し、フォーム2ではそのIDを使ってデータベースから値を取得して表示します。この際、データテーブルが出来ますので、それをそのままクリスタルレポートに使用することができます。

    フォーム5の検索結果一覧で変更ができるようにすると、画面上で変更されているだけでデータベースにそれが反映されていない状態があり得ますから、その場合、フォーム2に表示される内容が異なります。これは誤りではないのですが、ユーザーにとってわかりにくいので工夫が必要です。手っ取り早くはフォーム5で修正ができないようにしてしまうことです。

    以上を踏まえれば、以下のような流れが考えられます。
    フォーム5の検索結果は、得意先情報が識別できる程度の情報を表示し、その検索結果のうちの一件を選択した際にIDを取得し(IDはここでは得意先コードですか?)、フォーム2ではそのIDを使ってデータベースを検索し、データテーブルにFillして、得意先の詳細を表示します。印刷は簡単で、データテーブルから行います。

    なお、ご自分でOleDbDataAdapterなどを直接操作せず、TableAdapterを利用されることをお勧めします。この場合、型付データテーブルというものが作成されますので、それを使ってクリスタルレポートをデザインできるようになり、便利です。


    ★良い回答には回答済みマークを付けよう! わんくま同盟 MVP - Visual C# http://d.hatena.ne.jp/trapemiya/

    2012年11月28日 3:06
    モデレータ
  • trapemiya様

    ありがとうございます。

    1.フォーム5の検索結果は、得意先情報が識別できる程度の情報を表示します→フォーム5内のデータグリッドビューで表示されています。

    2. その検索結果のうちの1件を選択した際にID(得意先コード)を取得します→フォーム5においてデータグリッドドビュー内のセルをダブルクリックしてフォーム2のテキストボックスに得意先情報(郵便番号、住所、得意先名、得意先コード等)表示させています。コードは以下になります Form2.TextBox1.Text = Me.DataGridView1.SelectedRows(0).Cells(0).Value 取得するというのは、フォーム5からフォーム2に表示させることでしょうか?

    3.フォーム2で、そのIDを使ってデータベースを検索します→この意味が理解できません。検索するのは、アクセスからですか?そして検索してデータテーブルを作成するのですか?

    4. データテーブルへFillして、得意先の詳細を表示します→この意味が理解できません。

    3.4について参考になる情報等ありますでしょうか?

    宜しくお願いします。



    2012年11月28日 5:16
  • > 取得するというのは、フォーム5からフォーム2に表示させることでしょうか?

    違います。フォーム5のDataGridViewにおいて、ユーザーが選択した行のIDを取得するということです。IDがわかれば、そのIDを使ってAccessからその得意先を取得することができます。ところでID、つまり主キーは得意先コードでよろしいですか?

    >3.フォーム2で、そのIDを使ってデータベースを検索します→この意味が理解できません。検索するのは、アクセスから
    >ですか?そして検索してデータテーブルを作成するのですか?

    >4. データテーブルへFillして、得意先の詳細を表示します→この意味が理解できません。

    フォーム5で選択したIDをフォーム2に渡します。フォーム2ではそのIDを使って得意先を取得し、表示します。取得はAccessから行います。
    今回はフォーム5とフォーム2で、表示される得意先の項目数に差が無いかもしれませんが、差がある場合もあります。例えば、フォーム5の検索結果一覧では得意先名のみを表示し、フォーム2では住所などを含めた得意先の全情報を表示します。フォーム2で表示される項目数はフォーム5より多いので、詳細という言葉を使いました。

    >3.4について参考になる情報等ありますでしょうか?

    例えば次のように考えると視界が一気に広がるかもしれません。

    フォーム5で得意先を得意先名で検索します。そのうちの一つをダブルクリックして開くのも別のフォーム5で行います。この時、フォーム5が2つ同時に開いていることになります。2番目のフォーム5では、今度は得意先名ではなくID(得意先コード?)で検索します。
    実際には2番目のフォーム5をフォーム2にしなければなりませんが、フォーム2に変更しても、DataGridViewが複数のテキストボックスに代わるだけです。


    ★良い回答には回答済みマークを付けよう! わんくま同盟 MVP - Visual C# http://d.hatena.ne.jp/trapemiya/

    2012年11月28日 6:02
    モデレータ
  • trapemiya様

    ありがとうございます

    主キーは、得意先コードにします

    ・SQLの構文を変更しました

    strSQL = "select 得意先コード,得意先名 FROM 得意先T WHERE (((得意先T.得意先名) Like '%" & TextBox1.Text & "%'))" 
    →データグリッドビューでは、得意先コードと得意先名のみ表示されるようになりました。                   

    ・Windowsフォーム5からフォーム2に渡す際に、得意先コードのみ渡すようにしました 

    Form2TextBox1.Text = Me.DataGridView1.SelectedRows(0).Cells(0).Value     
    Form2TextBox3~6.Text ~.valueの構文を外しました   

    フォーム2のテキストボックスに得意先コードが表示されます。
    フォーム2のテキストボックスに表示されている得意先コードをキーワードにして、アクセスから検索して、
    得意先の住所、得意先名、郵便番号等をフォーム2のテキストボックスに表示させれば、
    データテーブルになるのでしょうか?   
    データテーブルになってから、クリスタルレポートへどのようにして渡せば良いのでしょうか?                                             

    当方VS2010Proを初めて1週間に満たないものでして、すぐに理解できず申し訳ありません

    2012年11月28日 8:17
  • >得意先の住所、得意先名、郵便番号等をフォーム2のテキストボックスに表示させれば、
    >データテーブルになるのでしょうか?

    掲載されたコードに、
    OLEDA.Fill(OLEDS, "得意先T")
    とあります。これで得意先Tというデータテーブルが作成されます。これと同様にフォーム2でもコードを組まれれば、データテーブルが作成されます。
    テキストボックスへは、そのデータテーブルの値を読み取ってセットするか、もしくはバインドします(確かバインドできたと思います)

    >データテーブルになってから、クリスタルレポートへどのようにして渡せば良いのでしょうか? 

    これは質問内容が変わりますから、新しくスレッド立てて下さい。その際、ご自分で調べられて、どこまでできたけどここからがわからないというふうに、具体的に書いていただくと的確な回答が早く付きやすくなります。


    ★良い回答には回答済みマークを付けよう! わんくま同盟 MVP - Visual C# http://d.hatena.ne.jp/trapemiya/

    2012年11月28日 8:56
    モデレータ
  • trapemiya様

    ありがとうございます。                                                                 >OLEDA.Fill(OLEDS, "得意先T")
    とあります。これで得意先Tというデータテーブルが作成されます。これと同様にフォーム2でもコードを組まれれば、データテーブルが作成されます。そこでフォーム2に以下のコードを作成しましたが、datasourceの箇所(※)でエラーが出てしまいます。

    Dim OLEDBCon As OleDb.OleDbConnection = _
                    New OleDb.OleDbConnection
            Dim OLEDA As OleDb.OleDbDataAdapter
            Dim OLEDS As DataSet = New DataSet("TABLEDATA")
            
            Try
               OLEDA.Fill(OLEDS, "得意先T")                                                         TextBox1.Text.DataSource = OLEDS.Tables("得意先T")※                                  Catch ex As Exception
                MessageBox.Show(ex.Message)
            End Try

    フォーム5からフォーム2に渡す際に、フォーム2のテキストボックスに得意先コードのみ表示されています。                  フォーム2でボタンをクリックすると、上記のコードが実施されるようにしたいのですが。datasourceはフォーム2のテキストボックス1になるので、上記のコードにしています データテーブルが作成されていないと思いますが、どのようにすればよいでしょうか?

    宜しくお願いします

    2012年11月29日 1:08
  • 以下を参考にしてみて下さい。

    Imports System.Data.SqlClient
    
    Public Class TextBoxBindTest
    
        Dim dt As DataTable
    
        Private Sub Button1_Click(sender As System.Object, e As System.EventArgs) Handles Button1.Click
    
            dt = New DataTable
    
            Using cn As New SqlConnection(My.MySettings.Default.TESTConnectionString)
                Using cmd As New SqlCommand
    
                    With cmd
                        .Connection = cn
                        .CommandType = CommandType.Text
                        .CommandText = "select test1 from TEST where ID = 3"
                    End With
    
                    Using da As New SqlDataAdapter
                        da.SelectCommand = cmd
                        da.Fill(dt)
                    End Using
    
                End Using
            End Using
    
            TextBox1.DataBindings.Add("Text", dt, "test1")
    
            '以下でも良い
            'TextBox1.Text = dt.Rows(0).Item("test1").ToString
    
        End Sub
    
    End Class


    ★良い回答には回答済みマークを付けよう! わんくま同盟 MVP - Visual C# http://d.hatena.ne.jp/trapemiya/

    2012年11月29日 8:02
    モデレータ
  • trapemiya様                                                           ありがとうございます。上記のコードを見ましたがやはりデータテーブルの作成がわかりません。                                     Windowsフォーム5からフォーム2に値を渡す際に、得意先コードのみ渡しています。そこからどのようにすればよいでしょうか?アクセスから検索を行うのはわかります。しかしそのやり方がさっぱりわかりません。フォーム5内で検索を掛けています。候補になった1つをダブルクリックしてフォーム2のテキストボックスに、その得意先コードまで表示させる事は出来ますが、その後の進め方がわかりません。                          表示させた後、フォーム2でボタンをクリックしてアクセスの得意先Tの得意先コードを検索して、ヒットしたものをフォーム2のテキストボックスに表示させるということでしょうか?表示させるものは、住所、郵便番号、得意先名などになるかと思います。たくさん質問ばかりして大変申し訳ございません。また丁寧に回答してくださっているにもかかわらず私が理解できず申し訳ございません。宜しくお願い申し上げます

    2012年11月29日 13:01
  • Windowsフォーム5からフォーム2に値を渡す際に、得意先コードのみ渡しています。そこからどのようにすればよいでしょうか?

    フォーム2のコンストラクタで、その得意先コードを使って得意先を1件検索し、それをテキストボックスに表示します。私が上記に掲載したコードではwhere ID=3 と固定で書いていますが、ここを渡された得意先コードで検索するようにします。

    候補になった1つをダブルクリックしてフォーム2のテキストボックスに、その得意先コードまで表示させる事は出来ますが、その後の進め方がわかりません。

    すぐ上に書いた通りです。私が上で掲載したコードを真似て、それをコンストラクタで実行するようにします。Accessですので、実際にはOledbを使うことになります。パラメータの指定も含めて、以下のページのGetSyainという関数を参考にされると良いと思います。

    MDB版:データベースアクセス
    http://park5.wakwak.com/~weblab/clsDBIO.html

    表示させた後、フォーム2でボタンをクリックしてアクセスの得意先Tの得意先コードを検索して、ヒットしたものをフォーム2のテキストボックスに表示させるということでしょうか?

    上記に書いた通り、コンストラクタで行って下さい。つまり、
    「コンストラクタでアクセスの得意先Tの得意先コードを検索して、ヒットしたものをフォーム2のテキストボックスに表示させる」
    ということです。

    ★良い回答には回答済みマークを付けよう! わんくま同盟 MVP - Visual C# http://d.hatena.ne.jp/trapemiya/

    2012年11月29日 14:47
    モデレータ
  • trapemiya様                                                                                              詳しいご説明頂きありがとうございます。

    差支えなければ、コードの上に何を表しているのか書いて頂けないでしょうか?

       

    2012年11月29日 23:50
  • どの辺りがわからないのでしょうか? そこを教えていただけると的を得た回答が付きやすいです。
    とりあえず、OLEDBでのアクセスに替え、一通りコメントを付けました。この辺りはADO.NETの基礎になりますので、よく理解された方が良いと思います。以下の記事は古いですが、ADO.NETの基礎は学べると思います。現在は、ADO.NETを楽に使用できるTableAdapterが追加されていますので、次はそれについて学んでください。

    ADO.NET基礎講座
    http://www.atmarkit.co.jp/fdotnet/basics/adonet_index/index.html

    Dim dt = New DataTable
    
    '本当は、プロジェクトの「プロパティ」→「設定」タブで接続文字列を定義し、以下の様に指定すると一元管理できて便利です。
    'ここでは、接続文字列にdb1ConnectionStringという名前を付けています。
    'Using cn As New OleDbConnection(My.MySettings.Default.db1ConnectionString)
    '
    'Usingを使用すると、最後で必ず自動的にDisposeメソッドを実行してくれます。データベースへの接続は使用し終わったら直ちに解放する必要が
    'ありますので、すぐにDisposeメソッドを実行する必要があります。
    Using cn As New OleDbConnection("Provider=Microsoft.Jet.OLEDB.4.0;Data Source=|DataDirectory|\db1.mdb;Persist Security Info=False")
    
        'SQLを発行するOleDbCommandクラスのインスタンスを生成します。
        Using cmd As New OleDbCommand
    
            'OleDbCommandの設定をします。SQL文中でパラメーターを使っているところに注意して下さい。パラメーターは@で始まります。
            'パラメーターを使わずに文字列を連結するとSQLインジェクションが発生する可能性があり、大変危険です。調べてみて下さい。
            With cmd
                .Connection = cn
                .CommandType = CommandType.Text
                .CommandText = "select name from table1 where ID = @ID"
                .Parameters.AddWithValue("@ID", 3)
            End With
    
            'データセットを扱うOleDbDataAdapterクラスのインスタンスを生成します。
            Using da As New OleDbDataAdapter
                'SQLを発行するコマンドをセットします。
                da.SelectCommand = cmd
                'すぐ上でセットしたSQLを発行するコマンドを使用して、データベースからデータを取得し、データテーブルにセットします。
                da.Fill(dt)
            End Using
    
        End Using
    End Using
    
    'TextBox1のTextプロパティにデータテーブルをバインドします。テキストボックスにはデータテーブルのカレント行の値が表示されます。
    'ここではデータテーブルに1行しかないので、それがカレント行になります。
    TextBox1.DataBindings.Add("Text", dt, "name")
    
    '別の方法として、以下でも表示できます。これはデータテーブルの1行目のnameという列の値を、TextBox1のTextプロパティにセットしています。
    '上記のようにバインドしていないので常に1行目のデータしか表示できませんが、今回はデータテーブルに1行しかないのでこれでもかまいません。
    'TextBox1.Text = dt.Rows(0).Item("name").ToString

    ★良い回答には回答済みマークを付けよう! わんくま同盟 MVP - Visual C# http://d.hatena.ne.jp/trapemiya/


    2012年11月30日 1:11
    モデレータ
  • ありがとうございました。また宜しくお願いします

    2012年12月1日 1:46