在 SharePoint 中创建 PerformancePoint Services 报表呈现器
了解如何在自定义报告扩展中为 PerformancePoint Services 创建呈现器组件。
什么是 PerformancePoint Services 的自定义报告呈现器?
在 PerformancePoint Services 中,自定义报表呈现器是在 Web 部件中呈现自定义报表的 Web 服务器控件。 呈现器可为报告可视化(如表和图)编写 HTML,提供用于处理报告参数的逻辑以及从存储库中检索报告对象。
下面的过程和代码示例以自定义对象示例中的 SampleReportRenderer 类为依据。 呈现器负责呈现表,并在其中填充从链接的筛选器收到的值。 有关 类的完整代码,请参阅代码示例:在 SharePoint 中为自定义PerformancePoint Services报表创建呈现器。
建议您将示例报告呈现器用作模板。 该示例说明如何调用 PerformancePoint Services API 中的对象,并演示针对 PerformancePoint Services 开发的最佳实践。
为自定义 PerformancePoint Services 报告创建呈现器
安装 PerformancePoint Services,或者将您的扩展使用的 DLL(步骤 3 中列出)复制到您的计算机上。 有关详细信息,请参阅 具有类库的 DLL。
在 Visual Studio 中,创建一个 C# 类库。 如果您已为扩展创建了一个类库,请添加新 C# 类。
您必须用强名称对您的 DLL 进行签名。 此外,请确保您的 DLL 所引用的所有程序集都具有强名称。 有关如何使用强名称对程序集进行签名以及如何创建公钥/私钥对的信息,请参阅 如何:创建公钥/私钥对。
将以下 PerformancePoint Services DLL 作为程序集引用添加到项目:
- Microsoft.PerformancePoint.Scorecards.Client.dll
- Microsoft.PerformancePoint.Scorecards.Server.dll
- Microsoft.PerformancePoint.Scorecards.Store.dll
根据扩展的功能不同,可能需要其他项目引用。
在呈现器类中,为以下 PerformancePoint Services 命名空间添加 using 指令:
- Microsoft.PerformancePoint.Scorecards
- Microsoft.PerformancePoint.Scorecards.Server.Extensions
- Microsoft.PerformancePoint.Scorecards.Store
根据您的扩展的功能,可能需要其他 using 指令。
继承自 ParameterizableControl 基类。
重写 GetElement 方法以从存储库检索报表对象。
重写 SetData 方法以设置报表数据集并检索传入的参数值。
重写 Render 方法以呈现报表可视化效果的 HTML。
代码示例:在 SharePoint 中创建自定义 PerformancePoint Services 报表呈现器
以下代码示例中的类将创建一个报告呈现器,该呈现器显示从示例筛选器传入的库存信息。
您必须先按创建和配置呈现器类中所述配置开发环境,然后才能编译此代码示例。
using System;
using System.Collections.Generic;
using System.Data;
using System.Web.UI;
using Microsoft.PerformancePoint.Scorecards;
using Microsoft.PerformancePoint.Scorecards.Server.Extensions;
using Microsoft.PerformancePoint.Scorecards.Store;
namespace Microsoft.PerformancePoint.SDK.Samples.SampleReport
{
// The class that define the sample report's renderer.
public class SampleReportRenderer : ParameterizableControl
{
private ReportView reportView;
private ReportView ReportView
{
get
{
// The GetElement method is used internally by this property, which is used
// in turn by the SetData method.
reportView = GetElement(ElementLocation) as ReportView;
return reportView;
}
}
// Initializes the current instance according to a standard interface. This method
// sets up the dataset.
public override void SetData(RepositoryLocation elementLocation, string resourcePath, string targetControlId, BIDataContainer dataContainer, bool accessibilityMode)
{
// The renderer must call the base implementation of the SetData method
// to set report properties.
base.SetData(elementLocation, resourcePath, targetControlId, dataContainer, accessibilityMode);
if (null != ReportView)
{
// If the report view's custom data represents a serialized object, deserialize
// it, and then use it to access a data source or other object.
string customData = ReportView.CustomData;
if (!string.IsNullOrEmpty(customData))
{
System.Diagnostics.Debug.WriteLine(string.Format("Report view '{0}' has the following custom data: {1}", ReportView.Name.Text, customData));
}
// Iterate through the user's selections sent by the filter.
// The MultiSelectTreeControl filter control can send multiple
// rows of data but other native controls send one message only.
foreach (ParameterMessage message in BIDataContainer.ParameterMessages)
{
// This line demonstrates how to do something with each incoming parameter message.
System.Diagnostics.Debug.WriteLine(string.Format("Parameter message: {0}", message.DisplayName));
}
}
}
// Render page content using the specified writer.
protected override void Render(HtmlTextWriter output)
{
try
{
if (null != ReportView && !string.IsNullOrEmpty(ReportView.CustomData))
{
output.RenderBeginTag(HtmlTextWriterTag.P);
output.RenderBeginTag(HtmlTextWriterTag.B);
// This line shows how to retrieve the content of the
// report's optional CustomData property. CustomData can store
// information that the report does not store elsewhere.
output.Write(string.Format("The ReportView "{0}" has CustomData information. The CustomData is "{1}"",
ReportView.Name.Text, ReportView.CustomData));
output.RenderEndTag(); // B
output.RenderEndTag(); // P
}
Dictionary<Guid, ParameterMessage> parametersIndex =
IndexParameterMessages(BIDataContainer.ParameterMessages.ToArray());
// Each connection gets a unique identifier.
foreach (Guid parameterMappingId in parametersIndex.Keys)
{
ParameterMessage message = parametersIndex[parameterMappingId];
output.RenderBeginTag(HtmlTextWriterTag.Table);
output.AddAttribute(HtmlTextWriterAttribute.Style, "ms-partline");
output.RenderBeginTag(HtmlTextWriterTag.Tr);
output.AddAttribute(HtmlTextWriterAttribute.Colspan, "5");
output.RenderBeginTag(HtmlTextWriterTag.Td);
output.RenderBeginTag(HtmlTextWriterTag.B);
output.Write(string.Format("EndPoint name is: {0}", message.Values.TableName));
output.RenderEndTag(); // B
output.RenderEndTag(); // Td
output.RenderEndTag(); // Tr
output.AddAttribute(HtmlTextWriterAttribute.Style, "\\"border-bottom:solid 10px #ffdd00; background:PapayaWhip\\"");
output.RenderBeginTag(HtmlTextWriterTag.Tr);
// Read the message.Values data table and print the column names.
foreach (DataColumn col in message.Values.Columns)
{
output.RenderBeginTag(HtmlTextWriterTag.Td);
output.Write(string.IsNullOrEmpty(col.Caption) ? "&nbsp;" : col.Caption);
output.RenderEndTag();
}
output.RenderEndTag(); // Tr
// Print the data from the Values property, which is a data table.
foreach (DataRow row in message.Values.Rows)
{
output.RenderBeginTag(HtmlTextWriterTag.Tr);
for (int i = 0; i < message.Values.Columns.Count; i++)
{
output.RenderBeginTag(HtmlTextWriterTag.Td);
output.Write(string.IsNullOrEmpty(row[i].ToString()) ? "&nbsp;" : row[i].ToString());
output.RenderEndTag();
}
output.RenderEndTag(); // Tr
}
output.RenderEndTag(); // table
}
}
catch (Exception e)
{
output.RenderBeginTag(HtmlTextWriterTag.H1);
output.Write("Error! An exception has occurred!");
output.RenderEndTag();
output.RenderBeginTag(HtmlTextWriterTag.P);
output.Write(e.Message);
output.RenderEndTag();
output.RenderBeginTag(HtmlTextWriterTag.P);
output.Write(e.StackTrace);
output.RenderEndTag();
}
}
// Get the report object.
protected override Element GetElement(RepositoryLocation elementLocation)
{
ReportView rv = null;
if (!RepositoryLocation.IsNullOrEmpty(elementLocation))
{
rv = SPDataStore.GlobalDataStore.GetReportViewForExecution(elementLocation);
}
return (rv);
}
}
}
后续步骤
创建报表呈现器和报表编辑器 (包括其用户界面后,如果需要) ,请部署扩展,如如何:手动注册PerformancePoint Services扩展中所述。