Public Class Form2

    Public Property Param As Form2Param
    Public v As Object
    Private Sub DataGridView1_CellClick(sender As Object, e As System.Windows.Forms.DataGridViewCellEventArgs) Handles dgv1.CellClick
        'セルがクリックされた時
        v = dgv1.CurrentCell.Value '該当セルの値を格納しておく
    End Sub
    Private Sub Form2_Load(sender As Object, e As EventArgs) Handles MyBase.Load
        DataToForm()
    End Sub

    Private Sub DataToForm()
        ListBox3.Items.Clear()
        ListBox4.Items.Clear()
        'データソースを設定してDataGridViewにデータを表示
        Dim BindingSource1 As New BindingSource
        BindingSource1.DataSource = Param.Table
        dgv1.DataSource = BindingSource1

        '主キーの列番号を格納
        ListBox1.Items.Clear() 'クリア
        Dim Table1 As DataTable = Param.Table
        Dim key_clm() As DataColumn = Table1.PrimaryKey '主キー情報を配列で取得
        Dim i As Integer
        For i = 0 To key_clm.GetUpperBound(0) '主キーの数だけループ
            ListBox1.Items.Add(key_clm(i).Ordinal) 'ListBox1に列番号を入れていく
            dgv1.Columns(i).HeaderCell.Style.BackColor = Color.LemonChiffon '主キーのヘッダー色
        Next i

        'フィールドの型格納
        ListBox2.Items.Clear() 'クリア
        i = 0
        Do While i <= Table1.Columns.Count - 1 '列の数だけループ
            Dim type_txt As String = Table1.Columns(i).DataType.Name
            If Table1.Columns(i).AutoIncrement = True Then type_txt = "A_" & type_txt 'オートインクリメントの場合
            ListBox2.Items.Add(type_txt) 'ListBox2に型名を入れていく
            i = i + 1 'カウントアップ
        Loop
        Text = Param.Title 'タイトルをテーブル名に

    End Sub

    Private Sub btnReLoad_Click(sender As Object, e As EventArgs) Handles btnReLoad.Click
        Dim m = Module1.GetInstance()
        m.DBrefresh()
        DataToForm()
    End Sub

    Private Function IsPrimaryKey() As Boolean

        For Each new_row As Integer In ListBox4.Items 'INSERT行をループ
            Return False '主キーでも追加なのでok
        Next
        For Each key_clm As Integer In ListBox1.Items '主キーの列番号をループ
            If ListBox1.Items(key_clm) = dgv1.CurrentCell.ColumnIndex Then '主キー列だったら
                MessageBox.Show("このセルは主キーなので変更できません", "エラー", MessageBoxButtons.OK, MessageBoxIcon.Error)
                RemoveHandler dgv1.CellValueChanged, AddressOf DataGridView1_CellValueChanged 'チェンジイベント一時無効
                dgv1.CurrentCell.Value = v '元の値に戻す
                AddHandler dgv1.CellValueChanged, AddressOf DataGridView1_CellValueChanged 'チェンジイベント有効
                Return True
            End If
        Next
        Return False
    End Function

    Private Sub DataGridView1_CellValueChanged(sender As Object, e As System.Windows.Forms.DataGridViewCellEventArgs) Handles dgv1.CellValueChanged
        'セルが変更された時
        'チェック
        If IsPrimaryKey() Then
            Exit Sub
        End If
        Dim flg As Boolean = False
        For Each i As Integer In ListBox3.Items 'UPDATEリストに既に行があるかチェック
            If i = dgv1.CurrentRow.Index Then flg = True
        Next
        For Each i As Integer In ListBox4.Items 'INSERTリストに既に行があるかチェック
            If i = dgv1.CurrentRow.Index Then flg = True
        Next
        If flg = False Then ListBox3.Items.Add(dgv1.CurrentRow.Index) 'なければUPDATEリストに追加

        dgv1.CurrentCell.Style.BackColor = Color.LavenderBlush '変更したセルに色をつける
    End Sub

    Private Sub DataGridView1_UserAddedRow(sender As Object, e As System.Windows.Forms.DataGridViewRowEventArgs) Handles dgv1.UserAddedRow
        '新しい行が追加された時
        Dim flg As Boolean = False
        For Each i As Integer In ListBox4.Items 'INSERTリストに既に行があるかチェック
            If i = dgv1.CurrentRow.Index Then flg = True
        Next
        If flg = False Then ListBox4.Items.Add(dgv1.CurrentRow.Index) '行数をListBox4に追加
    End Sub

    Private Sub DataGridView1_DataError(sender As Object, e As DataGridViewDataErrorEventArgs) Handles dgv1.DataError
        'データグリッドビューの編集でエラーが発生した時
        If Not (e.Exception Is Nothing) Then
            MessageBox.Show(e.ColumnIndex + 1 & "列 " & e.RowIndex + 1 & "行目 のセルでエラーが発生しました。" & vbCrLf & vbCrLf & e.Exception.Message, "エラー", MessageBoxButtons.OK, MessageBoxIcon.Error)
        End If
        e.Cancel = False '値を戻す
    End Sub


    Private Sub Button3_Click(sender As System.Object, e As System.EventArgs) Handles btnDelete.Click
        Dim m = Module1.GetInstance()
        '削除ボタンを押した時
        If dgv1.CurrentCellAddress.X = -1 Then 'どこも選択されていない場合
            MessageBox.Show("削除したい行を選択してください。", "確認", MessageBoxButtons.OK, MessageBoxIcon.Exclamation)
            Exit Sub
        End If

        If ListBox3.Items.Count = 0 And ListBox4.Items.Count = 0 Then
            If MessageBox.Show("選択されている行のデータを削除します。よろしいですか？", "確認", MessageBoxButtons.OKCancel, MessageBoxIcon.Exclamation) <> 1 Then Exit Sub
            m.result_flg = False
            m.DBdelete(Text, dgv1.CurrentRow.Index)
            If m.result_flg = True Then '成功フラグが立っていたときだけ
                m.DBrefresh() '再読込
                DataToForm()
                MessageBox.Show("削除しました。")
            End If
        Else
            MessageBox.Show("編集中のデータがあります。先に「保存」か「再読込」を行なってください。")
        End If
    End Sub

    Private Sub Button2_Click(sender As System.Object, e As System.EventArgs) Handles btnSave.Click
        Dim m = Module1.GetInstance()
        '保存ボタン
        If ListBox3.Items.Count = 0 And ListBox4.Items.Count = 0 Then
            Exit Sub '何もなければ終了
        End If

        m.result_flg = False
        Call m.DBsave(Text) 'テーブル名を持って SQL の処理へ
        If m.result_flg = True Then '成功フラグが立っていたら
            m.DBrefresh() '再読込
            DataToForm()
            MessageBox.Show("登録しました。")
        End If
    End Sub
End Class