PluginProbe
LearnPress – WordPress LMS Plugin for Create and Sell Online Courses / 4.4.9
LearnPress – WordPress LMS Plugin for Create and Sell Online Courses v4.4.9
4.4.9 4.4.8 4.4.7 4.4.6 4.4.5 4.4.4 4.4.3 4.4.2 4.4.1 4.4.0 4.3.9.1 4.3.9 4.3.8 4.3.7 4.1.6.9 4.1.6.9.1 4.1.6.9.2 4.1.6.9.3 4.1.6.9.4 4.1.7 4.1.7.1 4.1.7.2 4.1.7.3 4.1.7.3.1 4.1.7.3.2 All 140 releases
learnpress / inc / admin / class-lp-admin.php

class-lp-admin.php in LearnPress – WordPress LMS Plugin for Create and Sell Online Courses 4.4.9, at inc/admin/class-lp-admin.php

1,017 lines 31.9 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 /**
3 * @author ThimPress
4 * @package LearnPress/Admin/Classes
5 * @version 1.0.2
6 */
7
8 use LearnPress\Background\LPBackgroundAjax;
9 use LearnPress\Helpers\Template;
10 use LearnPress\Models\CourseModel;
11 use LearnPress\TemplateHooks\Admin\Notices\AdminNotesTemplate;
12 use LearnPress\TemplateHooks\TemplateAJAX;
13 use LearnPress\TemplateHooks\CourseBuilder\Course\BuilderCourseTemplate;
14
15 defined( 'ABSPATH' ) || exit;
16
17 if ( ! class_exists( 'LP_Admin' ) ) {
18 /**
19 * Class LP_Admin
20 */
21 class LP_Admin {
22 protected static $instance;
23
24 protected $pages = [];
25
26 /**
27 * Constructor
28 */
29 protected function __construct() {
30 $this->pages = [
31 'courses' => __( 'Courses', 'learnpress' ),
32 'instructors' => __( 'Instructors', 'learnpress' ),
33 'single_instructor' => __( 'Single Instructors', 'learnpress' ),
34 'profile' => __( 'Profile', 'learnpress' ),
35 'checkout' => __( 'Checkout', 'learnpress' ),
36 'become_a_teacher' => __( 'Become an Instructor', 'learnpress' ),
37 ];
38 $this->includes();
39 add_action( 'delete_user', array( $this, 'delete_user_data' ) );
40 //add_action( 'delete_user_form', array( $this, 'delete_user_form' ) );
41 add_action( 'admin_footer', array( $this, 'admin_notices' ) );
42 add_action( 'admin_enqueue_scripts', array( $this, 'load_modal' ) );
43 add_filter( 'admin_body_class', array( $this, 'body_class' ) );
44 //add_filter( 'manage_users_custom_column', array( $this, 'users_custom_column' ), 10, 3 );
45 //add_filter( 'manage_pages_columns', array( $this, 'page_columns_head' ) );
46 //add_filter( 'manage_pages_custom_column', array( $this, 'page_columns_content' ), 10, 2 );
47 add_filter( 'views_edit-page', array( $this, 'views_pages' ), 10 );
48 add_filter( 'views_users', array( $this, 'views_users' ), 10, 1 );
49 add_filter( 'user_row_actions', array( $this, 'user_row_actions' ), 10, 2 );
50 add_filter( 'get_pages', array( $this, 'add_empty_page' ), 1000, 2 );
51 add_filter( 'admin_footer_text', array( $this, 'admin_footer_text' ), 1 );
52 add_filter( 'views_plugins', array( $this, 'views_plugins' ) );
53
54 LP_Request::register( 'lp-action', array( $this, 'filter_users' ) );
55
56 add_filter( 'learn-press/modal-search-items-args', array( $this, 'filter_modal_search' ) );
57
58 /*add_filter(
59 'learn-press/dismissed-notice-response',
60 array(
61 $this,
62 'on_dismissed_notice_response',
63 ),
64 10,
65 2
66 );*/
67
68 // get list items course of user | tungnx
69 add_action( 'pre_get_posts', array( $this, 'get_course_items_of_user_backend' ), 10 );
70 add_action( 'pre_get_posts', array( $this, 'get_pages_of_lp' ), 10 );
71
72 // Set link item course when edit on Backend | tungnx
73 add_filter( 'get_sample_permalink_html', array( $this, 'lp_course_set_link_item_backend' ), 10, 5 );
74
75 // Add "Edit with Course Builder" button below title area for courses
76 add_action( 'edit_form_after_title', array( $this, 'add_course_builder_button' ) );
77
78 /*add_action(
79 'admin_init',
80 function () {
81 // From LP v4.2.3 temporary run create pages to add page instructors, single instructor for client upgrade LP.
82 // After a long time, will remove this code.
83 if ( is_admin() && ! defined( 'DOING_AJAX' ) ) {
84 LP_Install::create_pages();
85 }
86 }
87 );*/
88
89 add_filter( 'users_list_table_query_args', [ $this, 'exclude_temp_users' ] );
90
91 // Show label 'LearnPress Page' for page of LearnPress.
92 //add_filter('post_states_html');
93 add_filter( 'display_post_states', [ $this, 'show_label_page_type' ], 10, 2 );
94 }
95
96 /**
97 * @since 3.2.6
98 */
99 public function load_modal() {
100 // Now only add item(s) when create new Order is using.
101 if ( in_array( get_post_type(), array( LP_ORDER_CPT ) ) ) {
102 LP_Modal_Search_Items::instance();
103 }
104
105 /*if ( in_array( get_post_type(), array( LP_ORDER_CPT ) ) ) {
106 LP_Modal_Search_Users::instance();
107 }*/
108 }
109
110 /**
111 * @param $options
112 *
113 * @return array
114 */
115 public function filter_modal_search( $options ) {
116 $options = wp_parse_args( array( 'title' => __( 'Available Courses', 'learnpress' ) ), $options );
117
118 return $options;
119 }
120
121 public function add_empty_page( $pages, $args ) {
122 if ( empty( $pages ) && ! empty( $args['class'] ) && strpos( $args['class'], 'lp-list-pages' ) !== false ) {
123 $empty_page = get_default_post_to_edit( 'page' );
124 $empty_page->ID = '00000';
125 $pages[] = $empty_page;
126 }
127
128 return $pages;
129 }
130
131 /**
132 * Add 'LearnPress' tab into views of plugins manage.
133 *
134 * @param array $views
135 *
136 * @return array
137 * @since 3.0.0
138 */
139 public function views_plugins( $views ) {
140 global $s;
141
142 $search = $this->get_addons();
143 $count_activated = 0;
144
145 $active_plugins = get_option( 'active_plugins' );
146
147 if ( $active_plugins ) {
148 if ( $search ) {
149 foreach ( $search as $k => $v ) {
150 if ( in_array( $k, $active_plugins ) ) {
151 ++ $count_activated;
152 }
153 }
154 }
155 }
156
157 if ( $s && false !== stripos( $s, 'learnpress' ) ) {
158 $views['learnpress'] = sprintf(
159 '<a href="%s" class="current">%s <span class="count">(%d/%d)</span></a>',
160 admin_url( 'plugins.php?s=learnpress' ),
161 __( 'LearnPress', 'learnpress' ),
162 $count_activated,
163 sizeof( $search )
164 );
165 } else {
166 $views['learnpress'] = sprintf(
167 '<a href="%s">%s <span class="count">(%d/%d)</span></a>',
168 admin_url( 'plugins.php?s=learnpress' ),
169 __( 'LearnPress', 'learnpress' ),
170 $count_activated,
171 sizeof( $search )
172 );
173 }
174
175 return $views;
176 }
177
178 public function get_addons() {
179 $all_plugins = apply_filters( 'all_plugins', get_plugins() );
180
181 return array_filter( $all_plugins, array( $this, '_search_callback' ) );
182 }
183
184 /**
185 * Callback function for searching plugins have 'learnpress' inside.
186 *
187 * @param array $plugin
188 *
189 * @return bool
190 * @since 3.0.0
191 */
192 public function _search_callback( $plugin ) {
193 foreach ( $plugin as $value ) {
194 if ( is_string( $value ) && false !== stripos( strip_tags( $value ), 'learnpress' ) ) {
195 return true;
196 }
197 }
198
199 return false;
200 }
201
202 /**
203 * Check if a page is set for WooCommerce.
204 *
205 * @param int $id
206 *
207 * @return bool
208 */
209 /*protected function _is_wc_page( $id ) {
210 if ( class_exists( 'WooCommerce' ) ) {
211 if ( ! class_exists( 'WC_Admin_Post_Types' ) ) {
212 include_once dirname( WC_PLUGIN_FILE ) . '/includes/admin/class-wc-admin-post-types.php';
213 }
214
215 $wc_admin_post_types = new WC_Admin_Post_Types();
216 if ( is_callable( array( $wc_admin_post_types, 'add_display_post_states' ) ) ) {
217 $a = $wc_admin_post_types->add_display_post_states( array(), get_post( $id ) );
218 } else {
219 $a = $this->wc_add_display_post_states( array(), get_post( $id ) );
220 }
221 $wc_pages = array(
222 'wc_page_for_shop',
223 'wc_page_for_cart',
224 'wc_page_for_checkout',
225 'wc_page_for_myaccount',
226 'wc_page_for_terms',
227 );
228 foreach ( $wc_pages as $for_page ) {
229 if ( isset( $a[ $for_page ] ) ) {
230 return $a[ $for_page ];
231 }
232 }
233 }
234
235 return false;
236 }*/
237
238 /*public function wc_add_display_post_states( $post_states, $post ) {
239 if ( wc_get_page_id( 'shop' ) === $post->ID ) {
240 $post_states['wc_page_for_shop'] = __( 'Shop Page', 'learnpress' );
241 }
242
243 if ( wc_get_page_id( 'cart' ) === $post->ID ) {
244 $post_states['wc_page_for_cart'] = __( 'Cart Page', 'learnpress' );
245 }
246
247 if ( wc_get_page_id( 'checkout' ) === $post->ID ) {
248 $post_states['wc_page_for_checkout'] = __( 'Checkout Page', 'learnpress' );
249 }
250
251 if ( wc_get_page_id( 'myaccount' ) === $post->ID ) {
252 $post_states['wc_page_for_myaccount'] = __( 'My Account Page', 'learnpress' );
253 }
254
255 if ( wc_get_page_id( 'terms' ) === $post->ID ) {
256 $post_states['wc_page_for_terms'] = __( 'Terms and Conditions Page', 'learnpress' );
257 }
258
259 return $post_states;
260 }*/
261
262 /**
263 * Check if a page is set for Paid Membership Pro.
264 *
265 * @param int $id
266 *
267 * @return bool|mixed
268 */
269 /*protected function _is_pmpro_page( $id ) {
270 global $pmpro_pages;
271 if ( $pmpro_pages ) {
272 $pages = array(
273 'account' => __( 'Account', 'learnpress' ),
274 'billing' => __( 'Billing', 'learnpress' ),
275 'cancel' => __( 'Cancel', 'learnpress' ),
276 'checkout' => __( 'Checkout', 'learnpress' ),
277 'confirmation' => __( 'Confirmation', 'learnpress' ),
278 'invoice' => __( 'Invoice', 'learnpress' ),
279 'levels' => __( 'Levels', 'learnpress' ),
280 );
281
282 foreach ( $pages as $name => $text ) {
283 if ( $pmpro_pages[ $name ] == $id ) {
284 return $text;
285 }
286 }
287 }
288
289 return false;
290 }*/
291
292 /**
293 * Check if a page is set for Paid Membership Pro.
294 *
295 * @param int $id
296 *
297 * @return bool|mixed
298 */
299 /*protected function _is_bp_page( $id ) {
300 if ( function_exists( 'buddypress' ) ) {
301 $bp_pages = get_option( 'bp-pages' );
302 if ( ! $bp_pages ) {
303 return false;
304 }
305
306 $pages = array(
307 'members' => __( 'Members', 'learnpress' ),
308 'activity' => __( 'Activity', 'learnpress' ),
309 'register' => __( 'Register', 'learnpress' ),
310 'activate' => __( 'Activate', 'learnpress' ),
311 );
312
313 foreach ( $pages as $name => $text ) {
314 if ( isset( $bp_pages[ $name ] ) && $bp_pages[ $name ] == $id ) {
315 return $text;
316 }
317 }
318 }
319
320 return false;
321 }*/
322
323 /**
324 * Get pages is publish set by LearnPress.
325 *
326 * @return array
327 */
328 protected function _get_static_pages(): array {
329 $static_pages = [];
330 foreach ( $this->pages as $name => $title ) {
331 $page_id = learn_press_get_page_id( $name );
332
333 if ( $page_id && 'publish' === get_post_status( $page_id ) ) {
334 $static_pages[ $page_id ] = $title;
335 }
336 }
337
338 return $static_pages;
339 }
340
341 /**
342 * Show label LearnPress Page for pages set by LearnPress.
343 *
344 * @param array $post_states
345 * @param WP_Post $post
346 *
347 * @return array
348 * @since 4.3.2.6
349 * @version 1.0.0
350 */
351 public function show_label_page_type( $post_states, $post ) {
352 $post_type = get_post_type( $post );
353 if ( $post_type !== 'page' ) {
354 return $post_states;
355 }
356
357 $page_id_compare = $post->ID;
358 foreach ( $this->_get_static_pages() as $page_id => $title ) {
359 if ( $page_id == $page_id_compare ) {
360 $post_states['lp_page'] = sprintf(
361 '<span class="is-lp-page">%s</span>',
362 'LearnPress ' . $title . ' Page'
363 );
364 break;
365 }
366 }
367
368 return $post_states;
369 }
370
371 /**
372 * Add new column to WP Pages manage to show what page is assigned to.
373 *
374 * @param array $columns
375 *
376 * @return array
377 */
378 /*public function page_columns_head( $columns ) {
379
380 $_columns = $columns;
381 $columns = array();
382
383 foreach ( $_columns as $name => $text ) {
384 if ( $name === 'date' ) {
385 $columns['lp-page'] = __( 'LearnPress Page', 'learnpress' );
386 }
387 $columns[ $name ] = $text;
388 }
389
390 return $columns;
391 }*/
392
393 /**
394 * Display the page is assigned to LP Page.
395 *
396 * @param string $column_name
397 * @param int $post
398 */
399 /*public function page_columns_content( $column_name, $post ) {
400 $pages = $this->_get_static_pages();
401 switch ( $column_name ) {
402 case 'lp-page':
403 if ( ! empty( $pages['learnpress'][ $post ] ) ) {
404 echo wp_kses_post( $pages['learnpress'][ $post ] );
405 }
406
407 foreach ( $pages as $plugin => $plugin_pages ) {
408 if ( $plugin === 'learnpress' ) {
409 continue;
410 }
411
412 if ( ! empty( $pages[ $plugin ][ $post ] ) ) {
413 echo sprintf(
414 '<p class="for-plugin-page">(%s - %s)</p>',
415 $plugin,
416 $pages[ $plugin ][ $post ]
417 );
418 }
419 }
420 }
421 }*/
422
423 /**
424 * @param $actions
425 *
426 * @return mixed
427 */
428 public function views_pages( $actions ) {
429 $pages = $this->_get_static_pages();
430
431 if ( $pages ) {
432 $text = sprintf( __( 'LearnPress Pages (%d)', 'learnpress' ), sizeof( $pages ) );
433 if ( 'yes' !== LP_Request::get_param( 'lp-page' ) ) {
434 $actions['lp-page'] = sprintf(
435 '<a href="%s">%s</a>',
436 admin_url( 'edit.php?post_type=page&lp-page=yes' ),
437 $text
438 );
439 } else {
440 $actions['lp-page'] = $text;
441 }
442 }
443
444 return $actions;
445 }
446
447 /**
448 * Get pages set by LP with param url lp-page=yes
449 *
450 * @param WP_Query $q
451 *
452 * @return mixed
453 */
454 public function get_pages_of_lp( $q ) {
455 if ( ! is_admin() || ! $q->is_main_query() ) {
456 return $q;
457 }
458
459 if ( 'page' == LP_Request::get_param( 'post_type' ) && 'yes' == LP_Request::get_param( 'lp-page' ) ) {
460 $ids = $this->_get_static_pages();
461
462 if ( ! empty( $ids ) ) {
463 $ids = array_keys( $ids );
464 $q->set( 'post__in', $ids );
465 }
466 }
467
468 return $q;
469 }
470
471 /**
472 * Add actions to users list
473 *
474 * @param array $actions
475 * @param WP_User $user
476 *
477 * @return mixed
478 */
479 public function user_row_actions( $actions, $user ) {
480 $pending_request = self::get_pending_requests();
481 if ( LP_Request::get_param( 'lp-action' ) == 'pending-request' && $pending_request ) {
482 $actions = array();
483 $nonce = 'nonce=' . wp_create_nonce( 'lp-action-permit-role-teacher' );
484 if ( in_array( $user->ID, $pending_request ) ) {
485 $actions['accept'] = sprintf(
486 '<a href="%s">%s</a>',
487 admin_url( "users.php?lp-action=accept-request&user_id={$user->ID}&{$nonce}" ),
488 _x( 'Accept', 'pending-request', 'learnpress' )
489 );
490 $actions['delete deny'] = sprintf(
491 '<a class="submitdelete" href="%s">%s</a>',
492 admin_url( "users.php?lp-action=deny-request&user_id={$user->ID}&{$nonce}" ),
493 _x( 'Deny', 'pending-request', 'learnpress' )
494 );
495 }
496 }
497
498 return $actions;
499 }
500
501 public function exclude_temp_users( $args ) {
502 if ( LP_Request::get_param( 'lp-action' ) == 'pending-request' ) {
503 $args['include'] = self::get_pending_requests();
504 }
505
506 return $args;
507 }
508
509 /**
510 * Get pending requests be come a Teacher.
511 *
512 * @return array
513 */
514 public static function get_pending_requests() {
515 global $wpdb;
516 $query = $wpdb->prepare(
517 "
518 SELECT ID
519 FROM {$wpdb->users} u
520 INNER JOIN {$wpdb->usermeta} um ON um.user_id = u.ID AND um.meta_key = %s
521 WHERE um.meta_value = %s
522 ",
523 '_requested_become_teacher',
524 'yes'
525 );
526
527 return $wpdb->get_col( $query );
528 }
529
530 /**
531 * Filter user by custom param
532 *
533 * @param string $action
534 */
535 public function filter_users( $action ) {
536 if ( ! current_user_can( 'administrator' ) ) {
537 return;
538 }
539
540 $user_id = LP_Request::get_param( 'user_id', 'int' );
541 if ( ! $user_id || ! get_user_by( 'id', $user_id ) ) {
542 return;
543 }
544
545 $nonce = LP_Request::get_param( 'nonce' );
546 if ( ! wp_verify_nonce( $nonce, 'lp-action-permit-role-teacher' ) ) {
547 return;
548 }
549
550 $user_data = get_userdata( $user_id );
551 if ( in_array( $action, array( 'accept-request', 'deny-request' ) ) ) {
552 delete_user_meta( $user_id, '_requested_become_teacher' );
553 }
554
555 switch ( $action ) {
556 case 'accept-request':
557 $be_teacher = new WP_User( $user_id );
558 $be_teacher->set_role( LP_TEACHER_ROLE );
559
560 /**
561 * Send email to user when admin accept user become a teacher
562 * @use SendEmailAjax::send_mail_become_a_teacher_accept
563 */
564 $data_send = [
565 'params' => [ $user_data->user_email ],
566 'lp-load-ajax' => 'send_mail_become_a_teacher_accept',
567 ];
568 LPBackgroundAjax::handle( $data_send );
569
570 do_action( 'learn-press/user-become-a-teacher-accept', $user_data->user_email );
571 wp_redirect( admin_url( 'users.php?lp-action=accepted-request&user_id=' . $user_id ) );
572 exit();
573 case 'deny-request':
574 /**
575 * Send email to user when admin accept user become a teacher
576 * @use SendEmailAjax::send_mail_become_a_teacher_deny
577 */
578 $data_send = [
579 'params' => [ $user_data->user_email ],
580 'lp-load-ajax' => 'send_mail_become_a_teacher_deny',
581 ];
582 LPBackgroundAjax::handle( $data_send );
583
584 do_action( 'learn-press/user-become-a-teacher-deny', $user_data->user_email );
585 wp_redirect( admin_url( 'users.php?lp-action=denied-request&user_id=' . $user_id ) );
586 exit();
587 }
588 }
589
590 public function users_custom_column( $content, $column_name, $user_id ) {
591 }
592
593 /**
594 * Add new view to users views for filtering user by "pending request" of "become a teacher".
595 *
596 * @param array $views
597 *
598 * @return mixed
599 */
600 public function views_users( $views ) {
601 $pending_request = self::get_pending_requests();
602
603 if ( $pending_request ) {
604 if ( LP_Request::get_param( 'lp-action' ) == 'pending-request' ) {
605 $class = ' class="current"';
606 foreach ( $views as $k => $view ) {
607 $views[ $k ] = preg_replace( '!class="current"!', '', $view );
608 }
609 } else {
610 $class = '';
611 }
612 $views['pending-request'] = '<a href="' . admin_url( 'users.php?lp-action=pending-request' ) . '"' . $class . '>' . sprintf(
613 __(
614 'Pending Request %s',
615 'learnpress'
616 ),
617 '<span class="count">(' . count( $pending_request ) . ')</span>'
618 ) . '</a>';
619 }
620
621 return $views;
622 }
623
624 /**
625 * Custom admin body classes.
626 *
627 * @param array $classes
628 *
629 * @return array|string
630 */
631 public function body_class( $classes ) {
632 $post_type = get_post_type();
633
634 if ( preg_match( '~^lp_~', $post_type ) ) {
635 if ( $classes ) {
636 $classes = explode( ' ', $classes );
637 } else {
638 $classes = array();
639 }
640
641 $classes[] = 'learnpress';
642 $classes = array_filter( $classes );
643 $classes = array_unique( $classes );
644 $classes = join( ' ', $classes );
645 }
646
647 return $classes;
648 }
649
650 /**
651 * Display notices on Backend.
652 */
653 public function admin_notices() {
654 if ( function_exists( 'get_current_screen' ) ) {
655 $wp_screen = get_current_screen();
656 // Not run on course edit screen, it slows, can affect performance edit course.
657 if ( $wp_screen->id === LP_COURSE_CPT ) {
658 return;
659 }
660 }
661
662 // Request accept/denied user can become a teacher.
663 $action_become_teacher = LP_Request::get_param( 'lp-action' );
664 $user_id = LP_Request::get_param( 'user_id', 0, 'int' );
665 $type_action_become_teacher = array( 'accepted-request', 'denied-request' );
666 if ( in_array( $action_become_teacher, $type_action_become_teacher ) && $user_id && get_user_by( 'id', $user_id ) ) {
667 ?>
668 <div class="updated notice">
669 <p>
670 <?php
671 echo sprintf(
672 __( 'A user has %s to become a teacher.', 'learnpress' ),
673 $action_become_teacher == 'accepted-request' ? 'accepted' : 'denied'
674 );
675 ?>
676 </p>
677 </div>
678 <?php
679 }
680
681 // Load Ajax notes here
682 /** @use AdminNotesTemplate::render_notices */
683 $html_notices = TemplateAJAX::load_content_via_ajax(
684 [
685 'method_request' => 'GET',
686 'id_url' => 'admin-notices',
687 'html_loading_before_show_content' => '',
688 ],
689 [
690 'class' => AdminNotesTemplate::class,
691 'method' => 'render_notices',
692 ]
693 );
694
695 wp_enqueue_script( 'lp-admin-notices' );
696
697 echo Template::instance()->nest_elements(
698 [
699 '<div class="learn-press-admin-notices notice">' => '</div>',
700 ],
701 $html_notices
702 );
703 }
704
705 /**
706 * Admin footer add review.
707 *
708 * @param $footer_text
709 *
710 * @return string
711 */
712 public function admin_footer_text( $footer_text ) {
713 $current_screen = get_current_screen();
714 $pages = learn_press_get_screens();
715
716 if ( isset( $current_screen->id ) && apply_filters(
717 'learn_press_display_admin_footer_text',
718 in_array( $current_screen->id, $pages )
719 ) ) {
720 if ( ! get_option( 'learn_press_message_user_rated' ) ) {
721 $footer_text = sprintf(
722 __(
723 'If you like <strong>LearnPress</strong> please leave us a %1$s&#9733;&#9733;&#9733;&#9733;&#9733;%2$s rating. A huge thanks from the LearnPress team for your generosity.',
724 'learnpress'
725 ),
726 '<a href="https://wordpress.org/support/plugin/learnpress/reviews/?filter=5#postform" target="_blank" class="lp-rating-link" data-rated="' . esc_attr__(
727 'Thanks :)',
728 'learnpress'
729 ) . '">',
730 '</a>'
731 );
732 }
733 }
734
735 return $footer_text;
736 }
737
738 /*function delete_user_form() {
739 // What should be displayed here?
740 }*/
741
742 /**
743 * Delete records related user being deleted in other tables
744 *
745 * @param int $user_id
746 */
747 function delete_user_data( $user_id ) {
748 learn_press_delete_user_data( $user_id );
749 }
750
751 /**
752 * Send data to join newsletter or dismiss.
753 *
754 * @param array $data
755 * @param string $notice
756 *
757 * @return array
758 * @since 3.0.10
759 * @deprecated 4.2.3.1
760 */
761 /*public function on_dismissed_notice_response( $data, $notice ) {
762 switch ( $notice ) {
763 case 'skip-setup-wizard':
764 delete_option( 'learn_press_install' );
765 break;
766 case 'newsletter-button':
767 $context = LP_Request::get_string( 'context' );
768 if ( ! $context || $context != 'newsletter' ) {
769 break;
770 }
771
772 $user = learn_press_get_current_user();
773 if ( ! $user || $user->get_email() == '' ) {
774 $data['error'] = __( 'Failed while joining the newsletter! Please try again!', 'learnpress' );
775 }
776
777 $url = 'https://thimpress.com/mailster/subscribe';
778 $response = wp_remote_post(
779 $url,
780 array(
781 'method' => 'POST',
782 'timeout' => 45,
783 'redirection' => 5,
784 'httpversion' => '1.0',
785 'blocking' => true,
786 'headers' => array(),
787 'body' => array(
788 '_referer' => 'extern',
789 '_nonce' => '4b266caf7b',
790 'formid' => '19',
791 'email' => $user->get_email(),
792 'website' => site_url(),
793 ),
794 'cookies' => array(),
795 )
796 );
797
798 if ( is_wp_error( $response ) ) {
799 $error_message = $response->get_error_message();
800 $data['message'] = __( 'Something went wrong: ', 'learnpress' ) . $error_message;
801 } else {
802 $data['message'] = __(
803 'Thank you for subscribing! Please check and click the confirmation link from the email that we\'ve just sent to your inbox.',
804 'learnpress'
805 );
806 }
807 }
808
809 return $data;
810 }*/
811
812 /**
813 * Include all classes and functions used for admin
814 */
815 public function includes() {
816 // Common function used in admin
817 include_once 'lp-admin-functions.php';
818 include_once 'lp-admin-actions.php';
819 include_once 'class-lp-admin-assets.php';
820 LP_Admin_Assets::instance();
821 // For MCP
822 if ( learn_press_is_mcp_available() ) {
823 include_once 'class-lp-admin-mcp-api-keys.php';
824 LP_Admin_MCP_API_Keys::instance();
825 }
826 // End MCP
827 include_once 'class-lp-admin-webhooks.php';
828 LP_Admin_Webhooks::instance();
829 include_once 'class-lp-admin-dashboard.php';
830 // include_once 'class-lp-admin-tools.php';
831 include_once 'class-lp-admin-ajax.php';
832 include_once 'editor/class-lp-admin-editor.php';
833 include_once 'class-lp-admin-menu.php';
834 include_once 'helpers/class-lp-outdated-template-helper.php';
835 include_once 'class-lp-modal-search-items.php';
836 //include_once 'class-lp-modal-search-users.php';
837 include_once 'class-lp-setup-wizard.php';
838 // include_once 'class-lp-updater.php';
839 // include_once 'class-lp-install-sample-data.php'; // Replaced by LearnPress\Ajax\SampleDataAJAX.
840 // include_once 'class-lp-reset-data.php'; // Deprecated: replaced by CourseToolsAjax::reset_progress_items_course.
841 include_once LP_PLUGIN_PATH . 'inc/admin/views/meta-boxes/course/settings.php';
842 include_once LP_PLUGIN_PATH . 'inc/admin/views/meta-boxes/course/class-lp-meta-box-course-offline.php';
843 include_once LP_PLUGIN_PATH . 'inc/admin/views/meta-boxes/quiz/settings.php';
844 include_once LP_PLUGIN_PATH . 'inc/admin/views/meta-boxes/lesson/settings.php';
845 //include_once LP_PLUGIN_PATH . 'inc/admin/views/meta-boxes/question/settings.php';
846 }
847
848 /**
849 * Get courses, item's courses on Backend page post_type
850 *
851 * @param WP_Query $query
852 */
853 public function get_course_items_of_user_backend( WP_Query $query ) {
854 if ( ! $query->is_main_query() ) {
855 return;
856 }
857
858 /*global $post_type, $pagenow;
859
860 if ( current_user_can( ADMIN_ROLE ) ) {
861 return;
862 }
863
864 if ( ! current_user_can( LP_TEACHER_ROLE ) || ( $pagenow != 'edit.php' ) ) {
865 return;
866 }
867
868 $post_type_valid = apply_filters(
869 'learn-press/filter-user-access-types',
870 array( LP_COURSE_CPT, LP_LESSON_CPT, LP_QUIZ_CPT, LP_QUESTION_CPT )
871 );
872
873 if ( ! in_array( $post_type, $post_type_valid ) ) {
874 return;
875 }*/
876
877 // $query->set( 'author', get_current_user_id() );
878
879 // Hook only Co-instructor using.
880 return apply_filters( 'learnpress/get-post-type-lp-on-backend', $query );
881
882 //add_filter( 'views_edit-' . $post_type . '', '_learn_press_restrict_view_items', 10 );
883 //remove_filter( 'pre_get_posts', array( $this, 'get_course_items_of_user_backend' ), 10 );
884 }
885
886 /**
887 * Set link item of course when edit item on Backend
888 *
889 * @param string $post_link
890 * @param int $post_id
891 * @param string $new_title
892 * @param string $new_slug
893 * @param WP_Post|null $post
894 *
895 * @return string
896 * @author tungnx
897 * @since 3.2.7.5
898 * @version 4.0.1
899 */
900 public function lp_course_set_link_item_backend( $post_link = '', $post_id = 0, $new_title = '', $new_slug = '', $post = null ) {
901 try {
902 if ( in_array( $post->post_type, CourseModel::item_types_support() ) ) {
903 $course_id_of_item = LP_Course_DB::getInstance()->get_course_by_item_id( $post->ID );
904 if ( $course_id_of_item ) {
905 $course = learn_press_get_course( $course_id_of_item );
906 if ( $course ) {
907 $link_item = urldecode( $course->get_item_link( $post->ID ) );
908 $post_slug = $post->post_name;
909 $link_item_edit_slug = preg_replace( '/' . $post_slug . '$/', '', $link_item );
910
911 // For update new slug
912 if ( $new_slug ) {
913 $post_slug = $new_slug;
914 }
915 $post_slug = urldecode( $post_slug );
916
917 $slug_arr = explode( '/', $link_item_edit_slug );
918 $count_slug = count( $slug_arr );
919 unset( $slug_arr[ $count_slug - 2 ] );
920 $link_item_edit_slug = implode( '/', $slug_arr );
921
922 $post_link = '<strong>Permalink: </strong>';
923 $post_link .= '<span id="sample-permalink">';
924 $post_link .= '<a href="' . $link_item . '">' . $link_item_edit_slug . '<span id="editable-post-name">' . $post_slug . '</span>/</a>';
925 $post_link .= '</span>';
926 $post_link .= '&lrm;<span id="edit-slug-buttons">';
927 $post_link .= '<button type="button" class="edit-slug button button-small hide-if-no-js" aria-label="Edit permalink">Edit</button>';
928 $post_link .= '</span>';
929 $post_link .= '<span id="editable-post-name-full">' . $post_slug . '</span>';
930 }
931 } else {
932 $post_link_message = '<span>' . __(
933 'Permalink is only available if the item is already assigned to a course.',
934 'learnpress'
935 ) . '</span>';
936 $post_link = sprintf( '<div id="learn-press-box-edit-slug">%s</div>', $post_link_message );
937 }
938 } elseif ( LP_COURSE_CPT === get_post_type( $post ) ) {
939 $post_link = LP_Helper::handle_lp_permalink_structure( $post_link, $post );
940 }
941 } catch ( Throwable $e ) {
942 error_log( $e->getMessage() );
943 }
944
945 return $post_link;
946 }
947
948 /**
949 * Add "Edit with Course Builder" button below title area for courses
950 *
951 * @param WP_Post $post
952 *
953 * @since 4.3.0
954 */
955 public function add_course_builder_button( $post ) {
956 if ( ! $post || LP_COURSE_CPT !== $post->post_type ) {
957 return;
958 }
959
960 // Only show for existing courses (not new)
961 if ( 'auto-draft' === $post->post_status ) {
962 return;
963 }
964
965 $course_builder_url = BuilderCourseTemplate::instance()->get_link_edit( $post->ID ) ?? '';
966 ?>
967 <div class="lp-edit-with-course-builder" style="margin: 10px 0 20px 0;">
968 <a href="<?php echo esc_url( $course_builder_url ); ?>" class="button button-primary button-large" style="background: #7067ED; border-color: #7067ED; display: inline-flex; align-items: center; gap: 6px; padding: 0 16px; font-size: 14px; border-radius: 3px; line-height: 3;">
969 <svg width="26" height="18" viewBox="0 0 69 48" fill="none" xmlns="http://www.w3.org/2000/svg">
970 <path d="M50.9291 24.84L50.2591 21.69C50.5491 21.47 50.7391 21.11 50.7391 20.71C50.7391 20.03 50.1891 19.48 49.4991 19.48C48.8091 19.48 48.2591 20.03 48.2591 20.71C48.2591 21.11 48.4491 21.46 48.7391 21.69L48.0691 24.84C47.9891 25.21 48.1791 25.56 48.4791 25.56H50.5091C50.8091 25.56 50.9991 25.21 50.9191 24.84H50.9291Z" fill="white"></path>
971 <path d="M50.8892 13.24H50.0092V20.92H48.9892V13.21L46.2992 13.18C43.3992 8.47 38.1692 5.34 32.2192 5.34C30.8292 5.34 29.4792 5.51 28.1892 5.83L24.9492 2.53C24.7992 2.38 24.8892 2.14 25.0992 2.11L40.7292 0L48.5492 9.68L49.7592 11.17L51.0992 12.83C51.2292 12.99 51.1092 13.24 50.8992 13.23L50.8892 13.24Z" fill="white"></path>
972 <path d="M44.7392 13.1701L43.1392 17.1401C40.7292 13.1101 36.3092 10.4101 31.2592 10.4101C29.9992 10.4101 28.7892 10.5801 27.6292 10.8901L29.2292 6.93014C30.1992 6.74014 31.1992 6.64014 32.2192 6.64014C37.4092 6.64014 41.9892 9.22014 44.7392 13.1701Z" fill="white"></path>
973 <path d="M25.4692 23.6899V23.8499C25.4692 23.9599 25.4592 24.0699 25.4592 24.1899C25.4592 24.0199 25.4592 23.8499 25.4692 23.6899Z" fill="white"></path>
974 <path d="M43.3692 24.2601C43.3692 25.2901 43.2392 26.2901 42.9892 27.2501C42.3892 29.5401 41.1192 31.5601 39.4092 33.1001C37.9992 34.3601 36.2892 35.2901 34.3892 35.7701C33.4492 36.0101 32.4592 36.1401 31.4392 36.1401H27.9692V35.8001C27.9692 35.6601 27.9792 35.5301 27.9992 35.3901C28.2092 33.2201 29.5592 31.3901 31.4492 30.4901C31.6092 30.4101 31.7692 30.3401 31.9292 30.2801C32.1692 30.1901 32.4192 30.1201 32.6692 30.0601C32.7292 30.0501 32.7992 30.0301 32.8592 30.0201C35.4892 29.4101 37.4492 27.0601 37.4492 24.2501C37.4492 21.2701 35.2392 18.8001 32.3592 18.3901C32.0792 18.3501 31.7892 18.3301 31.4992 18.3301C31.2392 18.3301 30.9992 18.3501 30.7492 18.3801C28.2992 18.6901 26.2592 20.4801 25.6492 22.8201C25.5292 23.2901 25.4792 23.7701 25.4792 24.2401V42.7601C25.1492 45.6001 22.8092 47.8301 19.9092 47.9901H19.5592H16.4792C18.3092 46.6501 19.5092 44.5001 19.5092 42.0701V23.7001C19.5092 23.5601 19.5192 23.4301 19.5392 23.3001C19.6292 22.2301 19.8492 21.1901 20.2092 20.2201C20.4592 19.5401 20.7692 18.8801 21.1292 18.2501C21.7592 17.1801 22.5492 16.2201 23.4692 15.4001C24.6192 14.3701 25.9792 13.5601 27.4692 13.0401C28.7092 12.6001 30.0492 12.3701 31.4392 12.3701C32.4792 12.3701 33.4792 12.5001 34.4392 12.7501C36.6892 13.3301 38.6792 14.5401 40.2092 16.1901C40.2592 16.2401 40.3092 16.3001 40.3592 16.3501C40.3592 16.3501 40.3592 16.3501 40.3692 16.3601C41.9592 18.1401 43.0192 20.4101 43.2992 22.9001C43.3293 23.1701 43.3492 23.4501 43.3692 23.7201C43.3692 23.8901 43.3692 24.0601 43.3692 24.2401V24.2601Z" fill="white"></path>
975 <path d="M25.4692 23.6899V23.8499C25.4692 23.9599 25.4592 24.0699 25.4592 24.1899C25.4592 24.0199 25.4592 23.8499 25.4692 23.6899Z" fill="white"></path>
976 <path d="M6.13917 42.0799H18.0692C18.0592 45.3499 15.3792 47.9999 12.0892 47.9999H6.11917C2.83917 47.9999 0.16917 45.3499 0.14917 42.0799V12.3799H0.18917C3.46917 12.3799 6.13917 15.0299 6.13917 18.2999V42.0799Z" fill="white"></path>
977 <path d="M67.6736 23.2845L63.9566 19.5676C63.1998 18.8108 61.9757 18.8108 61.219 19.5676L59.0266 21.7599L65.4812 28.2145L67.6736 26.0222C68.4303 25.2654 68.4303 24.0413 67.6736 23.2845Z" fill="white"></path>
978 <path d="M45.4722 45.0411L46.3513 45.9203L42.078 46.7883C42.078 46.7883 42.0557 46.3432 41.477 45.7534C40.8983 45.1747 40.442 45.1524 40.442 45.1524L41.3101 40.879L42.1892 41.7582L59.817 24.1305L58.2256 22.5391L40.5979 40.1668L39.2513 46.7883C39.1066 47.4894 39.7298 48.1126 40.4309 47.968L47.0525 46.6214L64.6802 28.9937L63.0888 27.4023L45.4611 45.03L45.4722 45.0411Z" fill="white"></path>
979 <path d="M60.6182 24.9316L42.9905 42.5594L44.6932 44.2621L62.3209 26.6343L60.6182 24.9316Z" fill="white"></path>
980 </svg>
981 <?php esc_html_e( 'Edit with Course Builder', 'learnpress' ); ?>
982 </a>
983 </div>
984 <?php
985 }
986
987 /**
988 * @return false|string
989 * @since 3.2.8
990 * @editor tungnx
991 */
992 public function get_screen_id() {
993 global $current_screen;
994
995 return $current_screen ? $current_screen->id : false;
996 }
997
998 /**
999 * Get single instance of self
1000 *
1001 * @return bool|LP_Admin
1002 * @return bool|LP_Admin
1003 * @since 3.0.0
1004 *
1005 */
1006 public static function instance() {
1007 if ( ! self::$instance ) {
1008 self::$instance = new self();
1009 }
1010
1011 return self::$instance;
1012 }
1013 }
1014 }
1015
1016 return LP_Admin::instance();
1017