0

我有一个在注册期间使用的 z3c.form。其中一个字段是用户可能希望注册的电子邮件列表。

from zope import schema
from zope.schema.vocabulary import SimpleVocabulary

emailVocab = SimpleVocabulary.fromItems((
    ('sysn', u'System notifications (strongly recommended)'),
    ('mark', u'Marketing emails'),
    ('offe', u'Special offers')))

...

email_optin = schema.List(
    title = u'',
    description = u'',
    required = False,
    value_type = schema.Choice(source=emailVocab))

我希望默认选择其中的第一个,而其他不应该。我在规范中看不到这样做的方法。有任何想法吗?

4

1 回答 1

0

最简单的情况如使用 zope.schema 进行建模,默认值部分中所记录的那样z3c.form相关文档)。然而,由于默认值不应该是可变的,因为实例是在所有东西之间共享的,所以这很复杂,因此为了安全起见,defaultFactory实现了一个参数来处理这个问题。把所有这些放在一起,你应该有这样的东西:

import zope.schema
import zope.interface
from zope.schema.vocabulary import SimpleVocabulary

emailVocab = SimpleVocabulary.fromItems((
    ('sysn', u'System notifications (strongly recommended)'),
    ('mark', u'Marketing emails'),
    ('offe', u'Special offers')))

def default_email():
    return [u'Special offers']  # example


class IEmailPreference(zope.interface.Interface):

    # ...

    email_optin = zope.schema.List(
        title=u'',
        description=u'',
        required=False,
        value_type=zope.schema.Choice(source=emailVocab),
        defaultFactory=default_email,
    )

请注意,用于默认值的实际值不是token零件而是value零件,因此返回的是字符串'Special offers'而不是'offe'. 它记录在有关 Vocabularies 的文档中。如果人类可读的部分是标题,并且您希望实际值与令牌相同,则需要相应地调整代码。否则,要选择第一个,您只需default_emailreturn [u'System notifications (strongly recommended)']

为了完整起见,您的表单模块可能如下所示:

from z3c.form.browser.checkbox import CheckBoxFieldWidget
from z3c.form.form import Form

class EmailPreferenceForm(Form):

    fields = z3c.form.field.Fields(IEmailPreference)
    fields['email_optin'].widgetFactory = CheckBoxFieldWidget

或者,如果您不希望为此使用默认值或工厂填充接口,则可以使用值鉴别器来解决此问题,但这需要付出更多的努力,因此我通常会避免在这种情况下处理该问题够好了。

于 2015-08-18T03:54:02.937 回答