# Setting a field 'invisible' conditionnaly only in form view

**URL:** https://discuss.tryton.org/t/setting-a-field-invisible-conditionnaly-only-in-form-view/4186
**Category:** Developer
**Created:** [May 11, 2021, 2:06pm UTC](https://discuss.tryton.org/t/setting-a-field-invisible-conditionnaly-only-in-form-view/4186 "2021-05-11T14:06:26Z")
**Posts on this page:** 12
**Page:** 1

<div class="post-metadata">

### Author: ![maxx](https://discuss-cdn.tryton.org/user_avatar/discuss.tryton.org/maxx/32/2320_2.png) [@maxx](https://discuss.tryton.org/u/maxx)
#### Post date: [May 11, 2021, 2:06pm UTC](https://discuss.tryton.org/t/setting-a-field-invisible-conditionnaly-only-in-form-view/4186/1 "2021-05-11T14:06:27Z")

</div>

Hi, i’m customizing sale model to allow users to have also a reference field on sale\_lines. I’m doing the same way as the field ‘delivery\_date’ in purchase model.

```auto
class SaleLine(metaclass=PoolMeta):
    __name__ = 'sale.line'

    reference = fields.Function(fields.Char('Reference',
            states={
                'invisible': ((Eval('type') != 'line')
                    | Eval('reference_edit', False)),
                },
            depends=['type', 'reference_edit']),
        'on_change_with_reference')
    reference_edit = fields.Boolean(
        "Edit Reference",
        states={
            'invisible': Eval('type') != 'line',
            'readonly': Eval('sale_state').in_([
                    'done', 'cancelled']),
            },
        depends=['type', 'sale_state'],
        help="Check to edit the reference.")
    reference_store = fields.Char(
        "Reference",
        states={
            'invisible': ((Eval('type') != 'line')
                | ~Eval('reference_edit', False)),
            'readonly': Eval('sale_state').in_([
                    'done', 'cancelled']),
            },
        depends=['type', 'reference_edit', 'sale_state'])

    @classmethod
    def default_reference_edit(cls):
        return False

    @fields.depends('sale', '_parent_sale.reference', 'reference_edit',
        'reference_store')
    def on_change_with_reference(self, name=None):
        if self.reference_edit and self.reference_store:
            return self.reference_store
        if self.sale:
            return self.sale.reference

```

So users can have a reference by default which is sale\_reference in function field ‘reference’, but they could also having a different reference on the sale\_line by checking ‘reference\_edit’ and setting a value in field ‘reference\_store’

A switch is done in the view form to display the correct field (depending if ‘reference\_edit’ is checked or not):

**sale\_line\_form.xml**

```auto
<?xml version="1.0"?>
<!-- The COPYRIGHT file at the top level of this repository contains the full 
     copyright notices and license terms. -->
<data>
    <xpath expr="/form/notebook/page[@id='general']/field[@name='shipping_date']" position="after">
        <label id="reference" string="Reference:"/>
        <group id="reference" col="-1">
            <field name="reference" xexpand="0"/>
            <field name="reference_store" xexpand="0"/>
            <field name="reference_edit" xexpand="0"/>
        </group>
    </xpath>
</data>

```

Until now everything is working well…  
But i want also display that field ‘reference’ in the tree view…

**sale\_line\_tree.xml**

```auto
<?xml version="1.0"?>
<!-- The COPYRIGHT file at the top level of this repository contains the full 
     copyright notices and license terms. -->
<data>
    <xpath expr="/tree/field[@name='amount']" position="after">
        <field name="reference"/>
    </xpath>
</data>

```

My function field ‘reference’ can display the correct value depending if reference\_edit is checked or not.  
But as his state is ‘invisible’ when reference\_edit is checked, the value of ‘reference’ field is not displayed in the tree view…

So, my question:

- Is it possible to have the state ‘invisible’ only in form view ?
- Or should i create another function field ‘reference\_display’ (with the same code as ‘reference’ but without state condition to display this field correctly in the tree view ?
- Another idea ?

Thanks! 🙂

---

<div class="post-metadata">

### Author: ![pokoli](https://discuss-cdn.tryton.org/user_avatar/discuss.tryton.org/pokoli/32/22_2.png) [@pokoli](https://discuss.tryton.org/u/pokoli)
#### Post date: [May 11, 2021, 2:19pm UTC](https://discuss.tryton.org/t/setting-a-field-invisible-conditionnaly-only-in-form-view/4186/2 "2021-05-11T14:19:59Z")

</div>

We found the same problem when adding the delivery\_date of purchase lines in list view and we solved it adding another field just for displaying as you suggest here:

> [@maxx](#):
>
> Or should i create another function field ‘reference\_display’ (with the same code as ‘reference’ but without state condition to display this field correctly in the tree view ?

For me this make snse because on the list view you want to add another field which is always visible while on the form view you should show/hide two diferent fields depending on the checkbox.

---

<div class="post-metadata">

### Author: ![ced](https://discuss-cdn.tryton.org/user_avatar/discuss.tryton.org/ced/32/1237_2.png) [@ced](https://discuss.tryton.org/u/ced)
#### Post date: [May 11, 2021, 3:06pm UTC](https://discuss.tryton.org/t/setting-a-field-invisible-conditionnaly-only-in-form-view/4186/3 "2021-05-11T15:06:26Z")

</div>

I think the invisible state of `reference` should not be defined on the field but on the view (with `ModelView.view_attributes`) in such case because it depends on what is displayed.  
The standard `delivery_date` should also be fixed to use `view_attributes`.

---

<div class="post-metadata">

### Author: ![maxx](https://discuss-cdn.tryton.org/user_avatar/discuss.tryton.org/maxx/32/2320_2.png) [@maxx](https://discuss.tryton.org/u/maxx)
#### Post date: [May 12, 2021, 7:10am UTC](https://discuss.tryton.org/t/setting-a-field-invisible-conditionnaly-only-in-form-view/4186/4 "2021-05-12T07:10:28Z")

</div>

Thanks for the tip @ced  
I try this way (removing states on field reference and adding view\_attributes) but this is not working (am i missing something ? - How to know if xm path is correctly found ?) :

```auto
    reference = fields.Function(fields.Char('Reference'),
        'on_change_with_reference')
    reference_edit = fields.Boolean(
        "Edit Reference",
        states={
            'invisible': Eval('type') != 'line',
            'readonly': Eval('sale_state').in_([
                    'done', 'cancelled']),
            },
        depends=['type', 'sale_state'],
        help="Check to edit the reference.")
    reference_store = fields.Char(
        "Reference",
        states={
            'invisible': ((Eval('type') != 'line')
                | ~Eval('reference_edit', False)),
            'readonly': Eval('sale_state').in_([
                    'done', 'cancelled']),
            },
        depends=['type', 'reference_edit', 'sale_state'])

    @classmethod
    def view_attributes(cls):
        return super().view_attributes() + [
            ('/form//field[@name="reference"]',
                'states', {
                    'invisible': ((Eval('type') != 'line')
                        | (Eval('reference_edit', False))),
                }),
            ]

    @classmethod
    def default_reference_edit(cls):
        return False

    @fields.depends('sale', '_parent_sale.reference', 'reference_edit',
        'reference_store')
    def on_change_with_reference(self, name=None):
        if self.reference_edit and self.reference_store:
            return self.reference_store
        if self.sale:
            return self.sale.reference

```

**sale\_line\_form.xml**

```auto
<?xml version="1.0"?>
<!-- The COPYRIGHT file at the top level of this repository contains the full 
     copyright notices and license terms. -->
<data>
    <xpath expr="/form/notebook/page[@id='general']/field[@name='shipping_date']" position="after">
        <label id="reference" string="Reference:"/>
        <group id="reference" col="-1">
            <field name="reference" xexpand="0"/>
            <field name="reference_store" xexpand="0"/>
            <field name="reference_edit" xexpand="0"/>
        </group>
    </xpath>
</data>

```

---

<div class="post-metadata">

### Author: ![ced](https://discuss-cdn.tryton.org/user_avatar/discuss.tryton.org/ced/32/1237_2.png) [@ced](https://discuss.tryton.org/u/ced)
#### Post date: [May 12, 2021, 7:36am UTC](https://discuss.tryton.org/t/setting-a-field-invisible-conditionnaly-only-in-form-view/4186/5 "2021-05-12T07:36:27Z")

</div>

My bad the `states` attribute on the form view is not supported by the clients. This is probably because it will be ambiguous with `states` of the field.

Maybe another solution would be to add a `setter` to the `Function` field and a `readonly` states when the `edit` field is not checked (and of course for the proper state).

---

<div class="post-metadata">

### Author: ![maxx](https://discuss-cdn.tryton.org/user_avatar/discuss.tryton.org/maxx/32/2320_2.png) [@maxx](https://discuss.tryton.org/u/maxx)
#### Post date: [May 12, 2021, 7:57am UTC](https://discuss.tryton.org/t/setting-a-field-invisible-conditionnaly-only-in-form-view/4186/6 "2021-05-12T07:57:57Z")

</div>

> [@ced](#):
>
> My bad the `states` attribute on the form view is not supported by the clients. This is probably because it will be ambiguous with `states` of the field.

However, it seems used in other modules : [https://hg.tryton.org/modules/sale/file/tip/product.py#l94](https://hg.tryton.org/modules/sale/file/tip/product.py#l94)

---

<div class="post-metadata">

### Author: ![ced](https://discuss-cdn.tryton.org/user_avatar/discuss.tryton.org/ced/32/1237_2.png) [@ced](https://discuss.tryton.org/u/ced)
#### Post date: [May 12, 2021, 8:04am UTC](https://discuss.tryton.org/t/setting-a-field-invisible-conditionnaly-only-in-form-view/4186/7 "2021-05-12T08:04:30Z")

</div>

> [@maxx](#):
>
> However, it seems used in other modules : [modules/sale: 0ac079e22786 product.py](https://hg.tryton.org/modules/sale/file/tip/product.py#l94)

This is a `page` widget which is not linked to any field.

---

<div class="post-metadata">

### Author: ![maxx](https://discuss-cdn.tryton.org/user_avatar/discuss.tryton.org/maxx/32/2320_2.png) [@maxx](https://discuss.tryton.org/u/maxx)
#### Post date: [May 12, 2021, 9:04am UTC](https://discuss.tryton.org/t/setting-a-field-invisible-conditionnaly-only-in-form-view/4186/8 "2021-05-12T09:04:51Z")

</div>

> [@ced](#):
>
> Maybe another solution would be to add a `setter` to the `Function` field and a `readonly` states when the `edit` field is not checked (and of course for the proper state).

Ok, working this way 🙂 Thanks @ced and @pokoli !

```auto
     reference = fields.Function(fields.Char('Reference',
            states={
                'invisible': Eval('type') != 'line',
                'readonly': (Eval('sale_state').in_(['done', 'cancelled'])
                    | ~Eval('reference_edit')),
                },
            depends=['type', 'reference_edit', 'sale_state']),
        'on_change_with_reference', setter='set_reference_field')
    reference_edit = fields.Boolean(
        "Edit Reference",
        states={
            'invisible': Eval('type') != 'line',
            'readonly': Eval('sale_state').in_([
                    'done', 'cancelled']),
            },
        depends=['type', 'sale_state'],
        help="Check to edit the reference.")
    reference_store = fields.Char(
        "Reference",
        states={
            'readonly': Eval('sale_state').in_([
                    'done', 'cancelled']),
            },
        depends=['sale_state'])

    @classmethod
    def default_reference_edit(cls):
        return False

    @fields.depends('sale', '_parent_sale.reference', 'reference_edit',
        'reference_store')
    def on_change_with_reference(self, name=None):
        if self.reference_edit and self.reference_store:
            return self.reference_store
        if self.sale:
            return self.sale.reference

    @classmethod
    def set_reference_field(cls, lines, name, value):
        if not value:
            return
        cls.write(lines, {
                'reference_store': value,
                })

```

sale\_line\_form.xml

```auto
<?xml version="1.0"?>
<!-- The COPYRIGHT file at the top level of this repository contains the full 
     copyright notices and license terms. -->
<data>
    <xpath expr="/form/notebook/page[@id='general']/field[@name='shipping_date']" position="after">
        <label id="reference" string="Reference:"/>
        <group id="reference" col="-1">
            <field name="reference" xexpand="0"/>
            <field name="reference_edit" xexpand="0"/>
        </group>
    </xpath>
</data>

```

---

<div class="post-metadata">

### Author: ![ced](https://discuss-cdn.tryton.org/user_avatar/discuss.tryton.org/ced/32/1237_2.png) [@ced](https://discuss.tryton.org/u/ced)
#### Post date: [May 12, 2021, 9:22am UTC](https://discuss.tryton.org/t/setting-a-field-invisible-conditionnaly-only-in-form-view/4186/9 "2021-05-12T09:22:46Z")

</div>

I will be great to make the same design for existing standard modules.

---

<div class="post-metadata">

### Author: ![jaarias](https://discuss-cdn.tryton.org/user_avatar/discuss.tryton.org/jaarias/32/198_2.png) [@jaarias](https://discuss.tryton.org/u/jaarias)
#### Post date: [May 18, 2021, 8:48am UTC](https://discuss.tryton.org/t/setting-a-field-invisible-conditionnaly-only-in-form-view/4186/10 "2021-05-18T08:48:27Z")

</div>

[issue10431](https://bugs.tryton.org/issue10431) opened.

---

<div class="post-metadata">

### Author: ![jaarias](https://discuss-cdn.tryton.org/user_avatar/discuss.tryton.org/jaarias/32/198_2.png) [@jaarias](https://discuss.tryton.org/u/jaarias)
#### Post date: [June 3, 2021, 2:45pm UTC](https://discuss.tryton.org/t/setting-a-field-invisible-conditionnaly-only-in-form-view/4186/12 "2021-06-03T14:45:22Z")

</div>

I think it could be simplified using a functional also for _reference\_edit_ field, don’t you? It’s value would be _True_ when _reference\_store_ had some value, and _False_ otherwise. It would have a _setter_ that would copy the value from _reference_ to _reference\_store_ when checked and reset it if unchecked.

---

<div class="post-metadata">

### Author: ![system](https://discuss-cdn.tryton.org/uploads/default/original/1X/c6f8ec0a40525cdcd50058c734283450a4b3d38b.png) [@system](https://discuss.tryton.org/u/system)
#### Post date: [July 3, 2021, 2:46pm UTC](https://discuss.tryton.org/t/setting-a-field-invisible-conditionnaly-only-in-form-view/4186/13 "2021-07-03T14:46:11Z")

</div>

This topic was automatically closed 30 days after the last reply. New replies are no longer allowed.
