2

I have several fields on my Notes Document

FieldA_1 FieldA_2 FieldA_3 FieldA_4

FieldB_1 FieldB_2 FieldB_3 FieldB_4

On a composite control I have 2 edit boxes FieldA FieldB

I have a compositeData.ATM_NUM defined a custom control that is a drop down list with the values 1,2,3,4.

How do I bind the edit boxes on my control to their corresponding document fields using the composite data available?

For example, I wanted to do something like: "FieldA_"+ compositeData.ATM_NUM.

I tried the javascript solution in this thread:

Binding an edit box within a custom control to a form field programatically

But it did not seem to work.

Community
  • 1
  • 1
Bruce Stemplewski
  • 1,343
  • 1
  • 23
  • 66

3 Answers3

11

Try the following as value for e.g. field A:

<xp:inputText value="#{document['FieldA'+compositeData.ATM_NUM]}" />

You could also extend the property of the custom control to include the whole field name (and thereby transfer e.g. "FieldA_1" to the custom control). Then you should be able to do the following:

<xp:inputText value="#{document[compositeData.fieldName]}" />
Per Henrik Lausten
  • 21,331
  • 3
  • 29
  • 76
  • 3
    You might also want to check out this explanation of the technique Per is recommending: http://stackoverflow.com/questions/9719778/xpages-more-fields-unlimited-at-the-click-of-a-button/9720793#9720793 – Tim Tripcony Mar 28 '12 at 19:16
  • I tried value="#{document1[CMBUExistTermID+compositeData.ATM_NUM]}" but I got an error. I am going to try the field thing but would rather avoid it if I can. I'd like to figure out how to do it with just my composite "number" field. – Bruce Stemplewski Mar 28 '12 at 19:24
  • Also tried value="#{document1['CMBUExistTermID' + '4']}" which gives an error An exception occured trying to convert String "CMBUExistTermID" to type "java.lang.Double" but alue="#{document1['CMBUExistTermID4']}" works fine. – Bruce Stemplewski Mar 28 '12 at 19:37
  • is ATM_NUM a number? then you probably need to convert to a string: value="#{document1[CMBUExistTermID+compositeData.ATM_NUM.toString()]}" – Per Henrik Lausten Mar 28 '12 at 19:41
  • No ATM_NUM is a string. Besides even value="#{document1['CMBUExistTermID' + '4']}" gives me that double exception and it should not. – Bruce Stemplewski Mar 28 '12 at 19:45
  • Did you try this (with quotes around the first part of the field name)?: value="#{document1['CMBUExistTermID'+compositeData.ATM_NUM]}" – Per Henrik Lausten Mar 28 '12 at 19:52
  • Yes that is basically what I posted above. value="#{document1['CMBUExistTermID' + '4']}" I really wish these comments were easier to read, they are way to crowded. Easy to miss something. – Bruce Stemplewski Mar 28 '12 at 20:08
  • Yes, but please try with value="#{document1['CMBUExistTermID'+compositeData.ATM_NUM]}" because I suspect that the test with '4' tries to convert the first string to a double. – Per Henrik Lausten Mar 28 '12 at 20:22
  • let us [continue this discussion in chat](http://chat.stackoverflow.com/rooms/9429/discussion-between-bruce-stemplewski-and-per-henrik-lausten) – Bruce Stemplewski Mar 28 '12 at 20:47
  • 2
    Read/write bindings must be plain EL, which has a far more restrictive syntax than SSJS. If you wrap the field in a panel, you can define a dataContext, set its value to whatever expression you want to evaluate the field name, then pass its var to the data source in the field binding. Alternatively, you can wrap it in a Custom Control that accepts the field name as a parameter, then reference the compositeData in the field binding. – Tim Tripcony Mar 29 '12 at 08:17
6

An example for data binding for a custom control is this:

Create a custom control, add 2 custom properties: BindTo (String), canEdit (Boolean). Quite often you have the need to have a field readonly based on the state of your business logic rather than the fact that the rest is in edit mode.

 <xp:listBox id="listBox1"
        rendered="#{compositeData.canEdit}">
        <xp:this.value><![CDATA[${javascript:"#{"+compositeData.BindTo+"}"}]]></xp:this.value>
        <xp:selectItem itemLabel="red"></xp:selectItem>
        <xp:selectItem itemLabel="blue"></xp:selectItem>
        <xp:selectItem itemLabel="green"></xp:selectItem>
 </xp:listBox>
 <xp:text id="textForListbox"
        rendered="#{!compositeData.canEdit}">
        <xp:this.value><![CDATA[${javascript:"#{"+compositeData.BindTo+"}"}]]></xp:this.value>
 </xp:text>

The advantage of this approach (using ${javascript:"#{"+compositeData.BindTo+"}"}) is that you can bind that control to anything: a document, a scope variable, a bean etc.

stwissel
  • 20,110
  • 6
  • 54
  • 101
5

The problem is related to the time that compositeData is ready for your use. At the start it evaluates to "0" when your custom control is ready.

Try this:

<xp:inputText id="inputText1" 
           value="${javascript:'#{document1.SomeField'+compositeData.SomeParam+'}'}">
</xp:inputText>

It's important to use "$" sign there. It will create a binding to SomeField1, SomeField2 and so forth depending on SomeParam.

Serdar Basegmez
  • 3,355
  • 16
  • 20
  • Thanks Serdar, I tried that but it did not work. No errors or anything just did not populate the field as expected. Here is the actual formula I used. value="${javascript:'#{document1.CMBUAction'+compositeData.ATM_NUM+'}'}"> – Bruce Stemplewski Mar 29 '12 at 12:46
  • OK, where is the document1 defined? Inside CC or in the XPage? – Serdar Basegmez Mar 29 '12 at 13:01
  • I spoke too soon. It is working perfectly. What is the purpose of the $? Is any of this documented anywhere? – Bruce Stemplewski Mar 29 '12 at 14:07
  • $ implies that the inside script will be calculated once in the load phase. If you don't use $, the returning statement will not be evaluated as EL. I have used this for dynamic fields. In my case, a repeat control was creating Field1, Field2 like bindings for a dynamic questionnaire where number of questions were preconfigured. – Serdar Basegmez Mar 29 '12 at 14:44