PluginProbe ʕ •ᴥ•ʔ
Post Views Counter / 1.4.6
Post Views Counter v1.4.6
1.7.13 1.7.12 1.7.11 trunk 1.0.0 1.0.1 1.0.10 1.0.11 1.0.12 1.0.2 1.0.3 1.0.4 1.0.5 1.0.6 1.0.7 1.0.8 1.0.9 1.1.0 1.1.1 1.1.2 1.1.3 1.1.4 1.2.0 1.2.1 1.2.10 1.2.11 1.2.12 1.2.13 1.2.14 1.2.2 1.2.3 1.2.4 1.2.5 1.2.6 1.2.7 1.2.8 1.2.9 1.3 1.3.1 1.3.10 1.3.11 1.3.12 1.3.13 1.3.2 1.3.2.1 1.3.3 1.3.4 1.3.5 1.3.6 1.3.7 1.3.8 1.3.9 1.4 1.4.1 1.4.2 1.4.3 1.4.4 1.4.5 1.4.6 1.4.7 1.4.8 1.5.0 1.5.1 1.5.2 1.5.3 1.5.4 1.5.5 1.5.6 1.5.7 1.5.8 1.5.9 1.6.0 1.6.1 1.7.0 1.7.1 1.7.10 1.7.2 1.7.3 1.7.4 1.7.5 1.7.6 1.7.7 1.7.8 1.7.9
post-views-counter / includes / class-dashboard.php
post-views-counter / includes Last commit date
class-admin.php 2 years ago class-columns.php 2 years ago class-counter.php 2 years ago class-crawler-detect.php 2 years ago class-cron.php 2 years ago class-dashboard.php 2 years ago class-frontend.php 2 years ago class-functions.php 2 years ago class-query.php 2 years ago class-settings-api.php 2 years ago class-settings.php 2 years ago class-update.php 2 years ago class-widgets.php 2 years ago functions.php 2 years ago
class-dashboard.php
730 lines
1 <?php
2 // exit if accessed directly
3 if ( ! defined( 'ABSPATH' ) )
4 exit;
5
6 /**
7 * Post_Views_Counter_Dashboard class.
8 *
9 * @class Post_Views_Counter_Dashboard
10 */
11 class Post_Views_Counter_Dashboard {
12
13 private $widget_items = [];
14
15 /**
16 * Class constructor.
17 *
18 * @return void
19 */
20 public function __construct() {
21 // actions
22 add_action( 'admin_init', [ $this, 'init_admin_dashboard' ] );
23 }
24
25 /**
26 * Dashboard initialization.
27 *
28 * @global string $pagenow
29 *
30 * @return void
31 */
32 public function init_admin_dashboard() {
33 global $pagenow;
34
35 // setup widget items
36 $this->setup_widget_items();
37
38 // do it only on dashboard page
39 if ( $pagenow === 'index.php' ) {
40 // filter user_can_see_stats
41 if ( ! apply_filters( 'pvc_user_can_see_stats', current_user_can( 'publish_posts' ) ) )
42 return;
43
44 add_action( 'wp_dashboard_setup', [ $this, 'wp_dashboard_setup' ], 1 );
45 add_action( 'admin_enqueue_scripts', [ $this, 'admin_scripts_styles' ] );
46 // ajax endpoints
47 } elseif ( $pagenow === 'admin-ajax.php' ) {
48 add_action( 'wp_ajax_pvc_dashboard_post_most_viewed', [ $this, 'dashboard_post_most_viewed' ] );
49 add_action( 'wp_ajax_pvc_dashboard_post_views_chart', [ $this, 'dashboard_post_views_chart' ] );
50 add_action( 'wp_ajax_pvc_dashboard_user_options', [ $this, 'update_dashboard_user_options' ] );
51 }
52 }
53
54 /**
55 * Add dashboard widget.
56 *
57 * @return void
58 */
59 public function wp_dashboard_setup() {
60 // add dashboard widget
61 wp_add_dashboard_widget( 'pvc_dashboard', __( 'Post Views Counter', 'post-views-counter' ), [ $this, 'dashboard_widget' ] );
62 }
63
64 /**
65 * Enqueue admin scripts and styles.
66 *
67 * @return void
68 */
69 public function admin_scripts_styles() {
70 // get main instance
71 $pvc = Post_Views_Counter();
72
73 // styles
74 wp_enqueue_style( 'pvc-admin-dashboard', POST_VIEWS_COUNTER_URL . '/css/admin-dashboard.min.css', [], $pvc->defaults['version'] );
75 wp_enqueue_style( 'pvc-microtip', POST_VIEWS_COUNTER_URL . '/assets/microtip/microtip.min.css', [], '1.0.0' );
76
77 // scripts
78 wp_enqueue_script( 'pvc-admin-dashboard', POST_VIEWS_COUNTER_URL . '/js/admin-dashboard.js', [ 'jquery', 'pvc-chartjs' ], $pvc->defaults['version'], true );
79
80 // prepare script data
81 $script_data = [
82 'ajaxURL' => admin_url( 'admin-ajax.php' ),
83 'nonce' => wp_create_nonce( 'pvc-dashboard-widget' ),
84 'nonceUser' => wp_create_nonce( 'pvc-dashboard-user-options' )
85 ];
86
87 wp_add_inline_script( 'pvc-admin-dashboard', 'var pvcArgs = ' . wp_json_encode( $script_data ) . ";\n", 'before' );
88 }
89
90 /**
91 * Setup dashboard widget items.
92 *
93 * @return void
94 */
95 private function setup_widget_items() {
96 // standard items
97 $items = [
98 [
99 'id' => 'post-views',
100 'title' => __( 'Post Views', 'post-views-counter' ),
101 'description' => __( 'Displays a chart of most viewed post types.', 'post-views-counter' ),
102 'content' => '<canvas id="pvc-post-views-chart" height="' . (int) $this->calculate_canvas_size( Post_Views_Counter()->options['general']['post_types_count'] ) . '"></canvas>',
103 'position' => 2
104 ],
105 [
106 'id' => 'post-most-viewed',
107 'title' => __( 'Top Posts', 'post-views-counter' ),
108 'description' => __( 'Displays a list of most viewed single posts or pages.', 'post-views-counter' ),
109 'content' => '<div id="pvc-post-most-viewed-content" class="pvc-table-responsive"></div>',
110 'position' => 3
111 ]
112 ];
113
114 // filter items, do not allow to remove main items
115 $new_items = apply_filters( 'pvc_dashboard_widget_items', [] );
116
117 // any new items?
118 if ( is_array( $new_items ) && ! empty( $new_items ) ) {
119 foreach ( $new_items as $item ) {
120 // add new item
121 array_push( $items, $item );
122 }
123 }
124
125 // sort dashboard items by position
126 array_multisort( array_column( $items, 'position' ), SORT_ASC, SORT_NUMERIC, $items );
127
128 // set widget items
129 $this->widget_items = $items;
130 }
131
132 /**
133 * Calculate canvas height based on number of legend items.
134 *
135 * @param array $data
136 * @param bool $expression
137 * @return int
138 */
139 public function calculate_canvas_size( $data, $expression = true ) {
140 if ( $expression && ! empty( $data ) ) {
141 // treat every 4 legend items as 1 line - 23 pixels
142 $height = 23 * ( (int) ceil( count( $data ) / 4 ) - 1 );
143 } else
144 $height = 0;
145
146 return (int) ( 170 + $height );
147 }
148
149 /**
150 * Render dashboard widget.
151 *
152 * @return void
153 */
154 public function dashboard_widget() {
155 // get user options
156 $user_options = get_user_meta( get_current_user_id(), 'pvc_dashboard', true );
157
158 // empty options?
159 if ( empty( $user_options ) || ! is_array( $user_options ) )
160 $user_options = [];
161
162 // sanitize options
163 $user_options = map_deep( $user_options, 'sanitize_text_field' );
164
165 // get menu items
166 $menu_items = ! empty( $user_options['menu_items'] ) ? $user_options['menu_items'] : [];
167
168 // generate months
169 $months_html = wp_kses_post( $this->generate_months( current_time( 'timestamp', false ) ) );
170
171 // get widget items
172 $items = $this->widget_items;
173
174 $html = '
175 <div id="pvc-dashboard-accordion" class="pvc-accordion">';
176
177 foreach ( $items as $item ) {
178 $html .= $this->generate_dashboard_widget_item( $item, $menu_items, $months_html );
179 }
180
181 $html .= '
182 <div class="pvc-dashboard-block"><span>' . esc_html__( 'Powered by', 'post-views-counter' ) . ' <a href="https://postviewscounter.com/?utm_source=post-views-counter-lite&utm_medium=link&utm_campaign=powered-by" target="_blank">Post Views Counter</a></span></div>
183 </div>';
184
185 echo $html;
186 }
187
188 /**
189 * Generate dashboard widget item HTML.
190 *
191 * @param array $item
192 * @param array $menu_items
193 * @param string $esc_months_html
194 * @return string
195 */
196 public function generate_dashboard_widget_item( $item, $menu_items, $esc_months_html ) {
197 // get allowed html tags
198 $allowed_html = wp_kses_allowed_html( 'post' );
199 $allowed_html['canvas'] = [
200 'id' => [],
201 'height' => []
202 ];
203
204 return '
205 <div id="pvc-' . esc_attr( $item['id'] ) . '" class="pvc-accordion-item' . ( in_array( $item['id'], $menu_items, true ) ? ' pvc-collapsed' : '' ) . '">
206 <div class="pvc-accordion-header">
207 <div class="pvc-accordion-toggle"><span class="pvc-accordion-title">' . esc_html( $item['title'] ) . '</span><span class="pvc-tooltip" aria-label="' . esc_html( $item['description'] ) . '" data-microtip-position="top" data-microtip-size="large" role="tooltip"><span class="pvc-tooltip-icon"></span></span></div>
208 <!--
209 <div class="pvc-accordion-actions">
210 <a href="javascript:void(0);" class="pvc-accordion-action dashicons dashicons-admin-generic"></a>
211 </div>
212 -->
213 </div>
214 <div class="pvc-accordion-content">
215 <div class="pvc-dashboard-container loading">
216 <div class="pvc-data-container">
217 ' . wp_kses( $item['content'], $allowed_html ) . '
218 <span class="spinner"></span>
219 </div>
220 <div class="pvc-months">' . $esc_months_html . '</div>
221 </div>
222 </div>
223 </div>';
224 }
225
226 /**
227 * Render dashboard widget with post views.
228 *
229 * @return void
230 */
231 public function dashboard_post_views_chart() {
232 if ( ! apply_filters( 'pvc_user_can_see_stats', current_user_can( 'publish_posts' ) ) || ! check_ajax_referer( 'pvc-dashboard-widget', 'nonce' ) )
233 wp_die( __( 'You do not have permission to access this page.', 'post-views-counter' ) );
234
235 // get period
236 $period = isset( $_POST['period'] ) ? preg_replace( '/[^a-z0-9_|]/', '', $_POST['period'] ) : 'this_month';
237
238 // get post types
239 $post_types = Post_Views_Counter()->options['general']['post_types_count'];
240
241 // get dashboard user options
242 $user_options = $this->get_dashboard_user_options( get_current_user_id(), 'post_types' );
243
244 // get current date
245 $now = getdate( current_time( 'timestamp', get_option( 'gmt_offset' ) ) );
246
247 // get colors
248 $colors = Post_Views_Counter()->functions->get_colors();
249
250 // set chart labels
251 switch ( $period ) {
252 case 'this_week':
253 //TODO
254 $data = [
255 'design' => [
256 'fill' => true,
257 'backgroundColor' => 'rgba(' . $colors['r'] . ',' . $colors['g'] . ',' . $colors['b'] . ', 0.2)',
258 'borderColor' => 'rgba(' . $colors['r'] . ',' . $colors['g'] . ',' . $colors['b'] . ', 1)',
259 'borderWidth' => 1.2,
260 'borderDash' => [],
261 'pointBorderColor' => 'rgba(' . $colors['r'] . ',' . $colors['g'] . ',' . $colors['b'] . ', 1)',
262 'pointBackgroundColor' => 'rgba(255, 255, 255, 1)',
263 'pointBorderWidth' => 1.2
264 ]
265 ];
266
267 $data['data']['datasets'][0]['label'] = __( 'Post Views', 'post-views-counter' );
268 $data['data']['datasets'][0]['post_type'] = '_pvc_total_views';
269
270 for ( $day = 0; $day <= 6; $day++ ) {
271 $date = strtotime( $now['mday'] . '-' . $now['mon'] . '-' . $now['year'] . ' + ' . $day . ' days - ' . $now['wday'] . ' days' );
272 $query = new WP_Query(
273 wp_parse_args(
274 [
275 'post_type' => $post_types,
276 'posts_per_page' => -1,
277 'paged' => false,
278 'orderby' => 'post_views',
279 'suppress_filters' => false,
280 'no_found_rows' => true
281 ],
282 [
283 'views_query' => [
284 'year' => date( 'Y', $date ),
285 'month' => date( 'n', $date ),
286 'day' => date( 'd', $date )
287 ]
288 ]
289 )
290 );
291
292 $data['data']['labels'][] = date_i18n( 'j', $date );
293 $data['data']['dates'][] = date_i18n( get_option( 'date_format' ), $date );
294 $data['data']['datasets'][0]['data'][] = $query->total_views;
295 $data['data']['datasets'][$day]['data'][] = $query->total_views;
296 }
297 break;
298
299 case 'this_year':
300 $data = [
301 'design' => [
302 'fill' => true,
303 'backgroundColor' => 'rgba(' . $colors['r'] . ',' . $colors['g'] . ',' . $colors['b'] . ', 0.2)',
304 'borderColor' => 'rgba(' . $colors['r'] . ',' . $colors['g'] . ',' . $colors['b'] . ', 1)',
305 'borderWidth' => 1.2,
306 'borderDash' => [],
307 'pointBorderColor' => 'rgba(' . $colors['r'] . ',' . $colors['g'] . ',' . $colors['b'] . ', 1)',
308 'pointBackgroundColor' => 'rgba(255, 255, 255, 1)',
309 'pointBorderWidth' => 1.2
310 ]
311 ];
312
313 $data['data']['datasets'][0]['label'] = __( 'Total Views', 'post-views-counter' );
314 $data['data']['datasets'][0]['post_type'] = '_pvc_total_views';
315 $data['data']['datasets'][0]['hidden'] = in_array( '_pvc_total_views', $user_options, true );
316 $data['data']['datasets'][0]['data'] = [];
317
318 $sum = [];
319
320 // any post types?
321 if ( ! empty( $post_types ) ) {
322 // reindex post types
323 $post_types = array_combine( range( 1, count( $post_types ) ), array_values( $post_types ) );
324
325 $post_type_data = [];
326
327 foreach ( $post_types as $id => $post_type ) {
328 $post_type_obj = get_post_type_object( $post_type );
329
330 // unrecognized post type? (mainly from deactivated plugins)
331 if ( empty( $post_type_obj ) )
332 $label = $post_type;
333 else
334 $label = $post_type_obj->labels->name;
335
336 $data['data']['datasets'][$id]['label'] = $label;
337 $data['data']['datasets'][$id]['post_type'] = $post_type;
338 $data['data']['datasets'][$id]['hidden'] = in_array( $post_type, $user_options, true );
339 $data['data']['datasets'][$id]['data'] = [];
340
341 // get month views
342 $post_type_data[$id] = array_values(
343 pvc_get_views(
344 [
345 'fields' => 'date=>views',
346 'post_type' => $post_type,
347 'views_query' => [
348 'year' => date( 'Y' ),
349 'month' => '',
350 'week' => '',
351 'day' => ''
352 ]
353 ]
354 )
355 );
356 }
357
358 foreach ( $post_type_data as $post_type_id => $post_views ) {
359 foreach ( $post_views as $id => $views ) {
360 // generate chart data for specific post types
361 $data['data']['datasets'][$post_type_id]['data'][] = $views;
362
363 if ( ! array_key_exists( $id, $sum ) )
364 $sum[$id] = 0;
365
366 $sum[$id] += $views;
367 }
368 }
369 }
370
371 // this month all days
372 for ( $i = 1; $i <= 12; $i++ ) {
373 // generate chart data
374 $data['data']['labels'][] = $i;
375 $data['data']['dates'][] = date_i18n( 'F Y', strtotime( date( 'Y' ) . '-' . str_pad( $i, 2, '0', STR_PAD_LEFT ) . '-01' ) );
376 $data['data']['datasets'][0]['data'][] = ( array_key_exists( $i - 1, $sum ) ? $sum[$i - 1] : 0 );
377 }
378 break;
379
380 case 'this_month':
381 default:
382 // convert period
383 $time = $this->period2timestamp( $period );
384
385 // get date chunks
386 $date = explode( ' ', date( "m Y t F", $time ) );
387
388 $data = [
389 'months' => $this->generate_months( $time ),
390 'design' => [
391 'fill' => true,
392 'backgroundColor' => 'rgba(' . $colors['r'] . ',' . $colors['g'] . ',' . $colors['b'] . ', 0.2)',
393 'borderColor' => 'rgba(' . $colors['r'] . ',' . $colors['g'] . ',' . $colors['b'] . ', 1)',
394 'borderWidth' => 1.2,
395 'borderDash' => [],
396 'pointBorderColor' => 'rgba(' . $colors['r'] . ',' . $colors['g'] . ',' . $colors['b'] . ', 1)',
397 'pointBackgroundColor' => 'rgba(255, 255, 255, 1)',
398 'pointBorderWidth' => 1.2
399 ]
400 ];
401
402 $data['data']['datasets'][0]['label'] = __( 'Total Views', 'post-views-counter' );
403 $data['data']['datasets'][0]['post_type'] = '_pvc_total_views';
404 $data['data']['datasets'][0]['hidden'] = in_array( '_pvc_total_views', $user_options, true );
405 $data['data']['datasets'][0]['data'] = [];
406
407 $sum = [];
408
409 // any post types?
410 if ( ! empty( $post_types ) ) {
411 // reindex post types
412 $post_types = array_combine( range( 1, count( $post_types ) ), array_values( $post_types ) );
413
414 $post_type_data = [];
415
416 foreach ( $post_types as $id => $post_type ) {
417 $post_type_obj = get_post_type_object( $post_type );
418
419 // unrecognized post type? (mainly from deactivated plugins)
420 if ( empty( $post_type_obj ) )
421 $label = $post_type;
422 else
423 $label = $post_type_obj->labels->name;
424
425 $data['data']['datasets'][$id]['label'] = $label;
426 $data['data']['datasets'][$id]['post_type'] = $post_type;
427 $data['data']['datasets'][$id]['hidden'] = in_array( $post_type, $user_options, true );
428 $data['data']['datasets'][$id]['data'] = [];
429
430 // get month views
431 $post_type_data[$id] = array_values(
432 pvc_get_views(
433 [
434 'fields' => 'date=>views',
435 'post_type' => $post_type,
436 'views_query' => [
437 'year' => $date[1],
438 'month' => $date[0],
439 'week' => '',
440 'day' => '',
441 'hide_empty' => true
442 ]
443 ]
444 )
445 );
446 }
447
448 foreach ( $post_type_data as $post_type_id => $post_views ) {
449 foreach ( $post_views as $id => $views ) {
450 // generate chart data for specific post types
451 $data['data']['datasets'][$post_type_id]['data'][] = $views;
452
453 if ( ! array_key_exists( $id, $sum ) )
454 $sum[$id] = 0;
455
456 $sum[$id] += $views;
457 }
458 }
459 }
460
461 // this month all days
462 for ( $i = 1; $i <= $date[2]; $i++ ) {
463 // generate chart data
464 $data['data']['labels'][] = ( $i % 2 === 0 ? '' : $i );
465 $data['data']['dates'][] = date_i18n( get_option( 'date_format' ), strtotime( $date[1] . '-' . $date[0] . '-' . str_pad( $i, 2, '0', STR_PAD_LEFT ) ) );
466 $data['data']['datasets'][0]['data'][] = ( array_key_exists( $i - 1, $sum ) ? $sum[$i - 1] : 0 );
467 }
468 break;
469 }
470
471 echo wp_json_encode( $data );
472
473 exit;
474 }
475
476 /**
477 * Render dashboard widget with most viewed posts.
478 *
479 * @return void
480 */
481 public function dashboard_post_most_viewed() {
482 if ( ! apply_filters( 'pvc_user_can_see_stats', current_user_can( 'publish_posts' ) ) || ! check_ajax_referer( 'pvc-dashboard-widget', 'nonce' ) )
483 wp_die( __( 'You do not have permission to access this page.', 'post-views-counter' ) );
484
485 // get main instance
486 $pvc = Post_Views_Counter();
487
488 // get post types
489 $post_types = $pvc->options['general']['post_types_count'];
490
491 // get period
492 $period = isset( $_POST['period'] ) ? preg_replace( '/[^a-z0-9_|]/', '', $_POST['period'] ) : 'this_month';
493
494 // convert period
495 $time = $this->period2timestamp( $period );
496
497 // get date chunks
498 $date = explode( ' ', date( "m Y t F", $time ) );
499
500 // get stats
501 $query_args = [
502 'post_type' => $post_types,
503 'posts_per_page' => 10,
504 'paged' => false,
505 'suppress_filters' => false,
506 'no_found_rows' => true,
507 'views_query' => [
508 'year' => $date[1],
509 'month' => $date[0],
510 'hide_empty' => true
511 ]
512 ];
513
514 $posts = pvc_get_most_viewed_posts( $query_args );
515
516 $data = [
517 'months' => $this->generate_months( $time ),
518 'html' => ''
519 ];
520
521 $html = '
522 <table id="pvc-post-most-viewed-table" class="pvc-table pvc-table-hover">
523 <thead>
524 <tr>
525 <th scope="col">#</th>
526 <th scope="col">' . esc_html__( 'Post', 'post-views-counter' ) . '</th>
527 <th scope="col">' . esc_html__( 'Views', 'post-views-counter' ) . '</th>
528 </tr>
529 </thead>
530 <tbody>';
531
532 if ( $posts ) {
533 // active post types
534 $active_post_types = [];
535
536 foreach ( $posts as $index => $post ) {
537 setup_postdata( $post );
538
539 $html .= '
540 <tr>
541 <th scope="col">' . ( $index + 1 ) . '</th>';
542
543 // check post type existence
544 if ( array_key_exists( $post->post_type, $active_post_types ) )
545 $post_type_exists = $active_post_types[$post->post_type];
546 else
547 $post_type_exists = $active_post_types[$post->post_type] = post_type_exists( $post->post_type );
548
549 $title = get_the_title( $post );
550
551 if ( $title === '' )
552 $title = __( '(no title)' );
553
554 // edit post link
555 if ( $post_type_exists && current_user_can( 'edit_post', $post->ID ) ) {
556 $html .= '
557 <td><a href="' . esc_url( get_edit_post_link( $post->ID ) ) . '">' . esc_html( $title ) . '</a></td>';
558 } else {
559 $html .= '
560 <td>' . esc_html( $title ). '</td>';
561 }
562
563 $html .= '
564 <td>' . number_format_i18n( $post->post_views ) . '</td>
565 </tr>';
566 }
567 } else {
568 $html .= '
569 <tr class="no-posts">
570 <td colspan="3">' . esc_html__( 'No most viewed posts found.', 'post-views-counter' ) . '</td>
571 </tr>';
572 }
573
574 $html .= '
575 </tbody>
576 </table>';
577
578 $data['html'] = $html;
579
580 echo wp_json_encode( $data );
581
582 exit;
583 }
584
585 /**
586 * Generate dashboard widget months HTML.
587 *
588 * @param int $timestamp
589 * @return string
590 */
591 public function generate_months( $timestamp ) {
592 $dates = [
593 explode( ' ', date( "m F Y", strtotime( "-1 months", $timestamp ) ) ),
594 explode( ' ', date( "m F Y", $timestamp ) ),
595 explode( ' ', date( "m F Y", strtotime( "+1 months", $timestamp ) ) )
596 ];
597
598 $current = date( "Ym", current_time( 'timestamp', false ) );
599
600 if ( (int) $current <= (int) ( $dates[1][2] . $dates[1][0] ) )
601 $next = '<span class="next">' . $dates[2][1] . ' ' . $dates[2][2] . ' ›</span>';
602 else
603 $next = '<a class="next" href="#" data-date="' . ( $dates[2][0] . '|' . $dates[2][2] ) . '">' . $dates[2][1] . ' ' . $dates[2][2] . ' ›</a>';
604
605 $dates = [
606 'prev' => '<a class="prev" href="#" data-date="' . ( $dates[0][0] . '|' . $dates[0][2] ) . '">‹ ' . $dates[0][1] . ' ' . $dates[0][2] . '</a>',
607 'current' => '<span class="current">' . $dates[1][1] . ' ' . $dates[1][2] . '</span>',
608 'next' => $next
609 ];
610
611 return $dates['prev'] . $dates['current'] . $dates['next'];
612 }
613
614 /**
615 * Update dashboard widget user options.
616 *
617 * @return void
618 */
619 public function update_dashboard_user_options() {
620 if ( ! check_ajax_referer( 'pvc-dashboard-user-options', 'nonce' ) )
621 wp_die( __( 'You do not have permission to access this page.', 'post-views-counter' ) );
622
623 // valid data?
624 if ( isset( $_POST['nonce'], $_POST['options'] ) && ! empty( $_POST['options'] ) ) {
625 // get sanitized options
626 $update = map_deep( $_POST['options'], 'sanitize_text_field' );
627
628 // get user ID
629 $user_id = get_current_user_id();
630
631 // get user dashboard data
632 $user_options = get_user_meta( $user_id, 'pvc_dashboard', true );
633
634 // empty userdata?
635 if ( ! is_array( $user_options ) || empty( $user_options ) )
636 $user_options = [];
637
638 // empty post types?
639 if ( ! array_key_exists( 'post_types', $user_options ) || ! is_array( $user_options['post_types'] ) )
640 $user_options['post_types'] = [];
641
642 // hide post type?
643 if ( ! empty( $update['post_type'] ) ) {
644 // get allowed post types
645 $allowed_post_types = Post_Views_Counter()->options['general']['post_types_count'];
646
647 // simulate total post views as post type
648 $allowed_post_types[] = '_pvc_total_views';
649
650 if ( in_array( $update['post_type'], $allowed_post_types, true ) ) {
651 if ( isset( $update['hidden'] ) && $update['hidden'] === 'true' ) {
652 if ( ! in_array( $update['post_type'], $user_options['post_types'], true ) )
653 $user_options['post_types'][] = $update['post_type'];
654 } else {
655 if ( ( $key = array_search( $update['post_type'], $user_options['post_types'] ) ) !== false )
656 unset( $user_options['post_types'][$key] );
657 }
658 }
659 }
660
661 // empty menu items?
662 if ( ! array_key_exists( 'menu_items', $user_options ) || ! is_array( $user_options['menu_items'] ) )
663 $user_options['menu_items'] = [];
664
665 if ( ! empty( $update['menu_items'] ) && is_array( $update['menu_items'] ) ) {
666 $user_options['menu_items'] = [];
667
668 // get allowed menu items
669 $allowed_menu_items = array_column( $this->widget_items, 'id' );
670
671 foreach ( $update['menu_items'] as $menu_item => $hidden ) {
672 if ( in_array( $menu_item, $allowed_menu_items, true ) && $hidden === 'true' )
673 $user_options['menu_items'][] = $menu_item;
674 }
675 }
676
677 // filter user options
678 $user_options = apply_filters( 'pvc_update_dashboard_user_options', $user_options, $update, $user_id );
679
680 // update userdata
681 update_user_meta( $user_id, 'pvc_dashboard', $user_options );
682 }
683
684 exit;
685 }
686
687 /**
688 * Get user dashboard data.
689 *
690 * @param int $user_id
691 * @param string $data_type
692 * @return array
693 */
694 public function get_dashboard_user_options( $user_id, $data_type ) {
695 $user_options = get_user_meta( $user_id, 'pvc_dashboard', true );
696
697 if ( ! is_array( $user_options ) || empty( $user_options ) )
698 $user_options = [];
699
700 if ( ! array_key_exists( $data_type, $user_options ) || ! is_array( $user_options[$data_type] ) )
701 $user_options[$data_type] = [];
702
703 return $user_options[$data_type];
704 }
705
706 /**
707 * Convert period to timestamp.
708 *
709 * @param string $period
710 * @return int
711 */
712 public function period2timestamp( $period ) {
713 // whitelisted period?
714 if ( in_array( $period, [ 'this_week', 'this_year', 'this_month' ], true ) ) {
715 $timestamp = current_time( 'timestamp', false );
716 } else {
717 if ( preg_match( '/^([0-9]{2}\|[0-9]{4})$/', $period ) === 1 ) {
718 // month|year
719 $date = explode( '|', $period, 2 );
720
721 // get timestamp
722 $timestamp = strtotime( (string) $date[1] . '-' . (string) $date[0] . '-13' );
723 } else
724 $timestamp = current_time( 'timestamp', false );
725 }
726
727 return $timestamp;
728 }
729 }
730