
Hi,
We are trying to use HTML5 Report viewer in Angular 2 and Typescript. We are able to render report with hard coded parameters. Now we need to dynamically pass parameters both key and value.
ngAfterViewInit() {
var reportViewer = jQuery("#reportViewer1");
if (reportViewer) {
telerik_ReportViewer({
serviceUrl: this.baseUrl,
templateUrl: this.templateUrl,
reportSource: {
report: "test.testreport,report",
parameters: {
"p1": 1,
"p2": 2,
"p3": "head"
}
}
});
}
}
Instead of hard coded p1,p2, p3 we want to read key value pair from array and assign both key and value to parameters.
We are unable to get how to assign parameters dynamically. Please guide us. We are not able to find a sample which does this.
12 Answers, 1 is accepted


Hi
We are able to do this successfully in Angular 2.
below is my working code
in html
<style>
#reportViewer1 {
position: absolute;
left: 5px;
right: 5px;
top: 55px;
bottom: 5px;
font-family: 'segoe ui', 'ms sans serif';
overflow: hidden;
height: 650px;
width: 100%;
}
</style>
<div class="row padding padding-top">
<div id="reportViewer1" class="k-widget">
loading...
</div>
</div>
in ts
ngAfterViewInit() {
if (this.reportParameterService.reportQuery != null) {
let reportQuery: ReportQuery = this.reportParameterService.reportQuery;
let param: string = "{";
for (let item of reportQuery.Parameters.keys()) {
param = param + '"' + item + '"';
var val = reportQuery.Parameters.getValue(item);
param = param + ':"' + reportQuery.Parameters.getValue(item) + '",';
}
param = param.substr(0, param.length - 1);
param = param + '}';
var reportViewer = jQuery("#reportViewer1");
if (reportViewer) {
reportViewer.telerik_ReportViewer({
serviceUrl: this.baseUrl,
templateUrl: this.templateUrl,
reportSource: {
report: this.baseReportName + reportQuery.ReportName + this.baseDllName,
parameters: JSON.parse(param)
}
});
var rv = reportViewer.data("telerik_ReportViewer");
rv.commands.toggleParametersArea.exec();
}
}
else {
alert("No Report has been selected.");
}
}
My Data is wrapped in
import * as Collections from 'typescript-collections';
export class ReportQuery {
ReportName: String;
Parameters: Collections.Dictionary<String, any>;
SkipPreview: boolean;
constructor(reportname: string) {
if (reportname !== undefined) {
this.ReportName = reportname ;
this.Parameters = new Collections.Dictionary<String, any>();
this.SkipPreview = false;
}
}
}
and service class
import { Injectable } from '@angular/core';
import { ReportQuery } from '../models/queries/common/reportquery';
@Injectable()
export class ReportParameterService {
reportQuery: ReportQuery;
}

Thanks!
Did you have any problem with the templateUrl? This may be specific to Angular 4.0.x, but I had to rename the input variable to reportTemplateUrl in the ReportViewer javascript files because Angular was trying to load the value as a module.
Even so, I am still not getting the template to render the way I would expect...


Hi Dhananjaya. I have tons of trubles with report viewer integration in angular 2 (with webpack). Can you tell me witch files you include in the ts file where you put the viewer? How do you provide this files:
telerik/telerikReportViewer-11.0.17.222.js
telerik/telerikReportViewer.kendo-11.0.17.222.min.js
and css...
in your working project are you using webpack?
I've tried to follow your example but I get always the same error (proceeding in several ways):
"reportViewer.telerik_ReportViewer is not a function"
Thank you very very much for your help!

Hi Giovanni -
In my case, I decided to host the .js files on the same server as the REST service. However, I also had tried it in the /assets folder and that works fine as well.
My real problem came with the .css files. I am sure there are ways to make it work differently, but ultimately, I ended up using the Kendo CDN. However, the Blue Opal css file conflicts with the other Telerik kendo controls. My work around was to programatically add the css files to the header and remove them otherwise.
To solve your issue with the "is not a function" problem, declare it as a variable:
declare var jQuery: any;
declare var telerikReportViewer: any;
I have attached the .ts files - rename them from .png to view.

Hi Shawn,
Can you please share a working sample of it ?

@Rocco -
I don't have the bandwidth to put together a full working sample right now, but the files that I attached up above are the real meat of it. If you have any question, I can help out...
Shawn
You can upgrade to Telerik Reporting R2 2017 which includes a wrapper for Angular projects - Angular Report Viewer. An example is provided with your Telerik Reporting installation under C:\Program Files (x86)\Telerik\Reporting R2 2017\Examples\Angular.
Regards,
Stef
Telerik by Progress

Thanks @Shawn, I am able to successfully integrate it with my Angular 2 application. Can you provide me a sample code in order to pass parameters from one component to reportViewer Component using your ReportParameterSrevice
Thanks

Here is the latest version without the new Angular Wrapper (looking forward to implementing that). The Report Parameters are just passed via querystring:
export class ReportViewerComponent implements OnInit {
constructor(
private route: ActivatedRoute,
private router: Router,
private domService: DOMService){
}
private reportingApiUrl: string = environment.apiUrl + "/reporting/";
private templateUrl: string = "http://xxxxxx.net/reportviewer/templates/test.h";
private reportViewer: any;
private reportName: string;
private reportParams = new Array<
ReportParam
>();
ngOnInit(){
this.domService.addStyles([
}
ngAfterViewInit(){
this.reportViewer = jQuery("#reportViewer1");
this.reportName = this.route.snapshot.queryParams['reportName'];
if (!this.reportName)
return;
this.reportName += ".trdp";
var reportParamsQueryString: string = this.route.snapshot.queryParams['reportParams'];
if (reportParamsQueryString){
var reportParams = reportParamsQueryString.split(',')
reportParams.forEach(reportParam => {
var parts = reportParam.split(':');
var newParam: ReportParam = {
name: parts[0],
value: parts[1]
}
this.reportParams.push(newParam);
});
}
this.loadReport();
}
private loadReport (){
if (this.reportViewer) {
this.reportViewer.telerik_ReportViewer({
serviceUrl: this.reportingApiUrl,
reportSource: {
report: this.reportName,
parameters: JSON.parse(this.buildParameters(this.reportParams))
},
// Specifies whether the viewer is in interactive or print preview mode.
// PRINT_PREVIEW - Displays the paginated report as if it is printed on paper. Interactivity is not enabled.
// INTERACTIVE - Displays the report in its original width and height without paging. Additionally interactivity is enabled.
viewMode: telerikReportViewer.ViewModes.INTERACTIVE,
// Sets the scale mode of the viewer.
// Three modes exist currently:
// FIT_PAGE - The whole report will fit on the page (will zoom in or out), regardless of its width and height.
// FIT_PAGE_WIDTH - The report will be zoomed in or out so that the width of the screen and the width of the report match.
// SPECIFIC - Uses the scale to zoom in and out the report.
scaleMode: telerikReportViewer.ScaleModes.FIT_PAGE,
// Zoom in and out the report using the scale
// 1.0 is equal to 100%, i.e. the original size of the report
scale: 1.0,
});
};
}
private buildParameters(reportParams: ReportParam[]) : string {
let parameters: string = "{";
for (let param of reportParams) {
if (parameters.length > 1)
parameters = parameters + ',';
parameters = parameters + '"' + param.name + '"' + ':"' + param.value + '"'
}
parameters = parameters + '}';
return parameters;
}
}
export class ReportParam{
name: string;
value: string;
}

Hi Shawn, what is the best way of passing the complex parameters via route. Is it not better to use service?
Regards.