SQLFORM あれこれ ④ の続きです。今回も SQLFORM.grid を使ったカスタマイズを説明します。
SQLFORM.grid のカスタマイズ(一覧表示)
前回記事で、SQLFORM.grid の一覧表示画面を紹介した。
一覧画面のカスタマイズ用に使用可能なパラメータが、いくつか存在する。
表示項目を指定したり、項目の並び順を変えるカスタマイズでは、fields パラメータを使用する。項目のフィールド名を変更する場合は headers パラメータを指定する。サンプルコードは次のようになる。
1 2 3 4 5 6 7 8 | @auth.requires_login() def manage(): fields = [db.image.name, db.image.category] headers = {'image.name':T('Name'), 'image.category':T('Category')} grid = SQLFORM.grid(db.image, upload=URL(c='default', f='download'), fields=fields, headers=headers, csv=False) return dict(grid=grid) |
コードを実行すると、次の画面イメージが表示される。
少し説明すると、fields には、表示する Fieldオブジェクトを指定する。これはリスト値で、指定順に表示される。
headers は、辞書値でフィールドと名前を指定する。ここでは翻訳オブジェクトである T を使って、名前を指定している。
この他、csv パラメータも指定しているが、これは CSVエクスポートを無効にしている。
ここまでは普通の設定だ。もう少し難しいことを試してみよう。画像データがあるため、画像を表示するカスタマイズを試してみる。
テーブルに存在しないフィールドを表示するには、links パラメータを使用する。もともと links はレコードと関連するリンクを表示するためにあるようだが、無名関数(lambda)も使用可能なため、画像表示にも利用可能だ。links は、次のようにリスト値で指定する。
links =[lambda row: IMG(_src=row.url, _width=50, _height=40, _id='image') if row.url else IMG(_src=URL(c='default', f='download', args=row.file), _width=50, _height=40, _id='image')]
links で無名関数を指定した場合、パラメータとしてレコード一覧の Row オブジェクトをが渡される。このためサンプルコードでは、url に値がある場合は src 属性に urlを指定したIMGタグを、urlに値がない場合は src 属性に file を指定する。links はリスト値のため、複数の定義フィールドを指定することも可能だ。
また links でフィールドを追加する時に、タイトルを付加することも可能だ。その場合、辞書値で header と body を指定し、header にはタイトル、body にはフィールド定義を指定する。
links=[{'header':T('Image'), 'body':lambda row: IMG(_src=row.url, _width=50, _height=40, _id='image') if row.url else IMG(_src=URL(c='default', f='download', args=row.file), _width=50, _height=40, _id='image')}]
links パラメータを指定したコードを実行すると、次の画面イメージになる。
ここで注意して欲しいのは画面で、url と file フィールドも表示していることである。これは links に指定する無名関数のパラメータには、レコード一覧の Rowオブジェクトが使われるためである。つまり、無名関数で url と file フィールドを利用するために、レコード一覧に url と file が含まれている必要がある。
しかし無名関数に使用するといっても、一覧表示に url と file フィールドは不要だ。このため SQLFORM.grid の定義の前に、Fieldオブジェクトの readable 属性を False に指定する。
db.image.url.readable = db.image.file.readable = False
これによって一覧から、url と file フィールドを隠すことが可能になる。しかし、この設定で詳細表示(View)画面を表示させると、一覧と同様に url と file フィールドも表示されない。このため、ignore_rw パラメータを True に設定し、詳細画面では表示するように変更する。
以上まとめると、次のサンプルコードになる。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 | @auth.requires_login() def manage(): db.image.url.readable = db.image.file.readable = False fields = [db.image.name, db.image.category, db.image.url, db.image.file] headers = {'image.name':T('Name'), 'image.category':T('Category')} links=[{'header':T('Image'), 'body':lambda row: IMG(_src=row.url, _width=50, _height=40, _id='image') if row.url else IMG(_src=URL(c='default', f='download', args=row.file), _width=50, _height=40, _id='image')}] grid = SQLFORM.grid(db.image, upload=URL(c='default', f='download'), fields=fields, headers=headers, csv=False, links=links, ignore_rw=True) return dict(grid=grid) |
コードを実行すると画面イメージは、次のようになる。
SQLFORM.grid のカスタマイズ(新規作成・編集・詳細表示画面)
新規作成や編集、詳細表示画面などもカスタマイズ可能だ。このために次のパラメータが用意されている。
パラメータ | 制御する機能 |
---|---|
formargs | 新規作成・編集・詳細表示画面、共通パラメータ |
createargs | 新規作成画面のみ |
editargs | 編集画面のみ |
viewargs | 詳細表示画面のみ |
これらのパラメータには、通常の SQLFORM に指定できるパラメータを辞書値で設定する。サンプルコードを示してみる。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 | @auth.requires_login() def manage(): db.image.url.readable = db.image.file.readable = False fields = [db.image.name, db.image.category, db.image.url, db.image.file] headers = {'image.name':T('Name'), 'image.category':T('Category')} links=[{'header':T('Image'), 'body':lambda row: IMG(_src=row.url, _width=50, _height=40, _id='image') if row.url else IMG(_src=URL(c='default', f='download', args=row.file), _width=50, _height=40, _id='image')}] submit = BUTTON(I(_class='icon-ok icon-white', _style='margin-right: 5px;'), T('OK'), _class='btn btn-primary') cancel = BUTTON(I(_class='icon-remove', _style='margin-right: 5px;'), T('Cancel'), _class='btn', _style='margin-left:10px', _type='reset', _onclick="history.back();") formargs = {'showid':False, 'buttons':[submit,cancel]} grid = SQLFORM.grid(db.image, upload=URL(c='default', f='download'), fields=fields, headers=headers, csv=False, links=links, ignore_rw=True, formargs=formargs, onvalidation=check_image) return dict(grid=grid) |
サンプルコードでは、id の画面表示を制御する showid の設定を行うと共に、SQLFORM あれこれ③ で紹介した Twitter Bootstrap を使ったフォームボタンのカスタマイズ(buttons)を行なっている。15-20行目でオプションの定義を行い、26行目で formargs に定義したパラメータを渡している。
また、19行目で Cancel ボタンを押した場合、前ページに戻る JavaScript を設定している。これは、一覧ではページネーション(ページ割り)があるためだ。
Cancelボタンでは、location.href で page パラメータを指定していました。しかしキチンと動作しなかったため、JavaScript の history.back(); にコードを変更しました。
この他、入力値チェックのために、onvalidation パラメータも指定している。これは SQLFORM あれこれ② で最初に紹介した 次の check_image 関数を指定している。
1 2 3 4 5 6 7 8 | def check_image(form): file_delete = '%s__delete' % 'file' if form.vars.url is None and \ form.vars.file is None and (form.vars.has_key(file_delete) is False or \ form.vars.get(file_delete, False)): form.errors.url = T('must enter a url') form.errors.file = T('must select a file') |
このコードを実行すると、画面のイメージは次のようになる。
新規登録 | 編集 | 詳細表示 |
---|---|---|
編集と詳細表示の画面の左上には、links パラメータで設定した画像が表示されている。これは SQLFORM.grid の仕様により、この位置に表示されるようだ。表示・非表示を指定できるパラメータもない。もしこのイメージを非表示にしたい場合は、CSS ファイルに次の記述を追加する(links オプションで、IMGタグの id を image と指定しているため)。
.form_header>#image { display:None; }
このCSSを設定すると、画面表示は次のようになる。
編集 | 詳細表示 |
---|---|
以上で、SQLFORM.grid のカスタマイズの説明は終わりです。SQLFORM.grid はとても便利なのですが、カスタマイズには限界があります。例えば、SQLFORM あれこれ② で設定したような、DBテーブルにないフィールドを追加するとか、フィールドの属性追加や設定ができません。また一覧表示でも、編集・削除ボタンの位置変更や、links で設定したフィールドとDBフィールドの位置を入れ替えるなどの設定ができません。
このため 次回 はもう少し柔軟な設定が可能な、SQLTALBLE を使ったカスタマイズを紹介したいと思います。
SQLFORM.grid の他のパラメータについては、web2py Book に説明があります。
参考: web2py Book - SQLFORM.gridとSQLFORM.smartgrid