Xpage Custom Controls not displaying in edit mode - xpages

I have an xPage with a couple custom controls. One CC nested inside the other. When I place the xPage into edit mode the innermost CC does not swich to edit mode but it's containing CC does. What am I missing here? The edit button is just a simple 'change document mode' action.
xPage Code
<?xml version="1.0" encoding="UTF-8"?>
<xp:view xmlns:xp="http://www.ibm.com/xsp/core"
xmlns:xc="http://www.ibm.com/xsp/custom">
<xp:this.data>
<xp:dominoDocument var="document1" formName="Test"></xp:dominoDocument>
</xp:this.data>
<xp:button value="Edit" id="button1">
<xp:eventHandler event="onclick" submit="true" refreshMode="complete">
<xp:this.action>
<xp:changeDocumentMode mode="edit" var="document1"></xp:changeDocumentMode>
</xp:this.action></xp:eventHandler></xp:button>
<xp:button value="Submit" id="button2">
<xp:eventHandler event="onclick" submit="true"
refreshMode="complete" immediate="false" save="true">
</xp:eventHandler>
</xp:button>
<xc:Outer></xc:Outer>
</xp:view>
Outer Custom Control
<?xml version="1.0" encoding="UTF-8"?>
<xp:view xmlns:xp="http://www.ibm.com/xsp/core"
xmlns:xc="http://www.ibm.com/xsp/custom">
<xp:this.data>
<xp:dominoDocument var="document1" formName="Test"></xp:dominoDocument>
</xp:this.data>
<xp:table style="border-color:rgb(0,64,128);border-style:solid;border-width:medium">
<xp:tr>
<xp:td>
<xp:label id="label1" value="Outer CC"></xp:label>
</xp:td>
<xp:td>
<xp:button value="Edit" id="button1">
<xp:eventHandler event="onclick" submit="true"
refreshMode="complete">
<xp:this.action>
<xp:changeDocumentMode mode="edit"></xp:changeDocumentMode>
</xp:this.action>
</xp:eventHandler>
</xp:button>
<xp:button value="Submit" id="button2"><xp:eventHandler event="onclick" submit="true" refreshMode="complete" immediate="false" save="true"></xp:eventHandler></xp:button></xp:td>
</xp:tr>
<xp:tr>
<xp:td>
<xp:label value="Outer Field" id="label2"></xp:label>
</xp:td>
<xp:td>
<xp:inputText id="inputText1"
value="#{document1.FieldOuter}">
</xp:inputText>
</xp:td>
</xp:tr>
<xp:tr>
<xp:td></xp:td>
<xp:td></xp:td>
</xp:tr>
<xp:tr>
<xp:td></xp:td>
<xp:td>
<xc:Inner></xc:Inner></xp:td>
</xp:tr>
</xp:table>
</xp:view>
Inner Custom Control
<?xml version="1.0" encoding="UTF-8"?>
<xp:view xmlns:xp="http://www.ibm.com/xsp/core">
<xp:this.data>
<xp:dominoDocument var="document1" formName="Test"></xp:dominoDocument>
</xp:this.data>
<xp:table style="border-color:rgb(255,128,0);border-style:solid;border-width:medium">
<xp:tr>
<xp:td>
<xp:label value="Inner CC" id="label1"></xp:label>
</xp:td>
<xp:td>
<xp:button value="Edit" id="button1"><xp:eventHandler event="onclick" submit="true" refreshMode="complete">
<xp:this.action>
<xp:changeDocumentMode mode="edit" var="document1"></xp:changeDocumentMode>
</xp:this.action></xp:eventHandler></xp:button>
<xp:button value="Submit" id="button2"><xp:eventHandler event="onclick" submit="true" refreshMode="complete" immediate="false" save="true"></xp:eventHandler></xp:button></xp:td>
</xp:tr>
<xp:tr>
<xp:td>
<xp:label value="Field Inner" id="label2"></xp:label>
</xp:td>
<xp:td>
<xp:inputText id="inputText1" value="#{document1.FieldInner}"></xp:inputText>
</xp:td>
</xp:tr>
</xp:table>
</xp:view>

Each Custom Control and your xpage all have a datasource but they have the same name and are bound to the same document as they are not ignoring request params. The Change Document Mode button is looking for the first datasource on the page with the var specified and changing that to read only and hence only updating for fields that are bound to that datasource. I would ensure you only have a single datasource with the same name and work it that way.

Related

How to prevent server side validation from running when a button is clicked?

I have a required Edit Box in a facet of a dynamic content control. Client side validation is disabled. I want to have a cancel button in this facet that will take the user back to the previous facet they were on. The part I cannot figure out is how to tell the Edit Box to not run the validation when the Cancel button is clicked.
Here is my cancel button:
<xp:button value="Cancel" id="button1">
<xp:eventHandler event="onclick" submit="true" refreshMode="complete">
<xp:this.action><![CDATA[#{javascript:getComponent("dc").show(sessionScope.backBtn);}]]></xp:this.action>
</xp:eventHandler>
</xp:button>
Here is the required edit box:
<xp:inputText id="inputText1" value="#{document1.Vendor}" required="true" disableClientSideValidation="true">
<xp:this.validators>
<xp:validateRequired message="Vendor name is a required field."></xp:validateRequired>
</xp:this.validators>
</xp:inputText>
You need the immediate attribute on true, see example; immediate="true"
<xp:button id="buttonCancel" themeId="Button.Danger">
<i class="fa fa-undo"></i>
<xp:this.value><![CDATA[#{javascript:language.getLanguageString("button.cancel")}]]></xp:this.value>
<xp:eventHandler event="onclick"
submit="true" refreshMode="complete" immediate="true"
save="false">
<xp:this.action>
<xp:actionGroup>
<xp:executeScript
script="#{javascript:viewStateBean.restoreState = true}">
</xp:executeScript>
<xp:openPage
name="/languages.xsp">
</xp:openPage>
</xp:actionGroup>
</xp:this.action>
</xp:eventHandler>
</xp:button>
There's a property in the panel on the lefft where you can select not to run validation for the event of this button.

XPages and chained partial refresh

I would like to perform a partial refresh on a second panel after the first partial refresh has completed. This is my code from the source:
<xp:comboBox id="comboBox3" value="#{document1.Company}">
<xp:selectItem itemLabel="Select a Company" itemValue="Select a Company">
</xp:selectItem>
<xp:selectItems>
<xp:this.value><![CDATA[#{javascript:var db = sessionScope.serverPath + "!!" + sessionScope.dbName; #Trim(#Unique(#DbColumn(db, "vwTblCompany",1)));}]]></xp:this.value>
</xp:selectItems>
<xp:eventHandler event="onclick" submit="true"
refreshMode="partial" refreshId="pnlLocation">
</xp:eventHandler>
<xp:eventHandler event="onchange" submit="true" refreshMode="partial" disableValidators="true" refreshId="pnlLocation">
<xp:this.action><![CDATA[#{javascript:getComponent("comboBox4").setValue("Select a Location");}]]></xp:this.action>
</xp:eventHandler>
<xp:eventHandler>
<xp:this.onComplete><![CDATA[function() {
XSP.partialRefreshGet("#{id:pnlApprovalInfo}");
}]]></xp:this.onComplete>
</xp:eventHandler>
</xp:comboBox>
The error I get when I click on the keyword field is:
An error occurred while updating some of the page. Cannot read property 'call' of null.
Can someone show me what I'm doing wrong?
Thanks,
Dan
Never mind. I figured out how to do it:
<xp:comboBox id="comboBox3" value="#{document1.Company}">
<xp:selectItem itemLabel="Select a Company" itemValue="Select a Company">
</xp:selectItem>
<xp:selectItems>
<xp:this.value><![CDATA[#{javascript:var db = sessionScope.serverPath + "!!" + sessionScope.dbName; #Trim(#Unique(#DbColumn(db, "vwTblCompany",1)));}]]>
</xp:this.value>
</xp:selectItems>
<xp:eventHandler event="onclick" submit="true"
refreshMode="partial" refreshId="pnlLocation">
<xp:this.onComplete><![CDATA[XSP.partialRefreshGet("#{id:pnlApprovalInfo}")]]></xp:this.onComplete>
</xp:eventHandler>

Simple Action: Open Page $$PreviousPage and download control

I have a VERY simple edit document XPage that, once I place an upload and download control on it no longer works. The save action (Speichern) just has 2 actions, Save document and Open $$PreviousPage.This works perfectly (I have 3 DataViews that I call the page from). The page seems to "flash" when I press save now, the changes are NOT saved and I land back in the EditDocument XPage. I do no see any errors. Not quite sure what the problem is :o(
Here is the code:
<?xml version="1.0" encoding="UTF-8"?>
<xp:view xmlns:xp="http://www.ibm.com/xsp/core" xmlns:xc="http://www.ibm.com/xsp/custom">
<xp:this.data>
<xp:dominoDocument var="document1" formName="fmDoc" action="editDocument">
</xp:dominoDocument>
</xp:this.data>
<xc:ccPageLayout>
<xp:this.facets>
<xp:panel xp:key="facetMiddle">
<xp:table>
<xp:tr>
<xp:td>
<xp:label value="Titel" id="titel_Label1" for="titel1">
</xp:label>
</xp:td>
<xp:td>
<xp:inputText value="#{document1.Titel}" id="titel1">
</xp:inputText>
</xp:td>
</xp:tr>
<xp:tr>
<xp:td>
<xp:label value="Datum" id="dokDatum_Label1" for="dokDatum1">
</xp:label>
</xp:td>
<xp:td>
<xp:inputText value="#{document1.dokDatum}" id="dokDatum1">
<xp:dateTimeHelper id="dateTimeHelper1">
</xp:dateTimeHelper>
<xp:this.converter>
<xp:convertDateTime type="date" dateStyle="short">
</xp:convertDateTime>
</xp:this.converter>
</xp:inputText>
</xp:td>
</xp:tr>
<xp:tr>
<xp:td>
<xp:label value="Kategorie" id="label3" for="kategorie1">
</xp:label>
</xp:td>
<xp:td>
<xp:comboBox id="kategorie1" value="#{document1.kategorie}">
<xp:selectItems>
<xp:this.value><![CDATA[#{javascript:var currDB:NotesDatabase = database;
var profileDoc:NotesDocument=currDB.getProfileDocument("configDatabase","");
var docUID=profileDoc.getItemValueString("kategorieDok");
var categoryDoc:NotesDocument = currDB.getDocumentByUNID(docUID);
var categories = categoryDoc.getItemValueString("kategorie");
#Explode(#Text(categories), ";")
}]]></xp:this.value>
</xp:selectItems>
</xp:comboBox>
</xp:td>
</xp:tr>
<xp:tr>
<xp:td>
<xp:label value="Anhänge" id="label1" for="fileUpload1">
</xp:label>
</xp:td>
<xp:td>
<xp:fileUpload id="fileUpload1" value="#{document1.anhaenge}" useUploadname="true"></xp:fileUpload>
</xp:td>
</xp:tr>
<xp:tr>
<xp:td>
<xp:label value=" " id="label2" for="fileDownload1">
</xp:label>
</xp:td>
<xp:td>
<xp:fileDownload rows="5" id="fileDownload1" displayLastModified="false" value="#{document1.anhaenge}"
hideWhen="true" displayType="false" displayCreated="false" allowDelete="true">
</xp:fileDownload>
</xp:td>
</xp:tr>
<xp:tr>
<xp:td colspan="2">
<xp:inputRichText id="inputRichText1" value="#{document1.body}">
</xp:inputRichText>
</xp:td>
</xp:tr>
<xp:tr>
<xp:td colspan="2">
<xp:button value="Abbrechen" id="button1">
<xp:eventHandler event="onclick" submit="true" refreshMode="complete" immediate="true" save="false">
<xp:this.action>
<xp:openPage name="$$PreviousPage"></xp:openPage>
</xp:this.action>
</xp:eventHandler>
</xp:button>
<xp:button value="Speichern" id="button2">
<xp:eventHandler event="onclick" submit="true" refreshMode="complete" immediate="false" save="true">
<xp:this.action>
<xp:actionGroup>
<xp:saveDocument var="document1"></xp:saveDocument>
<xp:openPage name="$$PreviousPage"></xp:openPage>
</xp:actionGroup>
</xp:this.action>
</xp:eventHandler>
</xp:button>
</xp:td>
</xp:tr>
</xp:table>
</xp:panel>
</xp:this.facets>
</xc:ccPageLayout>
</xp:view>
OK, just in case anybody else has a similar problem. What I did was set the button as type "Submit" AND added a "Save document" and "Open page" action - that was the problem. As soon as I set the button as a "normal" button everything worked. Hope this helps somebody else!

Issue deleting documents from dialogbox

When deleting a document from a dialog box extension library. I'm facing an issue "Error: Domino Document has been deleted.". I have a repeat control with an icon trash for deleting document.
Using this code on a link and I setup a full refresh onclick
var deleteUNID = ItemOrderRow.getUniversalID();
var doc:NotesDocument = database.getDocumentByUNID(deleteUNID);
doc.remove(true);
Any idea how to counter the issue ?
Thx
I'd like to see more code, but I'm going to guess that the issue is what you're refreshing. I assume you're doing a partial refresh? You should be refreshing the repeat control I'd think. I suspect you're refreshing "ItemOrderRow"...
I think the problem is that you are not deleting the version of the document in memory, Try this instead:
ItemOrderRow.getDocument().remove(true)
or possibly
ItemOrderRow.remove(true)
Here is a part of the content of my dialog box:
<xp:table>
<xp:tr>
<xp:td colspan="2">
<xp:label value="Item Name" id="lblItemName">
</xp:label>
</xp:td>
<xp:td>
<xp:label value="Quantity" id="lblQuantity">
</xp:label>
</xp:td>
<xp:td>
<xp:label value="Unit price" id="lblPrice">
</xp:label>
</xp:td>
<xp:td>
<xp:label value="Value" id="lblOrderValue">
</xp:label>
</xp:td>
<xp:td>
<xp:label value="Client #" id="lblClientNumber"></xp:label>
</xp:td>
<xp:td colspan="2">
<xp:label value="Relation type" id="lblRelationType">
</xp:label>
</xp:td>
</xp:tr>
<xp:repeat id="rptArtOrder" rows="50" value="#{view3}" indexVar="ArtOrder" var="ItemOrderRow">
<xp:tr>
<xp:td>
<xp:link escape="true" id="delOrder">
<xp:image url="/trashcan.png" id="image2">
</xp:image>
<xp:eventHandler event="onclick" submit="true" refreshMode="complete">
<xp:this.action><![CDATA[#{javascript:
/*var deleteUNID = ItemOrderRow.getUniversalID();
var doc:NotesDocument = database.getDocumentByUNID(deleteUNID);
doc.remove(true);*/
ItemOrderRow.getDocument().removePermanently(true)}]]></xp:this.action>
</xp:eventHandler>
</xp:link>
</xp:td>
<xp:td>
<xp:text escape="true" id="OrCartItemName">
<xp:this.value><![CDATA[#{javascript:ItemOrderRow.getColumnValue("CartItemName")}]]></xp:this.value>
</xp:text>
</xp:td>
<xp:td>
<xp:text escape="true" id="OrCartItemQuantity">
<xp:this.value><![CDATA[#{javascript:ItemOrderRow.getColumnValue("CartItemQuantity")}]]></xp:this.value>
</xp:text>
</xp:td>
<xp:td>
<xp:text escape="true" id="OrCartItemPrice">
<xp:this.value><![CDATA[#{javascript:ItemOrderRow.getColumnValue("CartItemPrice")}]]></xp:this.value>
</xp:text>
</xp:td>
<xp:td>
<xp:text escape="true" id="OrCartItemValue">
<xp:this.value><![CDATA[#{javascript:ItemOrderRow.getColumnValue("$42")}]]></xp:this.value>
</xp:text>
</xp:td>
<xp:td>
<xp:inputText id="inputText1"></xp:inputText>
</xp:td>
<xp:td>
<xp:comboBox id="comboBox2">
<xp:selectItem itemLabel="-- Choose a relation type --">
</xp:selectItem>
<xp:selectItem itemLabel="type1">
</xp:selectItem>
<xp:selectItem itemLabel="type2">
</xp:selectItem>
</xp:comboBox>
</xp:td>
<xp:td>
</xp:td>
</xp:tr>
</xp:repeat>
</xp:table>

Radio button group Select & Change / onChange

It looks like the Select & Change / onChange event is not being called for my radion button group. In the SSJS sample below, the onChange event of radio button group should set the value of the edit box and also do a full update. Neither seems to be occurring.
<xp:radioGroup id="radioGroup1">
<xp:selectItem itemLabel="One"></xp:selectItem>
<xp:selectItem itemLabel="Two"></xp:selectItem>
<xp:selectItem itemLabel="Three"></xp:selectItem>
<xp:eventHandler event="onchange" submit="true"
refreshMode="complete">
<xp:this.action><![CDATA[#{javascript:getComponent("inputText1").setValue(getComponent("radioGroup1").getValue());}]]></xp:this.action>
</xp:eventHandler>
</xp:radioGroup>
On Select should set this: <xp:inputText id="inputText1"></xp:inputText>
<xp:br></xp:br>
Selected Value: <xp:text escape="true" id="computedField1" style="font-weight:bold"><xp:this.value><![CDATA[#{javascript:return getComponent("radioGroup1").getValue();}]]></xp:this.value></xp:text>
<xp:br></xp:br>
<xp:button value="Update" id="button1">
<xp:eventHandler event="onclick" submit="true"
refreshMode="complete">
</xp:eventHandler></xp:button>
<xp:br></xp:br>
OnChange event for a radio group doesn't work properly in IE. OnClick event works. So you need to write code based on the browser, as follows.
<xp:radioGroup id="radioGroup1">
<xp:selectItem itemLabel="One"></xp:selectItem>
<xp:selectItem itemLabel="Two"></xp:selectItem>
<xp:selectItem itemLabel="Three"></xp:selectItem>
<xp:eventHandler event="onchange" submit="true" refreshMode="partial" refreshId="panelRadioVal" rendered="#{javascript:!context.getUserAgent().isIE()}" />
<xp:eventHandler event="onclick" submit="true" refreshMode="partial" refreshId="panelRadioVal" rendered="#{javascript:context.getUserAgent().isIE()}" />
</xp:radioGroup>
<xp:panel id="panelRadioVal">
<xp:inputText value="#{javascript:getComponent('radioGroup1').getSubmittedValue()}" />
</xp:panel>
It looks like your first getComponent in your eventhandler should be "inputText1" not "inputText".
Also, why perform a full update and not a partial refresh? Just trying to understand the business case.

Resources