Should have said I'm using InfoPath 2007.
Anyway after countless attempts today I've semi-worked out the issue. It comes down to how the underlying schema is defined. If for instance I have a 'header' and 'items', with a 1-to-many relationship, I would need intermediate XML Group setup as optional.
Header 0 -n Items
Instead have:
Header 0-1 ItemGroup 0-n Items
This intermediate group would create, when dragging the fields from the datasource to the InfoPath Manifest, another optional section. The optional section, within properties ,this would have the XML ID that can be referred to within the code. Else you'll end up with a repeatable table and its container section without and XML I and hence wont be able to create the InnerXML. Wierd eh !!!
Code:
using Microsoft.Office.InfoPath;
using System;
using System.Windows.Forms;
using System.Xml;
using System.Xml.XPath;
using mshtml;
namespace GR
{
public partial class FormCode
{
// Member variables are not supported in browser-enabled forms.
// Instead, write and read these values from the FormState
// dictionary using code such as the following:
//
// private object _memberVariable
// {
// get
// {
// return FormState["_memberVariable"];
// }
// set
// {
// FormState["_memberVariable"] = value;
// }
// }
// NOTE: The following procedure is required by Microsoft Office InfoPath.
// It can be modified using Microsoft Office InfoPath.
public void InternalStartup()
{
((ButtonEvent)EventManager.ControlEvents["btSave"]).Clicked += new ClickedEventHandler(btSave_Clicked);
}
#region Utils
#region Check Nodes
public void DeleteNil(XPathNavigator node)
{
if (node.MoveToAttribute("nil", "http://www.w3.org/2001/XMLSchema-instance"))
node.DeleteSelf();
}
#endregion
#region DateFormat
private string formatPeriod(int Period)
{
string sPeriodFormat = string.Empty;
if (Period < 10)
{
sPeriodFormat = string.Format("0{0}", Period);
}
else
{
sPeriodFormat = string.Format("{0}", Period);
}
return sPeriodFormat;
}
private string formatDate(DateTime Date, bool JustDate)
{
// The date format must including preceeding zeros where less than 10.
// if the datatype defined as dateTime then must include the time as well.
if (JustDate)
{
return string.Format("{0}-{1}-{2}", Date.Year, formatPeriod(Date.Month), formatPeriod(Date.Day));
}
else
{
// Includes Time format
return string.Format("{0}-{1}-{2}T{3}:{4}:{5}", Date.Year, formatPeriod(Date.Month), formatPeriod(Date.Day), formatPeriod(Date.Hour), formatPeriod(Date.Minute), formatPeriod(Date.Second));
}
}
#endregion
#endregion
public void btSave_Clicked(object sender, ClickedEventArgs e)
{
// Save Changes
XPathNavigator xn = MainDataSource.CreateNavigator();
// Loop through the Items
XPathNodeIterator myXPathNodeIterator = xn.Select("/myFields/ItemGroup/Item", this.NamespaceManager);
// Loop through each item and create a goods receipt.
while (myXPathNodeIterator.MoveNext())
{
XPathNavigator navCurrent = myXPathNodeIterator.Current;
XPathNavigator xItem = navCurrent.SelectSingleNode("Qty", this.NamespaceManager);
string sQty = xItem.Value;
// Find the container group and create a new Goods Receipt Row
XPathNavigator xGroup = navCurrent.SelectSingleNode("GroupGR", this.NamespaceManager);
AddNewRow(ref xGroup);
// Now reference newly created row
XPathNavigator xnNewRow = navCurrent.SelectSingleNode("GroupGR/GR[last()]", this.NamespaceManager);
xnNewRow.SelectSingleNode("GRQty", this.NamespaceManager).SetValue(sQty);
// Delete empty GR
deleteEmptyGR(ref navCurrent);
}
}
private void deleteEmptyGR(ref XPathNavigator navCurrent)
{
// Issue with some of the Goods Receipt Rows being populated without rows
// Simply loop through them and delete accordingly
int iDeletionIndex = 0;
bool bEmptyRecordFound = false;
XPathNodeIterator xGR_Iterator = navCurrent.Select("GroupGR/GR", this.NamespaceManager);
while (xGR_Iterator.MoveNext())
{
iDeletionIndex++;
XPathNavigator xGRCurrent = xGR_Iterator.Current;
XPathNavigator xGRQty = xGRCurrent.SelectSingleNode("GRQty", this.NamespaceManager);
if (xGRQty.Value == null || xGRQty.Value == "" || xGRQty.Value == string.Empty)
{
// Assuming only one record found
bEmptyRecordFound = true;
break;
}
}
if (bEmptyRecordFound)
{
XPathNavigator xDelete = navCurrent.SelectSingleNode("GroupGR/GR[" + iDeletionIndex + "]", this.NamespaceManager);
xDelete.DeleteSelf();
}
}
public void AddNewRow(ref XPathNavigator docXN)
{
// Select the Container Node
XPathNavigator xnNode = this.Template.Manifest.SelectSingleNode("//xsf:xDocumentClass/xsf:views/xsf:view[@name='Entry']/xsf:editing/xsf:xmlToEdit[@name='GroupGR_2']/xsf:editWith/xsf:fragmentToInsert/xsf:chooseFragment/GroupGR", this.NamespaceManager);
//Append the node from the Manifest file to the main DOM
docXN.AppendChild(xnNode.InnerXml);
}
}
}