美文网首页OdooOdoo程序员
Odoo10开发教程八(向导与国际化)

Odoo10开发教程八(向导与国际化)

作者: luohuayong | 来源:发表于2017-04-06 08:57 被阅读1705次

    向导

    向导以动态形式描述与用户(或对话框)的交互式会话。向导与其他的模型不同,其基类是TransientModel而不是常见的ModelTransientModel类扩展自Model,并使用了其所有机制,具有以下特殊性:

    • 向导记录不是永久性的,会在一段时间后自动从数据库中删除。这就是为什么他们被称为瞬态
    • 向导模型不需要访问权限:用户拥有向导记录的所有权限
    • 向导记录可以通过many2one字段引用普通记录或向导记录,但普通记录无法通过many2one引用向导记录。
      我们要创建一个向导,用来让用户可以生成授课的参与者,或者一次创建一个授课列表。

    练习定义向导
    创建一个向导模型,这个向导模型通过many2one关联授课模型,并通过many2many关联合作伙伴模型。添加新文件openacademy/wizard.py

    openacademy/__init__.py

    from . import controllers
    from . import models
    from . import partner
    from . import wizard
    

    openacademy/wizard.py

    # -*- coding: utf-8 -*-
    
    from odoo import models, fields, api
    
    class Wizard(models.TransientModel):
        _name = 'openacademy.wizard'
    
        session_id = fields.Many2one('openacademy.session',
            string="Session", required=True)
        attendee_ids = fields.Many2many('res.partner', string="Attendees")
    
    启动向导

    向导通过ir.actions.act_window记录来启动,target字段设置值为new。后者将在一个弹出窗口中打开向导。操作可以有菜单项触发。还有另外一种方式来启动向导:使用类似于上面的ir.actions.act_window记录,但有一个额外字段src_model,指定那个模型的操作可用。该向导将出现在模型主视图的上下文操作中。因为这是在ORM中的内部钩子,所以这个操作通过在XML文件的act_window标签中进行定义。

    <act_window id="launch_the_wizard"
                name="Launch the Wizard"
                src_model="context.model.name"
                res_model="wizard.model.name"
                view_mode="form"
                target="new"
                key2="client_action_multi"/>
    

    向导使用常规视图并且它的按钮可以使用special="cancel"来关闭向导窗口而不需要保持。

    练习启动向导

    1. 为向导定义一个form视图
    2. 在授课模型的上下文中添加action用于启动向导
    3. 给向导的session字段定义默认值;使用上下文参数self._context来获取当前授课

    openacademy/wizard.py

    class Wizard(models.TransientModel):
        _name = 'openacademy.wizard'
    
        def _default_session(self):
            return self.env['openacademy.session'].browse(self._context.get('active_id'))
    
        session_id = fields.Many2one('openacademy.session',
            string="Session", required=True, default=_default_session)
        attendee_ids = fields.Many2many('res.partner', string="Attendees")
    

    openacademy/views/openacademy.xml

                      parent="openacademy_menu"
                      action="session_list_action"/>
    
            <record model="ir.ui.view" id="wizard_form_view">
                <field name="name">wizard.form</field>
                <field name="model">openacademy.wizard</field>
                <field name="arch" type="xml">
                    <form string="Add Attendees">
                        <group>
                            <field name="session_id"/>
                            <field name="attendee_ids"/>
                        </group>
                    </form>
                </field>
            </record>
    
            <act_window id="launch_session_wizard"
                        name="Add Attendees"
                        src_model="openacademy.session"
                        res_model="openacademy.wizard"
                        view_mode="form"
                        target="new"
                        key2="client_action_multi"/>
        </data>
    </odoo>
    

    练习注册与会者
    给向导添加按钮,并且实现相应的方法,将与会者添加到给定的授课。

    openacademy / views / openacademy.xml

                            <field name="attendee_ids"/>
                        </group>
                        <footer>
                            <button name="subscribe" type="object"
                                    string="Subscribe" class="oe_highlight"/>
                            or
                            <button special="cancel" string="Cancel"/>
                        </footer>
                    </form>
                </field>
            </record>
    

    openacademy/wizard.py

        session_id = fields.Many2one('openacademy.session',
            string="Session", required=True, default=_default_session)
        attendee_ids = fields.Many2many('res.partner', string="Attendees")
    
        @api.multi
        def subscribe(self):
            self.session_id.attendee_ids |= self.attendee_ids
            return {}
    

    练习与会者注册多个授课
    修改向导模型,以便与会者可以注册到多个授课

    openacademy/views/openacademy.xml

                    <form string="Add Attendees">
                        <group>
                            <field name="session_ids"/>
                            <field name="attendee_ids"/>
                        </group>
                        <footer>
                            <button name="subscribe" type="object"
    

    openacademy/wizard.py

    class Wizard(models.TransientModel):
        _name = 'openacademy.wizard'
    
        def _default_sessions(self):
            return self.env['openacademy.session'].browse(self._context.get('active_ids'))
    
        session_ids = fields.Many2many('openacademy.session',
            string="Sessions", required=True, default=_default_sessions)
        attendee_ids = fields.Many2many('res.partner', string="Attendees")
    
        @api.multi
        def subscribe(self):
            for session in self.session_ids:
                session.attendee_ids |= self.attendee_ids
            return {}
    

    国际化

    每个模块都可以在i18n目录提供自己的翻译,文件名的形式为LANG.po,其中LANG是语言的代码,或者是语言和国家的组合,例如:pt.po(葡萄牙语)和pt_BR.po(巴西葡萄牙语)。对于所有开启的语言,Odoo都会自动载入翻译。开发者总是使用英语建立模块,然后使用Odoo的文本POT导出功能导出模块术语(设置->翻译->导入/导出->导出翻译),生成模块的POT模板文件,然后到处PO翻译文件。许多IDE具有用于编辑和合并PO/POT文件的插件或功能。

    提示
    把Odoo生成的导出文件公布在Transifex,可以轻松的使用软件进行翻译。

    |- idea/ # The module directory
       |- i18n/ # Translation files
          | - idea.pot # Translation Template (exported from Odoo)
          | - fr.po # French translation
          | - pt_BR.po # Brazilian Portuguese translation
          | (...)
    

    提示
    默认情况下Odoo的POT导出仅提取XML文件的标签和Python代码中的字段定义,但是任何Python字符串都可以翻译,通过使用odoo._()方法,例如_("Label")


    练习
    翻译一个模块
    为已经安装的Odoo模块选择第二语言。使用Odoo提供的功能对模块进行翻译。

    1. 创建目录openacademy/i18n/
    2. 安装任意一种你希望的语言 (设置->翻译->加载翻译
    3. 同步翻译术语(设置->翻译->应用程序术语->同步术语
    4. 导出不指定语言的翻译模板文件(设置->翻译->导入/导出->导出翻译),保存在openacademy/i18n/
    5. 导出指定语言的翻译文件(设置->翻译->导入/导出->导出翻译),保存在openacademy/i18n/
    6. 打开导出的翻译文件(使用任意一款文本编辑软件或者专用的PO文件编辑器,例如POEdit然后翻译其中的术语)
    7. models.py文件中,为odoo._方法添加一个导入声明,并且标记需要翻译的字符串
    8. 重复3-6的步骤

    openacademy/models.py

    # -*- coding: utf-8 -*-
    
    from datetime import timedelta
    from odoo import models, fields, api, exceptions, _
    
    class Course(models.Model):
        _name = 'openacademy.course'
    
            default = dict(default or {})
    
            copied_count = self.search_count(
                [('name', '=like', _(u"Copy of {}%").format(self.name))])
            if not copied_count:
                new_name = _(u"Copy of {}").format(self.name)
            else:
                new_name = _(u"Copy of {} ({})").format(self.name, copied_count)
    
            default['name'] = new_name
            return super(Course, self).copy(default)
    
            if self.seats < 0:
                return {
                    'warning': {
                        'title': _("Incorrect 'seats' value"),
                        'message': _("The number of available seats may not be negative"),
                    },
                }
            if self.seats < len(self.attendee_ids):
                return {
                    'warning': {
                        'title': _("Too many attendees"),
                        'message': _("Increase seats or remove excess attendees"),
                    },
                }
    
        def _check_instructor_not_in_attendees(self):
            for r in self:
                if r.instructor_id and r.instructor_id in r.attendee_ids:
                    raise exceptions.ValidationError(_("A session's instructor can't be an attendee"))
    

    相关文章

      网友评论

        本文标题:Odoo10开发教程八(向导与国际化)

        本文链接:https://www.haomeiwen.com/subject/mzpuottx.html