ddraper

Aikau - Updates to Dynamic Visibility Config

Blog Post created by ddraper on Oct 28, 2014

Introduction

In this previous blog post I introduced the concept of dynamic visibility rules in Aikau page models. In the course of working on some prototype pages for features pencilled in for Alfresco 5.1 I realised that there were a few useful capabilities missing. This post is going to cover the new options that are available for declaratively configuring visibility rules.

 

 

Strict Mode

I was doing some more work on pickers (see this post for more info) and was trying to re-use the code we had for defining the classic picker style of 2 vertical lists with add, remove and re-order controls.

 

In the old YUI2 style pickers we had (e.g. for selecting tags) we don't hide the selected item (just the control for adding it) and I wanted to improve on this so that a picked item would be removed from the list of available items (but would be revealed when removed).

 

The current visibilityConfig options prevented this because the rules were defined such that if a rule was not evaluated to be true then the widget would be hidden. In actual fact what we want is a more flexible mode where only successfully evaluated rules will reveal a widget, but failed evaluation will have no effect.

 

I've now added in an additional attribute called 'strict' that is a boolean value (that defaults to true if omitted for backwards compatibility) that implements this feature, when a widget is configured with the following visibilityConfig:

...
visibilityConfig: {
  initialValue: true,
  rules: [
    {
      topic: 'ALF_REVEAL_WIDGET',
      attribute: 'reveal',
      is: [true],
      strict: false
    }
  ]
}
...

 

...then publishing the following payload on the 'ALF_REVEAL_WIDGET' topic:

{
  reveal: false
}

 

Will not hide the widget, because the 'strict' attribute is set to false. If the 'strict' attribute was set to true then the publication would result in the widget being hidden.

 

Invisibility Configuration

When trying to use the original visibilityConfig I realised that it was sometimes difficult (if not impossible) to configure a rule that just hid a widget.

 

When setting up the rules for the picker widget I wanted to define one rule that made an item appear (when removed from the picked item list) and another rule to make the item disappear (when added to the picked item list).

 

The problem was that I only knew what an attribute in the payload should be and not what it shouldn't be. Therefore I added the ability to configure 'invisibilityConfig' as well as 'visibilityConfig'.

 

This takes exactly the same attributes but when the rule is satisfied the widget will be hidden instead of revealed, e.g:

...
invisibilityConfig: {
  rules: [
    {
      topic: 'ALF_HIDE_WIDGET',
      attribute: 'hide',
      is: [true]
    }
  ]
},
...

 

...will result in a widget being hidden when the following payload is published on the 'ALF_HIDE_WIDGET' topic:

{
  hide: true
}

 

NOTE: Because we've omitted the 'strict' attribute publishing any other payload on the topic will result in the widget being revealed.

 

Using Current Item Data

In this previous blog I described how we could use the 'currentItem' attribute for controlling when widgets are rendered. The 'currentItem' attribute is typically assigned when to widgets that are created when iterating over items in a list (although any widget can be defined with a 'currentItem' attribute).

 

in the picker example I wanted to make use of the 'currentItem' attribute when defining 'visibilityConfig' and 'invisibilityConfig' because the rules would need to be specific to each rendered row in the list of pick-able items.

 

This was solved by adding in support for a new 'useCurrentItem' attribute (that defaults to false) that treats each value in the 'is' and 'isNot' arrays as a dot-notation property address in the 'currentItem'.

 

Putting It All Together

The end result of these 3 new attributes was the following configuration:

...
visibilityConfig: {
  rules: [
    {
      topic: 'ALF_ITEM_REMOVED',
      attribute: 'name',
      is: ['name'],
      useCurrentItem: true,
      strict: false
    }
  ]
},
invisibilityConfig: {
  rules: [
    {
      topic: 'ALF_ITEM_SELECTED',
      attribute: 'name',
      is: ['name'],
      useCurrentItem: true,
      strict: false
    }
  ]
},
...

 

This defines the behaviour that when an item that has the same name as the current item is selected (published on the 'ALF_ITEM_SELECTED' topic) it will be hidden, and when an item that has the same name as the current item is removed (published on the 'ALF_ITEM_REMOVED' topic) it will be displayed again.

Outcomes