来源:http://www.crystalreporter.idv.tw/crystalreporter/posts/list/83.page
因為開發報表時,我的做法是有查詢畫面讓使用者選擇篩選條件後,將這些參數設定到該報表中,所以在.NET中,會有一支共用的View程式來負責接收由查詢畫面傳來的參數後,再開啟報表。而傳遞方式就看各位的做法啦! 我是利用將這些資訊(如報表名稱、參數等)以XML型式存放到Cookie中(須處理Cookie的保留字)。
而Viewer程式則從Cookie中讀出報表資訊來處理並開放報表。
在Viewer程式中,我拉一個CrystalReportViewer物件,是用來開啟報表用的,而屬性我則更變PrintMode由Pdf改成ActiveX(因為我讓使用者可以直接列印報表到印表機,而不會轉成pdf檔)。

接下來就是程式了,

Imports CrystalDecisions.ReportAppServer.Controllers
Imports CrystalDecisions.ReportAppServer.ClientDoc
Imports CrystalDecisions.ReportAppServer.DataDefModel
Imports CrystalDecisions.Enterprise
Imports CrystalDecisions.Enterprise.Desktop
Imports System.Xml

Public Class View
Inherits Page

Protected WithEvents crViewer As CrystalDecisions.Web.CrystalReportViewer

'Enterprise variables
Dim ceSession As EnterpriseSession
Dim ceInfoStore As InfoStore
Dim ceEnterpriseService As EnterpriseService
Dim rptClientDoc As ReportClientDocument


Private Sub Page_Init(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Init
'CODEGEN: 此為 Web Form 設計工具所需的方法呼叫
'請勿使用程式碼編輯器進行修改。
InitializeComponent()

Try
If IsNothing(Application("CESession")) Then
Dim ceSessionMgr As SessionMgr = New SessionMgr
Application("CESession") = ceSessionMgr.Logon(Application("RPT_USER_ID"), Application("RPT_PWD"), Application("RPT_SERVER"), "secEnterprise")
End If
ceSession = CType(Application("CESession"), EnterpriseSession)
ceEnterpriseService = ceSession.GetService("", "InfoStore")
ceInfoStore = New InfoStore(ceEnterpriseService)

'從Cookie中取出Report的資訊
Dim strCookieXML As String = Request.Cookies("__RptCookie").Value
Dim objRptXML As XmlDocument = New XmlDocument
objRptXML.LoadXml(strCookieXML)
'1.找出Report Name
Dim strReportName As String = objRptXML.SelectSingleNode("//REPORT").Attributes("NAME").Value
''2.傳入報表名稱及Report Server的Info,取回ReportClientDocument物件
rptClientDoc = FetchReport(ceInfoStore, strReportName)
If rptClientDoc Is Nothing Then
Throw New Exception("無法在Report Server中找到此報表名稱!")
End If
' *** 設定主Report Parameter依XML中的參數值,設定到Report中"

Dim objNodeList As XmlNodeList = objRptXML.SelectNodes("//PARAMTER")
Dim objNode As XmlNode
If objNodeList.Count > 0 Then
Dim IsRangeValue As Boolean, strFromValue As String, strToValue As String
Dim strParamName As String
Dim rasParamValues As Values
Dim rasParamValue As ParameterFieldDiscreteValue
Dim strParameterReportName As String
For Each objNode In objNodeList
IsRangeValue = objNode.Attributes("IS_RANGE_VALUE").Value
strFromValue = objNode.Attributes("FROM_VALUE").Value
strToValue = objNode.Attributes("TO_VALUE").Value
strParamName = objNode.Attributes("PARA_NAME").Value
strParameterReportName = objNode.Attributes("SUB_REPORT_NAME").Value
If IsRangeValue Then
rasParamValues = New Values
rasParamValue = New ParameterFieldDiscreteValue
rasParamValue.Value = strFromValue
rasParamValues.Add(rasParamValue)

rasParamValue = New ParameterFieldDiscreteValue
rasParamValue.Value = strToValue
rasParamValues.Add(rasParamValue)

With rptClientDoc.DataDefController.ParameterFieldController
.SetCurrentValues(strParameterReportName, strParamName, rasParamValues)
End With

Else
rasParamValue = New ParameterFieldDiscreteValue
rasParamValue.Value = strFromValue
With rptClientDoc.DataDefController.ParameterFieldController
.SetCurrentValue(strParameterReportName, strParamName, rasParamValue)
End With
End If

Next
End If

With crViewer
.EnterpriseLogon = ceSession
.ReportSource = rptClientDoc
.DisplayGroupTree = False
End With
Catch ex As Exception
crViewer.Visible = False
Throw ex

End Try
End Sub

Public Function FetchReport(ByVal myInfoStore As InfoStore, ByVal sReportName As String) As ReportClientDocument

Dim ceReports As InfoObjects
Dim ceReport As InfoObject
Dim rasReport As ReportClientDocument = New ReportClientDocumentClass
Dim rptAppFactory As ReportAppFactory
Dim sQuery As String


'query the infostore to get the desired object we want its ID for the rptAppFactory
sQuery = "select SI_ID from CI_INFOOBJECTS where SI_NAME = '" + sReportName + "' and SI_PROGID='CrystalEnterprise.Report' and SI_INSTANCE = 0"

ceReports = myInfoStore.Query(sQuery)
If ceReports.Count > 0 Then
ceReport = ceReports.Item(1)
Dim myEnterpriseService = myInfoStore.EnterpriseSession.GetService("RASReportFactory")
Dim rrfObject As Object = myEnterpriseService.Interface
'grab the report app factory from the session
rptAppFactory = CType(rrfObject, ReportAppFactory)

'use RAS to open the report through the ReportAppFactory object
rasReport = rptAppFactory.OpenDocument(ceReport.ID, 0)


'return the RAS report objectS
Return rasReport
Else
Return Nothing
End If
End Function


End Class

希望對各位有所幫助,謝謝!
posted on 2005-11-10 13:24  James Wong   阅读(845)  评论(0编辑  收藏  举报