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 / custom-post-types / lesson.php

lesson.php in LearnPress – WordPress LMS Plugin for Create and Sell Online Courses 4.4.9, at inc/custom-post-types/lesson.php

451 lines 12.8 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 /**
3 * Class LP_Lesson_Post_Type
4 *
5 * @author ThimPress
6 * @package LearnPress/Classes
7 * @version 3.0.0
8 */
9
10 /**
11 * Prevent loading this file directly
12 */
13
14 use LearnPress\Databases\PostDB;
15 use LearnPress\Filters\LessonPostFilter;
16 use LearnPress\Filters\PostFilter;
17 use LearnPress\Models\CoursePostModel;
18 use LearnPress\Models\CourseSectionItemModel;
19 use LearnPress\Models\PostModel;
20 use LearnPress\Models\WPTables\LessonsTable;
21
22 defined( 'ABSPATH' ) || exit();
23
24 if ( ! class_exists( 'LP_Lesson_Post_Type' ) ) {
25
26 /**
27 * Class LP_Lesson_Post_Type
28 */
29 final class LP_Lesson_Post_Type extends LP_Abstract_Post_Type {
30 /**
31 * @var null
32 */
33 protected static $_instance = null;
34
35 /**
36 * @var string
37 */
38 protected $_post_type = LP_LESSON_CPT;
39
40 /**
41 * @var string
42 */
43 protected $_screen_list = 'edit-' . LP_LESSON_CPT;
44
45 /**
46 * LP_Lesson_Post_Type constructor.
47 *
48 * @param $post_type
49 */
50 public function __construct() {
51
52 // $this->add_map_method( 'before_delete', 'before_delete_lesson' );
53 // hide View Lesson link if not assigned to course
54
55 add_filter( 'views_edit-' . LP_LESSON_CPT, array( $this, 'views_pages' ), 10 );
56 add_filter( 'posts_pre_query', array( $this, 'posts_pre_query' ), 999, 2 );
57 // add_filter( 'posts_where_paged', array( $this, 'posts_where_paged' ), 10 );
58
59 parent::__construct();
60 }
61
62 /**
63 * Handle when save post.
64 *
65 * @param int $post_id
66 * @param WP_Post|null $post
67 * @param bool $is_update
68 *
69 * @return void
70 * @throws Exception
71 * @version 1.0.1
72 * @since 4.2.7.6
73 */
74 public function save_post( int $post_id, ?WP_Post $post = null, bool $is_update = false ) {
75 // Clear cache
76 $lpCache = new LP_Cache();
77 $lpCache->clear( "lessonPostModel/find/{$post_id}" );
78 $lpCache->clear( "lessonModel/find/{$post_id}" );
79
80 // Find courses have this lesson
81 $obj_course_ids = CourseSectionItemModel::get_courses_from_item_id( $post_id, LP_LESSON_CPT );
82 if ( ! empty( $obj_course_ids ) ) {
83 foreach ( $obj_course_ids as $obj_course_id ) {
84 $course_id = $obj_course_id->section_course_id;
85 $coursePostModel = CoursePostModel::find( $course_id, true );
86 if ( $coursePostModel ) {
87 $coursePostModel->save();
88 }
89 }
90 }
91 }
92
93 /**
94 * Declare class name of table list lessons.
95 *
96 * @param string $class_name
97 * @param array $args
98 *
99 * @return string
100 * @since 4.2.9.5
101 */
102 public function wp_list_table_class_name( $class_name, $args ) {
103 if ( $this->check_class_name_handle_table( $args['screen'] ) ) {
104 $class_name = LessonsTable::class;
105 }
106
107 return $class_name;
108 }
109
110 /**
111 * Query lp lessons in admin via Post DB
112 *
113 * @param array $posts
114 * @param WP_Query $wp_query
115 *
116 * @return array|WP_Query
117 * @since 4.4.8
118 * @version 1.0.0
119 */
120 public function posts_pre_query( $posts, $wp_query ) {
121 try {
122 if ( ! is_admin() ) {
123 return $posts;
124 }
125
126 // Check screen
127 if ( ! function_exists( 'get_current_screen' ) ) {
128 return $posts;
129 }
130
131 $curren_screen = get_current_screen();
132 if ( ! $curren_screen || $curren_screen->id !== 'edit-' . LP_LESSON_CPT ) {
133 return $posts;
134 }
135
136 $post_type = $wp_query->get( 'post_type' );
137 if ( empty( $post_type ) || $post_type !== LP_LESSON_CPT ) {
138 return $posts;
139 }
140
141 $posts_per_page = get_user_option( "edit_{$post_type}_per_page", get_current_user_id() );
142 if ( empty( $posts_per_page ) ) {
143 $posts_per_page = 20;
144 }
145
146 $paged = max( 1, get_query_var( 'paged' ) );
147 $author = $wp_query->get( 'author' );
148 $status = $wp_query->get( 'post_status' );
149 $search = $wp_query->get( 's' );
150 $month = $wp_query->get( 'm' );
151 $orderby = LP_Request::get_param( 'orderby', '', 'key' );
152 $order = LP_Request::get_param( 'order', '', 'key' );
153 $preview = LP_Request::get_param( 'preview', '', 'key' );
154 $course_id = LP_Request::get_param( 'course', '', 'int' );
155
156 $filter = new LessonPostFilter();
157 $filter->page = $paged;
158 $filter->limit = $posts_per_page;
159 $filter->only_fields = array_map(
160 function ( $field ) {
161 return "p.{$field}";
162 },
163 $filter->all_fields
164 );
165 $filter->field_count = 'p.ID';
166 $post_db = PostDB::getInstance();
167
168 if ( ! empty( $status ) ) {
169 $filter->post_status = array( $status );
170 }
171
172 if ( ! empty( $author ) ) {
173 $filter->post_author = absint( $author );
174 }
175
176 if ( ! empty( $search ) ) {
177 $filter->post_title = sanitize_text_field( wp_unslash( $search ) );
178 }
179
180 // Find lesson assign by course_id
181 if ( ! empty( $course_id ) ) {
182 $filter->join[] = "INNER JOIN {$post_db->tb_lp_section_items} si ON p.ID = si.item_id";
183 $filter->join[] = "INNER JOIN {$post_db->tb_lp_sections} st ON st.section_id = si.section_id";
184 $filter->where[] = $post_db->wpdb->prepare( 'AND st.section_course_id = %d', $course_id );
185 }
186
187 if ( ! empty( $month ) && is_numeric( $month ) && strlen( (string) $month ) === 6 ) {
188 $filter->where[] = $post_db->wpdb->prepare(
189 'AND YEAR(p.post_date) = %d AND MONTH(p.post_date) = %d',
190 substr( $month, 0, 4 ),
191 substr( $month, 4, 2 )
192 );
193 }
194
195 // Exclude status auto-draft
196 $filter->where[] = $post_db->wpdb->prepare( 'AND p.post_status != %s', PostModel::STATUS_AUTO_DRAFT );
197
198 // Join sections/courses when sorting by course-name
199 if ( $orderby === 'course-name' ) {
200 $filter->join[] = "LEFT JOIN {$post_db->wpdb->prefix}learnpress_section_items si ON p.ID = si.item_id";
201 $filter->join[] = "LEFT JOIN {$post_db->wpdb->prefix}learnpress_sections s ON s.section_id = si.section_id";
202 $filter->join[] = "LEFT JOIN {$post_db->wpdb->posts} c ON c.ID = s.section_course_id";
203 }
204
205 // Filter unassigned
206 if ( 'yes' === LP_Request::get_param( 'unassigned', '', 'key' ) ) {
207 $filter->where[] = "AND p.ID NOT IN(
208 SELECT si.item_id
209 FROM {$post_db->wpdb->learnpress_section_items} si
210 )";
211 }
212
213 // Filter preview.
214 // Non-preview lessons include those that do not have `_lp_preview` meta key.
215 if ( $preview ) {
216 $filter_preview = new LessonPostFilter();
217 $filter_preview->limit = -1;
218 $filter_preview->only_fields = [ PostFilter::COL_ID ];
219 $filter_preview->join[] = "INNER JOIN {$post_db->wpdb->postmeta} pm ON p.ID = pm.post_id";
220 $filter_preview->where[] = $post_db->wpdb->prepare(
221 'AND pm.meta_key = %s AND pm.meta_value = %s',
222 '_lp_preview',
223 'yes'
224 );
225 $filter_preview->return_string_query = true;
226
227 $preview_rows = $post_db->get_posts( $filter_preview );
228
229 $in = 'no' === $preview ? 'NOT' : '';
230 $filter->where[] = "AND p.ID {$in} IN({$preview_rows})";
231 }
232
233 if ( $orderby === 'course-name' ) {
234 $filter->order_by = 'c.post_title';
235 } elseif ( $orderby === 'title' ) {
236 $filter->order_by = 'p.post_title';
237 } elseif ( $orderby === 'author' ) {
238 $filter->order_by = 'p.post_author';
239 } elseif ( $orderby === 'date' ) {
240 $filter->order_by = 'p.post_date';
241 } else {
242 $filter->order_by = 'p.menu_order';
243 }
244
245 $filter->order = strtolower( $order ) === 'asc' ? 'ASC' : 'DESC';
246
247 // Get lp lessons
248 $total_rows = 0;
249 $lp_lessons = $post_db->get_posts( $filter, $total_rows );
250
251 $wp_query->post_count = count( $lp_lessons );
252 $wp_query->found_posts = $total_rows;
253 $posts = $lp_lessons;
254 } catch ( Throwable $e ) {
255 LP_Debug::error_log( $e );
256 }
257
258 return $posts;
259 }
260
261 /*public function posts_where_paged( $where ): string {
262 if ( ! $this->is_page_list_posts_on_backend() ) {
263 return $where;
264 }
265
266 global $wpdb;
267
268 if ( 'yes' === LP_Request::get( 'unassigned' ) ) {
269 $where .= $wpdb->prepare(
270 "
271 AND {$wpdb->posts}.ID NOT IN(
272 SELECT si.item_id
273 FROM {$wpdb->learnpress_section_items} si
274 INNER JOIN {$wpdb->posts} p ON p.ID = si.item_id
275 WHERE p.post_type = %s
276 )
277 ",
278 LP_LESSON_CPT
279 );
280 }
281
282 $preview = LP_Request::get( 'preview' );
283
284 if ( $preview ) {
285 $clause = $wpdb->prepare(
286 "
287 SELECT ID
288 FROM {$wpdb->posts} p
289 INNER JOIN {$wpdb->postmeta} pm ON p.ID = pm.post_id AND pm.meta_key = %s
290 WHERE pm.meta_value = %s
291 AND p.post_type = %s",
292 '_lp_preview',
293 'yes',
294 LP_LESSON_CPT
295 );
296
297 $in = '';
298 if ( 'no' === $preview ) {
299 $in = 'NOT';
300 }
301
302 $where .= " AND {$wpdb->posts}.ID {$in} IN({$clause})";
303 }
304
305 return $where;
306 }*/
307
308 /**
309 * Add filters to lesson view.
310 *
311 * @param array $views
312 *
313 * @return array
314 * @throws Exception
315 * @since 3.0.0
316 * @editor tungnx
317 * @version 1.0.2
318 */
319 public function views_pages( array $views ): array {
320 $count_unassigned_lesson = LP_Course_DB::getInstance()->get_total_item_unassigned( LP_LESSON_CPT );
321
322 if ( $count_unassigned_lesson > 0 ) {
323 $views['unassigned'] = sprintf(
324 '<a href="%s" class="%s">%s <span class="count">(%d)</span></a>',
325 admin_url( 'edit.php?post_type=' . LP_LESSON_CPT . '&unassigned=yes' ),
326 isset( $_GET['unassigned'] ) ? 'current' : '',
327 __( 'Unassigned', 'learnpress' ),
328 $count_unassigned_lesson
329 );
330 }
331
332 $total_preview_items = LP_Lesson_DB::getInstance()->get_total_preview_items();
333 if ( $total_preview_items > 0 ) {
334 $views['lesson-preview'] = sprintf(
335 '<a href="%s" class="%s">%s <span class="count">(%d)</span></a>',
336 admin_url( 'edit.php?post_type=' . LP_LESSON_CPT . '&preview=yes' ),
337 isset( $_GET['preview'] ) && $_GET['preview'] === 'yes' ? 'current' : '',
338 __( 'Preview', 'learnpress' ),
339 $total_preview_items
340 );
341 }
342
343 $total_no_preview_items = LP_Lesson_DB::getInstance()->get_total_no_preview_items( $total_preview_items );
344 if ( $total_no_preview_items > 0 ) {
345 $views['lesson-no-preview'] = sprintf(
346 '<a href="%s" class="%s">%s <span class="count">(%d)</span></a>',
347 admin_url( 'edit.php?post_type=' . LP_LESSON_CPT . '&preview=no' ),
348 isset( $_GET['preview'] ) && $_GET['preview'] === 'no' ? 'current' : '',
349 __( 'No Preview', 'learnpress' ),
350 $total_no_preview_items
351 );
352 }
353
354 return $views;
355 }
356
357 /**
358 * Register lesson post type.
359 */
360 public function args_register_post_type(): array {
361
362 return array(
363 'labels' => array(
364 'name' => esc_html__( 'Lessons', 'learnpress' ),
365 'menu_name' => esc_html__( 'Lessons', 'learnpress' ),
366 'singular_name' => esc_html__( 'Lesson', 'learnpress' ),
367 'add_new_item' => esc_html__( 'Add A New Lesson', 'learnpress' ),
368 'all_items' => esc_html__( 'Lessons', 'learnpress' ),
369 'view_item' => esc_html__( 'View Lesson', 'learnpress' ),
370 'add_new' => esc_html__( 'Add New', 'learnpress' ),
371 'edit_item' => esc_html__( 'Edit Lesson', 'learnpress' ),
372 'update_item' => esc_html__( 'Update Lesson', 'learnpress' ),
373 'search_items' => esc_html__( 'Search Lessons', 'learnpress' ),
374 'not_found' => esc_html__( 'No lesson found', 'learnpress' ),
375 'not_found_in_trash' => esc_html__( 'There was no lesson found in the trash', 'learnpress' ),
376 ),
377 'public' => true,
378 'query_var' => true,
379 'taxonomies' => array( 'lesson_tag' ),
380 'publicly_queryable' => true,
381 'show_ui' => true,
382 'has_archive' => false,
383 'capability_type' => LP_LESSON_CPT,
384 'map_meta_cap' => true,
385 'show_in_menu' => 'learn_press',
386 'show_in_admin_bar' => true,
387 'show_in_nav_menus' => true,
388 'show_in_rest' => learn_press_user_maybe_is_a_teacher(),
389 'supports' => array(
390 'title',
391 'editor',
392 'revisions',
393 'comments',
394 ),
395 'hierarchical' => false, // Lessons have no parent-child hierarchy.
396 'rewrite' => array(
397 'slug' => 'lessons',
398 'hierarchical' => true,
399 'with_front' => false,
400 ),
401 'exclude_from_search' => true,
402 );
403 }
404
405 /**
406 * Remove lesson form course items.
407 *
408 * @param int $post_id
409 *
410 * @since 3.0.0
411 */
412 /*public function before_delete( int $post_id = 0 ) {
413 $curd = new LP_Lesson_CURD();
414 $curd->delete( $post_id );
415 }*/
416
417 /**
418 * Lesson assigned view.
419 *
420 * @since 3.0.0
421 */
422 public function lesson_assigned() {
423 learn_press_admin_view( 'meta-boxes/course/assigned.php' );
424 }
425
426 public function meta_boxes() {
427 return array(
428 'lesson_assigned' => array(
429 'title' => esc_html__( 'Assigned', 'learnpress' ),
430 'callback' => array( $this, 'lesson_assigned' ),
431 'context' => 'side',
432 'priority' => 'high',
433 ),
434 );
435 }
436
437 /**
438 * @return LP_Lesson_Post_Type|null
439 */
440 public static function instance() {
441 if ( ! self::$_instance ) {
442 self::$_instance = new self();
443 }
444
445 return self::$_instance;
446 }
447 }
448
449 $lesson_post_type = LP_Lesson_Post_Type::instance();
450 }
451