I'd like to generate list of files with checkboxes. I've tried to use FieldList but it doesn't work as I expected. Instead of checkbox with assigned filename I'm getting checkbox with label named after the variable containing FieldList object. Is there any way to fix it?
app.py:
from flask import Flask, render_template
from flask_bootstrap import Bootstrap
from flask_wtf import FlaskForm
from wtforms import BooleanField, FieldList, SubmitField
app = Flask(__name__)
app.config['SECRET_KEY'] = 'development'
Bootstrap(app)
filenames = ['1.jpg', '2.jpg', '3.jpg', '4.jpg']
class FileListForm(FlaskForm):
filename = FieldList(BooleanField(), 'Files')
submit = SubmitField('Submit')
@app.route('/')
def listfiles():
form = FileListForm()
for filename in filenames:
form.filename.append_entry(filename)
return render_template('index.html',
form=form)
if __name__ == '__main__':
app.run(debug=True, port=5001)
templates/index.html
{% import "bootstrap/wtf.html" as wtf %}
{{ wtf.quick_form(form) }}
packages:
click==6.7
dominate==2.3.1
Flask==0.12.2
Flask-Bootstrap==3.3.7.1
Flask-WTF==0.14.2
itsdangerous==0.24
Jinja2==2.9.6
MarkupSafe==1.0
visitor==0.1.3
Werkzeug==0.12.2
WTForms==2.1
According to the documentation, WTForms' FieldList
shouldn't be used with BooleanField
:
Note: Due to a limitation in how HTML sends values,
FieldList
cannot encloseBooleanField
orSubmitField
instances.
(Even though the HTML output appears valid.) That said, you're not seeing what you're expecting to see because append_entry
's first parameter accepts the form input's value, not its label.
Instead, I'd recommend creating the form class dynamically:
filenames = ['1.jpg', '2.jpg', '3.jpg', '4.jpg']
class FileListFormBase(FlaskForm):
submit = SubmitField('Submit')
def file_list_form_builder(filenames):
class FileListForm(FileListFormBase):
pass
for (i, filename) in enumerate(filenames):
setattr(FileListForm, 'filename_%d' % i, BooleanField(label=filename))
return FileListForm()
@app.route('/')
def listfiles():
form = file_list_form_builder(filenames)
return render_template('index.html', form=form)
Note: The default HTML representation will have the "Submit" button at the top, since the library renders fields in the order they're defined. WTForms doesn't natively support ordering, so this may be a better solution for you even though it's less elegant:
filenames = ['1.jpg', '2.jpg', '3.jpg', '4.jpg']
def file_list_form_builder(filenames):
class FileListForm(FlaskForm):
pass
for (i, filename) in enumerate(filenames):
setattr(FileListForm, 'filename_%d' % i, BooleanField(label=filename))
setattr(FileListForm, 'submit', SubmitField('Submit'))
return FileListForm()
@app.route('/')
def listfiles():
form = file_list_form_builder(filenames)
return render_template('index.html', form=form)
この記事はインターネットから収集されたものであり、転載の際にはソースを示してください。
侵害の場合は、連絡してください[email protected]
コメントを追加