Infopath 2010 Part 2 (Cascading Dropdowns in Browser Based Forms)

One of my bug bears with Infopath 2007 was that in order to achieve cascading dropdowns of data within a browser based form this had to be achieved using code behind.Thankfully this is a new improved feature in 2010.As an example I have setup a Sharepoint list (see below) which contains a column called Customer and a column called Contact.  You will see that 3 contacts belong to customer A.

        

In my Infopath form (below) I have added a dropdown column which is bound to the customer column in the SharePoint list.  In this example I have selected Customer A.  The second dropdown for contacts pulls back the data from the contact field in the Sharepoint list but is filtered by the chosen company.Previously this wasn’t a supported feature in browser based forms.

Back to other Controls & Rule management next...

Currently rated 5.0 by 1 people

  • Currently 5/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Infopath 2010 part 1 (Infopath 2010 designing a basic form)

As previously promised I'm starting a series of blogs relating to the use of Infopath 2010.  Since the introduction of browser based Infopath forms to compliment the client version this is an application that we're getting more and more requests for.  For those used to using Infopath 2003 or 2007 I will try to focus on the new additional features that the 2010 version delivers.

The first thing to note is that there are now 2 client applications in Infopath 2010.  There is Infopath Designer 2010 and Infopath Editor 2010.  The names are pretty self explanatory - one app is used to design forms and the other is for users to fill in forms (I'm yet to look into whether these apps are seperately licensed).  My focus initially will be around the Infopath Designer app.

As per Infopath 2007 when you first launch the designer you have a selection of form templates to select from (see below)

 

 

 

 

 

 

 

 

 

 

 

 

However, there is also a new feature which allows you to build the form using pre-defined Page Layouts and Section Layouts (see below).  This will certainly speed up the building at least of fairly standard forms.You will also notice the now standard Office ribbon menu has now been adopted for Infopath JPart 2 to follow shortly will explain more about the new controls that are available and the improved management of data rules. 

 

Currently rated 5.0 by 1 people

  • Currently 5/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Looking forward to Infopath 2010

In addition to the launches of SharePoint 2010 and Office 2010 I'm also looking forward to the new version of Infopath - which funnily enough will be called Infopath 2010.

Infopath is a great tool for designing and deploying feature rich forms which ehlp to automate business processes, particularly when integrated with SharePoint.

Infopath 2010 will be offering a range of new controls, improved rule handling, quick form publishing (yes!) and the ability to edit Sharepoint List forms.  For more detail have a look on the Infopath Team Blog here

Very much looking forward to being able to use Infopath 2010 as soon as possible!

Be the first to rate this post

  • Currently 0/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

owssvr.dll - Beware of multiple selection lookups

owssvr.dll can be used in InfoPath projects to provide filtered or cascading drop down lists. Use an XML datasource - the syntax is http://yourserver/yourweb/_vti_bin/owssvr.dll?Cmd=Display&List={guid}&XMLDATA=TRUE.

However, beware if your list contains a lookupfield that allows multiple selections. If you have this, then the above syntax will return an invalid XML, or a blank data set.

List contains lookup field(s) with single selection - syntax works.
List contains lookup field(s) with multiple selection - syntax fails.

Be the first to rate this post

  • Currently 0/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Forms Server Caching

A client raised an interesting problem recently. InfoPath forms rendered using Forms Server were being cached in the browser (or rather IE)

On the development and test environments, the forms worked fine, but on pre-production, the caching started.
The caching represented itself by showing the dreaded 'The form has been closed' error when a user tried to open a form for a second time. verbose logging on the server showed that Forms Server itself was not appearing to do anything untoward.

The workaround at the moment is to open FormServer.aspx on in the LAYOUTS directory and add

<META HTTP-EQUIV="Pragma" CONTENT="no-cache">

into the head (stopping the browser from caching the page and form. (Important note - this is a shipped file and on production servers should not be modified.)

 

It is feasible to copy FormServer.aspx to somehting like ncFormServer.aspx and call your new url when opening a form, but I haven't yet tried this e.g. /_layouts/ncFormServer.aspx?XsnLocation=........&Source=....&OpenIn=Browser

Be the first to rate this post

  • Currently 0/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Taking the user to a specific URL after submitting an Infopath Form

In the link to the online form , you wll have or can specify a property 'Source=' . If this is defined, once the form is closed / submitted, it will redirect to this location.

So for example if you create a 'thank you' page at //url/pages/thankyou.aspx, the URL to the form will include &Source=http%3A%2F%2Furl%2Fpages%2FThankYou%2Easpx

An example URL to a browser form is below:

http://portal2007.development.local/hr/_layouts/FormServer.aspx?XsnLocation=http://mossserver:83/hr/Forms/addresschangeform.xsn&SaveLocation=http%3A%2F%2Fportal2007%2Edevelopment%2Elocal%2Fhr%2FChangeofAddress&Source=http%3A%2F%2Fportal2007%2Edevelopment%2Elocal%2Fhr%2FChangeofAddress%2FForms%2FAllItems%2Easpx&DefaultItemOpen=1

Be the first to rate this post

  • Currently 0/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Infopath Forms and the Changed Event

Firstly, huge kudos to Iain for reminding me of this today Embarassed

When you want to use teh 'Changed' event on a drop down list (or other control) in a browser based InfoPath form, you have to set the postback options to 'Always' = otherwise your event doesnt fire!

Thanks Iain

Be the first to rate this post

  • Currently 0/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Simple Webservice to enable InfoPath to communicate with data sources

Whilst InfoPath has dataconnection capabilites to 'talk' direct to SQL & retrieve data, these can be a little problematic. An alternative approach is to implement a simple webservice in front of SQL.

The following example shows a simple service... (note - the code is not optimised & is passing the SQL query over http!)

[WebMethod]
   public DataSet GetSQLData(string SqlStatement, string connection)
   {
     string conn = ConfigurationSettings.AppSettings[connection];
     DataSet wsDataSet = new DataSet();
      SqlConnection sqlConn = new SqlConnection(conn);
      SqlDataAdapter adapter = new SqlDataAdapter(SqlStatement,conn);
      adapter.Fill(wsDataSet);
     

    }
    return wsDataSet;
   }

We can create an InfoPath data connection now to talk to this service.

A similar approach can be taken to 'write' to SQL. This can be useful where you need InfoPath to submit only partial data to SQL rather than the whole form

   public string UpdateSQL(string SqlStatement, string connection)
   {
    string message = string.Empty;
    try
    {
     string skey = ConfigurationSettings.AppSettings["SecurityToken"];

      SqlConnection sqlConn = new SqlConnection(conn);
      SqlCommand cmd = new SqlCommand(SqlStatement, sqlConn);
      sqlConn.Open();
      cmd.ExecuteNonQuery();
      message = "succesful";
     else
      message = "Security Token Invalid";
    }
    catch (System.Exception e)
    {
     message = e.ToString();
    }
    return message;

To use, you can create 'Read' type web service

After configuring the Type (Web Service) and path, your service will be available as a secondary data source. Importantly, remove the check box on 'Automatically retrieve data'

Once completed, you can dynamically set the SqlStatement node (e.g. via a button rule)

Currently rated 3.3 by 3 people

  • Currently 3.333333/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Infopath - Advanced Design

Although Infopath designer can create most (much ?) of the User Interface, there can be times when it doesnt quite do what you need.

As an example, for drop down lists, you can pull in the values from an external data source

The dialog show the external connection and the value / display name as shown below

But what if you wanted to display both the id AND display name? The solution here is to drop into the XSL. Infopath uses XSL extensively & we can edit it if needed (Caution though, it is not as straight-forward as the normal editor & requires knowledge of XSLT). Note that the Infopath project must be saved as source files (if using Infopath.exe) or to access it in Visual Studio, close the manifest.xsf file.

By default, you will have View1.xsl - the xsl for the main view. Opening it will reveal something similar to that below, the xsl to display the drop down list and options

<select class="xdComboBox xdBehavior_Select" title="" style="WIDTH: 130px" size="1" xd:binding="my:TextNode" xd:boundProp="value" value="" xd:xctname="dropdown" xd:CtrlId="CTRL1" tabIndex="0">
      <xsl:attribute name="value">
       <xsl:value-of select="my:TextNode"/>
      </xsl:attribute>
      <xsl:choose>
       <xsl:when test="function-available('xdXDocument:GetDOM')">
        <option/>
        <xsl:variable name="val" select="my:TextNode"/>
        <xsl:if test="not(xdXDocument:GetDOM(&quot;CISF_DIVISION&quot;)/dfs:myFields/dfs:dataFields/d:CISF_DIVISION[@division_id=$val] or $val='')">
         <option selected="selected">
          <xsl:attribute name="value">
           <xsl:value-of select="$val"/>
          </xsl:attribute>
          <xsl:value-of select="$val"/>
         </option>
        </xsl:if>
        <xsl:for-each select="xdXDocument:GetDOM(&quot;CISF_DIVISION&quot;)/dfs:myFields/dfs:dataFields/d:CISF_DIVISION">
         <option>
          <xsl:attribute name="value">
           <xsl:value-of select="@division_id"/>
          </xsl:attribute>
          <xsl:if test="$val=@division_id">
           <xsl:attribute name="selected">selected</xsl:attribute>
          </xsl:if>
          <xsl:value-of select="@division"/>
         </option>
        </xsl:for-each>
       </xsl:when>
       <xsl:otherwise>
        <option>
         <xsl:value-of select="my:TextNode"/>
        </option>
       </xsl:otherwise>
      </xsl:choose>
     </select>

 The part we are interested in is the <option></option> values...

<option>
          <xsl:attribute name="value">
           <xsl:value-of select="@division_id"/>
          </xsl:attribute>
          <xsl:if test="$val=@division_id">
           <xsl:attribute name="selected">selected</xsl:attribute>
          </xsl:if>
          <xsl:value-of select="@division"/>
</option>

By changing this to the code below, we can show both the id and name values...

<option>
          <xsl:attribute name="value">
           <xsl:value-of select="@division_id"/>
          </xsl:attribute>
          <xsl:if test="$val=@division_id">
           <xsl:attribute name="selected">selected</xsl:attribute>
          </xsl:if>
          <xsl:value-of select="@division_id"/>
          <xsl:text> : </xsl:text>
          <xsl:value-of select="@division"/>
</option>

This will give us the following result

UPDATE

The example above was intended for Infopaht Client. AFIK the technique 'should' work for Forms server, but a quick test based upon a comment shows that the XSL may not render correctly

Be the first to rate this post

  • Currently 0/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

WebServices and InfoPath

I'm a big fan of using WebServices to take the code and logic away from InfoPath.

Although you can use managed code inside an InfoPath Project, for me it makes sense to use simple button / control rules (that can be defined in the InfoPath designer) and use a WebService to do the hard work.

As an example, we needed recently to be able to check for Sharepoint document libraries and optionally create them from within InfoPath.

We created a WebService to do this. The service could run on the Sharepoint server, and hene use the Sharepoint Object Model. This gave us a relatively simple service...

(note the following code has been simplified for the blog purpose)

public string CheckWSSFolder(string WebName, string ParentFolder, string FolderName, bool CreateFolder)
        {
            string returnMessage = string.Empty;

            SPSecurity.RunWithElevatedPrivileges(delegate()
            {
                using (SPSite site = new SPSite("http://serverurl"))
                {
                    site.AllowUnsafeUpdates = true;
                    using (SPWeb targetWeb = site.AllWebs[WebName])
                    {
                        targetWeb.AllowUnsafeUpdates = true;
                        if (! CreateFolder)
                        {
                            try
                            {
                                SPFolder rootFolder = targetWeb.GetFolder(ParentFolder);
                                SPFolder targetFolder = rootFolder.SubFolders[FolderName];
                                returnMessage = "Folder Exists";
                            }
                            catch (System.Exception err)
                            {
                                returnMessage = "Folder Not Found " + err.ToString();
                            }

                        }
                        else
                        {
                            try
                            {
                                SPFolder rootFolder = targetWeb.GetFolder(ParentFolder);
                                rootFolder.SubFolders.Add(FolderName);
                                returnMessage = "Folder Created";

                            }
                            catch (System.Exception err)
                            {
                                returnMessage = "Folder Not Created: " + err.ToString();
                            }
                        }
                        targetWeb.AllowUnsafeUpdates = false;
                    }
                    site.AllowUnsafeUpdates = false;
                }
            }
            );
            return returnMessage;
        }

Using this example, we could then create InfoPath data connections to consume this service. The connection type can be a simple 'read' service and the button / control rules can set the service input parameters...

Button Rules (xpath removed for simplicity)

Rule1
Set a Fields Value, Field = WebName, value = "the SPWeb Name"
Set a Fields Value, Field = FolderURL, value = "Folder URL or SubFolder URL (e.g. folder/subfoler)
Set a Fields Value, Field = CreateFolder, value = false

Rule2
Query using a Data Connection, connection = "Web service connection"

Rule3
Set a Fields Value, Field = my:Fields/my:FeedbackNode, value = message returned from webservice

Within the example above, two things to note:

a) We are using RunWithElevatedPrivileges to let the service run with full privilages

b) The AllowSafeUpdates = true had to be set to allow folder creation, then revoked at the end of the service.

Of course, the service can be used now by any InfoPath or other project.

Be the first to rate this post

  • Currently 0/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

 

Dilbert of the day