How to use json data in chart.js in an ionic app - json

I would like to implement chart.js, I followed the example HERE, it worked well with a sample array data, but now I want to put live data fetch in json format from my server, I could not get a head way.
this is my html page
<ion-header>
<ion-navbar>
<ion-title>results</ion-title>
</ion-navbar>
</ion-header>
<ion-content padding>
<ion-card >
<ion-card-header>
Bar Chart
</ion-card-header>
<ion-card-content>
<canvas width="800" height="800" #barCanvas></canvas>
</ion-card-content>
</ion-card>
</ion-content>
and my .ts page
import { Component, ViewChild } from '#angular/core';
import { IonicPage, NavController, NavParams } from 'ionic-angular';
import { Chart } from 'chart.js';
import { LoadingController, AlertController } from 'ionic-angular';
import {Http, Headers, RequestOptions} from "#angular/http";
import 'rxjs/add/operator/map';
#IonicPage()
#Component({
selector: 'page-results',
templateUrl: 'results.html',
})
export class ResultsPage {
#ViewChild('barCanvas') barCanvas;
barChart: any;
selectedOption:any;
items:any;
val : any=[];
val2 : any=[];
constructor(public navCtrl: NavController, public navParams: NavParams, private http: Http, public loading: LoadingController,
public alertCtrl: AlertController) {
}
ionViewDidLoad() {
this.selectedOption = this.navParams.get('options');
var headers = new Headers();
headers.append("Accept", 'application/json');
headers.append('Content-Type', 'application/json' );
let options = new RequestOptions({ headers: headers });
let data = {
option: this.selectedOption
};
let loader = this.loading.create({
content: 'Processing please wait...',
});
loader.present().then(() => {
this.http.post('mydomain/fetch_data.php',data, options)
.map(res => res.json())
.subscribe(res => {
loader.dismiss()
this.items=res.server_response;
console.log(this.items);
this.items.map((item)=>{
this.val1.push(item.options);
});
this.items.map((item)=>{
this.val2.push(item.result);
});
});
});
this.showChart();
}
showChart(){
this.barChart = new Chart(this.barCanvas.nativeElement, {
type: 'bar',
data: {
labels: this.val1,
datasets: [{
label: '# of Votes',
data: this.val2,
backgroundColor: [
'rgba(255, 99, 132, 0.2)',
'rgba(54, 162, 235, 0.2)',
'rgba(255, 206, 86, 0.2)',
'rgba(75, 192, 192, 0.2)'
],
borderColor: [
'rgba(255,99,132,1)',
'rgba(54, 162, 235, 1)',
'rgba(255, 206, 86, 1)',
'rgba(75, 192, 192, 1)'
],
borderWidth: 1
}]
},
options: {
scales: {
xAxes: [{
ticks: {
beginAtZero:true
}
}]
}
}
});
}
}
I got json data but to convert it to another array like labels: ["Red", "Brown", "Blue", "Yellow", "Green", "Purple", "Orange"], and data: [11, 15, 22, 4, 6, 2, 3] such that I can use it as val1 and val2 as shown above is my challenge.
Thank you in advance

First you install ng2-charts, and import { ChartsModule } from 'ng2-charts'; to app/app.module.ts
in example.html
<div style="display: block; color:white; responsive: true;
maintainAspectRatio: false;">
<canvas baseChart
height="350"
[colors]="chartColors"
[labels]="doughnutChartLabels"
[data]="doughnutChartData"
[chartType]="doughnutChartType"
(chartHover)="chartHovered($event)"
(chartClick)="chartClicked($event)"></canvas>
</div>
in example.ts
export class ExamplePage {
doughnutChartLabels: string[] = [];
doughnutChartData: number[] = [];
doughnutChartType: string = 'pie';
checkChart : boolean;
...}
pushItem(){
#pushed your json data in doughnutChartData
#end called this fonction in ionViewDidLoad and any methods
}
public chartClicked(e:any):void {
#...
}
public chartHovered(e:any):void {
#...
}

Related

Not able to show graph on click of a button

Graph is not displayed on click. I have
I have two child components
Data component for showing the list of employees
Rating component for showing employee's respective rating
I have put 'graph code' inside 'ngOnInit' function in Rating component, and click button is in Data component, with help of event emitting i am trying to pass a boolean value from Data to Rating .
As you can see below in rating.component.html, if the flag value becomes true, then show graph. But even after flag becomes true, graph is not visible.
Data component
import { DataService } from './../../services/data.service';
import { Component, OnInit, Output, EventEmitter} from '#angular/core';
#Component({
selector: 'app-data',
templateUrl: './data.component.html',
styleUrls: ['./data.component.css'],
})
export class DataComponent implements OnInit {
users: { name: string; city: string }[] = [];
visible = false;
#Output() show = new EventEmitter();
constructor(private dataSerivce: DataService) {}
ngOnInit(): void {
this.users = this.dataSerivce.getEmployees();
}
toggle() {
this.visible = !this.visible;
if (this.visible) {
console.log('enter');
this.show.emit(this.visible);
} else {
this.show.emit(null);
}
}
}
Rating component
import { Rating } from './../../../../models/rating.model';
import { DataService } from 'src/app/services/data.service';
import { Component, OnInit, Input, OnChanges, SimpleChanges} from '#angular/core';
import {Chart} from '../../../../node_modules/chart.js';
#Component({
selector: 'app-rating',
templateUrl: './rating.component.html',
styleUrls: ['./rating.component.css']
})
export class RatingComponent implements OnInit ,OnChanges{
rating: Rating[] = [];
#Input() flag = false;
constructor(private dataService: DataService) { }
ngOnInit() {
console.log('init');
var myChart= new Chart('myChart', {
type: 'bar',
data: {
labels: ['Technical', 'Communication', 'Experience', 'Leadership'],
datasets: [{
label: 'skill scores',
data: [10,15, 16, 22],
backgroundColor: [
'rgba(255, 99, 132, 0.2)',
'rgba(54, 162, 235, 0.2)',
'rgba(255, 206, 86, 0.2)',
'rgba(75, 192, 192, 0.2)'
],
borderColor: [
'rgba(255, 99, 132, 1)',
'rgba(54, 162, 235, 1)',
'rgba(255, 206, 86, 1)',
'rgba(75, 192, 192, 1)'
],
borderWidth: 1
}]
},
options: {
scales: {
yAxes: [{
ticks: {
beginAtZero: true
}
}]
}
}
});
}
ngOnChanges(changes: SimpleChanges){
console.log('first time');
}
private getRatings($event){
this.dataService.getRating().subscribe(res =>{
this.rating.push(res);
});
}
}
Rating html code
<div style="height:40%;width:40%;" class="center" *ngIf ="flag" >
<canvas
class="chart chart-bar"
chart-data="dataChart" id = "myChart"></canvas>
</div>
While the chart.js options might be correct, the current code in RatingComponent is not referencing the chart.js options to any particular DOM Element. This could be one of the reasons why the chart is not getting rendered.
ChartJS expects a reference to a DOM Element which it shall use to render the chart.
For example:
HTML Template:
<div #barchart class="barChart"><d/iv>
RatingsComponent :
import { Component, OnInit, ViewChild } from '#angular/core';
import { Chart } from 'chart.js';
#Component({
...
})
export class RatingComponent implements OnInit {
#ViewChild('barchart') private chartRef;
chart: any;
ngOnInit() {
// provide reference of the html component to the the Chart Instance.
this.chart = new Chart(this.chartRef.nativeElement, {
// insert chart options here
});
}
}
Alternatively
After looking at your update, I think the part that is causing issue is that you are not passing the required data to the canvas component.
According to the documentation of ChartJS.
HTML Code:
<div>
<div style="display: block">
<canvas baseChart
[datasets]="barChartData"
[labels]="barChartLabels"
[options]="barChartOptions"
[legend]="barChartLegend"
[chartType]="barChartType">
</canvas>
</div>
</div>
Component
import { Component, OnInit } from '#angular/core';#Component({
selector: 'app-my-bar-chart',
templateUrl: './my-bar-chart.component.html',
styleUrls: ['./my-bar-chart.component.css']
})
export class MyBarChartComponent implements OnInit { constructor() { }
public barChartOptions = {
scaleShowVerticalLines: false,
responsive: true
};
public barChartLabels = ['2006', '2007', '2008', '2009', '2010', '2011', '2012'];
public barChartType = 'bar';
public barChartLegend = true; public barChartData = [
{data: [65, 59, 80, 81, 56, 55, 40], label: 'Series A'},
{data: [28, 48, 40, 19, 86, 27, 90], label: 'Series B'}
];
ngOnInit() {
}}

Highcharts with json from django query not rendered

I'm following this article to render highchart with json data from django query. However chart is not rendered but I'm not getting any errors from Django or by the client when inspecting source. Appreciate if anyone can point the mistakes. Thank you in advance.
I'm using django 2.0 and python3.5
models.py
PLATFORM = (
('ipcore','IPCORE'),
('metro','METRO E'),
('edge','EDGE'),
('access','ACCESS'),
('voice','VOICE'),
('system','SYSTEM'),
('iptv','IPTV'))
class Contract(models.Model):
vendor_name = models.ForeignKey(Vendor, on_delete=models.CASCADE)
name = models.CharField(max_length=500)
contract_no = models.CharField(max_length=100, blank=True)
partner_name = models.CharField(max_length=200, blank=True)
value = models.DecimalField(max_digits=11, decimal_places=2,
blank=True, null=True)
platform = models.CharField(max_length=100, blank=True,
choices=PLATFORM)
views.py
def json_example(request):
return render(request, 'app/json_example.html')
def chart_data(request):
dataset=Contract.objects.all().values('platform').
exclude(platform='').annotate(Sum('value')).order_by('value__sum')
platform_name = dict()
for platform_tuple in Contract.PLATFORM:
platform_name[platform_tuple[0]] = platform_tuple[1]
chart = {
'chart': {'type': 'pie'},
'title': {'text': 'Contract Value for Every platform'},
'series': [{
'name': 'Platform',
'data': list(map(lambda row: {'name':
platform_name[row['platform']],
'y': row['value__sum']}, dataset))
}]
}
return JsonResponse(chart)
urls.py
url('json_example/', views.json_example, name='json_example'),
url('json_example/data/', views.chart_data, name='chart_data'),
json_example.html
<!doctype html>
<html>
<head>
<meta charset="utf-8">
<title>Contract Inventory Highcharts Example</title>
</head>
<body>
<div id="container" data-url="{% url 'chart_data' %}"></div>
<script src="https://code.highcharts.com/highcharts.src.js"></script>
<script src="https://code.jquery.com/jquery-3.3.1.min.js"></script>
<script>
$.ajax({
url: $("#container").attr("data-url"),
dataType: 'json',
success: function (data) {
Highcharts.chart("container", data);
}
});
</script>
</body>
</html>
This is the json data from dataset.
[{"platform": "IPTV", "value__sum": "0.00"}, {"platform": "METRO E", "value__sum": "71372564.20"}, {"platform": "EDGE", "value__sum": "73867073.63"}, {"platform": "SYSTEM", "value__sum": "135465418.85"}, {"platform": "IPCORE", "value__sum": "467810178.41"}]
This is the json data from dataset.
[{"platform": "IPTV", "value__sum": "0.00"}, {"platform": "METRO E", "value__sum": "71372564.20"}, {"platform": "EDGE", "value__sum": "73867073.63"}, {"platform": "SYSTEM", "value__sum": "135465418.85"}, {"platform": "IPCORE", "value__sum": "467810178.41"}]
Your json data doesn't contain chart options. It should be something like this:
'{"title":{"text":"Title"},"series":[{"name":"Installation","data":[43934,52503,57177,69658,97031,119931,137133,154175]}]}'
What's more, you should parse json to js object before passing it to Highcharts constructor:
<script>
$.ajax({
url: $("#container").attr("data-url"),
dataType: 'json',
success: function (data) {
var chartData = JSON.parse(data);
Highcharts.chart("container", chartData);
}
});
</script>
Check the example:
https://jsfiddle.net/BlackLabel/7zfyhnbr/
You have to format the data in such a way that it should match the highcharts ploting object. Please checkout the below code.
data = [
{"platform": "IPTV", "value__sum": "0.00"},
{"platform": "METRO E", "value__sum": "71372564.20"},
{"platform": "EDGE", "value__sum": "73867073.63"},
{"platform": "SYSTEM", "value__sum": "135465418.85"},
{"platform": "IPCORE", "value__sum": "467810178.41"}];
x_axis_data = [];
y_axis_data = [];
for(index=0; index < data.length; index++) {
item = data[index];
x_axis_data.push(item['platform'])
y_axis_data.push(parseFloat(item['value__sum']))
}
Highcharts.chart('container', {
title: {
text: 'learnbatta.com'
},
xAxis: {
title: {
text: 'X Value'
},
categories: x_axis_data
},
yAxis: {
title: {
text: 'Y Value'
},
},
series: [{
name: 'Curve',
data: y_axis_data
}]
});
<!DOCTYPE html>
<html>
<head>
<title></title>
<script src="http://code.highcharts.com/highcharts.js"></script>
<script src="http://code.highcharts.com/modules/exporting.js"></script>
<script src="https://ajax.googleapis.com/ajax/libs/jquery/3.3.1/jquery.min.js"></script>
</head>
<body>
<div id="container"></div>
</body>
</html>
You have to update your code like below
<script>
$.ajax({
url: $("#container").attr("data-url"),
dataType: 'json',
success: function (data) {
var data = JSON.parse(data);
x_axis_data = [];
y_axis_data = [];
for(index=0; index < data.length; index++) {
item = data[index];
x_axis_data.push(item['platform'])
y_axis_data.push(parseFloat(item['value__sum']))
}
Highcharts.chart('container', {
title: {
text: 'learnbatta.com'
},
xAxis: {
title: {
text: 'X Value'
},
categories: x_axis_data
},
yAxis: {
title: {
text: 'Y Value'
},
},
series: [{
name: 'Curve',
data: y_axis_data
}]
});
}
});
</script>
I've manage to solve it by updated my views.py using django rest API and my template accordingly. Here is my updated code:
views.py
from rest_framework.views import APIView
from rest_framework.response import Response
class ChartView(View):
def get(self, request, *args, **kwargs):
return render(request, 'app/charts.html')
class ChartData(APIView):
authentication_classes = []
permission_classes = []
def get(self, request, format=None):
totalvendor= Contract.objects.all().values("vendor_name_id__name").
annotate(Count("id")).order_by('-id__count')[:8]
labels = totalvendor.values_list('vendor_name_id__name')
default_items = totalvendor.values_list('id__count', flat=True)
default_items = list(default_items)
data = {
"labels": labels,
"default": default_items,
}
return Response(data)
Pass an array from queryset to template and js
Here is my urls.py
url(r'^chart/', views.ChartView.as_view(), name='chart'),
url(r'^api/chart/data/$', ChartData.as_view(), name='chartdata'),
Here my code for charts.html
<script>
{% block jquery %}
var endpoint = '/api/chart/data/'
var defaultData = []
var labels = [];
$.ajax({
method: "GET",
url: endpoint,
success: function(data){
labels = data.labels
defaultData = data.default
setChart()
},
error: function(error_data){
console.log("error")
console.log(error_data)
}
})
function setChart(){
var ctx = document.getElementById("myChart");
var ctx2 = document.getElementById("myChart2");
var myChart = new Chart(ctx2, {
type: 'bar',
data: {
labels: labels,
datasets: [{
label: 'Value Contract for Platform',
data: defaultData,
backgroundColor: [
'rgba(255, 99, 132, 0.2)',
'rgba(54, 162, 235, 0.2)',
'rgba(255, 206, 86, 0.2)',
'rgba(75, 192, 192, 0.2)',
'rgba(153, 102, 255, 0.2)',
'rgba(255, 159, 64, 0.2)'
],
borderColor: [
'rgba(255,99,132,1)',
'rgba(54, 162, 235, 1)',
'rgba(255, 206, 86, 1)',
'rgba(75, 192, 192, 1)',
'rgba(153, 102, 255, 1)',
'rgba(255, 159, 64, 1)'
],
borderWidth: 1
}]
},
options: {
title:{
display:true,
text:'Count Contract for Every Platform',
fontSize:18,
position:'top'
},
legend:{
display:false,
position:'right',
labels:{
fontColor:'#000'
}
},
scales: {
yAxes: [{
ticks: {
beginAtZero:true
}
}]
}
}
});
var myChart = new Chart(ctx, {
type: 'polarArea',
data: {
labels: labels,
datasets: [{
label: 'Count Contract for Platform',
data: defaultData,
backgroundColor: [
'rgba(255, 99, 132, 0.2)',
'rgba(54, 162, 235, 0.2)',
'rgba(255, 206, 86, 0.2)',
'rgba(75, 192, 192, 0.2)',
'rgba(153, 102, 255, 0.2)',
'rgba(255, 159, 64, 0.2)'
],
borderColor: [
'rgba(255,99,132,1)',
'rgba(54, 162, 235, 1)',
'rgba(255, 206, 86, 1)',
'rgba(75, 192, 192, 1)',
'rgba(153, 102, 255, 1)',
'rgba(255, 159, 64, 1)'
],
borderWidth: 1
}]
},
options: {
scales: {
yAxes: [{
ticks: {
beginAtZero:true
}
}]
}
}
});
}
// var ctx = document.getElementById("myChart");
{% endblock %}
</script>
{% block content %}
<div class='row'>
<div class='col-sm-12' url-endpoint='{% url "chartdata" %}'>
<h1>Data Presentation</h1>
<div class=''>
<div class='col-sm-6'>
<canvas id="myChart" width="400" height="400"></canvas>
</div>
<div class='col-sm-6'>
<canvas id="myChart2" width="400" height="400"></canvas>
</div>
</div>
</div>
</div>
{% endblock content %}
Anyway thanks to those who answered my questions

How to pass data received from service to angular datatable

I have just started working on Angular 4 and I am trying to render some data which I receive from angular service in json format, into angular-datatable, but whichever option i try its not working for me.
The table is coming, the columns are coming, however the data inside the columns are not displaying.
Any help would be great,
Thanks in advance..!!!!
Please find my code below:
component.html
<table datatable [dtOptions]="dtOptions" class="row-border hover"></table>
component.ts
import { Component, OnInit } from '#angular/core';
import { FleetDataService } from '../../services/fleet-data.service';
import { Subject } from 'rxjs/Subject';
#Component({
selector: 'app-dashboard',
templateUrl: './dashboard.component.html',
styleUrls: ['./dashboard.component.scss']
})
export class DashboardComponent implements OnInit {
private fleetData: any;
dtOptions: DataTables.Settings = {};
dtTrigger: Subject<any> = new Subject();
constructor(private getFleetData:FleetDataService) { }
ngOnInit() {
this.getFleetData.getFleetData().subscribe(
fleetData => {
this.fleetData = fleetData;
console.log(this.fleetData);
this.dtTrigger.next();
},
err => {
console.log(err);
}
);
this.dtOptions = {
pagingType: 'full_numbers',
columns: [{
title: 'First Name',
data: this.fleetData
}, {
title: 'Last Name',
data: this.fleetData
}, {
title: 'Score',
data: this.fleetData
}]
};
}
}
component.service
import { Injectable } from '#angular/core';
import { HttpModule, Http, Response, Headers, RequestOptions } from
'#angular/http';
import { Observable } from 'rxjs/Rx';
#Injectable()
export class FleetDataService {
constructor(private http: Http) { }
getFleetData() {
return this.http.get("../../assets/data/test.json")
.map((res:Response) => res.json())
.catch((error:any) => Observable.throw(error.json().error || 'Server
Error'));
}
}
test.json
[{
"FirstName": "Jill",
"LastName": "Smith",
"Score": "disqualified"
}, {
"FirstName": "Eve",
"LastName": "Jackson",
"Score": "94"
}, {
"FirstName": "John",
"LastName": "Doe",
"Score": "80"
}, {
"FirstName": "Adam",
"LastName": "Johnson",
"Score": "67"
}]
You set your dtOptions outside the subscribe.
If you do this the fleetData stays empty so dtOptions is never set correctly, because an Observable is asynchronous. I propose this code:
export class DashboardComponent implements OnInit {
dtOptions: DataTables.Settings = {};
dtTrigger: Subject<any> = new Subject();
constructor(private getFleetData:FleetDataService) { }
ngOnInit() {
this.getFleetData.getFleetData().subscribe(
fleetData => {
console.log(fleetData);
this.buildDtOptions(fleetData)
this.dtTrigger.next();
},
err => {
console.log(err);
});
}
private buildDtOptions(fleetData: any): void {
this.dtOptions = {
pagingType: 'full_numbers',
columns: [
{title: 'First Name', data: fleetData},
{title: 'Last Name', data: fleetData},
{title: 'Score', data: fleetData}
]
};
}
}
For this error: ERROR TypeError: Cannot read property 'aDataSort' of undefined. You can do a spinner (ngIf / else) in the view and when data are loaded you display the datatable

ERROR Error: Error trying to diff '[object Object]'. Only arrays and iterables are allowed

I have issue with nested JSON file. I use primeNG templates dataTable and treeTable. When I try to access data via API call in console I can see data but in template I'm getting this error:
ERROR Error: Error trying to diff '[object Object]'. Only arrays and iterables are allowed
json file
{
"CategoryId": "257cf663-f6ba-40f7-69b8-08d527528e70",
"Name": "House Only",
"OverBudgetCalculator": true,
"Scopes": [
{
"ScopeId": 1,
"Name": "Budget",
"Question": {
"QuestionId": 1,
"Content": "What is your maximum budget ?",
"QuestionType": "range",
"Strict": true,
"NeutralScore": 10,
"Weight": 100,
"UpDownSelectionApplied": false,
"Active": true,
"RelatedProductFields": [
{
"RelatedProductFieldId": 3,
"FieldName": "Budget",
"Step": 1000,
"Min": 0,
"Max": 0
}
],
"Answers": []
}
},
{
"ScopeId": 2,
"Name": "Levels",
"Question": {
"QuestionId": 2,
"Content": "Do you want a single or double ?",
"QuestionType": "singleSelection",
"Strict": true,
"NeutralScore": 10,
"Weight": 95,
"UpDownSelectionApplied": false,
"Active": true,
"RelatedProductFields": [
{
"RelatedProductFieldId": 10,
"FieldName": "House_Only_Levels",
"Step": 0,
"Min": 0,
"Max": 0
}
],
"Answers": [
{
"AnswerId": 18,
"Title": "Double Story",
"Content": "Double Story",
"MatchRule": "Double",
"UpDownSpecifications": [],
"Selected": false
},
{
"AnswerId": 19,
"Title": "Single Story",
"Content": "Single Story",
"MatchRule": "Single",
"UpDownSpecifications": [],
"Selected": false
}
]
}
scope.service.ts
import { Injectable } from '#angular/core';
import { Http, Response, Headers, RequestOptions } from "#angular/http";
import { AppSessionService } from '#shared/common/session/app-session.service';
import { Observable } from 'rxjs/Observable';
import { Scope } from './scope';
import { TreeTableModule } from 'primeng/components/treetable/treetable';
#Injectable()
export class ScopeService {
constructor(
private http: Http,
private appSessionService: AppSessionService) { }
// GET api/categories/scopes/257CF663-F6BA-40F7-69B8-08D527528E70
getScopes(categoryId): Observable<any> {
let headers = new Headers({ 'Content-Type': 'application/json' })
let options = new RequestOptions({ headers: headers });
return this.http.get('/api/categories/' + categoryId)
.map((res: Response) => res.json())
.catch(this.handleErrorObservable);
}
private extractData(res: Response) {
let body = res.json();
return body.data || {};
}
private handleErrorObservable(error: Response | any) {
console.error(error.message || error);
return Observable.throw(error.message || error);
}
}
scope.component.ts
import { Component, Injector, OnInit, ViewChild } from '#angular/core';
import { AppComponentBase } from '#shared/common/app-component-base';
import { appModuleAnimation } from '#shared/animations/routerTransition';
import { ScopeService } from './scope.service';
import { DataTable } from 'primeng/components/datatable/datatable';
import { Paginator } from 'primeng/components/paginator/paginator';
import { TreeTableModule } from 'primeng/components/treetable/treetable';
#Component({
templateUrl: './scopes.component.html',
animations: [appModuleAnimation()]
})
export class ScopesComponent extends AppComponentBase implements OnInit {
errorMessage: String;
scopes: any = [];
categoryId: String = '257CF663-F6BA-40F7-69B8-08D527528E70';
constructor(
injector: Injector,
private scopeService: ScopeService
) {
super(injector);
}
ngOnInit(): void {
this.getScopes(this.categoryId);
}
getScopes(categoryId) {
this.scopeService.getScopes(categoryId).subscribe(values => {
this.scopes = values;
console.log(this.scopes);
})
}
}
This is component file with treeTable
scope.component.html (treeTable)
<p-treeTable [value]="scopes" [style]="{'margin-top':'50px'}">
<p-header>Editable Cells with Templating</p-header>
<p-column field="CategoryId" header="ScopeId">
<ng-template let-node="rowData" pTemplate="body">
<input type="text" [(ngModel)]="categories.Scopes.ScopeId" style="width:100%;border-width:0px 0px 1px 0px">
</ng-template>
</p-column>
<p-column field="Name" header="Name">
<ng-template let-node="rowData" pTemplate="body">
<input type="text" [(ngModel)]="categories.Scopes.Name" style="width:100%;border-width:0px 0px 1px 0px">
</ng-template>
</p-column>
</p-treeTable>
This is component file with dataDatable.
scope.components.html (dataTable)
<p-dataTable [value]="scopes"
selectionMode="single"
[rows]="10"
[responsive]="true">
<p-column field="Scopes" header="Scope name">
<ng-template let-account="rowData" pTemplate="body">
<ul>
<li *ngFor="let scope of categories.scopes">
{{scope.ScopeId}} - {{scope.Name}}
</li>
</ul>
</ng-template>
</p-column>
</p-dataTable>
When I use dataTable option I'm getting different error.
ERROR TypeError: val.slice is not a function
enter image description here
enter image description here

Ionic 3 Accordion List with a Native Element Chart

I am trying to make an accordion list where when a user clicks on it, and it then displays a chart of data. The problem is the chart shows originally, but when I close the accordion list then it doesn't show again upon reopening. So basically open app, shows chart, click accordion element, chart disappears, click accordion element, it expands, but the chart doesn't show.
chart-page.html
<ion-header>
<ion-navbar>
<ion-title>Health Summary</ion-title>
</ion-navbar>
</ion-header>
<ion-content padding>
<ion-list>
<ion-item padding (click)="toggleChartThisWeek(thisWeek)">
This Week
<div *ngIf="thisWeek">
<br>
<canvas #lineCanvas></canvas>
<br>
</div>
</ion-item>
</ion-list>
</ion-content>
chart-page.ts
import { Component, ViewChild } from '#angular/core';
import { IonicPage, NavController, NavParams, Platform } from 'ionic-angular';
import { Chart } from 'chart.js';
#IonicPage()
#Component({
selector: 'page-chart-page',
templateUrl: 'chart-page.html',
})
export class ChartPage {
#ViewChild('lineCanvas') lineCanvas;
lineChart: any;
chartLabels: any = ["January", "February", "March", "April", "May", "June", "July"];
chartData: any = [65, 59, 80, 81, 56, 55, 40];
thisWeek: any = true;
constructor(public navCtrl: NavController, public navParams: NavParams, public platform: Platform) {
}
ionViewDidLoad() {
console.log('ionViewDidLoad HealthSummaryPage');
this.lineChart = new Chart(this.lineCanvas.nativeElement, {
type: 'line',
data: {
labels: this.chartLabels,
datasets: [
{
label: "My First dataset",
fill: false,
lineTension: 0.1,
backgroundColor: "rgba(75,192,192,0.4)",
borderColor: "rgba(75,192,192,1)",
borderCapStyle: 'butt',
borderDash: [],
borderDashOffset: 0.0,
borderJoinStyle: 'miter',
pointBorderColor: "rgba(75,192,192,1)",
pointBackgroundColor: "#fff",
pointBorderWidth: 1,
pointHoverRadius: 5,
pointHoverBackgroundColor: "rgba(75,192,192,1)",
pointHoverBorderColor: "rgba(220,220,220,1)",
pointHoverBorderWidth: 2,
pointRadius: 1,
pointHitRadius: 10,
data: this.chartData,
spanGaps: false,
}
]
}
});
}
ionViewWillEnter() {
}
toggleChartThisWeek() {
if(this.thisWeek) {
this.thisWeek = false;
} else {
this.thisWeek = true;
}
}
}
How do I get it to appear every time? Do I need to store it into a variable, and if so, how do I do that?
Check the code below which hopefully forces angular to redraw the template fully:
import { Component, ViewChild } from '#angular/core';
import { IonicPage, NavController, NavParams, Platform } from 'ionic-angular';
import { Chart } from 'chart.js';
#IonicPage()
#Component({
selector: 'page-chart-page',
templateUrl: 'chart-page.html',
})
export class ChartPage {
#ViewChild('lineCanvas') lineCanvas;
lineChart: any;
chartLabels: any = ["January", "February", "March", "April", "May", "June", "July"];
chartData: any = [65, 59, 80, 81, 56, 55, 40];
thisWeek: any = true;
constructor(
public navCtrl: NavController,
public navParams: NavParams,
public platform: Platform) {
}
ionViewDidEnter() {
console.log('ionViewDidEnter() HealthSummaryPage');
}
drawChart(){
if (! this.lineCanvas) { return; }
this.lineChart = new Chart(this.lineCanvas.nativeElement, {
type: 'line',
data: {
labels: this.chartLabels,
datasets: [
{
label: "My First dataset",
fill: false,
lineTension: 0.1,
backgroundColor: "rgba(75,192,192,0.4)",
borderColor: "rgba(75,192,192,1)",
borderCapStyle: 'butt',
borderDash: [],
borderDashOffset: 0.0,
borderJoinStyle: 'miter',
pointBorderColor: "rgba(75,192,192,1)",
pointBackgroundColor: "#fff",
pointBorderWidth: 1,
pointHoverRadius: 5,
pointHoverBackgroundColor: "rgba(75,192,192,1)",
pointHoverBorderColor: "rgba(220,220,220,1)",
pointHoverBorderWidth: 2,
pointRadius: 1,
pointHitRadius: 10,
data: this.chartData,
spanGaps: false,
}
]
}
});
}
toggleChartThisWeek() {
if(this.thisWeek) {
this.thisWeek = false;
} else {
this.thisWeek = true;
this.drawChart();
}
}
}