PluginProbe
WPJAM Basic / trunk
WPJAM Basic vtrunk
wpjam-basic / public / wpjam-functions.php

wpjam-functions.php in WPJAM Basic trunk, at public/wpjam-functions.php

1,017 lines 33.2 KB
No matching file
Up and down to move Enter to open Esc to close
Raw Download Zip
1 <?php
2 // args
3 function wpjam_args($args=[]){
4 return new WPJAM_Args($args);
5 }
6
7 // register
8 function wpjam_register($group, $name, $args=[]){
9 return $group && $name ? wpjam_registry($group)->add_object($name, $args) : null;
10 }
11
12 function wpjam_unregister($group, $name){
13 $group && $name && wpjam_registry($group)->remove_object($name);
14 }
15
16 function wpjam_get_registered($group, $name){
17 return $group && $name ? wpjam_registry($group)->get_object($name) : null;
18 }
19
20 function wpjam_get_registereds($group, $args=[]){
21 return $group ? wpjam_registry($group)->get_objects($args) : [];
22 }
23
24 function wpjam_registry($name, $args=[]){
25 return WPJAM_Registry::get_instance(strtolower($name), $args);
26 }
27
28 // Handler
29 function wpjam_get_handler(...$args){
30 static $object;
31 $object ??= new WPJAM_Handler();
32
33 return $args ? $object(...$args) : $object;
34 }
35
36 function wpjam_register_handler($name, $args=[]){
37 return wpjam_get_handler()($name, $args, true);
38 }
39
40 function wpjam_call_handler($name, $method, ...$args){
41 return wpjam_get_handler()->$method($name, ...$args);
42 }
43
44 // Builtin
45 function wpjam_get_builtin_type($class){
46 while($parent = get_parent_class($class)){
47 if(in_array($parent, ['WPJAM_Instance', 'WPJAM_Core'])){
48 return try_prefix($class, '-', 'WPJAM_') && class_exists('WP_'.$class) ? strtolower($class) : null;
49 }
50
51 $class = $parent;
52 }
53 }
54
55 // Data Type
56 function wpjam_register_data_type($name, $args=[]){
57 return WPJAM_Data_Type::register($name, $args);
58 }
59
60 function wpjam_get_data_type($name, $args=[]){
61 return WPJAM_Data_Type::get_instance($name, $args);
62 }
63
64 // Platform & Path
65 function wpjam_register_platform($name, $args){
66 return WPJAM_Platform::register($name, $args);
67 }
68
69 function wpjam_get_current_platform($args=[], $output='name'){
70 $args = ($output == 'bit' && $args && wp_is_numeric_array($args)) ? ['bit'=>$args] : ($args ?: ['path'=>true]);
71 $object = array_find(WPJAM_Platform::get_by($args), fn($v)=> $v && $v->verify());
72
73 return ($output === 'object' || !$object) ? $object : $object->$output;
74 }
75
76 function wpjam_get_path($platform, $page_key, $args=[]){
77 return wpjam_call_method(WPJAM_Platform::get($platform), 'get_path', $page_key, $args);
78 }
79
80 function wpjam_get_tabbar($platform, $page_key=''){
81 return wpjam_call_method(WPJAM_Platform::get($platform), 'get_tabbar', $page_key) ?: [];
82 }
83
84 function wpjam_get_page_keys($platform, $args=null, $operator='AND'){
85 $object = WPJAM_Platform::get($platform);
86
87 return is_string($args) && in_array($args, ['with_page', 'page'])
88 ? wpjam_array(wpjam_call_method($object, 'get_page') ?: [], fn($pk, $page)=> [null, ['page'=>$page, 'page_key'=>$pk]])
89 : array_keys(wpjam_filter(wpjam_call_method($object, 'get_paths') ?: [], (is_array($args) ? $args : []), $operator));
90 }
91
92 function wpjam_register_path($name, ...$args){
93 return WPJAM_Path::create($name, ...$args);
94 }
95
96 function wpjam_unregister_path($name, $platform=''){
97 return WPJAM_Path::remove($name, $platform);
98 }
99
100 function wpjam_get_path_fields($platforms=null, $args=[]){
101 return WPJAM_Path::get_fields($platforms, $args);
102 }
103
104 function wpjam_parse_path_item($item, $platform=null, $suffix=''){
105 return WPJAM_Path::parse_item($platform, $item, $suffix);
106 }
107
108 function wpjam_validate_path_item($item, $platforms, $suffix=''){
109 return WPJAM_Path::validate_item($platforms, $item, $suffix);
110 }
111
112 // Option
113 function wpjam_get_option($name, ...$args){
114 $output = $args && in_array($args[0], ['object', 'model', 'registered'], true) ? 'object' : '';
115 $object = WPJAM_Option_Setting::get_instance($name, ...($output === 'object' ? $args : []));
116
117 return $output === 'object' ? $object : $object->get_blog_option(...$args);
118 }
119
120 function wpjam_update_option($name, $value, $blog_id=0){
121 return wpjam_get_option($name, 'object')->update_blog_option($blog_id, $value);
122 }
123
124 function wpjam_get_site_option($name){
125 return wpjam_get_option($name, 'object')->get_site_option();
126 }
127
128 function wpjam_update_site_option($name, $value){
129 return wpjam_get_option($name, 'object')->update_site_option($value);
130 }
131
132 function wpjam_get_setting($name, $setting, $blog_id=0){
133 return wpjam_get_option($name, 'object')->get_blog_setting($blog_id, $setting);
134 }
135
136 function wpjam_update_setting($name, $setting, $value='', $blog_id=0){
137 return wpjam_get_option($name, 'object')->update_blog_setting($blog_id, $setting, $value);
138 }
139
140 function wpjam_delete_setting($name, $setting, $blog_id=0){
141 return wpjam_get_option($name, 'object')->delete_blog_setting($blog_id, $setting);
142 }
143
144 function wpjam_get_site_setting($name, $setting){
145 return wpjam_get_option($name, 'object')->get_site_setting($setting);
146 }
147
148 function wpjam_register_option($name, $args=[]){
149 return WPJAM_Option_Setting::create($name, $args);
150 }
151
152 function wpjam_add_option_section($name, ...$args){
153 return wpjam_get_option($name, 'object')->add_section(...$args);
154 }
155
156 function wpjam_call_option($name, $method, ...$args){
157 $object = wpjam_get_option($name, class_exists($name) ? 'model' : 'object');
158
159 return $method == 'get_object' ? $object : [$object, $method](...$args);
160 }
161
162 function wpjam_setting(...$args){
163 if($args && is_array($args[0]) && ($args = $args[0])){
164 if($option = $args['option_name'] ?? ''){
165 $object = wpjam_get_option($option, 'object');
166 $name = $args['setting_name'] ?? ($args['setting'] ?? null);
167 $value = ($object->option_type === 'array' && $object->get_fields()) ? $object->prepare_by_fields() : $object->get_option();
168
169 return [(($args['output'] ?? '') ?: ($name ?: $option))=> ($name ? wpjam_get($value, $name) : $value)];
170 }
171 }else{
172 $args[0] == 'option' && array_shift($args);
173
174 return WPJAM_Option_Setting::get_instance(...$args); // �
175 �容
176 }
177 }
178
179 // JSON
180 function wpjam_register_json($name, $args=[]){
181 return WPJAM_JSON::register($name, $args);
182 }
183
184 function wpjam_register_api($name, $args=[]){
185 return wpjam_register_json($name, $args);
186 }
187
188 function wpjam_get_json(...$args){
189 $output = $args ? (in_array($args[0], ['name', 'object'], true) ? array_shift($args) : 'object') : 'name';
190 $name = $args ? $args[0] : WPJAM_JSON::get_current();
191
192 return $output === 'name' ? $name : WPJAM_JSON::get($name);
193 }
194
195 function wpjam_parse_json_module($module){
196 return wpjam_catch('WPJAM_JSON::parse_module', $module);
197 }
198
199 function wpjam_is_json_request(){
200 return get_option('permalink_structure')
201 ? (bool)preg_match("/\/api\/.*\.json/", $_SERVER['REQUEST_URI'])
202 : (($_GET['module'] ?? '') == 'json');
203 }
204
205 function wpjam_json_source($name, $cb, $query_args=['source_id']){
206 ($name == wpjam_param('source')) && add_filter('wpjam_pre_json', fn($pre)=> is_array($result = $cb(wpjam_param($query_args))) ? $result : $pre);
207 }
208
209 // Meta Type
210 function wpjam_register_meta_type($name, $args=[]){
211 $global = $args['global'] ?? false;
212 $table = $args['table_name'] ?? $name.'meta';
213 $global && wp_cache_add_global_groups($name.'_meta');
214
215 $GLOBALS['wpdb']->$table ??= $args['table'] ?? $GLOBALS['wpdb']->{$global ? 'base_prefix' : 'prefix'}.$name.'meta';
216
217 return WPJAM_Meta_Type::register($name, $args);
218 }
219
220 function wpjam_get_meta_type($name){
221 return WPJAM_Meta_Type::get($name);
222 }
223
224 function wpjam_register_meta_option($type, $name, $args){
225 return wpjam_call_method(wpjam_get_meta_type($type), 'call_option', $name, $args);
226 }
227
228 function wpjam_unregister_meta_option($type, $name){
229 return wpjam_call_method(wpjam_get_meta_type($type), 'call_option', '-'.$name);
230 }
231
232 function wpjam_get_meta_options($type, $args=[]){
233 return wpjam_call_method(wpjam_get_meta_type($type), 'get_options', $args) ?: [];
234 }
235
236 function wpjam_get_meta_option($type, $name, $output='object'){
237 $option = wpjam_call_method(wpjam_get_meta_type($type), 'call_option', $name);
238
239 return $output == 'object' ? $option : ($option ? $option->to_array() : []);
240 }
241
242 function wpjam_get_by_meta($type, $key, $value=null, $column=null){
243 return wpjam_call_method(wpjam_get_meta_type($type), 'get_by_key', $key, $value, $column) ?: [];
244 }
245
246 function wpjam_get_metadata($type, $object_id, ...$args){
247 return wpjam_call_method(wpjam_get_meta_type($type), 'get_data_with_default', $object_id, ...$args);
248 }
249
250 function wpjam_update_metadata($type, $object_id, $key, ...$args){
251 return wpjam_call_method(wpjam_get_meta_type($type), 'update_data_with_default', $object_id, $key, ...$args);
252 }
253
254 function wpjam_delete_metadata($type, $object_id, $key){
255 return $key && array_map(fn($k)=> wpjam_call_method(wpjam_get_meta_type($type), 'delete_data', $object_id, $k), (array)$key) || true;
256 }
257
258 // Post Type
259 function wpjam_register_post_type($name, $args=[]){
260 return WPJAM_Post_Type::register($name, $args+['_jam'=>true]);
261 }
262
263 function wpjam_get_post_type_object($name){
264 return WPJAM_Post_Type::get(is_numeric($name) ? get_post_type($name) : $name);
265 }
266
267 function wpjam_add_post_type_field($type, $key, ...$args){
268 return wpjam_get_post_type_object($type)->add_field($key, ...$args);
269 }
270
271 function wpjam_remove_post_type_field($type, $key){
272 wpjam_get_post_type_object($type)->remove_field($key);
273 }
274
275 function wpjam_get_post_type_setting($type, $key, $default=null){
276 return ($object = wpjam_get_post_type_object($type)) ? ($object->$key ?? $default) : $default;
277 }
278
279 function wpjam_update_post_type_setting($type, $key, $value){
280 if($object = wpjam_get_post_type_object($type)){
281 return $object->$key = $value;
282 }
283 }
284
285 // Post Option
286 function wpjam_register_post_option($meta_box, $args=[]){
287 return wpjam_register_meta_option('post', $meta_box, $args);
288 }
289
290 function wpjam_unregister_post_option($meta_box){
291 wpjam_unregister_meta_option('post', $meta_box);
292 }
293
294 function wpjam_get_post_options($type='', $args=[]){
295 return wpjam_get_meta_options('post', array_filter(['post_type'=>$type])+$args);
296 }
297
298 function wpjam_get_post_option($name, $output='object'){
299 return wpjam_get_meta_option('post', $name, $output);
300 }
301
302 // Post Column
303 function wpjam_register_posts_column($name, ...$args){
304 return is_admin() ? wpjam_register_list_table_column($name, ['data_type'=>'post_type']+(is_array($args[0]) ? $args[0] : array_combine(['title', 'callback'], $args))) : null;
305 }
306
307 // Post
308 function wpjam_get_post($post, $args=[], $output=null){
309 $object = WPJAM_Post::get_instance($post, is_array($args) || $args === 'object' ? null : $args);
310
311 return ($output ?? $args) === 'object' ? $object : wpjam_call_method($object, 'parse_for_json', is_array($args) ? $args : []);
312 }
313
314 function wpjam_get_post_object($post, $type=null){
315 return $post ? wpjam_get_post($post, $type, 'object') : null;
316 }
317
318 function wpjam_validate_post($value, $type=null){
319 return WPJAM_Post::validate($value, $type);
320 }
321
322 function wpjam_get_posts($vars, ...$args){
323 [$args, $parse] = $args && is_array($args[0]) ? array_pad($args, 2, true) : [[], $args[0] ?? false];
324
325 if(is_scalar($vars) || wp_is_numeric_array($vars)){
326 $ids = wp_parse_id_list($vars);
327 $posts = WPJAM_Post::get_by_ids($ids);
328
329 return $parse ? wpjam_array($ids, fn($k, $v)=> [null, wpjam_get_post($v, $args) ?: null], true) : $posts;
330 }
331
332 return wpjam_query('parse', $vars, ['parse'=>$parse]+$args);
333 }
334
335 function wpjam_get_post_views($post=null){
336 return ($post = get_post($post)) ? (int)get_post_meta($post->ID, 'views', true) : 0;
337 }
338
339 function wpjam_update_post_views($post=null, $offset=1){
340 return ($post = get_post($post)) ? wpjam_tap(wpjam_get_post_views($post)+$offset, fn($views)=> update_post_meta($post->ID, 'views', $views)) : false;
341 }
342
343 function wpjam_get_post_excerpt($post=null, $length=0, $more=null){
344 if(!($post = get_post($post)) || $post->post_excerpt || is_serialized($post->post_content)){
345 return $post ? wp_strip_all_tags($post->post_excerpt, true) : '';
346 }
347
348 $excerpt = wpjam_call_with_suppress([
349 ['the_content', 'wp_filter_content_tags', 12],
350 ['the_content', 'do_blocks', 9],
351 ['the_content', 'do_shortcode', 11]
352 ], 'wpjam_get_post_content', $post);
353
354 return mb_strimwidth(
355 wp_strip_all_tags(excerpt_remove_footnotes(excerpt_remove_blocks(strip_shortcodes($excerpt))), true),
356 0,
357 ($length ?: apply_filters('excerpt_length', 200)),
358 ($more ?? apply_filters('excerpt_more', ' &hellip;')),
359 'utf-8'
360 );
361 }
362
363 function wpjam_get_post_content($post=null, $raw=false){
364 return ($post = get_post($post)) ? ($raw
365 ? get_the_content('', false, $post)
366 : apply_filters('the_content', str_replace(']]>', ']]&gt;', get_the_content('', false, $post)))
367 ) : '';
368 }
369
370 function wpjam_get_post_first_image_url($post=null, $size='full'){
371 foreach(($post = get_post($post)) && $post->post_content ? [
372 ['/class=[\'"].*?wp-image-([\d]*)[\'"]/i', 'wp_get_attachment_image_url'],
373 ['/<img.*?src=[\'"](.*?)[\'"].*?>/i', 'wpjam_get_thumbnail'],
374 ] : [] as [$regex, $cb]){
375 if(preg_match($regex, $post->post_content, $m)){
376 return $cb($m[1], $size);
377 }
378 }
379
380 return '';
381 }
382
383 function wpjam_get_post_thumbnail_url($post=null, $size='full', $crop=1){
384 foreach(($post = get_post($post)) ? ['thumbnail', 'images', 'filter'] : [] as $k){
385 if($k == 'thumbnail'){
386 $v = post_type_supports($post->post_type, $k) ? get_the_post_thumbnail_url($post->ID, 'full') : '';
387 }else{
388 $v = $k == 'images' ? array_first(wpjam_get_post_images($post, false)) : apply_filters('wpjam_post_thumbnail_url', '', $post);
389 }
390
391 if($v){
392 return wpjam_get_thumbnail($v, ($size ?: (wpjam_get_post_type_setting($post->post_type, 'thumbnail_size') ?: 'thumbnail')), $crop);
393 }
394 }
395
396 return '';
397 }
398
399 function wpjam_get_post_images($post=null, $args=[]){
400 $images = ($post = get_post($post)) && post_type_supports($post->post_type, 'images') ? get_post_meta($post->ID, 'images', true) : [];
401
402 return (!$images || $args === false)
403 ? ($images ?: [])
404 : wpjam_get_post_type_object($post->post_type)->parse_images($images, $args+['post_id'=>$post->ID]);
405 }
406
407 function wpjam_get_post_id_field($type='post', $args=[]){
408 return WPJAM_Post::get_field(['post_type'=> $type]+$args);
409 }
410
411 // Query
412 function wpjam_query($vars, ...$args){
413 if($vars === 'data_type'){
414 $name = wpjam_pull($args[0], 'data_type');
415 $args = wp_parse_args(($args[0]['query_args'] ?? $args[0]) ?: [])+wpjam_pull($args[0], ['search']);
416
417 return ['items'=>[wpjam_get_data_type($name, $args) ?: wpjam_throw('invalid_data_type'), 'query_items']($args)];
418 }
419
420 $type = is_string($vars) && !method_exists('WPJAM_Query', $vars) ? $vars : '';
421 $vars = $type ? array_shift($args) : (is_bool($vars) ? ($vars ? 'parse' : 'render') : $vars);
422 $object = WPJAM_Query::get_instance($type ?: 'post');
423
424 return is_string($vars) ? $object->$vars(...$args) : $object->query($vars, ...$args);
425 }
426
427 function wpjam_parse_query_vars($vars, $param=false){
428 return ($param || !wpjam_is_json_request()) ? wpjam_query('parse_vars', $vars, $param) : $vars;
429 }
430
431 function wpjam_get_query_var($key, $wp=null){
432 return ($wp ?: $GLOBALS['wp'])->query_vars[$key] ?? null;
433 }
434
435 // $number
436 // $post_id, $args
437 function wpjam_get_related_posts_query($post, ...$args){
438 return wpjam_query(['related_query'=>true, 'post'=>($args ? $post : null)], ($args ? $args[0] : ['number'=>$post]));
439 }
440
441 function wpjam_get_related_posts($post=null, $args=[], $parse=false){
442 return wpjam_query($parse, ['post'=>$post, 'related_query'=>true], $args);
443 }
444
445 function wpjam_get_new_posts($args=[], $parse=false){
446 return wpjam_query($parse, ['posts_per_page'=>5, 'orderby'=>'date'], $args);
447 }
448
449 function wpjam_get_top_viewd_posts($args=[], $parse=false){
450 return wpjam_query($parse, ['posts_per_page'=>5, 'orderby'=>'meta_value_num', 'meta_key'=>'views'], $args);
451 }
452
453 function wpjam_pagenavi($total=0, $display=true){
454 return wpjam_echo('<div class="pagenavi">'.paginate_links(array_filter(['prev_text'=>'&laquo;', 'next_text'=>'&raquo;', 'total'=>$total])).'</div>', $display);
455 }
456
457 // Taxonomy
458 function wpjam_register_taxonomy($name, ...$args){
459 return WPJAM_Taxonomy::register($name, (count($args) == 2 ? ['object_type'=>$args[0]]+$args[1] : $args[0])+['_jam'=>true]);
460 }
461
462 function wpjam_get_taxonomy($name){
463 return WPJAM_Taxonomy::get(is_numeric($name) ? get_term_field('taxonomy', $name) : $name);
464 }
465
466 function wpjam_add_taxonomy_field($tax, $key, ...$args){
467 return wpjam_get_taxonomy($tax)->add_field($key, ...$args);
468 }
469
470 function wpjam_remove_taxonomy_field($tax, $key){
471 wpjam_get_taxonomy($tax)->remove_field($key);
472 }
473
474 function wpjam_get_taxonomy_setting($tax, $key, $default=null){
475 return ($object = wpjam_get_taxonomy($tax)) ? ($object->$key ?? $default) : $default;
476 }
477
478 function wpjam_update_taxonomy_setting($tax, $key, $value){
479 if($object = wpjam_get_taxonomy($tax)){
480 return $object->$key = $value;
481 }
482 }
483
484 if(!function_exists('taxonomy_supports')){
485 function taxonomy_supports($tax, $feature){
486 return (bool)wpjam_call_method(wpjam_get_taxonomy($tax), 'supports', $feature);
487 }
488 }
489
490 if(!function_exists('add_taxonomy_support')){
491 function add_taxonomy_support($tax, $feature){
492 return wpjam_call_method(wpjam_get_taxonomy($tax), 'add_support', $feature);
493 }
494 }
495
496 if(!function_exists('remove_taxonomy_support')){
497 function remove_taxonomy_support($tax, $feature){
498 return wpjam_call_method(wpjam_get_taxonomy($tax), 'remove_support', $feature);
499 }
500 }
501
502 function wpjam_get_taxonomy_query_key($tax){
503 return ['category'=>'cat', 'post_tag'=>'tag_id'][$tax] ?? $tax.'_id';
504 }
505
506 function wpjam_get_term_id_field($tax='category', $args=[]){
507 return WPJAM_Term::get_field(['taxonomy'=>$tax]+$args);
508 }
509
510 // Term Option
511 function wpjam_register_term_option($name, $args=[]){
512 return wpjam_register_meta_option('term', $name, $args);
513 }
514
515 function wpjam_unregister_term_option($name){
516 wpjam_unregister_meta_option('term', $name);
517 }
518
519 function wpjam_get_term_options($tax='', $args=[]){
520 return wpjam_get_meta_options('term', array_filter(['taxonomy'=>$tax])+$args);
521 }
522
523 function wpjam_get_term_option($name, $output='object'){
524 return wpjam_get_meta_option('term', $name, $output);
525 }
526
527 // Term Column
528 function wpjam_register_terms_column($name, ...$args){
529 return is_admin() ? wpjam_register_list_table_column($name, ['data_type'=>'taxonomy']+(is_array($args[0]) ? $args[0] : array_combine(['title', 'callback'], $args))) : null;
530 }
531
532 // Term
533 function wpjam_get_term($term, $args=[], $output=null){
534 $object = WPJAM_Term::get_instance($term, is_array($args) ? wpjam_pull($args, 'taxonomy') : ($args === 'object' ? null : $args));
535
536 return ($output ?? $args) === 'object' ? $object : wpjam_call_method($object, 'parse_for_json', is_array($args) ? $args : []);
537 }
538
539 function wpjam_get_term_object($term, $tax=''){
540 return wpjam_get_term($term, $tax, 'object');
541 }
542
543 function wpjam_validate_term($value, $tax=null){
544 return WPJAM_Term::validate($value, $tax);
545 }
546
547 function wpjam_get_terms($vars, ...$args){
548 if(is_scalar($vars) || wp_is_numeric_array($vars)){
549 $terms = WPJAM_Term::get_by_ids(wp_parse_id_list($vars));
550
551 return $args && $args[0] ? array_map('wpjam_get_term', $terms) : $terms;
552 }
553
554 $args = $args[0] ?? [];
555
556 return wpjam_query('term', $vars, is_numeric($args)
557 ? ['depth'=>$args]
558 : (is_bool($args) ? ['parse'=>$args] : (is_array($args) ? $args : []))
559 );
560 }
561
562 function wpjam_get_all_terms($tax){
563 return get_terms(['suppress_filter'=>true, 'taxonomy'=>$tax, 'hide_empty'=>false, 'orderby'=>'none', 'get'=>'all']);
564 }
565
566 function wpjam_get_term_thumbnail_url($term=null, $size='full', $crop=1){
567 $term = get_term($term ?? get_queried_object());
568 $thumb = $term ? (get_term_meta($term->term_id, 'thumbnail', true) ?: apply_filters('wpjam_term_thumbnail_url', '', $term)) : '';
569
570 return $thumb ? wpjam_get_thumbnail($thumb, ($size ?: (wpjam_get_taxonomy_setting($term->taxonomy, 'thumbnail_size') ?: 'thumbnail')), $crop) : '';
571 }
572
573 if(!function_exists('get_term_taxonomy')){
574 function get_term_taxonomy($id){
575 return get_term_field('taxonomy', $id);
576 }
577 }
578
579 if(!function_exists('get_term_level')){
580 function get_term_level($id){
581 return ($term = wpjam_trap('get_term', $id, null)) ? ($term->parent ? count(get_ancestors($term->term_id, $term->taxonomy, 'taxonomy')) : 0) : null;
582 }
583 }
584
585 if(!function_exists('get_term_depth')){
586 function get_term_depth($id){
587 if($tax = wpjam_trap('get_term_taxonomy', $id, null)){
588 $id = get_term($id)->term_id;
589 $max = array_reduce(get_term_children($id, $tax), fn($m, $c)=> max($m, count(get_ancestors($c, $tax, 'taxonomy'))), 0);
590
591 return $max ? $max - get_term_level($id) : 0;
592 }
593 }
594 }
595
596 // User
597 function wpjam_get_user($user, $size=96, $output=null){
598 $object = WPJAM_User::get_instance($user);
599
600 return ($output ?? $size) === 'object' ? $object : wpjam_call_method($object, 'parse_for_json', $size);
601 }
602
603 function wpjam_get_user_object($user){
604 return wpjam_get_user($user, 'object');
605 }
606
607 if(!function_exists('get_user_field')){
608 function get_user_field($field, $user=null, $context='display'){
609 return (($user = get_userdata($user)) && isset($user->$field)) ? sanitize_user_field($field, $user->$field, $user->ID, $context) : '';
610 }
611 }
612
613 function wpjam_get_authors($args=[]){
614 return WPJAM_User::get_authors($args);
615 }
616
617 function wpjam_get_current_user($required=false){
618 $value = wpjam_var('user', fn()=> apply_filters('wpjam_current_user', null));
619
620 return $required ? (is_null($value) ? new WP_Error('bad_authentication') : $value) : wpjam_if_error($value, null);
621 }
622
623 // Bind
624 function wpjam_get_bind($type, $appid){
625 return WPJAM_Bind::get($type.':'.$appid) ?: WPJAM_Bind::register((($model = $type.'_bind') && class_exists($model)
626 ? new $model($appid)
627 : new WPJAM_Bind($type, $appid)
628 ));
629 }
630
631 // User Signup
632 function wpjam_register_user_signup($name, $args){
633 return WPJAM_User_Signup::create($name, $args);
634 }
635
636 function wpjam_get_user_signups($args=[], $output='objects', $operator='and'){
637 return WPJAM_User_Signup::get_registereds($args, $output, $operator);
638 }
639
640 function wpjam_get_user_signup($name){
641 return WPJAM_User_Signup::get($name);
642 }
643
644 // Comment
645 if(!function_exists('get_comment_parent')){
646 function get_comment_parent($comment_id){
647 return ($comment = get_comment($comment_id)) ? $comment->comment_parent : null;
648 }
649 }
650
651 // Widget
652 function wpjam_register_widget($id, $name, $options){
653 wpjam_load('widgets_init', fn()=> register_widget(new WPJAM_Widget($id, $name, $options)));
654 }
655
656 // Shortcode
657 function wpjam_do_shortcode($content, $tags){
658 return ($tags = array_filter($tags, fn($t)=> str_contains($content, '['.$t)))
659 ? preg_replace_callback('/'.get_shortcode_regex($tags).'/', 'do_shortcode_tag', $content)
660 : $content;
661 }
662
663 function wpjam_parse_shortcode_attr($str, $tag){
664 return preg_match('/'.get_shortcode_regex((array)$tag).'/', $str, $m) ? shortcode_parse_atts($m[3]) : [];
665 }
666
667 // File
668 function wpjam_url($dir, $scheme=null){
669 $path = str_replace([rtrim(ABSPATH, '/'), '\\'], ['', '/'], $dir);
670
671 return $scheme == 'relative' ? $path : site_url($path, $scheme);
672 }
673
674 function wpjam_dir($url){
675 return ABSPATH.str_replace(site_url('/'), '', $url);
676 }
677
678 function wpjam_file(...$args){
679 $object = WPJAM_File::get_instance();
680
681 return $args ? (method_exists($object, $args[0]) ? [$object, array_shift($args)] : $object)(...$args) : $object;
682 }
683
684 function wpjam_mimes($accept){
685 return wpjam_file('mimes', $accept);
686 }
687
688 function wpjam_upload($name, $args=[]){
689 return wpjam_file('upload', $name, $args);
690 }
691
692 function wpjam_download_url($url, $name='', $media=true, $post_id=0){
693 return wpjam_file('download', $url, is_array($name) ? $name : compact('name', 'media', 'post_id'));
694 }
695
696 function wpjam_get_file_data($file, $type='data'){
697 return wpjam_file('parse', $file, $type);
698 }
699
700 function wpjam_is_external_url($url, $scene=''){
701 $host = '//'.explode('//', site_url(), 2)[1];
702
703 return apply_filters('wpjam_is_external_url', array_all(['http:', 'https:', ''], fn($v)=> !str_starts_with($url, $v.$host)), $url, $scene);
704 }
705
706 function wpjam_media($name, $args=[]){
707 $result = wpjam_upload($name ?: 'media', $args);
708 $media = $args['media'] ?? false;
709
710 return [(($args['output'] ?? '') ?: 'url') => add_query_arg(
711 wpjam_image($media ? $result : $result['file'], 'size') ?: [],
712 $media ? wp_get_attachment_url($result) : $result['url']
713 )];
714 }
715
716 function wpjam_image($img, $type=''){
717 if($type == 'query'){
718 return wpjam_map(wp_parse_args(parse_url($img, PHP_URL_QUERY)), fn($v, $k)=> in_array($k, ['width', 'height']) ? (int)$v : $v);
719 }elseif($type == 'size'){
720 $size = wpjam_file($img, 'size', is_numeric($img) ? 'id' : (str_starts_with($img, 'http') ? 'url' : 'file'));
721
722 return $size ? array_map('intval', $size)+['orientation'=> $size['height'] > $size['width'] ? 'portrait' : 'landscape'] : $size;
723 }
724 }
725
726 function wpjam_is_image($img, $type=''){
727 return ($type == 'id' || (!$type && is_numeric($img)))
728 ? wp_attachment_is_image($img)
729 : preg_match('/\.('.implode('|', wp_get_ext_types()['image']).')$/i', wpjam_suffix(explode('?', $img)[0], '-', '#'));
730 }
731
732 function wpjam_fetch_external_images(&$urls, $post_id=0){
733 $args = ['post_id'=>$post_id, 'media'=>(bool)$post_id, 'field'=>'url'];
734 $result = wpjam_fill($urls, fn($v)=> $v && wpjam_is_external_url($v, 'fetch') ? wpjam_if_error(wpjam_download_url($v, $args), '') : '');
735 $result = array_filter($result);
736 $urls = array_keys($result);
737
738 return array_values($result);
739 }
740
741 // 1. $img
742 // 2. $img, ['width'=>100, 'height'=>100] // 这个为最标准版本
743 // 3. $img, 100x100
744 // 4. $img, 100
745 // 5. $img, [100,100]
746 // 6. $img, 100, 100, $crop=1
747 // 7. $img, [100,100], $crop=1
748 function wpjam_get_thumbnail($img, ...$args){
749 $url = ($img && is_numeric($img)) ? wp_get_attachment_url($img) : $img;
750 $url = $url ? remove_query_arg(['orientation', 'width', 'height'], wpjam_zh_urlencode($url)) : $url;
751 $args = count($args) > 1 && is_numeric($args[0]) ? [array_slice($args, 0, 2), ...array_slice($args, 2)] : $args;
752 $size = (!$args || !$args[0]) ? [] : (isset($args[1]) ? ['crop'=>$args[1]] : [])+wpjam_parse_size($args[0], $args[2] ?? 1);
753
754 return $url ? apply_filters('wpjam_thumbnail', $url === 'args' ? '' : $url, $size) : '';
755 }
756
757 function wpjam_parse_size($size, $ratio=1){
758 $keys = ['width', 'height'];
759
760 if(is_numeric($size)){
761 $size = [$size];
762 }elseif(is_string($size)){
763 $set = wp_get_additional_image_sizes()[$size] ?? [];
764 $size = ($sep = $set ? '' : array_find(['*', 'x', 'X'], fn($v)=> str_contains($size, $v))) ? explode($sep, $size) : $size;
765 }
766
767 if(is_array($size)){
768 $size = wp_is_numeric_array($size) ? wpjam_array($keys, fn($i, $k)=>[$k, $size[$i] ?? 0]) : $size+array_fill_keys($keys, 0);
769 $size += ['crop'=>array_all($keys, fn($k)=> $size[$k])];
770 }else{
771 $name = $size == 'thumb' ? 'thumbnail' : (string)$size;
772 $args = ['thumbnail'=>[100, 100], 'medium'=>[300, 300], 'medium_large'=>[768, 0], 'large'=>[1024, 1024]][$name] ?? [];
773 $size = wpjam_map(
774 [...($args ? ['size_w', 'size_h'] : $keys), 'crop'],
775 fn($v, $k)=> $args ? (get_option($name.'_'.$v, null) ?? ($args[$k] ?? false)) : ($set[$v] ?? 0)
776 );
777
778 if($size[0] && !in_array($name, ['thumbnail', 'medium']) && ($cw = $GLOBALS['content_width'] ?? 0)){
779 $size[0] = min($cw*$ratio, $size[0]);
780 }
781
782 $size = array_combine([...$keys, 'crop'], $size);
783 }
784
785 return wpjam_fill($keys, fn($k)=> (int)$size[$k]*$ratio)+$size;
786 }
787
788 function wpjam_constrain_dimensions($size, $max){
789 $size = wpjam_parse_size($size);
790
791 if(($max[0] ?? '') && ($max[1] ?? '')){
792 $max = $size['width'] && $size['height'] ? wp_constrain_dimensions($size['width'], $size['height'], $max[0], $max[1]) : $max;
793 $size = array_merge($size, wpjam_fill(['width', 'height'], fn($k, $i)=> min($size[$k], $max[$i])));
794 }
795
796 return $size;
797 }
798
799 function wpjam_bits($str){
800 return 'data:'.finfo_buffer(finfo_open(), $str, FILEINFO_MIME_TYPE).';base64, '.base64_encode($str);
801 }
802
803 // Attr
804 function wpjam_attr($attr, $type=''){
805 return WPJAM_Attr::create($attr, $type);
806 }
807
808 function wpjam_is_bool_attr($attr){
809 return WPJAM_Attr::is_bool($attr);
810 }
811
812 // Tag
813 function wpjam_tag($tag='', $attr=[], $text=''){
814 return new WPJAM_Tag($tag, $attr, $text);
815 }
816
817 function wpjam_wrap($text, $wrap='', ...$args){
818 if($wrap === 'expandable'){
819 return wpjam_expandable($text, ...$args);
820 }
821
822 if((is_array($wrap) || is_closure($wrap))){
823 $text = is_callable($wrap) ? $wrap($text, ...$args) : $text;
824 $wrap = '';
825 }
826
827 return ($text instanceof WPJAM_Tag ? $text : wpjam_tag('', [], $text))->wrap($wrap, ...$args);
828 }
829
830 function wpjam_is_single_tag($tag){
831 return WPJAM_Tag::is_single($tag);
832 }
833
834 function wpjam_html_tag_processor($html, $query=null){
835 $proc = new WP_HTML_Tag_Processor($html);
836
837 return $proc->next_tag($query) ? $proc : null;
838 }
839
840 // Field
841 function wpjam_fields($fields, ...$args){
842 if($args && is_bool($args[0])){
843 return WPJAM_Fields::parse($fields, ...$args);
844 }
845
846 $echo = $args && $args[0] && wpjam_pull($args[0], 'echo', array_all(['data', 'value_callback', 'model', 'id'], fn($k)=> !array_key_exists($k, $args[0])));
847
848 return wpjam_echo(WPJAM_Fields::create($fields, ...$args), $echo);
849 }
850
851 function wpjam_field($field, ...$args){
852 if(is_array($field)){
853 $args = $args[0] ?? [];
854 $echo = wpjam_pull($field, 'echo') ?? wpjam_pull($args, 'echo');
855 $wrap = wpjam_pull($args, 'wrap_tag');
856 $object = WPJAM_Field::create($field);
857
858 return wpjam_echo(isset($wrap) ? $object->wrap($wrap, $args) : ($args ? $object->render($args) : $object), (bool)$echo);
859 }
860 }
861
862 function wpjam_parse_show_if($if){
863 return wp_is_numeric_array($if) && count($if) >= 2
864 ? array_combine(
865 count($if) == 2 ? ['key', 'value'] : ['key', 'compare', 'value'],
866 count($if) > 3 ? array_slice($if, 0, 3) : $if
867 )
868 : (is_array($if) && !empty($if['key']) ? $if : null);
869 }
870
871 function wpjam_form($fields, ...$args){
872 return wpjam_echo((is_object($fields) ? $fields : wpjam_fields($fields))->form(...$args), !is_array($args[0]));
873 }
874
875 function wpjam_button($object, $key=null, ...$args){
876 if($key === 'next'){
877 return [];
878 }
879
880 if(!$key && $object->next){
881 $button = ['next'=>'下一步'];
882 }else{
883 $button = maybe_callback($object->submit_text, ...[...$args, $object->name]) ?? (wp_strip_all_tags($object->title) ?: wp_strip_all_tags($object->page_title));
884
885 $button = is_array($button) ? $button : [$object->name=>$button];
886 }
887
888 $button = wpjam_map(array_filter($button), fn($v)=> is_array($v) ? $v : ['text'=>$v]);
889
890 return $key
891 ? ($button[$key] ?? wp_die('无效的提交按钮'))
892 : ($button ? wpjam_tag('p', ['submit'], implode(wpjam_map($button, fn($v, $k)=> get_submit_button($v['text'], $v['class'] ?? 'primary', $k, false)))) : wpjam_tag());
893 }
894
895 function wpjam_options($field, $args=[]){
896 $type = $args['type'] ??= (is_array($field) ? '' : 'select');
897 $items = wpjam_filter(is_array($field) ? $field : (wpjam($field) ?: []), $args['filter'] ?? []);
898
899 return wpjam_reduce($items, function($carry, $item, $opt, $args){
900 if(!is_array($item) && !is_object($item)){
901 $carry[$opt] = $item;
902 }elseif(!isset($item['options'])){
903 $title = ($args['title_field'] ?? '') ?: 'title';
904 $opt = wpjam_get($item, ($args['name_field'] ?? '') ?: 'name') ?: $opt;
905
906 $carry[$opt] = (($args['type'] ?? '') == 'select'
907 ? wpjam_pick($item, [$title])
908 : (($item['field'] ?? '') ?: [])+['label'=>($item[$title] ?? '')]
909 )+wpjam_pick($item, ['label', 'image', 'description', 'alias', 'fields', 'show_if']);
910 }
911
912 return $carry;
913 }, ($type == 'select' ? [''=>__('&mdash; Select &mdash;', 'wpjam')] : []), 'options', $args);
914 }
915
916 function wpjam_icon($icon){
917 return (is_array($icon) || is_object($icon))
918 ? (($k = wpjam_find(['dashicon', 'remixicon'], fn($k)=> wpjam_get($icon, $k))) ? wpjam_icon(wpjam_get($icon, $k)) : null)
919 : (str_starts_with($icon, 'ri-') ? wpjam_tag('i', $icon) : wpjam_tag('span', ['dashicons', wpjam_prefix($icon, 'dashicons-')]));
920 }
921
922 function wpjam_pattern($key, ...$args){
923 return $key ? wpjam('pattern', $key, ...($args ? [array_combine(['pattern', 'custom_validity'], $args)] : [])) : [];
924 }
925
926 // cache
927 function wpjam_cache($name, ...$args){
928 return (!$args || is_array($args[0])) ? WPJAM_Cache::create($name, ...$args) : WPJAM_Cache::remember($name, ...$args);
929 }
930
931 function wpjam_counts($name, $cb){
932 return WPJAM_Cache::remember($name, 'counts', $cb);
933 }
934
935 function wpjam_transient($name, $cb, $args=[], $global=false){
936 return WPJAM_Cache::remember($name, (bool)$global, $cb, $args);
937 }
938
939 function wpjam_increment($name, $max=0, $expire=86400, $global=false){
940 return wpjam_transient($name, fn($v)=> ($max && (int)$v >= $max) ? 1 : (int)$v+1, ['expire'=>$expire, 'force'=>'set'], $global);
941 }
942
943 function wpjam_lock($name, $expire=10, $group=false){
944 $group = is_bool($group) ? ($group ? 'site-' : '').'transient' : ($group ?: 'default');
945
946 return $expire == -1
947 ? wp_cache_delete($name, $group)
948 : (wp_cache_get($name, $group, true) || !wp_cache_add($name, 1, $group, $expire));
949 }
950
951 function wpjam_remaining($group, $max, $time, $count=true){
952 $group = explode(':', $group, 2);
953 $name = $group[1] ?? wpjam_visitor($group[0]);
954 $group = $group[0].'_limit';
955 $times = wp_cache_get($name, $group) ?: 0;
956
957 if(($rest = $max - $times) > 0){
958 $count && wp_cache_set($name, $times+1, $group, ($times+1 == $max && $time > 60) ? $time : 60);
959
960 return $rest;
961 }
962
963 return 0;
964 }
965
966 function wpjam_visitor($context=''){
967 return apply_filters('wpjam_visitor', '', $context)
968 ?: (function_exists('is_user_logged_in') && is_user_logged_in() ? 'user:'.get_current_user_id() : 'ip:'.wpjam_get_ip());
969 }
970
971 // Code
972 function wpjam_generate_verification_code($key, $group='default'){
973 return WPJAM_Cache::verification($group, $key);
974 }
975
976 function wpjam_verify_code($key, $code, $group='default'){
977 return WPJAM_Cache::verification($group, $key, $code);
978 }
979
980 // Deleted ids
981 function wpjam_deleted_ids($name, ...$args){
982 return WPJAM_Cache::deleted_ids($name, ...$args);
983 }
984
985 function wpjam_max_id($name, $clean=false){
986 return WPJAM_Cache::table($name, 'max_id', $clean);
987 }
988
989 function wpjam_table_status($name, $clean=false){
990 return WPJAM_Cache::table($name, 'status', $clean);
991 }
992
993 // LazyLoader
994 function wpjam_lazyloader($name, ...$args){
995 $object = WPJAM_Lazyloader::get_instance();
996
997 return in_array($name, ['queue', 'load']) ? $object->$name(...$args) : $object->loader($name, ...$args);
998 }
999
1000 function wpjam_lazyload($name, $ids){
1001 return wpjam_lazyloader('queue', $name, $ids);
1002 }
1003
1004 function wpjam_load_pending($name, $cb){
1005 wpjam_lazyloader('load', $name, $cb);
1006 }
1007
1008 // Notice
1009 function wpjam_add_admin_notice($notice, $blog_id=0){
1010 return WPJAM_Notice::add($notice, 'admin', $blog_id);
1011 }
1012
1013 function wpjam_add_user_notice($user_id, $notice){
1014 return WPJAM_Notice::add($notice, 'user', $user_id);
1015 }
1016
1017