Passing parameters without refreshing the page

Recently a reader had an interesting problem. Her client needed a prompt page from which they could open different reports. As it stands now, the client needed to select their prompts, hit the finish button, and then click on the links. She wanted a way to skip the second step – select the prompts, and have those values pass in the drill through.

With the prompt API, and a bit of JS, this is incredibly easy.

The first step is to identify the target report. You can get the report search path through the properties. Click on the “View the search path, ID and URL Location” link, and a window will pop up with the path and other details.
1. Get search path

Notice the double quotes? That can potentially cause trouble with the JavaScript, so I recommend using a URL Encoder: /content/folder[@name=’JavaScript Examples’]/folder[@name=’Drill Target’]/report[@name=’Target’] becomes %2Fcontent%2Ffolder%5B%40name%3D%27JavaScript%20Examples%27%5D%2Ffolder%5B%40name%3D%27Drill%20Target%27%5D%2Freport%5B%40name%3D%27Target%27%5D

The example I’m posting will be using the URL Encoded version.

The next step will be the JavaScript:

<script>

  var paulScripts = {}
    , oCR = cognos.Report.getReport("_THIS_")
    , gateway = window['oCV_THIS_'].getRV().getCV().sGateway
    , report1 = decodeURIComponent("%2Fcontent%2Ffolder%5B%40name%3D%27JavaScript%20Examples%27%5D%2Ffolder%5B%40name%3D%27Drill%20Target%27%5D%2Freport%5B%40name%3D%27Target%27%5D%0A%0A");
 

  /* function paulScripts.URLEncode - Paul Mendelson = 2013-10-21
   * Based on the JSONEncode function, this will return the use/display values of
   * a prompt in a format that can be based via POST or GET.
   * usage: 'p_Parameter1='+paulScripts.URLEncode(paulScripts.getControl('MyPrompt'))
   */
  paulScripts.URLEncode = function(promptControl){
    var urlData = '<selectChoices>'
      , aPromptValues = promptControl.getValues()
      , nonRange = []
      , range =[];

    if (aPromptValues.length == 0) {return false}
   
    for (var j=0; j< aPromptValues.length; j++) {
      var promptValue =  aPromptValues[j];
     
      if (promptValue.use) {// Non Range value
        nonRange.push("<selectOption useValue='"+promptValue.use + "' displayValue='"+ promptValue.display + "'/>");
        }
      else { // Range value   
        var rangeStart = promptValue.start
          , rangeEnd = promptValue.end
          , start, end, startDisp, endDisp;
        if (rangeStart && rangeEnd) { //has both Start and End (bounded)
          rangeStart.display?startDisp = " displayValue='"+ rangeStart.display+"'":"";
          rangeEnd.display?endDisp = " displayValue='"+ rangeEnd.display+"'":"";
          range.push("<selectBoundRange><start useValue='"+rangeStart.use +"'" + startDisp +"/><end useValue='"+rangeEnd.use +"'" + endDisp +"/></selectBoundRange>")
        }
        else if (rangeStart && !rangeEnd) {//unboundedEndRange
          rangeStart.display?startDisp = " displayValue='"+ rangeStart.display+"'":"";
          range.push("<selectUnboundedEndRange><start useValue='"+rangeStart.use +"'" + startDisp +"/></selectUnboundedEndRange>");
        }
        else if (!rangeStart && rangeEnd) {
          rangeEnd.display?endDisp = " displayValue='"+ rangeEnd.display+"'":"";
          range.push("<selectUnboundedStartRange><end useValue='"+rangeEnd.use +"'" + endDisp +"/></selectUnboundedStartRange>");
        }
        else {
          alert ("Range not set.");
        } // end if
      } // end if
    } // end for
    if(nonRange.length>0) urlData += nonRange.join();
    if(range.length>0) urlData += range.join();
    urlData+='</selectChoices>';
    return urlData.replace(/&/g,'&amp;');
  }

  /* function paulScripts.getPrompts
   * Paul Mendelson - 2013-10-21
   * Retrieves all the prompts on the page and returns the parameter values
   */
  paulScripts.getPrompts = function(){
  //find all of the controls and stick them in aPromptControls.
    var aPromptControls = oCR.prompt.getControls( ),
    prompts = [];

  //loop through the controls - finding the name and values and sticking them into the names array
    for(i=0;i<aPromptControls.length;i++)
    {
      if(aPromptControls[i].getValues().length == 0) continue;
      prompts.push(aPromptControls[i].getParameterName());
      prompts.push(paulScripts.URLEncode (aPromptControls[i]));
    }
   
  return  prompts;
  }

paulScripts.runReport = function(reportName,reportPath,gateway, prompts){
  var basicInfo = [
          reportName, "toolbar=no,height=200,width=400"
        , 'ui.gateway' , gateway
        , 'ui.tool' , 'CognosViewer'
        , 'ui.action' , 'run'
        , 'ui.object' , reportPath
        , "run.prompt" ,"false"
        , "cv.toolbar" ,"false"
        , "cv.header" ,"false"
        , "run.prompt", "false"
    ];

    basicInfo=basicInfo.concat(prompts);
  return cognosLaunchInWindow.apply(this,basicInfo);
  }



</script>
 

Let’s go through the functions.

var paulScripts = {}
, oCR = cognos.Report.getReport(“_THIS_”)
, gateway = window[‘oCV_THIS_’].getRV().getCV().sGateway
, report1 = decodeURIComponent(“%2Fcontent%2Ffolder%5B%40name%3D%27JavaScript%20Examples%27%5D%2Ffolder%5B%40name%3D%27Drill%20Target%27%5D%2Freport%5B%40name%3D%27Target%27%5D%0A%0A”);

We’re defining the variables on the page. Notice that I’m hardcoding the report search path into a variable here. There’s actually no reason to do that, we could put it directly into the function, or put it into another prompt, or even insert it into a table and build a list with each row calling another report.

The gateway variable is pulling the gateway from the report you’re running. Another gateway could be entered here, if needed.

The paulScripts.URLEncode will take a prompt control, process the selected values, and spit out a string that Cognos can use to populate parameters.

paulScripts.getPrompts will look for every prompt on the page, and create an array of the parameter names and the selected strings. This makes updating the report simple – you won’t need to modify and JavaScript when adding or removing prompts.

paulScripts.runReport is the last function. It uses the cognosLaunchInWindow function to run a report in the specified window, using the specified search path, on the specified gateway, with the results of the paulScripts.getPrompts function.

To use it, all you need to do is creating an onclick event like this:

<input type="button" onclick="paulScripts.runReport('_blank',report1,gateway, paulScripts.getPrompts())" value="Run Report 1"/>

And finally, we can test it:
passingPrompts

This report was built on 10.2.1, but should work on all versions 10.2 and up.
Passing Parameters Without Refresh (4707 downloads)

Manipulate drill through definitions with JavaScript

This article is based on 10.2, and uses the 10.2 Prompt API. It can be easily adapted to earlier versions however.

When defining a drillthrough you can set various settings as report target, output format, locales and more. Unfortunately there is no easy way to change those settings on the fly. On the other hand, I just did all the work so now there is an easy way.

Drillthrough definitions come in two basic parts. The second part, which won’t be delved into in this article, has the actual values being passed. These can be seen in the links themselves.
drillthrough HTML
Looking at the code itself (modified for legibility):

<SPAN
  dtTargets='
    <drillTarget
      drillIdx="0"
      label="DrillThrough">
      <drillParameter
        name="Product Line"
        value="[sales_and_marketing].[Products].[Products].[Product line]-&amp;gt;:[PC].[@MEMBER].[991]"
        displayValue="Camping Equipment"/>
      <drillParameter
        name="Year"
        value="[sales_and_marketing].[Time].[Time].[Year]-&amp;gt;:[PC].[@MEMBER].[20100101-20101231]"
        displayValue="2010"/>
    </drillTarget>'>
  <SPAN class=hy tabIndex=-1>
    81,929,179.22
  </SPAN>
</SPAN>

This can be modified by looping through with JavaScript fairly easily, but I’ll leave that for another time.

The first part describes the actual settings – the metadata of the drill. This is stored in JavaScript object in the page, which makes it significantly easier to modify. Stringifying the object returns (again, modified for legibility):

[
  {"m_label":"DrillThrough"
  ,"m_outputFormat":"HTMLFragment"
  ,"m_outputLocale":"en-us"
  ,"m_showInNewWindow":"true"
  ,"m_method":"execute"
  ,"m_path":"/content/folder[@name='JavaScript Examples']/folder[@name='Modifying Drillthrough Definitions']/report[@name='Drill 1']"
  ,"m_bookmark":""
  ,"m_parameters":"<bus:parameters xsi:type="SOAP-ENC:Array" SOAP-ENC:arrayType="bus:baseParameter[2]"><item xsi:type="bus:parameter"><bus:name xsi:type="xs:string">Product Line</bus:name><bus:type xsi:type="bus:parameterDataTypeEnum">memberUniqueName</bus:type></item><item xsi:type="bus:parameter"><bus:name xsi:type="xs:string">Year</bus:name><bus:type xsi:type="bus:parameterDataTypeEnum">memberUniqueName</bus:type></item></bus:parameters>"
  ,"m_objectPaths":"<bus:objectPaths xsi:type="SOAP-ENC:Array" SOAP-ENC:arrayType="bus:searchPathSingleObject[4]"><item xsi:type="bus:searchPathSingleObject">storeID(&quot;i326070F7595B4B5BBCD38D945E66AAEB&quot;)</item><item xsi:type="bus:searchPathSingleObject">storeID(&quot;iDB36CF1A0D654E99B3117B0B6A7F8789&quot;)/model[last()]</item><item xsi:type="bus:searchPathSingleObject">/content/folder[@name=&apos;Samples&apos;]/folder[@name=&apos;Cubes&apos;]/package[@name=&apos;Sales and Marketing (cube)&apos;]/model[@name=&apos;2008-07-25T15:28:38.072Z&apos;]</item><item xsi:type="bus:searchPathSingleObject">/content/folder[@name=&apos;Samples&apos;]/folder[@name=&apos;Cubes&apos;]/package[@name=&apos;Sales and Marketing (cube)&apos;]/model[last()]</item></bus:objectPaths>"
  ,"m_prompt":"false"
  ,"m_dynamicDrillThrough":false
  ,"m_parameterProperties":"<PARAMETER-PROPERTIES/>"}
  ,
  {"m_label":"DrillThrough"
  ,"m_outputFormat":"HTMLFragment"
  ,"m_outputLocale":"en-us"
  ,"m_showInNewWindow":"true"
  ,"m_method":"execute"
  ,"m_path":"/content/folder[@name='JavaScript Examples']/folder[@name='Modifying Drillthrough Definitions']/report[@name='Drill 1']"
  ,"m_bookmark":""
  ,"m_parameters":"<bus:parameters xsi:type="SOAP-ENC:Array" SOAP-ENC:arrayType="bus:baseParameter[2]"><item xsi:type="bus:parameter"><bus:name xsi:type="xs:string">Product Line</bus:name><bus:type xsi:type="bus:parameterDataTypeEnum">memberUniqueName</bus:type></item><item xsi:type="bus:parameter"><bus:name xsi:type="xs:string">Year</bus:name><bus:type xsi:type="bus:parameterDataTypeEnum">memberUniqueName</bus:type></item></bus:parameters>"
  ,"m_objectPaths":"<bus:objectPaths xsi:type="SOAP-ENC:Array" SOAP-ENC:arrayType="bus:searchPathSingleObject[4]"><item xsi:type="bus:searchPathSingleObject">storeID(&quot;i326070F7595B4B5BBCD38D945E66AAEB&quot;)</item><item xsi:type="bus:searchPathSingleObject">storeID(&quot;iDB36CF1A0D654E99B3117B0B6A7F8789&quot;)/model[last()]</item><item xsi:type="bus:searchPathSingleObject">/content/folder[@name=&apos;Samples&apos;]/folder[@name=&apos;Cubes&apos;]/package[@name=&apos;Sales and Marketing (cube)&apos;]/model[@name=&apos;2008-07-25T15:28:38.072Z&apos;]</item><item xsi:type="bus:searchPathSingleObject">/content/folder[@name=&apos;Samples&apos;]/folder[@name=&apos;Cubes&apos;]/package[@name=&apos;Sales and Marketing (cube)&apos;]/model[last()]</item></bus:objectPaths>"
  ,"m_prompt":"false"
  ,"m_dynamicDrillThrough":false
  ,"m_parameterProperties":"<PARAMETER-PROPERTIES/>"}]

Each of these settings is easily changed (except for the the m_parameters and m_parameterProperties because that means changing the settings on the actual drills themselves). People with sharp eyes may notice that both drillthrough definitions are exactly the same. Why does it appear twice? The drillthrough appears twice in my report’s crosstab. The definition appears for the detail row and again for the totals row. If I was passing the individual month with the detail, then the first drillthrough in the object would include the month.

Because the drills can appear twice, any function written to rewrite the settings must include a loop to check the m_label in each element.

Consider the following:

<script>
var paulScripts = {},  oCR = cognos.Report.getReport( "_THIS_" );

paulScripts.getControl = function (promptName) {
  return oCR.prompt.getControlByName(promptName);
}

/*
 * function: changeDrillAttribute
 * By Paul Mendelson
 * This allows the user to change any attribute in the drill. Attributes may be:
 * m_label, m_outputFormat, m_outputLocale, m_showInNewWindow, m_method, m_path,
 * m_bookmark, m_parameters, m_objectPaths, m_prompt, m_dynamicDrillThrough,
 * m_parameterProperties
 * Drills may appear multiple times in the object, so the loop goes through the entire array. Each
 * matching drill will have the attribute changed as desired.
 * Valid m_outputFormat:  CSV, HTML, layoutDataXML, MHT,  PDF, rawXML, singleXLS, spreadsheetML, XLS,
 * XML, XLWA.
 * m_path: /content/folder[@name='folderName']/folder[@name='folderName']/report[@name='reportName']
 */

paulScripts.changeDrillAttribute = function (drillName,attribute,newValue){
  var oCV = window['oCV'+'_THIS_']
  , drillsObj = oCV.getRV().getCV().getDrillTargets();

  for(var i=0;i<drillsObj.length;i++){
   if( drillsObj[i].m_label == drillName) drillsObj[i][attribute] = newValue;
  }
}

</script>

paulScripts.changeDrillAttribute function will receive the name of the drill, the attribute to change, and the new value of that attribute. It will then loop through all of the elements in the drill targets, and if the label matches, change the attribute.

The following screenshot shows the crosstab containing the drill, and two radio button groups.
radios can change the drill

The radios have a validator set on them to invoke the changeDrillAttribute function.

<script>
paulScripts.getControl('Format').setValidator(
  function (values) {
  paulScripts.changeDrillAttribute ('DrillThrough','m_outputFormat',values[0].use);
  return true;
  }
);

paulScripts.getControl('Target').setValidator(
  function (values) {
  paulScripts.changeDrillAttribute ('DrillThrough','m_path',values[0].use);
  return true;
  }
);

</script>

Whenever the radio is changed, it will modify the drill appropriately. That setValidator function is the only use of the new Prompt API, so this can be changed very easily to previous versions by using onChange events.

Ultimately the end user can decide which report he wants to drill to, and in what format, without having to right-click. Because users don’t like right-clicking.

The following XML is the report. Remember to create two targets for the drill and to fix the value prompt. To get the path of the report, simply go to the properties of the report, click on “View the search path, ID and URL” and copy the search path.

<report xmlns="http://developer.cognos.com/schemas/report/9.0/" useStyleVersion="10" expressionLocale="en-us">
				<modelPath>/content/folder[@name='Samples']/folder[@name='Cubes']/package[@name='Sales and Marketing (cube)']/model[@name='2008-07-25T15:28:38.072Z']</modelPath>
				<drillBehavior modelBasedDrillThru="true"/>
				<queries>
					<query name="Query1">
						<source>
							<model/>
						</source>
						<selection><dataItemLevelSet name="Year"><dmLevel><LUN>[sales_and_marketing].[Time].[Time].[Year]</LUN><itemCaption>Year</itemCaption></dmLevel><dmDimension><DUN>[sales_and_marketing].[Time]</DUN><itemCaption>Time</itemCaption></dmDimension><dmHierarchy><HUN>[sales_and_marketing].[Time].[Time]</HUN><itemCaption>Time</itemCaption></dmHierarchy></dataItemLevelSet><dataItemLevelSet name="Quarter"><dmLevel><LUN>[sales_and_marketing].[Time].[Time].[Quarter]</LUN><itemCaption>Quarter</itemCaption></dmLevel><dmDimension><DUN>[sales_and_marketing].[Time]</DUN><itemCaption>Time</itemCaption></dmDimension><dmHierarchy><HUN>[sales_and_marketing].[Time].[Time]</HUN><itemCaption>Time</itemCaption></dmHierarchy></dataItemLevelSet><dataItemLevelSet name="Product line"><dmLevel><LUN>[sales_and_marketing].[Products].[Products].[Product line]</LUN><itemCaption>Product line</itemCaption></dmLevel><dmDimension><DUN>[sales_and_marketing].[Products]</DUN><itemCaption>Products</itemCaption></dmDimension><dmHierarchy><HUN>[sales_and_marketing].[Products].[Products]</HUN><itemCaption>Products</itemCaption></dmHierarchy></dataItemLevelSet><dataItemMeasure name="Revenue"><dmMember><MUN>[sales_and_marketing].[Measures].[Revenue]</MUN><itemCaption>Revenue</itemCaption></dmMember><dmDimension><DUN>[sales_and_marketing].[Measures]</DUN><itemCaption>Measures</itemCaption></dmDimension><XMLAttributes><XMLAttribute name="RS_dataType" value="9" output="no"/></XMLAttributes></dataItemMeasure></selection>
					</query>
				</queries>
				<layouts>
					<layout>
						<reportPages>
							<page name="Page1"><style><defaultStyles><defaultStyle refStyle="pg"/></defaultStyles></style>
								<pageBody><style><defaultStyles><defaultStyle refStyle="pb"/></defaultStyles></style>
									<contents>
										<HTMLItem>
			<dataSource>
				<staticValue>&lt;script&gt;
var paulScripts = {},  oCR = cognos.Report.getReport( "_THIS_" );

paulScripts.getControl = function (promptName) {
  return oCR.prompt.getControlByName(promptName);
}

/*
 * function: changeDrillAttribute
 * Paul Mendelson
 * This allows the user to change any attribute in the drill. Attributes may be:
 *   m_label, m_outputFormat, m_outputLocale, m_showInNewWindow, m_method, m_path,
  * m_bookmark, m_parameters, m_objectPaths, m_prompt, m_dynamicDrillThrough,
  * m_parameterProperties
  * Drills may appear multiple times in the object, so the loop goes through the entire array. Each
  * matching drill will have the attribute changed as desired.
  *  Valid m_outputFormat:  CSV, HTML, layoutDataXML, MHT,  PDF, rawXML, singleXLS, spreadsheetML, XLS,
  * XML, XLWA.
  * m_path: /content/folder[@name='folderName']/folder[@name='folderName']/report[@name='reportName']
  */

paulScripts.changeDrillAttribute = function (drillName,attribute,newValue){
  var oCV = window['oCV'+'_THIS_']
  , drillsObj = oCV.getRV().getCV().getDrillTargets();

  for(var i=0;i&lt;drillsObj.length;i++){
   if( drillsObj[i].m_label == drillName) drillsObj[i][attribute] = newValue;
  }
}

  &lt;/script&gt;
	</staticValue>
			</dataSource>
		</HTMLItem>
									<table><style><defaultStyles><defaultStyle refStyle="tb"/></defaultStyles><CSS value="border-collapse:collapse"/></style><tableRows><tableRow><tableCells><tableCell><contents><crosstab refQuery="Query1" horizontalPagination="true" name="Crosstab1">
											<crosstabCorner><style><defaultStyles><defaultStyle refStyle="xm"/></defaultStyles></style><contents><textItem><dataSource><dataItemLabel refDataItem="Revenue"/></dataSource></textItem></contents></crosstabCorner>

											<noDataHandler>
												<contents>
													<block>
														<contents>
															<textItem>
																<dataSource>
																	<staticValue>No Data Available</staticValue>
																</dataSource>
																<style>
																	<CSS value="padding:10px 18px;"/>
																</style>
															</textItem>
														</contents>
													</block>
												</contents>
											</noDataHandler>
											<style>
												<defaultStyles>
													<defaultStyle refStyle="xt"/>
												</defaultStyles>
												<CSS value="border-collapse:collapse"/>
											</style>
										<crosstabRows><crosstabNode><crosstabNestedNodes><crosstabNode><crosstabNodeMembers><crosstabNodeMember refDataItem="Quarter" edgeLocation="e2"><style><defaultStyles><defaultStyle refStyle="ml"/></defaultStyles></style><contents><textItem><dataSource><memberCaption/></dataSource></textItem></contents></crosstabNodeMember></crosstabNodeMembers></crosstabNode><crosstabNode><crosstabNodeMembers><crosstabNodeMember refDataItem="Year" edgeLocation="e3"><style><defaultStyles><defaultStyle refStyle="ml"/></defaultStyles></style><contents><textItem><dataSource><memberCaption/></dataSource></textItem></contents></crosstabNodeMember></crosstabNodeMembers></crosstabNode></crosstabNestedNodes><crosstabNodeMembers><crosstabNodeMember refDataItem="Year" edgeLocation="e1"><style><defaultStyles><defaultStyle refStyle="ml"/></defaultStyles></style><contents><textItem><dataSource><memberCaption/></dataSource></textItem></contents></crosstabNodeMember></crosstabNodeMembers></crosstabNode></crosstabRows><crosstabColumns><crosstabNode><crosstabNodeMembers><crosstabNodeMember refDataItem="Product line" edgeLocation="e4"><style><defaultStyles><defaultStyle refStyle="ml"/></defaultStyles></style><contents><textItem><dataSource><memberCaption/></dataSource></textItem></contents></crosstabNodeMember></crosstabNodeMembers></crosstabNode></crosstabColumns><defaultMeasure refDataItem="Revenue"/><crosstabFactCell><contents><textItem><dataSource><cellValue/></dataSource><reportDrills><reportDrill name="DrillThrough"><drillLabel><dataSource><staticValue/></dataSource></drillLabel><drillTarget method="execute" showInNewWindow="true"><reportPath path="/content/folder[@name='JavaScript Examples']/folder[@name='Modifying Drillthrough Definitions']/report[@name='Drill 1']"><XMLAttributes><XMLAttribute name="ReportName" value="Drill 1" output="no"/><XMLAttribute name="class" value="report" output="no"/></XMLAttributes></reportPath><drillLinks><drillLink><drillTargetContext><parameterContext parameter="Product Line"/></drillTargetContext><drillSourceContext><dataItemContext refDataItem="Product line"/></drillSourceContext></drillLink><drillLink><drillTargetContext><parameterContext parameter="Year"/></drillTargetContext><drillSourceContext><dataItemContext refDataItem="Year"/></drillSourceContext></drillLink></drillLinks></drillTarget></reportDrill></reportDrills><style><defaultStyles><defaultStyle refStyle="hy"/></defaultStyles></style></textItem></contents><style><defaultStyles><defaultStyle refStyle="mv"/></defaultStyles></style></crosstabFactCell></crosstab></contents></tableCell><tableCell><contents><table><style><defaultStyles><defaultStyle refStyle="tb"/></defaultStyles><CSS value="border-collapse:collapse"/></style><tableRows><tableRow><tableCells><tableCell><contents><selectValue parameter="Format" selectValueUI="radioGroup" name="Format"><selectOptions><selectOption useValue="PDF"/><selectOption useValue="spreadsheetML"/><selectOption useValue="HTMLFragment"/><selectOption useValue="HTML"/></selectOptions><defaultSelections><defaultSimpleSelection>HTMLFragment</defaultSimpleSelection></defaultSelections></selectValue></contents></tableCell></tableCells></tableRow><tableRow><tableCells><tableCell><contents><selectValue parameter="Target" name="Target" selectValueUI="radioGroup"><selectOptions><selectOption useValue="/content/folder[@name='JavaScript Examples']/folder[@name='Modifying Drillthrough Definitions']/report[@name='Drill 1']"><displayValue>Target 1</displayValue></selectOption><selectOption useValue="/content/folder[@name='JavaScript Examples']/folder[@name='Modifying Drillthrough Definitions']/report[@name='Drill 2']"><displayValue>Target 2</displayValue></selectOption></selectOptions><defaultSelections><defaultSimpleSelection>/content/folder[@name='JavaScript Examples']/folder[@name='Modifying Drillthrough Definitions']/report[@name='Drill 1']</defaultSimpleSelection></defaultSelections></selectValue></contents></tableCell></tableCells></tableRow></tableRows></table></contents><style><CSS value="vertical-align:top"/></style></tableCell></tableCells></tableRow></tableRows></table><HTMLItem>
			<dataSource>
				<staticValue>&lt;script&gt;
paulScripts.getControl('Format').setValidator(
  function (values) {
  paulScripts.changeDrillAttribute ('DrillThrough','m_outputFormat',values[0].use);
  return true;
  }
);

paulScripts.getControl('Target').setValidator(
  function (values) {
  paulScripts.changeDrillAttribute ('DrillThrough','m_path',values[0].use);
  return true;
  }
);

&lt;/script&gt;</staticValue>
			</dataSource>
		</HTMLItem></contents>
								</pageBody>

							</page>
						</reportPages>
					</layout>
				</layouts>
			<XMLAttributes><XMLAttribute name="RS_CreateExtendedDataItems" value="true" output="no"/><XMLAttribute name="listSeparator" value="," output="no"/><XMLAttribute name="RS_modelModificationTime" value="2008-07-25T15:28:38.133Z" output="no"/></XMLAttributes><reportName>Report</reportName></report>