親です。

読んだ本とかについて書いてます

【Python】Django - プルダウンのフォームを作る

おつです。Djangoをいじっている中でプルダウンメニューが作りたくなったので、その作り方を簡単にまとめます。

あと技術記事は大体こっちに移転したのでこちらのブログも読んでもらえると好きがこぼれ落ちます。

moryata.com

基本の作り方はふたつ

基本的な作り方は二つある。forms.pyで指定するやりかたと、models.pyで指定するやりかた。

①forms.pyで指定する
これが一番シンプル。あらかじめ定数リストにプルダウンメニューの中身をセットしてあげて、それを表示させる。

# forms.py

# プルダウンの選択肢
CHOICES = (
    ("request.POSTの中身", "画面に表示される内容")
    ("0", "1,000")
    ("1", "2,000")
    ("2", "3,000")
    ("3", "4,000")
)
class InputForm(forms.Form):
    """定数リストによるプルダウンメニュー"""
    pulldown = forms.ChoiceField(widget=forms.Select, 
                                 choices=CHOICES, # 定数リストを指定する
                                 label="ラベル名")

②models.pyで指定
これもノリとしては同じ。modelをそもそも選択肢の中から選ぶようにしている。

# プルダウンの選択肢
CHOICES = (
    ("request.POSTの中身", "画面に表示される内容")
    ("0", "1,000")
    ("1", "2,000")
    ("2", "3,000")
    ("3", "4,000")
)

class InputArea(models.Model):
    # 入力必須
    pulldown = models.CharField(verbose_name="カラム名", 
                                choices=CHOICES)

かつ、forms.pyでこのmodelを引き込んでやれば良い。

発展的なやり方

発展的なやり方として、プルダウンに表示するリストを動的に取得するというのがある。詳しいやり方は下記リンクから見れる。

qiita.com

基本的な作りとしては、

book = forms.ModelChoiceField(label='book',queryset=Book.objects.all())

という感じ。
ModelChoiceFieldってのが、モデルを活かす(intとかの指定をしなくて良い)感じのフォームを作るよという意味で、かつ、querysetって引数で選択肢にしたいリストを指定している。querysetって名前からもわかるように、ここの引数にはDjangoのモデルから何か取ってくるときみたいなコードを書く。(ORマッパーでの操作を書く)

で、ここからは俺が困っちゃったことなんだけど、modelで取得できたobjectなんだけど、俺はあるモデルのあるカラムを取得したかったんですよ。けど、実際上のように書くと、指定しているモデルの代表みたいなカラムが出てきてしまう。(strで返している値だと思う)
これだとあんまり意味なくて、うーんどうしようかなって感じ。俺みたいにあるモデルの特定のカラムに登録されている値を重複なく取り出してプルダウンに動的にセットする、みたいなのしたい人たくさんいる気がするんだけど、残念ながらまだインターネットにはそういう情報は出てきてない。もし知っていたら教えて欲しいところだ。今は内包表記で頑張って定数リストを作成しています。

その後思ったこと

やってないけど、model_viewみたいな感じでformの再定義をしてつどつどviewでリストを作成して渡してあげるとかは可能なんじゃないかなって思った。分からんけど。

以上!!!