cancel
Showing results for 
Search instead for 
Did you mean: 

Binding Report Source on WPF Crystal Report Viewer Solution

Former Member
0 Kudos

I spent an hour or two trying to find a solution to this problem so I thought I would post it here for others.

The problem:

You wish to bind the report source of your viewer to a property, but you find that the property is not available directly on the viewer. You are following the MVVM pattern and you do not wish to add the code directly behind the view as you wish to set the report source from the view model.

This is how I solved it - if anyone has any comments or suggestions I would appreciate it.

Create a static class to hold an attached property we will use on our viewer:

public static class ReportSourceBehaviour
    {

        public static readonly DependencyProperty ReportSourceProperty =
            DependencyProperty.RegisterAttached(
            "ReportSource",
            typeof(object),
            typeof(ReportSourceBehaviour),
            new PropertyMetadata(ReportSourceChanged)
            );

        private static void ReportSourceChanged(
            DependencyObject d,
            DependencyPropertyChangedEventArgs e)
        {
            var crviewer = d as CrystalReportsViewer;
            if (crviewer != null)
            {
                crviewer.ViewerCore.ReportSource = e.NewValue;
            }
        }

        public static void SetReportSource(DependencyObject target, object value)
        {
            target.SetValue(ReportSourceProperty, value);
        }

        public static object GetReportSource(DependencyObject target)
        {
            return target.GetValue(ReportSourceProperty);
        }
        
    }

Note the ReportSourceChanged code in particular, this is where we set the report source on the viewer.

Then we need to add the binding on the viewer. This stumped me for a while as I could not work out why the the datacontext of the viewer would not pick up the viewmodel (the datacontext of the viewer seems to reference itself rather than pickup the datacontext of its parent). The simplest answer I found was to bind to the parent datacontext.

First setup the namespaces if you haven't already (adjust the namespace to suit):

xmlns:sap="clr-namespace:SAPBusinessObjects.WPF.Viewer;assembly=SAPBusinessObjects.WPF.Viewer"
xmlns:local="clr-namespace:[NamespaceWhereReportSourceBehaviourResides]"

Then add in the viewer:

<sap:CrystalReportsViewer local:ReportSourceBehaviour.ReportSource="{Binding Path=DataContext.ReportSource, RelativeSource={RelativeSource Mode=FindAncestor, AncestorType=FrameworkElement}}" />

Note the binding path, this needs to point to the property on your viewmodel that holds the reportsource (in my case the property is just called reportsource).

Hope this helps someone out there.

Accepted Solutions (1)

Accepted Solutions (1)

Former Member
0 Kudos

Hi James,

thank you, i made as you proposed but i have got problem passing parameter, is there something special to do than :

  ReportSource.SetParameterValue(0, myValue1);

  ReportSource.SetParameterValue(1, myValue2);

  ReportSource.SetParameterValue(2, ...);

  .....

I have got 15 parameter... and There are some strange bugs... It take 2-3 first parameters than for the others, it always ask me the value popup, like he can't see the values... then each time, i retest it doesn't ask me the same values for the same variable without i chnaged something in the code !!!! really strange ?

any idea ?

former_member183750
Active Contributor
0 Kudos

I'd recommend looking at some samples. For starters look at vbnet_win_paramengine.zip available from here:

http://wiki.sdn.sap.com/wiki/x/JQBmBQ

And I am pretty sure the search string 'crystal net parameter' will return a number of very good resources. Search box is in the top right corner of this web page...

- Ludek

Senior Support Engineer AGS Product Support, Global Support Center Canada

Follow us on Twitter

Share Your Knowledge in SCN Topic Spaces

Former Member
0 Kudos

It's been a long time since I looked at this, but I've had a quick
look at my code and the only thing I can spot is that I am setting the
parameters on a ReportDocument variable before passing to the
ReportViewer.

ReportDocument report = new ReportDocument();

report.Load(reportPath);

report.SetParameterValue(parameterName, parameterValue);

It could be why 2-3 are working as you have race condition between the
viewer loading the report and you setting the parameters.  Try setting
the parameters BEFORE you set the report source on the viewer.

Answers (0)