none
DataGridView内のコンボボックス選択時、バインド先のDataTableを即更新する方法 RRS feed

  • 質問

  • いつも大変お世話になっています。

    開発環境:Win7 x86 Visual Studio 2013 C#

    表題の通り、

    「DataGridView内のコンボボックス選択時、バインド先のDataTableを即更新する方法」

    があればご教授ください。

    DataGridViewにDataTableをバインドさせています。

    DataGridViewの構成は、起動後に作成していきます。

    今テストしている構成は、DataGridViewにコンボボックス4列です。

    Formの構成は、上半分をDataGridView、下半分をイメージ表示エリアとし、

    DataGridViewの入力が更新されるたびに、イメージも更新させています。

    TextBoxColumnであれば、セルの移動のタイミングでイメージを更新させるのでうまくいっています。、

    ComboBoxColumnではカレントセルのまま、選択直後にイメージ表示を更新させたい考えています。

    下記のソースのように、

    コンボボックスでの選択が変更された時点で(dataGridViewComboBox_SelectionChangeCommitted())、

    イメージの更新を行っていますが、DataTableが更新されていないので、イメージも変わりません。

    また、EndEdit()を試してみましたが、ダメでした(十分に理解できていません)。

    解決策がないようであれば、コンボボックス選択後、自動で次の列に移動する(Tabキー発生)方法はありますでしょうか?

    以上、よろしくお願いいたします。

    //--- 試してみましたがダメでした ---//
    //            dataGridView1.EndEdit();
    //            dataTable.Rows[dataGridView1.CurrentCell.RowIndex].EndEdit();
    //            System.Windows.Forms.DataGridViewRow dgr = this.dataGridView1.CurrentRow;
    //            System.Data.DataRowView drv = (System.Data.DataRowView)dgr.DataBoundItem;
    //            drv.EndEdit();
    //--- 試してみましたがダメでした ---//

            // ----------------------------------------------------------------------------------
            // コンボボックスの選択が変更された時、カードイメージを更新するための実装↓↓↓↓↓↓
            // ----------------------------------------------------------------------------------
            /// <summary>
            /// 編集中の行番号
            /// </summary>
            /// <remarks></remarks>
            private int _editingRow;
    
            private DataGridViewComboBoxEditingControl dataGridViewComboBox = null;
    
    
    
            /// <summary>
            /// セルが編集中になった時の処理
            /// </summary>
            /// <param name="sender">イベントの発生元</param>
            /// <param name="e">イベントの情報</param>
            /// <remarks>編集中のTextBoxEditingControlにKeyPressイベント設定</remarks>
            private void dataGridView1_EditingControlShowing(
                object sender, DataGridViewEditingControlShowingEventArgs e)
            {
                //表示されているコントロールがDataGridViewComboBoxEditingControlか調べる
                if (e.Control is DataGridViewComboBoxEditingControl)
                {
                    DataGridView dgv = (DataGridView)sender;
    
                    //編集のために表示されているコントロールを取得
                    this.dataGridViewComboBox =
                        (DataGridViewComboBoxEditingControl)e.Control;
                    //SelectionChangeCommittedイベントハンドラを追加
                    this.dataGridViewComboBox.SelectionChangeCommitted +=
                        new EventHandler(dataGridViewComboBox_SelectionChangeCommitted);
    
                    _editingRow = dgv.CurrentRow.Index;
                }
            }
    
    
            //CellEndEditイベントハンドラ
            private void DataGridView1_CellEndEdit(object sender,
                DataGridViewCellEventArgs e)
            {
                //SelectionChangeCommittedイベントハンドラを削除
                if (this.dataGridViewComboBox != null)
                {
                    this.dataGridViewComboBox.SelectionChangeCommitted -=
                        new EventHandler(dataGridViewComboBox_SelectionChangeCommitted);
                    this.dataGridViewComboBox = null;
                }
            }
    
            //DataGridViewに表示されているコンボボックスの
            //SelectionChangeCommittedイベントハンドラ
            private void dataGridViewComboBox_SelectionChangeCommitted(object sender,
                EventArgs e)
            {
    
    //--- 試してみましたがダメでした ---//
    //            dataGridView1.EndEdit();
    //            dataTable.Rows[dataGridView1.CurrentCell.RowIndex].EndEdit();
    //            System.Windows.Forms.DataGridViewRow dgr = this.dataGridView1.CurrentRow;
    //            System.Data.DataRowView drv = (System.Data.DataRowView)dgr.DataBoundItem;
    //            drv.EndEdit();
    //--- 試してみましたがダメでした ---//
    
                // カードイメージの更新
                dataGridView1_Update(_editingRow, false);     // 即カードイメージ更新
            }
            // --------------------------------------------------------------------------------
            // コンボボックスの選択が変更された時、カードイメージを更新するための実装↑↑↑↑↑
            // --------------------------------------------------------------------------------
    


    kizakura_ui

    2015年10月1日 4:34

回答

すべての返信

  • 検索しただけですが、以下の2つの方法で実現できそうな気がします。用途によって、2つの方法を使い分けられると良いと思います。

    commit changed in DataGridView when selection changed in ComboBox
    http://stackoverflow.com/questions/4737646/commit-changed-in-datagridview-when-selection-changed-in-combobox

    DataGridView ComboBox Column: Change cell value after selection from dropdown is made?
    http://stackoverflow.com/questions/9608343/datagridview-combobox-column-change-cell-value-after-selection-from-dropdown-is


    ★良い回答には回答済みマークを付けよう! MVP - .NET  http://d.hatena.ne.jp/trapemiya/

    • 回答としてマーク kizakura_ui 2015年10月1日 5:46
    2015年10月1日 4:53
    モデレータ
  • ご指導ありがとうございます。

    選択後にDataTableが更新され、思い通りのイメージが表示されました。

    長い時間悩んでいたので、本当に助かりました。

    質問時には記載していなかったのですが、

    下記コードのように、選択データをそのままDataTableにセットするのではなく、

    対応するコードをセットするよう設定しています。

    教えていただいた一つ目の方法は、

    選択データがそのままDataTableにセットされてしまうので使えませんでしたが、

    二つ目の方法では、ちゃんとコードがセットされていました。

    >用途によって、2つの方法を使い分けられると良いと思います。

    すごい!と感動しています。

    ありがとうございました。

    今後とも、ご指導よろしくお願いいたします。

                        //現在のセルだけにコンボボックス表示
                        c.DisplayStyleForCurrentCellOnly = true;
                        //DataGridViewComboBoxColumnのDataSourceを設定
                        c.DataSource = format.stt[i].Table;
                        //実際の値が"Value"列、表示するテキストが"Display"列とする
                        c.ValueMember = "Code";
                        c.DisplayMember = "Display";
    


    kizakura_ui

    2015年10月1日 5:58