Posts in Category "Designer"

Required Digital Signatures in LiveCycle form

Description:
Recently, I had a project in which a form was being routed to three people in a serial fashion. However, prior to submitting the form we wanted to test whether the current user had signed the form in his/her designated spot. In order for the digital signatures to remain valid we could not make adjustments to the XML Schema and then use the RenderForm activity in LiveCycle– signatures would have been broken. So we had to put all the code to handle this in the form.

Situation:
There are three roles, Employee, Supervisor, and Reviewer. The form is routed through a LiveCycle process in that order. The Supervisor and Reviewer can either Approve or Decline the form. If the form is Declined it gets routed back to the Employee.

Setting up the form:

  • Add a Text Field, name it requiredSignature, and set its presence to Invisible and set its value to “Employee”
  • Add 3 digital signature fields and named them: employeeSignature, supervisorSignature, and reviewerSignature
  • Put the Approve/Decline option as a drop-down list into the form instead of in Workspace User Action so we did not have to depend on the AWS_ACTION drop down and Form Bridge because we are submitting as a PDF due to the digital signatures, everything is self-contained in the form.
  • The bottom of the form looks like this:

    Three Digital Signatures

    Three Digital Signatures

 

Code:

Three things you should know about the following code:

  1. signatureValidate returns:
    -1 — Not a signature field
    0 — Signature is blank
    1 — Unknown status
    2 — Signature is invalid
    3 — Signature of document is valid, identity of signer could not be verified
    4 — Signature of document is valid and identity of signer is valid.
  2. event.target.getField() you must include [0] in order target the designated field.
  3. [signatureField].mandatory makes that signatureField required prior to submit; [signatureField].disabled makes that signatureField no longer required in order to submit the form.

To be placed on the in the preSubmit Event for the form:

if (requiredSignature.rawValue==”Employee”){

var oState = event.target.getField(“employeeSignature[0]“).signatureValidate();

if (oState > 3){

employeeSignature.mandatory = “disabled”;
requiredSignature.rawValue=”Supervisor”;

}
else{

employeeSignature.mandatory = “error”;

}

}

else if (requiredSignature.rawValue==”Supervisor”){

var oState = event.target.getField(“supervisorSignature[0]“).signatureValidate();

if (oState > 3){

supervisorSignature.mandatory = “disabled”;
requiredSignature.rawValue=”Reviewer”;

}
else{

supervisorSignature.mandatory = “error”;

}

}else if(requiredSignature.rawValue==”Reviewer”){

var oState = event.target.getField(“reviewerSignature[0]“).signatureValidate();
if (oState > 3){

reviewerSignature.mandatory = “disabled”;

}

else{

reviewerSignature.mandatory = “error”;

}

}

else if(requiredSignature.rawValue==”Decline”){

requiredSignature.rawValue=”Employee”;

}

 

On the Supervisor Approve/Decline Drop-down list add the following code to the exit Event:

var oState = event.target.getField(employeeSignature[0]“).signatureValidate();

if(this.rawValue == “Approve”){

if (requiredSignature.rawValue==”Supervisor”){
//do nothing


}

else if(requiredSignature.rawValue==”Decline”){

requiredSignature.rawValue=”Supervisor”;

if (oState > 3){

supervisorSignature.mandatory = “error”;

}

supervisorSignature.presence = “visible”;
supervisorSignatureDate.presence = “visible”;

}

}

else{

if (requiredSignature.rawValue==”Supervisor”){

if (oState > 3)
{

requiredSignature.rawValue=”Decline”;

}
supervisorSignature.mandatory = “disabled”;

}

supervisorSignature.presence = “hidden”;
supervisorSignatureDate.presence = “hidden”;

}

 

Result:

If an Employee attempts to Submit the form without signing the form, he/she will get the following Error Message:

Employee Signature Error Message

Employee Signature Error Message

LC Designer: Single Web Service with Many Services

One side-effect of using Web Services in LC Designer is that you create a lot of data connections; in LC Designer and other IDEs consuming Web Services is not a big deal. For Form Desingers in particular, they seem to be consuming a lot more than the other development groups like: Java, AJAX, etc. And what amounts to is a tens of unique Web Services called within a single form. The problem is keeping up with all the WSDL and server changes. I’ve watched a developer change twenty forms because a single webservice was changed. I’ll show you a simple technique that can solve these problems.

What I do instead of creating many web services is that I create a single web service: invoke(Stirng in, String out)

This web service does nothing else but take a String as input parameter and write a String out as an output parameter. For the format of the String I use JSON. So the web service is more like: invoke(JSON in, JSON out).

Within the JSON in my object has the following:

jsonInputObject:{

       serviceID, //Says which service to invoke.

       messageObject:  {

              //Message specific stuff here

        }

}

I like JSON since its natively represented in JavaScript and I can represent what ever I want. Since most of the web service calls from LC Designer are stateless, I don’t worry about the overhead of using a stateful mechanism which adds bloat. 

Using a single web service that makes a call for you on the server side has the following advantages:

  • Don’t have to stub out a unique service call for every service
  • All services are available to you during design time.
  • Unit testing is easier because you can test your JavaScript on the form against a fixed JSON test object.
  • Adding an optional input parameter or adding a additional return parameters doesn’t require regeneration of your stubbed code.

So below is an example of what my LC Worflow process looks like:

 

ExampleService.png

In this implementation, there are only two services. One to retreive group information and other for office information. Instead of creating two web services, I just have one. For this project I’ll keep adding services to this process. I’ve had projects where are twenty service calls are represented with a single web service call.

 

LiveCycle Development Techniques

Whenever I start development on a LiveCycle project, which usually involves LC Forms, LC Reader Extensions, LC Output, and LC PDF Generator. I utilize Acrobat for most of my prototyping and debugging. I’ll list the frequently used techniques:

  1. LC Reader Extensions – For those beginning to build forms with LC Designer know their form will be Reader Extended before going into production. I’ve seen cases where they will modify a form, manually Reader Extend, and then test their change. To save time, get a copy of Acrobat installed on your machine and use that to test changes. The other way is just too
    masochistic.
  2. LC Forms – Most likely you will be exporting data from a PDF or importing data into a PDF. You need to test a form or a generated XML that binds to a form. A quick way is to open the pdf in Acrobat then to -
    • Export Data from a form: Acrobat menu -> Forms -> Manage Form Data -> Export Data
    • Import Data into a form:  Acrobat menu ->  Forms -> Manage Form Data -> Import Data
  3. LC PDF Generator – You run into a problem where LC PDF Generator gives you an error while converting a non-PDF file. Open the non-PDF file in its native application and print as a PDF. The most common error is permission not to export data or print.
  4. LC Output – Here I prefer to use a unit test case, in most cases flattening a PDF will work file in Acrobat but making an API call reveals more details.

Hope this helps.

Dynamically creating a table with data in LiveCycle form using JavaScript

Stefan Cameron wrote an article on scripting table columns a while back. Taking that idea, how would you dynamically create a table based on some data? Well, there are a couple of ways and this blog post will show you one way of achieving it.

Continue reading…

Generating JavaScript Documentation for Script Objects

One of the things many developers often fail to do is to document their code. Code and documentation comments are not only useful to yourself but also to other developers who may have to contribute to your work or use your work as part of their work. They help increase maintainability, code readability and ease of use. As previously posted, you can create script objects in Adobe LiveCycle Designer to extend standard JavaScript classes with prototype functions and properties. Your script objects can then be distributed among teams for reuse. However, if your script objects contain a large number of functions and properties, your end users may request for documentation.

Continue reading…

Using JSON to Exchange Data with Web Services in XFA Forms

Continuing from my previous post on extending the JavaScript prototype property, another most under-utilized technique is the use of JavaScript Object Notation (JSON) as a data exchange format between a form and web services. Did you ever think of using JSON in form development? No? Me neither. I never thought of it until one of my customers suggested the possibility. It was an elegant solution, as our web services were getting more complex, we were wrestling on reading the data versus implementing solutions. JSON gave us a way to reduce hassle of working with complex objects.

Continue reading…