はじめに
Windows Forms の ComboBox を使っていると、
「選択が変わったときに何か処理をしたい」という場面が必ず出てきます。
そんなときの基本となるイベントが SelectedIndexChanged です。
💡 一言でいうと:
「選択されているインデックス(SelectedIndex)が変わったら呼ばれるイベント」です。
ユーザー操作でも、プログラムから変更しても発生します。
「選択されているインデックス(SelectedIndex)が変わったら呼ばれるイベント」です。
ユーザー操作でも、プログラムから変更しても発生します。
SelectedIndexChangedイベントとは?
SelectedIndexChanged は、ComboBox の SelectedIndex プロパティが変化したときに発生するイベントです。
- ユーザーがドロップダウンから別の項目を選択したとき
- コードで
SelectedIndexを変更したとき(例:comboBox1.SelectedIndex = 0;) - Items や DataSource を変更した結果、現在の選択が変わったとき
これらの場合に、SelectedIndexChanged イベントハンドラが呼び出されます。
イベントの基本的な使い方
デザイナーでの設定
- フォームデザイナーで ComboBox を選択
- プロパティウィンドウで「イベント(稲妻アイコン)」をクリック
SelectedIndexChangedをダブルクリック
これで、フォームコードにハンドラメソッドが自動生成されます。
コードでイベントを登録する
public Form1()
{
InitializeComponent();
comboBox1.SelectedIndexChanged += comboBox1_SelectedIndexChanged;
}
private void comboBox1_SelectedIndexChanged(object sender, EventArgs e)
{
// 選択が変わったときの処理を書く
MessageBox.Show($"選択されたインデックス: {comboBox1.SelectedIndex}\n" +
$"選択された項目: {comboBox1.SelectedItem}");
}
実用例:選択内容に応じてラベル表示を変える
選択された項目に応じて、ラベルの内容を更新するシンプルな例です。
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
comboBox1.Items.AddRange(new[]
{
"Python",
"C#",
"Java",
"JavaScript"
});
comboBox1.SelectedIndexChanged += comboBox1_SelectedIndexChanged;
comboBox1.SelectedIndex = 0; // 初期選択
}
private void comboBox1_SelectedIndexChanged(object sender, EventArgs e)
{
label1.Text = $"今選んでいる言語: {comboBox1.SelectedItem}";
}
}
ユーザーが項目を切り替えるたびに、ラベルの表示も自動で切り替わるようになります。
SelectionChangeCommittedとの違い
ComboBox には SelectedIndexChanged に似たイベントとして
SelectionChangeCommitted があります。
違いをざっくり表にすると次のようになります。
| イベント名 | 発生タイミング | コードから選択変更した場合 |
|---|---|---|
SelectedIndexChanged |
SelectedIndex が変わったときは常に | ✔ 発生する |
SelectionChangeCommitted |
ユーザー操作により選択が確定したとき | ✖ 原則発生しない |
📝 使い分けの目安
・「ユーザーが選んだときだけ処理したい」 →
・「コードから選択変更した場合も含めて処理したい」 →
・「ユーザーが選んだときだけ処理したい」 →
SelectionChangeCommitted・「コードから選択変更した場合も含めて処理したい」 →
SelectedIndexChanged
よくあるパターンとサンプル
選択インデックスを使うパターン
private void comboBox1_SelectedIndexChanged(object sender, EventArgs e)
{
int index = comboBox1.SelectedIndex;
switch (index)
{
case 0:
labelDetail.Text = "初心者向けの説明を表示します。";
break;
case 1:
labelDetail.Text = "中級者向けの説明を表示します。";
break;
case 2:
labelDetail.Text = "上級者向けの説明を表示します。";
break;
default:
labelDetail.Text = "レベルを選択してください。";
break;
}
}
SelectedValue を使う(DataSource + ValueMember の場合)
private void comboBoxDept_SelectedIndexChanged(object sender, EventArgs e)
{
if (comboBoxDept.SelectedValue is int deptId)
{
labelDeptInfo.Text = $"選択された部門ID: {deptId}";
// deptId を使ってDBから詳細を取得する…など
}
}
初期化時に余計なイベントが走る問題への対処
Items や DataSource を設定した直後にも SelectedIndex が変化するため、
フォームのロード時に SelectedIndexChanged が発生してしまうことがあります。
その場合、次のようにフラグでガードするのが定番です。
private bool _isInitializing = true;
public Form1()
{
InitializeComponent();
comboBox1.SelectedIndexChanged += comboBox1_SelectedIndexChanged;
comboBox1.Items.AddRange(new[] { "A", "B", "C" });
comboBox1.SelectedIndex = 0; // ここでイベントが飛ぶ可能性
_isInitializing = false;
}
private void comboBox1_SelectedIndexChanged(object sender, EventArgs e)
{
if (_isInitializing)
{
// 初期化中は何もしない
return;
}
// 本来の処理
label1.Text = $"選択: {comboBox1.SelectedItem}";
}
🔐 ロード処理やデータ再読込のたびに「余計な処理が走っている気がする…」という場合は、
フラグを導入してイベントを無効化するのがおすすめです。
フラグを導入してイベントを無効化するのがおすすめです。
ありがちな落とし穴
- ハンドラ内で SelectedIndex を変更して無限ループ
イベントハンドラの中でSelectedIndexを書き換えると、その変更でまたイベントが発生します。
必要に応じてフラグで一時的に無効化するか、変更が本当に必要なときだけ実行するように条件分岐しましょう。 - 重い処理を直接書きすぎる
SelectedIndex が変わるたびに DB アクセスや Web API 呼び出しを行うと、
コンボボックスの操作が重く感じられることがあります。
可能なら非同期処理やキャッシュを検討しましょう。 - SelectedItem/SelectedValue が null のケース
Items が 0 件、SelectedIndex = -1 の場合などは、SelectedItemやSelectedValueがnullになります。
先にSelectedIndex >= 0を確認してからアクセスすると安全です。
まとめ
SelectedIndexChangedは 「選択されたインデックスが変わったとき」に発生するイベント。- ユーザー操作だけでなく、コードから SelectedIndex を変更した場合も発生する。
- ユーザー操作だけを扱いたい場合は
SelectionChangeCommittedも検討。 - 初期化中やデータ再読込時に余計な処理が走る場合は、フラグでガードする。
- 重い処理・再帰的な SelectedIndex 変更には注意。
ComboBox を使った UI では、SelectedIndexChanged はほぼ必須のイベントです。
まずは単純に「ラベルのテキストを変える」といった用途から使い始めて、
徐々に DataSource・SelectedValue を組み合わせた本格的な画面制御へ広げていきましょう。
Please follow and like us:

コメント