在服务器端静默打印报表

2023-12-03

我正在尝试编写一个程序,允许我将 ssrs 报告(.rdl 文件)从服务器端代码打印到预定打印机,而不会出现任何弹出窗口询问我要使用哪台打印机,这可以完成吗?


EDIT
还粘贴了代码ReportViewerDisposer我正在使用的实现。

和班级一起ReportViewerDisposer found here我正在使用以下代码,它是一个较大项目的一部分,但您应该能够轻松调整它:

private string m_printerName;
private string m_server;
private string m_path;
private string m_name;
private Dictionary<string, string> m_parameters;
private SizeF m_pageSize;
private float m_marginLeft;
private float m_marginTop;
private float m_marginRight;
private float m_marginBottom;
private short m_copies;

private int m_currentPageIndex;
private List<Stream> m_reportStreams;

public void PrintReport()
{
    string mime, extension;

    ReportViewer viewer = new ReportViewer();
    ReportViewerDisposer disposer = new ReportViewerDisposer(viewer);
    try
    {
    viewer.ProcessingMode = ProcessingMode.Remote;
    viewer.ServerReport.ReportServerUrl = new Uri(String.Format("http://{0}/ReportServer", m_server));
    viewer.ServerReport.ReportPath = String.Format("/{0}/{1}", m_path, m_name);

    List<ReportParameter> param = new List<ReportParameter>();
    foreach (ReportParameterInfo paramInfo in viewer.ServerReport.GetParameters())
    {
        if (m_parameters.ContainsKey(paramInfo.Name.ToUpperInvariant()))
        {
        string value = m_parameters[paramInfo.Name.ToUpperInvariant()];
        param.Add(new ReportParameter(paramInfo.Name, value));
        }
    }

    viewer.ServerReport.SetParameters(param);
    viewer.RefreshReport();

    CultureInfo us = new CultureInfo("en-US");
    string deviceInfo = String.Format(
      "<DeviceInfo>" +
      "  <OutputFormat>EMF</OutputFormat>" +
      "  <PageWidth>{0}cm</PageWidth>" +
      "  <PageHeight>{1}cm</PageHeight>" +
      "  <MarginTop>{2}cm</MarginTop>" +
      "  <MarginLeft>{3}cm</MarginLeft>" +
      "  <MarginRight>{4}cm</MarginRight>" +
      "  <MarginBottom>{5}cm</MarginBottom>" +
      "</DeviceInfo>",
      Math.Round(m_pageSize.Width, 2).ToString(us),
      Math.Round(m_pageSize.Height, 2).ToString(us),
      Math.Round(m_marginTop, 2).ToString(us),
      Math.Round(m_marginLeft, 2).ToString(us),
      Math.Round(m_marginRight, 2).ToString(us),
      Math.Round(m_marginBottom, 2).ToString(us));

    m_reportStreams = new List<Stream>();
    try
    {
        NameValueCollection urlAccessParameters = new NameValueCollection();
        urlAccessParameters.Add("rs:PersistStreams", "True");

        Stream s = viewer.ServerReport.Render("IMAGE", deviceInfo, urlAccessParameters, out mime, out extension);
        m_reportStreams.Add(s);

        urlAccessParameters.Remove("rs:PersistStreams");
        urlAccessParameters.Add("rs:GetNextStream", "True");
        do
        {
        s = viewer.ServerReport.Render("IMAGE", deviceInfo, urlAccessParameters, out mime, out extension);
        if (s.Length != 0) m_reportStreams.Add(s);
        }
        while (s.Length > 0);

        DoPrint();
    }
    finally
    {
        foreach (Stream s in m_reportStreams)
        {
        s.Close();
        s.Dispose();
        }
        m_reportStreams = null;
    }
    }
    finally
    {
    disposer.CollectGarbageOnDispose = true;
    disposer.Dispose();
    }
}


private void DoPrint()
{
    m_currentPageIndex = 0;

    PrintDocument printDoc = new PrintDocument();
    try
    {
    printDoc.PrintController = new StandardPrintController();
    printDoc.PrinterSettings.PrinterName = m_printerName;
    printDoc.PrinterSettings.Copies = m_copies;

    if (!printDoc.PrinterSettings.IsValid)
    {
        throw new ArgumentException(String.Format("Drucker '{0}' ist nicht gültig!", m_printerName));
    }

    // Drucke das Dokument aus
    printDoc.PrintPage += new PrintPageEventHandler(PrintPage);
    printDoc.QueryPageSettings += new QueryPageSettingsEventHandler(QueryPageSettings);
    printDoc.Print();
    }
    finally
    {
    printDoc.PrintPage -= new PrintPageEventHandler(PrintPage);
    printDoc.QueryPageSettings -= new QueryPageSettingsEventHandler(QueryPageSettings);
    printDoc.Dispose();
    }
}

private void PrintPage(object sender, PrintPageEventArgs ev)
        {
    if (m_currentPageIndex < m_reportStreams.Count)
    {
    Metafile mf = new Metafile(m_reportStreams[m_currentPageIndex++]);
    try
    {
        ev.Graphics.DrawImage(mf, ev.PageBounds);
    }
    finally
    {
        mf.Dispose();
    }
    }
    ev.HasMorePages = m_currentPageIndex < m_reportStreams.Count;
}


private void QueryPageSettings(object sender, QueryPageSettingsEventArgs e)
{
    e.PageSettings.Landscape = m_pageSize.Width > m_pageSize.Height;
}


private class ReportViewerDisposer : IDisposable
{ 
    // Fields  
    private bool _CollectGarbageOnDispose = true;
    private ReportViewer _ReportViewer;
    private bool disposedValue = false;
    private const string EVENTHANDLER_ON_USER_PREFERENCE_CHANGED = "OnUserPreferenceChanged";
    private const string LIST_HANDLERS = "_handlers";
    private const string ON_USER_PREFERENCE_CHANGED_EVENT = "OnUserPreferenceChangedEvent";
    private const string SYSTEM_EVENT_INVOKE_INFO = "SystemEventInvokeInfo";
    private const string TARGET_DELEGATE = "_delegate";
    private const string TOOLSTRIP_CONTROL_NAME = "reportToolBar";
    private const string TOOLSTRIP_TEXTBOX_CONTROL_NAME_CURRENT_PAGE = "currentPage";
    private const string TOOLSTRIP_TEXTBOX_CONTROL_NAME_TEXT_TO_FIND = "textToFind";

    // Methods  
    public ReportViewerDisposer(ReportViewer rptv)
    {
    if (rptv == null)
    {
        throw new ArgumentNullException("ReportViewer cannot be null.");
    }
    this._ReportViewer = rptv;
    }

    public void Dispose()
    {
    this.Dispose(true);
    GC.SuppressFinalize(this);
    }

    protected virtual void Dispose(bool disposing)
    {
    if (!this.disposedValue && disposing)
    {
        this.TearDownReportViewer();
        this._ReportViewer.Dispose();
        if (this._CollectGarbageOnDispose)
        {
        GC.Collect();
        GC.WaitForPendingFinalizers();
        GC.Collect();
        }
    }
    this.disposedValue = true;
    }

    private void NullRefOnUserPreferenceChanged(object o, string field)
    {
    try
    {
        FieldInfo fi = o.GetType().GetField(field, BindingFlags.NonPublic | BindingFlags.Instance);
        if (fi != null)
        {
        int i;
        ToolStripTextBox tb = (ToolStripTextBox)fi.GetValue(o);
        object tbc = tb.Control;
        Delegate d = Delegate.CreateDelegate(typeof(UserPreferenceChangedEventHandler), tbc, EVENTHANDLER_ON_USER_PREFERENCE_CHANGED);
        object handlers = typeof(SystemEvents).GetField(LIST_HANDLERS, BindingFlags.NonPublic | BindingFlags.Static).GetValue(null);
        object upcHandler = typeof(SystemEvents).GetField(ON_USER_PREFERENCE_CHANGED_EVENT, BindingFlags.NonPublic | BindingFlags.Static).GetValue(null);
        object systemEventInvokeInfo = typeof(SystemEvents).GetNestedType(SYSTEM_EVENT_INVOKE_INFO, BindingFlags.NonPublic | BindingFlags.Instance);
        IList upcHandlerList = (IList)((IDictionary)handlers)[upcHandler];
        int targetCount = 0;
        for (i = 0; i < upcHandlerList.Count; i++)
        {
            systemEventInvokeInfo = upcHandlerList[i];
            Delegate target = (Delegate)systemEventInvokeInfo.GetType().GetField(TARGET_DELEGATE, BindingFlags.NonPublic | BindingFlags.Instance).GetValue(systemEventInvokeInfo);
            if (target.Target == d.Target)
            {
            targetCount++;
            }
        }
        for (i = 1; i <= targetCount; i++)
        {
            SystemEvents.UserPreferenceChanged -= ((UserPreferenceChangedEventHandler)d);
        }
        }
    }
    catch
    {
    }
    } 

    private void TearDownReportViewer()
    {
    FieldInfo fi = this._ReportViewer.GetType().GetField(TOOLSTRIP_CONTROL_NAME, BindingFlags.NonPublic | BindingFlags.Instance);
    if (fi != null)
    {
        object o = fi.GetValue(this._ReportViewer);
        this.NullRefOnUserPreferenceChanged(o, TOOLSTRIP_TEXTBOX_CONTROL_NAME_CURRENT_PAGE);
        this.NullRefOnUserPreferenceChanged(o, TOOLSTRIP_TEXTBOX_CONTROL_NAME_TEXT_TO_FIND);
    }
    }

    // Properties  
    public bool CollectGarbageOnDispose
    {
    get
    {
        return this._CollectGarbageOnDispose;
    }
    set
    {
        this._CollectGarbageOnDispose = value;
    }
    }
} 
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

在服务器端静默打印报表 的相关文章

  • 当从后台工作程序发生事件时,XlCall.Excel(XlCall.xlcCalculateNow) 抛出 XlCallException

    我有一个 ExcelFunction 来排队一些计算 ExcelFunction public static void QueueCalcs takes ranges var calcRequests builds list of calc
  • 从 Invoke 方法获取 RETURN

    我正在尝试从另一个线程上的列表框项目中读取值 我尝试创建一种新方法来运行调用命令 我可以设法将命令发送到列表框 例如通过调用方法添加 但我似乎无法得到响应 我似乎无法获取该项目的值 我尝试了几种方法 一旦我将它从空变为字符串 事情就开始变得
  • 通过另一个列表更新列表(linq)

    我有类 Data 的对象列表 如下所示 class Data int code string name DateTime date update 我还有另一个课程列表 例如 class RefCodes int old code int n
  • 通过 SOAP 的 Gmt php 或 UTC C# 等效项

    is C DateTime UtcNow和 PHPdate c 是等价的 我怀疑 因为当我肥皂时 我得到了 C
  • .pdbs 会减慢发布应用程序的速度吗?

    如果 dll 中包含 pdb 程序调试 文件 则行号将出现在引发的任何异常的堆栈跟踪中 这会影响应用程序的性能吗 这个问题与发布与调试 即优化 无关 这是关于拥有 pdb 文件的性能影响 每次抛出异常时都会读取 pdb 文件吗 加载程序集时
  • 具有多个谓词的 C++11 算法

    功能如std find if来自algorithmheader 确实很有用 但对我来说 一个严重的限制是我只能为每次调用使用 1 个谓词count if 例如给定一个像这样的容器std vector我想同时应用相同的迭代find if 多个
  • 在 Mac OS X 上安装 libxml2 时出现问题

    我正在尝试在我的 Mac 操作系统 10 6 4 上安装 libxml2 我实际上正在尝试在 Python 中运行 Scrapy 脚本 这需要我安装 Twisted Zope 现在还需要安装 libxml2 我已经下载了最新版本 2 7 7
  • DataGridView 列中的数字文本框

    我有一个DataGridView 我想要它的第一列或任何所需的列 其中有textboxes在其中 成为NUMERIC ONLY 我目前正在使用这段代码 private void dataGridViewItems EditingContro
  • make_shared<>() 中的 WKWYL 优化是否会给某些多线程应用程序带来惩罚?

    前几天我偶然看到这个非常有趣的演示 http channel9 msdn com Events GoingNative GoingNative 2012 STL11 Magic Secrets作者 Stephan T Lavavej 其中提
  • 关闭整数的最右边设置位

    我只需要关闭最右边的设置位即可 我的方法是找到最右边位的位置 然后离开该位 我编写这段代码是为了这样做 int POS int n int p 0 while n if n 2 0 p else break n n 2 return p i
  • 为什么 std::function 不是有效的模板参数,而函数指针却是?

    我已经定义了名为的类模板CallBackAtInit其唯一目的是在初始化时调用函数 构造函数 该函数在模板参数中指定 问题是模板不接受std function作为参数 但它们接受函数指针 为什么 这是我的代码 include
  • 如何增加ofstream的缓冲区大小

    我想增加 C 程序的缓冲区大小 以便它不会过于频繁地写入 默认缓冲区是 8192 字节 我尝试使用 pubsetbuf 将其增加到 200K 原始代码 ofstream fq fastq1 cstr ios out fastq1 is a
  • 如何在新窗口中打开图像或pdf文件?

    我有一个 gridview 它包含文件名和文件路径 图像和 pdf 格式文件 其中我使用了模板字段 在该字段下放置了 1 个图像按钮 单击该图像按钮 即 查看 按钮 时 我想在新窗口中打开所选文件 这是我的代码 protected void
  • 如何使用 C# 查询远程 MS ACCESS .mdb 数据库

    我正在尝试使用 C 查询 mote MS ACCESS 数据库 mdb 文件 将文件复制到本地计算机时可以成功查询它 我只想远程放置文件 所以我的客户端程序不包含原始数据 static string m path http www xyz
  • MSChart 控件中的自定义 X/Y 网格线

    我有一个带有简单 2D 折线图的 C Windows 窗体 我想向其中添加自定义 X 或 Y 轴标记 并绘制自定义网格线 例如 以突出显示的颜色 虚线 我查看了 customLabels 属性 但这似乎覆盖了我仍然想显示的默认网格 这是为了
  • 在 Qt 中播放通知(频率 x)声音 - 最简单的方法?

    Qt 5 1 或更高版本 我需要播放频率为 x 的通知声音 n 毫秒 如果我能像这样组合音调那就太好了 1000Hz 持续 2 秒 然后 3000Hz 持续 1 秒 最简单的方法是使用文件 WAV MP3 例如如此处所述 如何用Qt播放声音
  • 时间:2019-03-17 标签:c#TimerStopConfusion

    我想通过单击按钮时更改文本颜色来将文本框文本设置为 闪烁 我可以让文本按照我想要的方式闪烁 但我希望它在闪烁几次后停止 我不知道如何在计时器触发几次后让它停止 这是我的代码 public Form1 InitializeComponent
  • 初始化列表在 VC10 中不起作用

    我在 VC 2010 中编写了这个程序 class class1 public class1 initializer list
  • 在 C 中使用 #define 没有任何价值

    If a define没有任何价值地使用 例如 define COMMAND SPI 默认值是0吗 不 它的评估结果为零 从字面上看 该符号被替换为空 然而 一旦你有了 define FOO 预处理器条件 ifdef FOO现在将是真的 另
  • Emacs C++,打开相应的头文件

    我是 emacs 新手 我想知道 是否有在头文件 源文件和相应的源文件 头文件之间切换的快捷方式 是否有像通用 emacs 参考卡那样的参考卡 Thanks There s ff find other file 您可以使用以下方法将其绑定到

随机推荐

  • 在数据步骤中表达“PUT所有变量”以导出SAS数据

    目标 使用数据步骤将整个 SAS 数据集导出到制表符分隔的文本文件 问题 在我能找到的每个例子中 例如this one 必须指定 PUT 语句后面的数据步骤中的每个变量 难道没有一种简单的方法来只要求 所有 变量吗 我已经尝试过使用PUT
  • 将上传的文件作为电子邮件附件发送

    我是网页设计的新手 我需要用 HTML 创建一个表单 要求用户输入多个字段并上传他 她的简历 当他提交表格时 他的提交内容应该通过电子邮件发送给我 并附上他的简历作为电子邮件的附件 我使用 PHP 来发送电子邮件 一切正常 除了文件未附加到
  • 无法访问 XCTestCase 对象中的 AppDelegate(或引用它的任何内容)

    我正在尝试在我的 swift iOS 应用程序上开始单元测试 但遇到了完全的障碍 我似乎无法访问任何使用我的 appDelegate 的内容 我的 appDelegate 有一个UserController存储和管理登录用户及其各种数据的对
  • 用音频录制点击的按钮

    我正在创造一种乐器 我希望录制按钮可以录制音频和点击的内容 但是当我点击录制按钮时 它只录制音频 我想录制音频以及用户点击的内容 这是我的记录代码 public void startRecord throws Exception recor
  • 使用 sed 引用特殊字符

    我试图查看传递给我的程序的变量 变量是 1 并用所述特殊字符的引号形式替换任何特殊字符 以免特殊字符实际上执行通常的操作 我的代码是 bin sh target 1 newtarget echo target sed e s g newta
  • “数组/指针等效”的现代术语是什么?

    几乎每个阅读本文的人都可能熟悉有关 C 的以下三个关键事实 当您在表达式中提及数组的名称时 它 大多数情况下 计算结果为指向数组第一个元素的指针 数组下标 运算符 对于指针和数组来说同样有效 看似数组的函数参数实际上声明了一个指针 这三个事
  • 如何获取用户数据中的 AWS 实例标签?

    我将 aws ec2 userdata 与 windows powershell 脚本结合使用 我需要实例引导 我的想法是 EC2实例标签添加 它的键名称 Version 它的值 1 0 0 158 branchname 我尝试获取用户数据
  • 如何使用PHP和SQL Server 2008调用存储过程

    我正在使用 SQL Server 2008 和 PHP 我想在 PHP 中调用存储过程 请指导我 Regards read mssql execute conn mssql connect host user pass mssql sele
  • 是否可以在 C# 中使用 Microsoft 的脱机文件 API?

    我正在尝试弄清楚如何使用离线文件API来自 C 如果可能 我相信 如果 API 是 COM API 那么理论上我应该能够使用以下方法从 C 调用它here 不幸的是 我不知道它是否是 COM API 也不知道如何判断 作为一个更一般的旁注
  • 手动优化嵌套循环

    我正在做一项家庭作业 我必须手动优化嵌套循环 我的程序将在禁用优化的情况下编译 作业的目标是在 6 秒内运行整个程序 少于 4 5 秒的加分 我只允许更改一小块代码 起点是这样的 for j 0 j lt ARRAY SIZE j sum
  • Scala REPL“错误:值>不是类型参数T的成员”

    这是我的文件 trait Set T def contains x T Boolean def incl x T Set T def union that Set T Set T class Empty T extends Set T ov
  • 如何在Monodroid中使用dropnet、sharp box等库

    我已经在图像上传器上创建了一个桌面应用程序 现在我想使用 Monodroid 将其移植到 Android 应用程序将图像上传到保管箱 在桌面版本中 我使用了 dropnet 它引用了 sharpbox Json 等 有什么方法可以在我的 m
  • 如何让ANTLR消耗所有可见元素?

    这是我的语法 grammar test text foo EOF foo X foo foo foo tail tail foo 我正在解析这段文字 X X X X 这是我得到的树 语法应该改变什么才能让我只得到一个tail包含所有元素的集
  • C 使用 scanf() 进行 |分隔字符串

    我想输入一些字符串然后两个整数 字符串由 分隔 而整数则由 分隔 在网上浏览时我看到了某种语法 其中涉及 我正在使用这个 但它根本不起作用 有人可以指出我应该做什么以及为什么我所做的事情是错误的吗 sscanf str s s s i i
  • 将 SXSSF 保存为 .xls 文件

    我正在使用 Apache POI 库将大量数据导入 Excel 文件 我不能使用 HSSF 模型 因为它需要太多内存并且 Java 会抛出内存堆异常 我发现的方法是 SXSSF 工作簿模型 它将每 N 行写入文件 而不是将所有工作簿存储在内
  • oracle如何在没有UNION的情况下将列转置为行

    假设我的表中有 4 列 id col1 col2 col3 现在我想将其转置为一列但分为 4 行 result someid col1data col2data col3data 我怎样才能做到这一点 谢谢 这可以使用以下方法完成unpiv
  • Fortran 结构体指针

    我在将一个指向结构的指针分配给一个指向结构的指针时遇到问题 我使用 gfortran 4 6 3 文件名是 test pointer struct f08 因此我使用 Fortran 2008 标准 由 gfortran 4 6 3 支持
  • 多个主题的 firebase 消息传递条件不起作用

    我正在使用节点 firebase admin 向 Android 设备发送消息 所有作品 除非我尝试向多个主题发送消息 在下面的示例代码中 我只是订阅了 2 个主题 然后直接向某个条件下的多个主题发送通知 我的手机上什么也没有到达 当您只发
  • C++ Hello World 体系结构 x86_64 的未定义符号:

    应该很简单 但是当我编译 C Hello World 代码时返回一堆未定义的符号错误 my first program in C include
  • 在服务器端静默打印报表

    我正在尝试编写一个程序 允许我将 ssrs 报告 rdl 文件 从服务器端代码打印到预定打印机 而不会出现任何弹出窗口询问我要使用哪台打印机 这可以完成吗 EDIT还粘贴了代码ReportViewerDisposer我正在使用的实现 和班级