#665 複数値のリストで選択値を先頭に表示する方法 フォーム、クエリ

テーブルのデザインで「複数の値の許可」プロパティが”はい”に設定されているフィールドをフォームに表示した場合、その複数値がひとつの欄にカンマ区切りで列挙されて表示されます。


また、その値を変更・追加・削除したい場合は、その値を直接編集することはできず、ドロップダウンリストのチェックボックスのON/OFFで切り替えを行います。


このドロップダウンリストには、その値集合ソースにもよりますが、テーブルの主キーやクエリの並べ替え順でデータが表示されます。また値集合ソースのすべてのデータが表示されますので、チェックマークを付けるにもしても外すにしても、それを探すのに手間が掛かるかもしれません。

そこで、その並び順を変更して、現在チェックマークが付いている項目をまず先頭に表示し、付いていない項目をそれ以降に表示する方法を紹介します。
※ここでは、チェックマークが付いているグループについてはさらにその中で「仕入先ID」順に表示し、付いていないグループについてもその中では「仕入先ID」順に表示させるようにします。

それには、そのコントロールの「値集合ソース」となっているクエリの内容を下記のように作り替えます。

変更前のクエリ
ここでは単一のクエリでその値集合ソースを作っています。

SELECT 仕入先ID, 会社名
FROM 仕入先
ORDER BY 仕入先ID;






変更後のクエリ
複数のクエリを使って値集合ソースを構成します。

まず第1段階として、フォームのカレントレコードに表示されている「商品コード」の「仕入先ID」だけをリストアップするクエリを作ります(ここではその名前を「qsel商品マスタ複数値リスト_sub」とします)。

SELECT 商品コード, 仕入先.Value AS 仕入先ID
FROM mtbl商品マスタ
WHERE 商品コード=[Forms]![frm商品マスタ複数値リスト]![商品コード];





ここで、FROM句に指定されている「mtbl商品マスタ」はフォームのレコードソースとなっているテーブルです。また、フォーム名は「frm商品マスタ複数値リスト」です。また「仕入先」ではなく「仕入先.Value」の方をSELECTすることで、ひとつの「仕入先」フィールドに保存されている複数値をそれぞれ1レコードとして出力するようにしています。これらの設定によりこのクエリでは「frm商品マスタ複数値リスト」フォームのカレントレコードの商品コードに準じた仕入先がリストアップされることになります。

次に第2段階として、ドロップダウンリストに表示するデータの大元である「仕入先」テーブルと、上記で作った「qsel商品マスタ複数値リスト_sub」クエリとを結合したクエリを作ります。

SELECT 仕入先.仕入先ID, 会社名
FROM 仕入先 LEFT JOIN qsel商品マスタ複数値リスト_sub ON 仕入先.仕入先ID = qsel商品マスタ複数値リスト_sub.仕入先ID
ORDER BY CLng(Nz([qsel商品マスタ複数値リスト_sub].[仕入先ID],99999999)), 仕入先.仕入先ID;



ここでのポイントのひとつは、チェックの有無に関わらず「仕入先」テーブルの全レコードを表示しなければいけないので、両者の結合方法を『'仕入先' の全レコードと 'qsel商品マスタ複数値リスト_sub' の同じ結合フィールドのレコードだけを含める。』に設定することです。



さらに、並び順を想定したものにするためにもう一工夫します。チェックが付いたものを先に持ってくるために、その基準とする下記のような演算フィールドを設けます。

  式1: CLng(Nz([qsel商品マスタ複数値リスト_sub].[仕入先ID],99999999))

ここでは、「qsel商品マスタ複数値リスト_sub」クエリ上に「仕入先」テーブルと同じ仕入先IDが存在していればその値をそのまま使い、もしなければ(上記結合方法の場合はNullとなっています)、”99999999”といったようなあり得ない適当な大きな数値に置き換えています。その上でそのフィールドを「昇順」に設定することによって、チェックマークの付いた仕入先IDが先に表示されることになります。

あとは、チェックあり/なしそれぞれのグループ内でさらに「仕入先ID」順に並べ替えるので、「仕入先」テーブルの方の「仕入先ID」を2つめの「昇順」として設定します。

※上記2つの「昇順」設定のフィールドは非表示とします(クエリデザインビューの「表示」行のチェックマークを外します)。




変更後のクエリの再クエリ
最後に、フォームのプログラムとして簡単なコードを追加する必要があります。 上記のクエリはフォームのカレントレコードの値を参照していますが、一度参照されるとフォーム側でレコードが移動しても参照先は自動では切り替わりません。そこで、フォーム側でレコードが移動するたびにそのコントロール(ここでは「仕入先」)を再クエリし、移動後のレコードの値を参照し直すようにしてやります。

それには、次のようなコードをフォームのモジュールに記述します。

Private Sub Form_Current()
'フォームのレコード移動時

  Me!仕入先.Requery

End Sub



実行例
| Index | Prev | Next |



T'sFactory
Accessで動く生産管理DB
Ureru Express
Webで使う販売顧客管理
Access開発&アドバイス
DB開発やテクニカルアドバイス
Copyright © T'sWare All rights reserved