Category Archives: Developing with IBM Content Navigator

Display a new icon for each row

This post we’ll go through how to add a new custom icon, next to the lock, compound, … icons.

This is not something that can be done with configuration in ICN. It needs some customization which is near hacking but that will give us what we want.

First step, if you are intending to display an icon based on a custom property, you will have to, either add the property as an icon so it gets fetched, or customize ICN to fetch it, this is explain here.

When this is done, you can proceed to the customization of the client to use the property and display the icon. This is a 2 step process.

  • Aspect the factory of IconValue which is the multiStateIcon method of the class ecm.widget.listview.decorators.common to add your icon when toString is called on the returned object
  • Aspect the createResultSet method of the class ecm.model.ContentItem to increase the size of the first column of the Content list view

First will result in this customization, here I’m using an existing class (ecmRecordIcon) since we are not using it, but you can add some css code in the css of your plugin and use your own icon of course:

// No need to use .prototype on common since it's already a Singleton, no instance are create with new
aspect.after(common, "multiStateIcon", function (result) {
    aspect.after(result, "toString", function (resToString) {
        if (this.item && this.item.attributes.MultiFiledIn) {
            resToString += '<img class="ecmStatusIcon ecmRecordIcon" alt="Multi Filed In Document" title="Multi Filed In Document" src="' + this._blankGif + '" />';
            resToString += '<div class="dijitHidden">Multi Filed In Document</div>';
        }
        return resToString;
    });
    return result;
});

The second will look like this:

// ContentItem.createResultSet is a static method from ContentItem, no need to aspect the prototype
aspect.after(ContentItem, "createResultSet", function (result) {
    if (result && result.structure && result.structure.cells && result.structure.cells.length > 0) {
        var s = result.structure.cells[0][0];
        s.width = "71px"; // 71 is good for one new icon, add 16 per icon
        s.widthWebKit = "71px"; // You can also reuse te value and just add 16px to make it more flexible and cleaner
    }
    return result;
});

And this is it. This way the IconValue will add your icon when its toString is called, and the resultSet will add some extra space to make sure it is still displayed on one line.

Use a custom property in Action.isVisible or isEnabled

Sometimes, we want to use a custom property to decide if an action should be displayed, enabled or hidden. The items provided by ICN as parameters of these functions are items as they are shown in the view, as rows. They don’t have all properties fetched, only the system ones and the ones you configured to be shown as extra columns (since they have to be fetched in order to be displayed).

As you may have noticed when overriding the isVisible and isEnabled functions, they are synchronous and they expect an immediate return. That means fetching the attributes using the item.retrieveAttributes function won’t work since it’s an asynchronous function (there is one round trip made to the ICN server to fetch them).

In this post, we’ve seen how to fetch custom attributes for all rows without showing them in a column. We will now see another way to do this, by making the ContextMenu actually asynchronous. Since the isVisible and isEnabled functions are synchronous, we will actually retrieve the attributes before showing the Context Menu for the item.
Continue reading

Fetch a custom property for all objects or rows

This post explains how to fetch a custom property you’ve added on a class for all documents retrieved by ICN, before all attributes are actually retrieved using the ContentItem.retrieveAttributes function. That means all items when displayed as row in the Content List view will have this property (also named attribute in ICN) already fetched. There are use cases for this, two of them being:

  • Using a custom attribute in the isVisible or isEnable function of an action, to decide if the action should be displayed based on business logic. I wrote about this here
  • Using a custom property to display a new icon along with the lock/compound/readon-only/… icons. I wrote about this here

After spending some time investigating how ICN works to know what custom properties to fetch when retrieving the content of a folder (openFolder action), I came to the conclusion it goes through two steps:
Continue reading

Create your custom attribute editor (part 6)

Last part of this tutorial will be about enhancing our editor to make it a bit nicer. The idea is to create a property editor to select a file within the repository. We will use the DocumentSelector dialog we wrote here.

We are actually really close of achieving this, we will just hook up the click event of the input field to start the DocumentSelector dialog, and we will also add a Browse button on the right of the input to make it more user-friendly.
Continue reading

Write a filtered Repository File Selector Dojo dialog

This tutorial will explain how to write a dialog allowing users to choose a file in a repository with a pretty tree selector. We will also add a feature to filter files based on extension. The tree will only show documents ending with a valid filter.

This is the final result:

ICN_FileChooser_01

Continue reading

Create your custom attribute editor (part 5)

Add custom settings to your editor

We learned in previous parts how property editors work, how to write a custom editor, a widget for the editor, and how to test it.

In this part, we will learn how to add custom settings to your editor, located right below the editor select box in the Entry Template Designer tool. It looks like this: (remember, in our current version there is nothing)

ICN_editor_settings_7

Settings are part of the the editorConfig you are injecting in the ControlRegistry object (ControlRegistry.editors.editorConfigs array). The config can have a settings property, which is an array of object defining the settings. Here is how it looks like:
Continue reading

Create your custom attribute editor (part 4)

To summarize what we’ve done so far:

  • In part 1, we created a new plugin and learned how to inject a custom editor in the ICN configuration
  • In part 2, we wrote our custom editor
  • In part 3, we wrote our custom widget

We will now deploy the plugin and use our custom editor in an entry template. Then we will add a new document using this entry template, and we should see our custom editor in used.
Continue reading

Create your custom attribute editor (part 3)

Create the widget

In part 2, we learned how to write the Editor and how to inject it in the ICN configuration. In this part, we will write the widget used to edit the property value.

For this tutorial , we will focus on a simple widget, composed only of a text box. I will add an extra part at the end of this tutorial describing a more complex widget.

HTML Template

As you may already know, a dojo widget (dijit) is made of two files, the dojo class (JavaScript) and the template (HTML). First, let’s create the html template, defining our widget presentation. Create the file customEditorPluginDojo/widgets/templates/MyCustomTextWidget.html and paste in it the following content:


<div class="myClass">
    <!-- The node that should get the focus should have the focusNode attach point. pvr/widget/_Property._createEditorWidget needs this because it wants to set the aria-labelledby on it -->
    <input data-dojo-type="ecm.widget.ValidationTextBox" data-dojo-attach-point="inputField,focusNode" name="${id}_inputText" id="${id}_inputText" />
</div>

Continue reading

Create your custom attribute editor (part 2)

Create the editor

In part 1, we learned how to inject our new editor in the list of existing editors in order to use it in the Entry Template Designer tool. That’s sweet, but we still don’t have a custom editor. We could, of course use the existing ones (take a look at the pvr/widget/editors folder) if they fit our needs, but if not, this is how to create a new editor from scratch.

Basics

The basic idea is quite simple, an editor is a dojo widget, extending :

  • the widget used for editing (TextBox, CheckBox, Select, Custom Widget, …): Allows you to edit the value of the property
  • The pvr/widget/editors/mixin/_EditorMixin class: Takes care of all communication between the property object and your editor widget

So let’s start with creating our editor file customEditorPluginDojo/editors/MyCustomEditor.js. The skeleton of our editor will be:
Continue reading

Create your custom attribute editor (part 1)

In this series of posts, we will learn how to develop and use a new attribute/property editor in your Entry Template layout.

ICN_editor_settings

This is not as easy as it first sounds, so I will split this tutorial in 6 parts.

Here is the summary of all parts, they should be taken in order.

  1. Part 1: Principle and configuration injection
  2. Part 2: Create the editor
  3. Part 3: Create the widget
  4. Part 4: Deploy and test
  5. Part 5: Add custom settings
  6. Part 6: Create a fancier widget and extra editor configuration

First part, how is it all connected

It’s good to start with some basic comprehension of how the editor mechanism works in ICN. The most important class is the ecm/model/configuration/ControlRegistry class

Everything starts with this class, this is the main registry storing the configuration of the editors. This consists of:

  • The editors configuration: Label, class, options
  • The mappings: types/cardinality to editor and free/choices/coumpound to editor

This is how looks this class:
Continue reading