PluginProbe
Visualizer – Tables & Charts Manager with Built-in AI Generator / 3.7.9
Visualizer – Tables & Charts Manager with Built-in AI Generator v3.7.9
4.0.7 4.0.6 4.0.5 4.0.4 4.0.3 3.0.5 3.0.6 3.0.7 3.0.8 3.0.9 3.1.0 3.1.1 3.1.2 3.1.3 3.10.0 3.10.1 3.10.10 3.10.11 3.10.12 3.10.13 3.10.14 3.10.15 3.10.2 3.10.3 3.10.4 All 148 releases
← All changes | classes/Visualizer/Gutenberg/src/Editor.js +196 -39 3.1.33.7.9 View file →
@@ -28,8 +28,9 @@
28 28 Button,
29 29 ButtonGroup,
30 30 Dashicon,
31 31 Placeholder,
32 + Notice,
32 33 Spinner
33 34 } = wp.components;
34 35
35 36 class Editor extends Component {
@@ -42,8 +43,16 @@
42 43 this.editPermissions = this.editPermissions.bind( this );
43 44 this.readUploadedFile = this.readUploadedFile.bind( this );
44 45 this.editURL = this.editURL.bind( this );
45 46 this.editSchedule = this.editSchedule.bind( this );
47 + this.editJSONSchedule = this.editJSONSchedule.bind( this );
48 + this.editJSONURL = this.editJSONURL.bind( this );
49 + this.editJSONHeaders = this.editJSONHeaders.bind( this );
50 + this.editJSONRoot = this.editJSONRoot.bind( this );
51 + this.editJSONPaging = this.editJSONPaging.bind( this );
52 + this.JSONImportData = this.JSONImportData.bind( this );
53 + this.editDatabaseSchedule = this.editDatabaseSchedule.bind( this );
54 + this.databaseImportData = this.databaseImportData.bind( this );
46 55 this.uploadData = this.uploadData.bind( this );
47 56 this.getChartData = this.getChartData.bind( this );
48 57 this.editChartData = this.editChartData.bind( this );
49 58 this.updateChart = this.updateChart.bind( this );
@@ -69,13 +78,22 @@
69 78 async componentDidMount() {
70 79
71 80 // Fetch review again if block loaded after saving.
72 81 if ( this.props.attributes.id ) {
73 - let result = await apiFetch({ path: `wp/v2/visualizer/${this.props.attributes.id}` });
82 + let result = await apiFetch({ path: `wp/v2/visualizer/${this.props.attributes.id}` }).catch( function( error ) {
83 + });
74 84
75 - this.setState({
76 - chart: result['chart_data']
77 - });
85 + if ( result ) {
86 + this.setState({
87 + chart: result['chart_data']
88 + });
89 + } else {
90 +
91 + // if the chart is not found.
92 + this.setState({
93 + route: 'error'
94 + });
95 + }
78 96 }
79 97 }
80 98
81 99 async getChart( id ) {
@@ -87,14 +105,16 @@
87 105
88 106 this.setState({
89 107 route: 'chartSelect',
90 108 chart: result['chart_data'],
91 - isLoading: false
109 + isLoading: true,
110 + isModified: true
92 111 });
93 112
94 113 this.props.setAttributes({
95 114 id,
96 - route: 'chartSelect'
115 + route: 'chartSelect',
116 + lazy: -1
97 117 });
98 118 }
99 119
100 120 editChart() {
@@ -138,11 +158,83 @@
138 158
139 159 editSchedule( schedule ) {
140 160 let chart = { ...this.state.chart };
141 161 chart['visualizer-chart-schedule'] = schedule;
162 + this.setState({
163 + chart,
164 + isModified: true
165 + });
166 + }
167 +
168 + editJSONSchedule( schedule ) {
169 + let chart = { ...this.state.chart };
170 + chart['visualizer-json-schedule'] = schedule;
171 + this.setState({
172 + chart,
173 + isModified: true
174 + });
175 + }
176 +
177 + editJSONURL( url ) {
178 + let chart = { ...this.state.chart };
179 + chart['visualizer-json-url'] = url;
142 180 this.setState({ chart });
143 181 }
144 182
183 + editJSONHeaders( headers ) {
184 + let chart = { ...this.state.chart };
185 + delete headers.username;
186 + delete headers.password;
187 + chart['visualizer-json-headers'] = headers;
188 + this.setState({ chart });
189 + }
190 +
191 + editJSONRoot( root ) {
192 + let chart = { ...this.state.chart };
193 + chart['visualizer-json-root'] = root;
194 + this.setState({ chart });
195 + }
196 +
197 + editJSONPaging( root ) {
198 + let chart = { ...this.state.chart };
199 + chart['visualizer-json-paging'] = root;
200 + this.setState({ chart });
201 + }
202 +
203 + JSONImportData( name, series, data ) {
204 + let chart = { ...this.state.chart };
205 + chart['visualizer-source'] = name;
206 + chart['visualizer-default-data'] = 0;
207 + chart['visualizer-series'] = series;
208 + chart['visualizer-data'] = data;
209 + this.setState({
210 + chart,
211 + isModified: true
212 + });
213 + }
214 +
215 + editDatabaseSchedule( schedule ) {
216 + let chart = { ...this.state.chart };
217 + chart['visualizer-db-schedule'] = schedule;
218 + this.setState({
219 + chart,
220 + isModified: true
221 + });
222 + }
223 +
224 + databaseImportData( query, name, series, data ) {
225 + let chart = { ...this.state.chart };
226 + chart['visualizer-source'] = name;
227 + chart['visualizer-default-data'] = 0;
228 + chart['visualizer-series'] = series;
229 + chart['visualizer-data'] = data;
230 + chart['visualizer-db-query'] = query;
231 + this.setState({
232 + chart,
233 + isModified: true
234 + });
235 + }
236 +
145 237 uploadData( scheduled = false ) {
146 238 this.setState({
147 239 isLoading: 'uploadData',
148 240 isScheduled: scheduled
@@ -230,13 +322,13 @@
230 322 chart
231 323 });
232 324 }
233 325
234 - editChartData( chartData, type ) {
326 + editChartData( chartData, source ) {
235 327 let chart = { ...this.state.chart };
236 328 let series = [];
237 329 let settings = { ...chart['visualizer-settings'] };
238 -
330 + let type = chart['visualizer-chart-type'];
239 331 chartData[0].map( ( i, index ) => {
240 332 series[index] = {
241 333 label: i,
242 334 type: chartData[1][index]
@@ -247,32 +339,64 @@
247 339
248 340 let map = series;
249 341 let fieldName = 'series';
250 342
251 - if ( 'pie' === chart['visualizer-chart-type']) {
252 - map = chartData;
253 - fieldName = 'slices';
254 - }
343 + switch ( type ) {
344 + case 'pie':
345 + map = chartData;
346 + fieldName = 'slices';
255 347
348 + // pie charts are finicky about a number being a number
349 + // and editing a number makes it a string
350 + // so let's convert it back into a number.
351 + chartData.map( ( i, index ) => {
352 + switch ( series[1].type ) {
353 + case 'number':
354 + i[1] = parseFloat( i[1]);
355 + break;
356 + }
357 + });
358 + break;
359 + case 'tabular':
360 +
361 + // table charts are finicky about a boolean being a boolean
362 + // and editing a boolean makes it a string
363 + // so let's convert it back into a boolean.
364 + chartData.map( ( i, index ) => {
365 + series.map( ( seriesObject, seriesIndex ) => {
366 + switch ( seriesObject.type ) {
367 + case 'boolean':
368 + if ( 'string' === typeof i[seriesIndex]) {
369 + i[seriesIndex] = 'true' === i[seriesIndex];
370 + }
371 + break;
372 + }
373 + });
374 + });
375 + break;
376 + }
377 +
256 378 map.map( ( i, index ) => {
257 - if ( 'pie' !== chart['visualizer-chart-type'] && 0 === index ) {
258 - return;
379 + if ( 'pie' !== type && 0 === index ) {
380 + return;
259 381 }
260 382
261 - const seriesIndex = 'pie' !== chart['visualizer-chart-type'] ? index - 1 : index;
383 + const seriesIndex = 'pie' !== type ? index - 1 : index;
262 384
263 - if ( settings[fieldName][seriesIndex] === undefined ) {
264 - settings[fieldName][seriesIndex] = {};
385 + if ( Array.isArray( settings[fieldName]) && settings[fieldName][seriesIndex] === undefined ) {
386 + settings[fieldName][seriesIndex] = {};
265 387 settings[fieldName][seriesIndex].temp = 1;
266 - }
388 + }
267 389 });
268 390
269 - settings[fieldName] = settings[fieldName].filter( ( i, index ) => {
270 - const length = 'pie' !== chart['visualizer-chart-type'] ? map.length - 1 : map.length;
271 - return index < length;
272 - });
391 + if ( Array.isArray( settings[fieldName]) ) {
392 + settings[fieldName] = settings[fieldName].filter( ( i, index ) => {
393 + const length = -1 >= [ 'pie', 'tabular', 'dataTable' ].indexOf( type ) ? map.length - 1 : map.length;
394 + return index < length;
395 + });
396 + }
273 397
274 - chart['visualizer-source'] = type;
398 + chart['visualizer-source'] = source;
275 399 chart['visualizer-default-data'] = 0;
276 400 chart['visualizer-data'] = chartData;
277 401 chart['visualizer-series'] = series;
278 402 chart['visualizer-settings'] = settings;
@@ -299,19 +423,22 @@
299 423 if ( 'pie' === data['visualizer-chart-type']) {
300 424 fieldName = 'slices';
301 425 }
302 426
303 - Object.keys( data['visualizer-settings'][fieldName])
304 - .map( i => {
305 - if ( data['visualizer-settings'][fieldName][i] !== undefined ) {
306 - if ( data['visualizer-settings'][fieldName][i].temp !== undefined ) {
307 - delete data['visualizer-settings'][fieldName][i].temp;
308 - }
309 - }
310 - }
311 - );
427 + // no series for bubble and timeline charts.
428 + if ( -1 >= [ 'bubble', 'timeline' ].indexOf( data['visualizer-chart-type']) ) {
429 + Object.keys( data['visualizer-settings'][fieldName])
430 + .map( i => {
431 + if ( data['visualizer-settings'][fieldName][i] !== undefined ) {
432 + if ( data['visualizer-settings'][fieldName][i].temp !== undefined ) {
433 + delete data['visualizer-settings'][fieldName][i].temp;
434 + }
435 + }
436 + }
437 + );
438 + }
312 439
313 - apiRequest({ path: `/visualizer/v1/update-chart?id=${this.props.attributes.id}`, method: 'POST', data: data }).then(
440 + apiRequest({ path: `/visualizer/v1/update-chart?id=${ this.props.attributes.id }`, method: 'POST', data: data }).then(
314 441 ( data ) => {
315 442
316 443 this.setState({
317 444 isLoading: false,
@@ -326,11 +453,24 @@
326 453 );
327 454 }
328 455
329 456 render() {
457 + if ( 'error' === this.state.route ) {
458 + return (
459 + <Notice
460 + status="error"
461 + isDismissible={ false }
462 + >
463 + <Dashicon icon="chart-pie" />
464 + { __( 'This chart is not available; it might have been deleted. Please delete this block and resubmit your chart.' ) }
465 + </Notice>
466 + );
467 + }
468 +
330 469 if ( 'renderChart' === this.state.route && null !== this.state.chart ) {
331 470 return (
332 471 <ChartRender
472 + id={ this.props.attributes.id }
333 473 chart={ this.state.chart }
334 474 className={ this.props.className }
335 475 editChart={ this.editChart }
336 476 />
@@ -348,24 +488,29 @@
348 488 </div>
349 489
350 490 { 'home' === this.state.route && (
351 491 <div className="visualizer-settings__content">
352 -
353 492 <div className="visualizer-settings__content-description">
354 493 { __( 'Make a new chart or display an existing one?' ) }
355 494 </div>
356 495
357 - <div className="visualizer-settings__content-option locked">
496 + { /* You can apply "locked" class to lock any of the following list items. */ }
358 497
498 + <a
499 + href={ visualizerLocalize.adminPage }
500 + target="_blank"
501 + className="visualizer-settings__content-option"
502 + >
503 +
359 504 <span className="visualizer-settings__content-option-title">
360 - { __( 'Create a new chart (coming soon)' ) }
505 + { __( 'Create a new chart' ) }
361 506 </span>
362 507
363 508 <div className="visualizer-settings__content-option-icon">
364 - <Dashicon icon="lock" />
509 + <Dashicon icon="arrow-right-alt2" />
365 510 </div>
366 511
367 - </div>
512 + </a>
368 513
369 514 <div
370 515 className="visualizer-settings__content-option"
371 516 onClick={ () => {
@@ -396,8 +541,10 @@
396 541 { ( 'showCharts' === this.state.route && false === this.state.isLoading ) && <Charts getChart={ this.getChart }/> }
397 542
398 543 { ( 'chartSelect' === this.state.route && null !== this.state.chart ) &&
399 544 <ChartSelect
545 + id={ this.props.attributes.id }
546 + attributes={ this.props.attributes }
400 547 chart={ this.state.chart }
401 548 editSettings={ this.editSettings }
402 549 editPermissions={ this.editPermissions }
403 550 url={ this.state.url }
@@ -403,8 +550,16 @@
403 550 url={ this.state.url }
404 551 readUploadedFile={ this.readUploadedFile }
405 552 editURL={ this.editURL }
406 553 editSchedule={ this.editSchedule }
554 + editJSONURL={ this.editJSONURL }
555 + editJSONHeaders={ this.editJSONHeaders }
556 + editJSONSchedule={ this.editJSONSchedule }
557 + editJSONRoot={ this.editJSONRoot }
558 + editJSONPaging={ this.editJSONPaging }
559 + JSONImportData={ this.JSONImportData }
560 + editDatabaseSchedule={ this.editDatabaseSchedule }
561 + databaseImportData={ this.databaseImportData }
407 562 uploadData={ this.uploadData }
408 563 getChartData={ this.getChartData }
409 564 editChartData={ this.editChartData }
410 565 isLoading={ this.state.isLoading }
@@ -439,10 +594,11 @@
439 594 { false === this.state.isModified ?
440 595 <Button
441 596 isDefault
442 597 isLarge
598 + className="visualizer-bttn-done"
443 599 onClick={ () => {
444 - this.setState({ route: 'renderChart' });
600 + this.setState({ route: 'renderChart', isModified: true });
445 601 this.props.setAttributes({ route: 'renderChart' });
446 602 } }
447 603 >
448 604 { __( 'Done' ) }
@@ -449,8 +605,9 @@
449 605 </Button> :
450 606 <Button
451 607 isPrimary
452 608 isLarge
609 + className="visualizer-bttn-save"
453 610 isBusy={ 'updateChart' === this.state.isLoading }
454 611 disabled={ 'updateChart' === this.state.isLoading }
455 612 onClick={ this.updateChart }
456 613 >