Quantcast
Channel: SQL Server Reporting Services, Power View forum
Viewing all articles
Browse latest Browse all 28687

HOW TO: Print a report directly to a printer

$
0
0

The code below is a class file done in vb.net. The original idea came from reading this forum and some blogs.

 

To use the code below, you can create a windows application or service.

then create a class file and drop this code in it.

Remeber to reference the  2005 report execution service and also in the program settings include the path to your server.

IE: ReportExecutionService = http://localhost/ReportServer/ReportExecution2005.asmx or whatever your server URL is at.

Setup the public properties for printername (sharenames work fine), Number of copies and Report name.

That is all there is to it. This code is REALLY expandable to add more options.

Please remember to let me kow if you like this.

Imports

System

Imports

System.Drawing

Imports

System.Drawing.Imaging

Imports

System.Drawing.Printing

Imports

System.IO

Imports

System.Web.Services.Protocols

Imports

PrintReport.ReportExecution

Imports

System.Runtime.InteropServices ' For Marshal.Copy

Namespace

PrintReport

Friend Class app

Private m_sPrinterName As String

Private m_sReportName As String

Private m_sNumCopies As Integer

<STAThread()> _

Public Sub Main(ByVal args As String())

Dim pe As PrintMain = New PrintMain()

pe.PrintReport(m_sPrinterName, m_sReportName, m_sNumCopies)

End Sub

Public Property pPrinterName()

Get

Return m_sPrinterName

End Get

Set(ByVal value)

m_sPrinterName = value

End Set

End Property

Public Property pReportName()

Get

Return m_sReportName

End Get

Set(ByVal value)

m_sReportName = value

End Set

End Property

Public Property pNumCopies()

Get

Return m_sNumCopies

End Get

Set(ByVal value)

m_sNumCopies = value

End Set

End Property

End Class

Friend Class PrintMain

Private rs As New ReportExecutionService()

Private m_renderedReport As Byte()()

Private m_delegate As Graphics.EnumerateMetafileProc = Nothing

Private m_currentPageStream As MemoryStream

Private m_metafile As Metafile = Nothing

Private m_numberOfPages As Integer

Private m_currentPrintingPage As Integer

Private m_lastPrintingPage As Integer

Public Sub New()

' Create proxy object and authenticate

rs.Credentials = System.Net.CredentialCache.DefaultCredentials

rs.Url =

My.Settings.ReportExecutionService '"http://localhost/ReportServer/ReportExecution2005.asmx"

End Sub

Public Function RenderReport(ByVal reportPath As String) As Byte()()

' Private variables for rendering

Dim deviceInfo As String

Dim format As String = "IMAGE"

Dim firstPage As Byte() = Nothing

Dim encoding As String = ""

Dim mimeType As String = ""

Dim warnings As Warning() = Nothing

Dim reportHistoryParameters As ParameterValue() = Nothing

Dim streamIDs As String() = Nothing

Dim pages As Byte()() = Nothing

Dim historyID As String = Nothing

Dim showHideToggle As String = Nothing

Dim execInfo As New ExecutionInfo

Dim execHeader As New ExecutionHeader()

Dim SessionId As String

Dim extension As String = ""

rs.ExecutionHeaderValue = execHeader

execInfo = rs.LoadReport(reportPath, historyID)

'rs.SetExecutionParameters(parameters, "en-us")

SessionId = rs.ExecutionHeaderValue.ExecutionID

' Build device info based on the start page

deviceInfo =

String.Format("<DeviceInfo><OutputFormat>{0}</OutputFormat></DeviceInfo>", "emf")

'Exectute the report and get page count.

Try

' Renders the first page of the report and returns streamIDs for

' subsequent pages

firstPage = rs.Render(format, deviceInfo, extension, encoding, mimeType, warnings, streamIDs)

' The total number of pages of the report is 1 + the streamIDs

m_numberOfPages = streamIDs.Length + 1

pages =

New Byte(m_numberOfPages - 1)() {}

' The first page was already rendered

pages(0) = firstPage

Dim pageIndex As Integer = 1

Do While pageIndex < m_numberOfPages

' Build device info based on start page

deviceInfo =

String.Format("<DeviceInfo><OutputFormat>{0}</OutputFormat><StartPage>{1}</StartPage></DeviceInfo>", "emf", pageIndex + 1)

pages(pageIndex) = rs.Render(format, deviceInfo, extension, encoding, mimeType, warnings, streamIDs)

pageIndex += 1

Loop

Catch ex As SoapException

'Console.WriteLine(ex.Detail.InnerXml)

Catch ex As Exception

'Console.WriteLine(ex.Message)

Finally

'Console.WriteLine("Number of pages: {0}", pages.Length)

End Try

Return pages

End Function

Public Function PrintReport(ByVal printerName As String, ByVal ReportName As String, Optional ByVal NumCopies As Integer = 0) As Boolean

Me.RenderedReport = Me.RenderReport(ReportName)

Try

' Wait for the report to completely render.

If m_numberOfPages < 1 Then

Return False

End If

Dim printerSettings As PrinterSettings = New PrinterSettings()

printerSettings.MaximumPage = m_numberOfPages

printerSettings.MinimumPage = 1

printerSettings.PrintRange = PrintRange.SomePages

printerSettings.FromPage = 1

printerSettings.ToPage = m_numberOfPages

printerSettings.Copies = NumCopies

printerSettings.PrinterName = printerName

Dim pd As PrintDocument = New PrintDocument()

m_currentPrintingPage = 1

m_lastPrintingPage = m_numberOfPages

pd.PrinterSettings = printerSettings

' Print report

'Console.WriteLine("Printing report...")

AddHandler pd.PrintPage, AddressOf pd_PrintPage

pd.Print()

Catch ex As Exception

'Console.WriteLine(ex.Message)

Finally

' Clean up goes here.

End Try

Return True

End Function

Private Sub pd_PrintPage(ByVal sender As Object, ByVal ev As PrintPageEventArgs)

ev.HasMorePages =

False

If m_currentPrintingPage <= m_lastPrintingPage AndAlso MoveToPage(m_currentPrintingPage) Then

' Draw the page

ReportDrawPage(ev.Graphics)

' If the next page is less than or equal to the last page,

' print another page.

If m_currentPrintingPage <= m_lastPrintingPage Then

m_currentPrintingPage += 1

ev.HasMorePages =

True

End If

End If

End Sub

' Method to draw the current emf memory stream

Private Sub ReportDrawPage(ByVal g As Graphics)

If Nothing Is m_currentPageStream OrElse 0 = m_currentPageStream.Length OrElse Nothing Is m_metafile Then

Return

End If

SyncLock Me

' Set the metafile delegate.

Dim width As Integer = m_metafile.Width

Dim height As Integer = m_metafile.Height

m_delegate =

New Graphics.EnumerateMetafileProc(AddressOf MetafileCallback)

' Draw in the rectangle

Dim destPoint As Point = New Point(0, 0)

g.EnumerateMetafile(m_metafile, destPoint, m_delegate)

' Clean up

m_delegate =

Nothing

End SyncLock

End Sub

Private Function MoveToPage(ByVal page As Int32) As Boolean

' Check to make sure that the current page exists in

' the array list

If Nothing Is Me.RenderedReport(m_currentPrintingPage - 1) Then

Return False

End If

' Set current page stream equal to the rendered page

m_currentPageStream =

New MemoryStream(Me.RenderedReport(m_currentPrintingPage - 1))

' Set its postion to start.

m_currentPageStream.Position = 0

' Initialize the metafile

If Not Nothing Is m_metafile Then

m_metafile.Dispose()

m_metafile =

Nothing

End If

' Load the metafile image for this page

m_metafile =

New Metafile(CType(m_currentPageStream, Stream))

Return True

End Function

Private Function MetafileCallback(ByVal recordType As EmfPlusRecordType, ByVal flags As Integer, ByVal dataSize As Integer, ByVal data As IntPtr, ByVal callbackData As PlayRecordCallback) As Boolean

Dim dataArray As Byte() = Nothing

' Dance around unmanaged code.

If data <> IntPtr.Zero Then

' Copy the unmanaged record to a managed byte buffer

' that can be used by PlayRecord.

dataArray =

New Byte(dataSize - 1) {}

Marshal.Copy(data, dataArray, 0, dataSize)

End If

' play the record.

m_metafile.PlayRecord(recordType, flags, dataSize, dataArray)

Return True

End Function

Public Property RenderedReport() As Byte()()

Get

Return m_renderedReport

End Get

Set(ByVal value As Byte()())

m_renderedReport = value

End Set

End Property

 

End Class

end

namespace

 

 

 

 

 


Viewing all articles
Browse latest Browse all 28687

Trending Articles



<script src="https://jsc.adskeeper.com/r/s/rssing.com.1596347.js" async> </script>