hook( 'init' );
}
public function init() {
// Options
$raw_options = get_option( self::OPTION );
if ( ! is_array( $raw_options ) ) {
$raw_options = array();
}
if ( ! isset( $raw_options['key'] ) ) {
// Normally, we shouldn't set defaults, but the key is a
// generate-once deal, so we do that now if it does not exist.
$raw_options['key'] = md5( wp_generate_password( 128, true, true ) );
update_option( self::OPTION, $raw_options );
}
// Now grab the options, with defaults merged in
$this->options = $this->get_options();
// Cron job
if ( ! wp_next_scheduled( self::CRON_HOOK ) ) {
wp_schedule_event( current_time( 'timestamp' ), 'daily', self::CRON_HOOK );
}
// Standard hooks
$this->hook( 'map_meta_cap' );
$this->hook( 'admin_menu' );
$this->hook( 'save_post' );
$this->hook( 'post_updated_messages' );
$this->hook( 'clean_post_cache' );
$this->hook( 'wp_dashboard_setup' );
$this->hook( 'page_css_class' );
$this->hook( 'wp_list_pages' );
$this->hook( 'query' );
$this->hook( 'delete_post' );
$this->hook( 'current_screen' );
$this->hook( 'rest_api_init' );
// Custom callbacks
$this->hook( 'wp_trash_post', 'delete_post' );
$this->hook( 'load-post.php', 'load_post' );
$this->hook( 'load-post-new.php', 'load_post_new' );
$this->hook( self::CRON_HOOK, 'api_slurp' );
$this->hook( 'post_submitbox_misc_actions', 'submitbox_actions' );
$this->hook( 'admin_init', 'ajax_listener' );
$this->hook( 'post_type_link', 'page_link' );
$this->hook( 'wp_ajax_cws_wp_help_settings', 'ajax_settings' );
$this->hook( 'wp_ajax_cws_wp_help_reorder', 'ajax_reorder' );
$this->hook( 'enqueue_block_editor_assets', 20 );
if ( 'dashboard-submenu' != $this->get_option( 'menu_location' ) ) {
$this->admin_base = 'admin.php';
if ( 'bottom' != $this->get_option( 'menu_location' ) ) {
add_filter( 'custom_menu_order', '__return_true' );
$this->hook( 'menu_order' );
}
} else {
$this->admin_base = 'index.php';
}
$this->hook( 'page_attributes_dropdown_pages_args', 'page_attributes_dropdown' );
$this->hook( 'plugin_action_links_' . plugin_basename( $this->__FILE__ ), 'action_links' );
$this->hook( 'network_admin_plugin_action_links_' . plugin_basename( $this->__FILE__ ), 'action_links' );
// menu_order debug
// add_filter( 'the_title', function( $title, $post_id ) { $post = get_post( $post_id ); return $title . ' [' . $post->menu_order . ']'; }, 10, 2 );
// Register the wp-help post type
if ( current_user_can( $this->view_cap( 'read_posts' ) ) ) {
$this->register_post_type();
}
// Check for API requests
if ( isset( $_REQUEST['wp-help-key'] ) && $this->get_option( 'key' ) === $_REQUEST['wp-help-key'] ) {
$this->api_request();
}
// Debug:
// $this->api_slurp();
}
public function rest_api_init() {
register_rest_field(
self::POST_TYPE,
'is_default_doc',
array(
'get_callback' => function ( $doc ) {
return $this->is_default_doc( $doc['id'] );
},
'update_callback' => function ( $value, WP_Post $doc ) {
if ( $this->is_default_doc( $doc ) && ! $value ) {
$this->unset_default_doc();
} elseif ( $value ) {
$this->set_default_doc( $doc );
}
},
)
);
}
/**
* Enqueues block editor scripts.
*
* @return void
*/
public function enqueue_block_editor_assets() {
// Gutenberg.
if ( self::is_block_editor() && self::POST_TYPE === get_post_type() ) {
$asset = $this->include_file( '/dist/block-editor.asset.php' );
wp_enqueue_script( 'cws-wp-block-editor', $this->get_url() . 'dist/block-editor.js', $asset['dependencies'], $asset['version'], true );
wp_set_script_translations( 'cws-wp-block-editor', 'wp-help' );
wp_dequeue_style( 'twentytwenty-block-editor-styles' );
/**
* Fires after assets have been enqueued for the editing interface.
*/
do_action( 'cws_wp_help_editor_assets' );
}
}
/**
* Removes editor styles when our CPT edit screen is loaded.
*
* @param WP_Screen $screen The current screen
* @return void
*/
public function current_screen( $screen ) {
if ( $screen->base === 'post' && $screen->post_type === self::POST_TYPE ) {
remove_editor_styles();
}
}
protected function register_post_type() {
register_post_type( self::POST_TYPE,
array(
'label' => _x( 'Publishing Help', 'post type label', 'wp-help' ),
'public' => false,
'show_ui' => true,
'show_in_menu' => false,
'show_in_admin_bar' => true,
'show_in_rest' => true,
'hierarchical' => true,
'supports' => array( 'title', 'editor', 'revisions', 'page-attributes' ),
'map_meta_cap' => true,
'capabilities' => array(
// Normally requires 'edit_posts'
'read_posts' => $this->view_cap( 'read_posts' ),
// Normally requires 'edit_pages'
'read_private_posts' => $this->edit_cap( 'read_private_posts' ),
'edit_posts' => $this->edit_cap( 'edit_posts' ),
'publish_posts' => $this->edit_cap( 'publish_posts' ),
'edit_others_posts' => $this->edit_cap( 'edit_others_posts' ),
'create_posts' => $this->edit_cap( 'create_posts' ),
),
'labels' => array(
'name' => __( 'Help Documents', 'wp-help' ),
'singular_name' => __( 'Help Document', 'wp-help' ),
'add_new_item' => __( 'Add New Help Document', 'wp-help' ),
'edit_item' => __( 'Edit Help Document', 'wp-help' ),
'new_item' => __( 'New Help Document', 'wp-help' ),
'view_item' => __( 'View Help Document', 'wp-help' ),
'search_items' => __( 'Search Documents', 'wp-help' ),
'not_found' => __( 'No Help Documents Found', 'wp-help' ),
'not_found_in_trash' => __( 'No Help Documents found in Trash', 'wp-help' ),
'parent' => __( 'Parent Help Document', 'wp-help' ),
'add_new' => _x( 'Add New', 'i.e. Add new Help Document', 'wp-help' ),
'edit' => _x( 'Edit', 'i.e. Edit Help Document', 'wp-help' ),
'view' => _x( 'View', 'i.e. View Help Document', 'wp-help' ),
'filter_items_list' => __( 'Filter documents list', 'wp-help' ),
'items_list_navigation' => __( 'Documents list navigation', 'wp-help' ),
'items_list' => __( 'Documents list', 'wp-help' ),
'item_published' => __( 'Document published.', 'wp-help' ),
'item_published_privately' => __( 'Document published privately.', 'wp-help' ),
'item_reverted_to_draft' => __( 'Document reverted to draft.', 'wp-help' ),
'item_scheduled' => __( 'Document scheduled.', 'wp-help' ),
'item_updated' => __( 'Document updated.', 'wp-help' ),
),
)
);
}
protected function view_cap( $original_cap ) {
return apply_filters( 'cws_wp_help_view_documents_cap', 'edit_posts', $original_cap );
}
protected function edit_cap( $original_cap ) {
return apply_filters( 'cws_wp_help_edit_documents_cap', 'edit_pages', $original_cap );
}
protected function get_option_defaults() {
return apply_filters( 'cws_wp_help_option_defaults', array(
'h2' => _x( 'Publishing Help', 'h2 default title', 'wp-help' ),
'h3' => _x( 'Help Topics', 'h3 default title', 'wp-help' ),
'menu_location' => 'below-dashboard',
) );
}
protected function get_options() {
$raw_options = get_option( self::OPTION );
if ( ! is_array( $raw_options ) ) {
$raw_options = array();
}
return array_merge( $this->get_option_defaults(), $raw_options );
}
protected function get_cap( $cap ) {
$post_type_object = get_post_type_object( self::POST_TYPE );
if ( ! $post_type_object ) {
return 'do_not_allow';
}
return $post_type_object->cap->{$cap};
}
public function action_links( $links ) {
$links['donate'] = '' . __( 'Donate', 'wp-help' ) . '';
return $links;
}
public function inline_file( $path ) {
return file_get_contents( trailingslashit( $this->get_path() ) . $path );
}
public function wp_dashboard_setup() {
if ( current_user_can( $this->get_cap( 'read_posts' ) ) ) {
$this->help_topics_html = $this->get_help_topics_html();
if ( $this->help_topics_html ) {
wp_add_dashboard_widget( 'cws-wp-help-dashboard-widget', $this->get_option( 'h2' ), array( $this, 'dashboard_widget' ) );
}
}
}
public function dashboard_widget() {
$this->include_file( '/templates/dashboard-widget.php' );
}
public function delete_post( $post_id ) {
// If the default doc was deleted, unset it as default.
if ( self::POST_TYPE === get_post_type( $post_id ) && $this->is_default_doc( $post_id ) ) {
$this->unset_default_doc();
}
}
public function page_css_class( $classes, $page, $depth, $args, $current_page = null ) {
if ( ! $this->filter_wp_list_pages ) {
return $classes;
}
if ( $this->is_slurped( $page->ID ) ) {
$classes[] = 'cws-wp-help-is-slurped';
} else {
$classes[] = 'cws-wp-help-local';
}
return $classes;
}
public function wp_list_pages( $html ) {
if ( ! $this->filter_wp_list_pages ) {
return $html;
}
return preg_replace( '#
]+>#', '$0', $html );
}
public function query( $query ) {
if (
$this->filter_wp_list_pages_sql && // We are filtering
preg_match( '#^\s*SELECT\s+#', $query) && // This is a SELECT query
preg_match( '#post_type\s*=\s*([\'"])' . self::POST_TYPE . '\1#', $query ) // This is a query for our post type
) {
$query = preg_replace(
'#post_status\s*=\s*([\'"])private\1#', // We want private posts, but also:
"post_status IN('private','publish')", // Published ones too.
$query
);
$this->filter_wp_list_pages_sql = false;
}
return $query;
}
public function page_attributes_dropdown( $args, $post ) {
if ( self::POST_TYPE !== get_post_type( $post ) ) {
return $args;
}
$pages = get_pages( array(
'post_type' => self::POST_TYPE,
'child_of' => 0,
'parent' => 0,
'post_status' => 'publish',
'hierarchical' => false,
'meta_key' => '_cws_wp_help_slurp_source',
'meta_value' => $this->get_slurp_source_key(),
) );
$args['exclude'] = array();
foreach ( $pages as $p ) {
$args['exclude'][] = absint( $p->ID );
}
return $args;
}
public function clean_post_cache( $post_id, $post ) {
if ( self::POST_TYPE === $post->post_type ) {
wp_cache_delete( 'get_pages', 'posts' ); // See: http://core.trac.wordpress.org/ticket/21279
}
}
protected function explain_slurp( $id ) {
if ( current_user_can( 'manage_options' ) && ! current_user_can( 'edit_post', $id ) ) {
// Post is remote. Explain
echo ' ' . __( '— Remote document', 'wp-help' ) . '';
}
}
public function load_post() {
if ( isset( $_GET['post'] ) && self::POST_TYPE === get_post_type( $_GET['post'] ) ) {
$this->edit_enqueues();
}
}
public function load_post_new() {
if ( isset( $_GET['post_type'] ) && self::POST_TYPE === $_GET['post_type'] ) {
$this->edit_enqueues();
}
}
protected function edit_enqueues() {
wp_enqueue_script( 'jquery' );
$this->hook( 'admin_footer', 'edit_page_js' );
}
public function edit_page_js() {
$this->include_file( 'templates/edit-page-js.php' );
}
public function map_meta_cap( $caps, $cap, $user_id, $args ) {
if ( preg_match( '#^(delete|edit)_(post|page)$#', $cap ) ) {
if ( self::POST_TYPE !== get_post_type( $args[0] ) ) {
return $caps;
}
// If this belongs to the currently connected slurp source, disallow editing
if ( $this->is_slurped( $args[0] ) ) {
$caps = array( 'do_not_allow' );
}
}
return $caps;
}
protected function get_slurp_source_key() {
return substr( md5( $this->get_option( 'slurp_url' ) ), 0, 8 );
}
protected function is_slurped( $post_id ) {
return $this->get_slurp_source_key() === get_post_meta( $post_id, '_cws_wp_help_slurp_source', true );
}
public function api_slurp() {
if ( ! $this->get_option( 'slurp_url' ) ) {
return;
}
$result = wp_remote_get( add_query_arg( 'time', time(), $this->get_option( 'slurp_url' ) ) );
if ( $result['response']['code'] == 200 ) {
$topics = new WP_Query( array(
'post_type' => self::POST_TYPE,
'posts_per_page' => -1,
'post_status' => 'publish',
) );
$source_id_to_local_id = array();
if ( $topics->posts ) {
foreach ( $topics->posts as $p ) {
if ( $this->is_slurped( $p->ID ) && $source_id = get_post_meta( $p->ID, '_cws_wp_help_slurp_id', true ) ) {
$source_id_to_local_id[ $source_id ] = $p->ID;
}
}
}
$posts = json_decode( $result['body'] );
$source_post_ids = array();
// First pass: just insert whatever is missing, without fixing post_parent
foreach ( $posts as $p ) {
$p = (array) $p;
$source_post_ids[ absint( $p['ID'] ) ] = absint( $p['ID'] );
// These things are implied in the API, but we need to set them before inserting locally
$p['post_type'] = self::POST_TYPE;
$p['post_status'] = 'publish';
// $p['menu_order'] += 100000;
$copy = $p;
if ( isset( $source_id_to_local_id[ $p['ID'] ] ) ) {
// Exists. We know the local ID.
$copy['ID'] = $source_id_to_local_id[ $p['ID'] ];
wp_update_post( $copy );
} else {
// This is new. Insert it.
unset( $copy['ID'] );
$new_local_id = wp_insert_post( $copy );
// Update our lookup table
$source_id_to_local_id[ $p['ID'] ] = $new_local_id;
// Update postmeta
update_post_meta( $new_local_id, '_cws_wp_help_slurp_id', absint( $p['ID'] ) );
update_post_meta( $new_local_id, '_cws_wp_help_slurp_source', $this->get_slurp_source_key() );
}
}
// Set the default document
foreach ( $posts as $p ) {
if ( isset( $p->default ) && isset( $source_id_to_local_id[ $p->ID ] ) ) {
update_option( self::DEFAULT_DOC, $source_id_to_local_id[ $p->ID ] );
break;
}
}
// Delete any abandoned posts
$topics = new WP_Query( array(
'post_type' => self::POST_TYPE,
'posts_per_page' => -1,
'post_status' => 'any',
'meta_query' => array(
array(
'key' => '_cws_wp_help_slurp_id',
'value' => 0,
'compare' => '>',
'type' => 'NUMERIC',
),
),
) );
if ( $topics->posts ) {
foreach ( $topics->posts as $p ) {
if ( $source_id = get_post_meta( $p->ID, '_cws_wp_help_slurp_id', true ) ) {
// This was slurped. Was it absent from the API response? Or was it from a different source?
if ( ! $this->is_slurped( $p->ID ) || ! isset( $source_post_ids[ absint( $source_id ) ] ) ) {
// Wasn't in the response. Delete it.
wp_delete_post( $p->ID );
}
}
}
}
// Reparenting and link fixing
$topics = new WP_Query( array(
'post_type' => self::POST_TYPE,
'posts_per_page' => -1,
'post_status' => 'publish',
'meta_query' => array(
array(
'key' => '_cws_wp_help_slurp_id',
'value' => 0,
'compare' => '>',
'type' => 'NUMERIC',
),
),
) );
if ( $topics->posts ) {
foreach ( $topics->posts as $p ) {
$new = array();
if ( strpos( $p->post_content, 'http://wp-help-link/' ) !== false ) {
$new['post_content'] = $this->make_links_local( $p->post_content );
if ( $new['post_content'] === $p->post_content ) {
unset( $new['post_content'] );
}
}
$new['post_parent'] = $this->local_id_from_slurp_id( $p->post_parent );
if ( $new['post_parent'] === $p->post_parent ) {
unset( $new['post_parent'] );
}
if ( $new ) {
$new['ID'] = $p->ID;
wp_update_post( $new );
}
}
}
}
}
protected function api_request() {
if ( ! headers_sent() ) {
header( 'Content-Type: application/json; charset=' . get_option( 'blog_charset' ) );
}
die( json_encode( $this->get_topics_for_api() ) );
}
public function convert_links_cb( $matches ) {
if ( preg_match( '#page=wp-help-documents&(amp;)?document=([0-9]+)#', $matches[2], $url ) ) {
return 'href=' . $matches[1] . 'http://wp-help-link/' . $url[2] . $matches[1];
}
return $matches[0];
}
protected function convert_links( $content ) {
$content = preg_replace_callback( '#href=(["\'])([^\\1]+)\\1#', array( $this, 'convert_links_cb' ), $content );
$admin_url = parse_url( admin_url( '/' ) );
$content = preg_replace( '#(https?)://' . preg_quote( $admin_url['host'] . $admin_url['path'], '#' ) . '#', '', $content );
return $content;
}
public function make_links_local_cb( $matches ) {
$local_id = $this->local_id_from_slurp_id( $matches[2] );
if ( $local_id ) {
return 'href=' . $matches[1] . get_permalink( absint( $local_id ) ) . $matches[1];
}
return $matches[0];
}
protected function make_links_local( $content ) {
return preg_replace_callback( '#href=(["\'])http://wp-help-link/([0-9]+)\\1#', array( $this, 'make_links_local_cb' ), $content );
}
protected function local_id_from_slurp_id( $id ) {
if ( ! $id ) {
return false;
}
$local = new WP_Query( array(
'post_type' => self::POST_TYPE,
'posts_per_page' => 1,
'post_status' => 'publish',
'meta_query' => array(
array(
'key' => '_cws_wp_help_slurp_id',
'value' => $id,
),
),
) );
if ( $local->posts ) {
return $local->posts[0]->ID;
}
return false;
}
protected function get_topics_for_api() {
$topics = new WP_Query( array(
'post_type' => self::POST_TYPE,
'posts_per_page' => -1,
'post_status' => 'publish',
'orderby' => 'parent menu_order',
'order' => 'ASC',
) );
$default_doc = get_option( self::DEFAULT_DOC );
$menu_order = array();
foreach ( $topics->posts as $k => $post ) {
$c =& $topics->posts[ $k ];
unset( $c->guid, $c->post_author, $c->comment_count, $c->post_mime_type, $c->post_status, $c->post_type, $c->pinged, $c->to_ping, $c->filter, $c->ping_status, $c->comment_status, $c->post_password );
if ( isset( $menu_order[ $c->post_parent ] ) ) {
$menu_order[ $c->post_parent ]++;
} else {
$menu_order[ $c->post_parent ] = 1;
}
$c->menu_order = $menu_order[ $c->post_parent ];
if ( ! $c->post_parent ) {
unset( $c->post_parent );
}
$c->post_content = $this->convert_links( $c->post_content );
if ( $c->ID == $default_doc ) {
$c->default = true;
}
}
return $topics->posts;
}
public function menu_order( $menu ) {
$custom_order = array();
foreach ( $menu as $index => $item ) {
if ( 'index.php' == $item ) {
if ( 'below-dashboard' == $this->get_option( 'menu_location' ) ) {
$custom_order[] = 'index.php';
}
$custom_order[] = self::MENU_SLUG;
if ( 'above-dashboard' == $this->get_option( 'menu_location' ) ) {
$custom_order[] = 'index.php';
}
} elseif ( self::MENU_SLUG != $item ) {
$custom_order[] = $item;
}
}
return $custom_order;
}
protected function get_option( $key ) {
if ( 'menu_location' == $key && isset( $_GET['wp-help-preview-menu-location'] ) ) {
return $_GET['wp-help-preview-menu-location'];
}
return isset( $this->options[ $key ] ) ? $this->options[ $key ] : false;
}
protected function update_options( $options ) {
$this->options = $options;
update_option( self::OPTION, $options );
}
protected function api_url() {
return home_url( '/?wp-help-key=' . $this->get_option( 'key' ) );
}
public function ajax_settings() {
if ( current_user_can( 'manage_options' ) && check_ajax_referer( 'cws-wp-help-settings' ) ) {
$error = false;
$refresh = false;
$old_menu_location = $this->options['menu_location'];
$old_slurp_url = $this->options['slurp_url'];
$this->options['h2'] = stripslashes( $_POST['h2'] );
$this->options['h3'] = stripslashes( $_POST['h3'] );
$slurp_url = stripslashes( $_POST['slurp_url'] );
if ( $slurp_url === $this->api_url() ) {
$error = __( 'What are you doing? You’re going to create an infinite loop!', 'wp-help' );
} elseif ( empty( $slurp_url ) ) {
$this->options['slurp_url'] = '';
} elseif ( strpos( $slurp_url, '?wp-help-key=' ) === false ) {
$error = __( 'That is not a WP Help URL. Make sure you copied it correctly.', 'wp-help' );
} else {
$this->options['slurp_url'] = esc_url_raw( $slurp_url );
}
if ( $this->options['slurp_url'] !== $old_slurp_url && ! empty( $this->options['slurp_url'] ) ) {
$refresh = true;
}
if ( ! $error ) {
$this->options['menu_location'] = stripslashes( $_POST['menu_location'] );
}
$this->update_options( $this->options );
$result = array(
'slurp_url' => $this->options['slurp_url'],
'error' => $error,
);
if ( $refresh ) {
$this->api_slurp();
$result['topics'] = $this->get_help_topics_html( true );
} elseif ( ! empty( $this->options['slurp_url'] ) ) {
// It didn't change, but we should trigger an update in the background
wp_schedule_single_event( current_time( 'timestamp' ), self::CRON_HOOK );
}
die( json_encode( $result ) );
} else {
die( '-1' );
}
}
public function ajax_reorder() {
if ( current_user_can( $this->get_cap( 'publish_posts' ) ) && check_ajax_referer( 'cws-wp-help-reorder' ) ) {
$order = array();
foreach ( $_POST['order'] as $o ) {
$order[] = str_replace( 'page-', '', $o );
}
$val = -100000;
foreach ( $order as $o ) {
if ( 'cws-wp-help-remote-docs-block' === $o ) {
$val = 100000;
continue;
}
$val += 10;
if ( $p = get_page( $o ) ) {
if ( intval( $p->menu_order ) !== $val ) {
wp_update_post( array(
'ID' => $p->ID,
'menu_order' => $val,
) );
}
}
}
}
}
public function ajax_listener() {
if ( ! defined( 'DOING_AJAX' ) || ! DOING_AJAX || ! isset( $_POST['action'] ) || 'wp-link-ajax' != $_POST['action'] ) {
return;
}
// It's the right kind of request
// Now to see if it originated from our post type
$qs = parse_url( $_SERVER['HTTP_REFERER'], PHP_URL_QUERY );
wp_parse_str( $qs, $vars );
if ( isset( $vars['post_type'] ) ) {
$post_type = $vars['post_type'];
} elseif ( isset( $vars['post'] ) ) {
$post = get_post( $vars['post'] );
$post_type = $post->post_type;
} else {
// Can't determine post type. Bail.
return;
}
if ( self::POST_TYPE == $post_type ) {
// Nice! This originated from our post type
// Now we make our post type public, and initiate a query filter
// There really should be a better way to do this. :-\
$this->hook( 'pre_get_posts', 'only_query_help_docs' );
global $wp_post_types;
$wp_post_types[ self::POST_TYPE ]->publicly_queryable = $wp_post_types[ self::POST_TYPE ]->public = true;
}
}
public function only_query_help_docs( $q ) {
$q->set( 'post_type', self::POST_TYPE );
}
public function admin_menu() {
if ( 'dashboard-submenu' != $this->get_option( 'menu_location' ) ) {
$hook = add_menu_page( $this->get_option( 'h2' ), $this->get_option( 'h2' ), $this->get_cap( 'read_posts' ), self::MENU_SLUG, array( $this, 'render_listing_page' ), 'dashicons-editor-help' );
} else {
$hook = add_dashboard_page( $this->get_option( 'h2' ), $this->get_option( 'h2' ), $this->get_cap( 'read_posts' ), self::MENU_SLUG, array( $this, 'render_listing_page' ) );
}
$this->hook( "load-{$hook}", 'enqueue' );
}
public function submitbox_actions() {
if ( self::POST_TYPE !== get_post_type() ) {
return;
}
$this->include_file( 'templates/submitbox-actions.php' );
}
public function save_post( $post_id ) {
if ( isset( $_POST['_cws_wp_help_nonce'] ) && wp_verify_nonce( $_POST['_cws_wp_help_nonce'], 'cws-wp-help-save_' . $post_id ) ) {
if ( isset( $_POST['cws_wp_help_make_default_doc'] ) ) {
$this->set_default_doc( $post_id );
} elseif ( $this->is_default_doc( $post_id ) ) {
$this->unset_default_doc();
}
}
return $post_id;
}
public function get_default_doc() {
return absint( get_option( self::DEFAULT_DOC, 0 ) );
}
public function is_default_doc( $post = null ) {
$post = get_post( $post );
return $post->ID === $this->get_default_doc();
}
public function set_default_doc( $post ) {
$post = get_post( $post );
$id = absint( $post ? $post->ID : 0 );
return update_option( self::DEFAULT_DOC, $id );
}
public function unset_default_doc() {
return update_option( self::DEFAULT_DOC, 0 );
}
public function post_updated_messages( $messages ) {
global $post_ID, $post;
$permalink = get_permalink( $post_ID );
$messages[ self::POST_TYPE ] = array(
0 => '', // Unused. Messages start at index 1.
1 => sprintf( __( 'Document updated. View document', 'wp-help' ), esc_url( $permalink ) ),
2 => __( 'Custom field updated.', 'wp-help' ),
3 => __( 'Custom field deleted.', 'wp-help' ),
4 => __( 'Document updated.', 'wp-help' ),
5 => isset( $_GET['revision'] ) ? sprintf( __( 'Document restored to revision from %s', 'wp-help' ), wp_post_revision_title( (int) $_GET['revision'], false ) ) : false,
6 => sprintf( __( 'Document published. View document', 'wp-help' ), esc_url( $permalink ) ),
7 => __( 'Document saved.', 'wp-help' ),
8 => sprintf( __( 'Document submitted. Preview document', 'wp-help' ), esc_url( add_query_arg( 'preview', 'true', $permalink ) ) ),
9 => sprintf( __( 'Document scheduled for: %1$s. Preview document', 'wp-help' ), date_i18n( __( 'M j, Y @ G:i', 'wp-help' ), strtotime( $post->post_date ) ), esc_url( $permalink ) ),
10 => sprintf( __( 'Document draft updated. Preview document', 'wp-help' ), esc_url( add_query_arg( 'preview', 'true', $permalink ) ) ),
);
return $messages;
}
public function enqueue() {
wp_enqueue_style( 'cws-wp-help', $this->get_url() . 'dist/wp-help.css', array(), self::CSS_JS_VERSION );
$asset = $this->include_file( '/dist/index.asset.php' );
wp_enqueue_script( 'cws-wp-help', $this->get_url() . 'dist/index.js', array_merge( array( 'jquery', 'jquery-ui-sortable' ), $asset['dependencies'] ), $asset['version'] );
if ( function_exists( 'has_blocks' ) ) {
$document_id = $this->get_default_doc();
if ( isset( $_GET['document'] ) ) {
$document_id = absint( $_GET['document'] );
}
if ( has_blocks( $document_id ) ) {
wp_enqueue_style( 'wp-block-library' );
wp_enqueue_style( 'wp-block-library-theme' );
}
}
do_action( 'cws_wp_help_load' ); // Use this to enqueue your own styles for things like shortcodes.
}
public function maybe_just_menu() {
if ( isset( $_GET['wp-help-preview-menu-location'] ) ) {
$this->hook( 'in_admin_header', 'kill_it', 0 );
}
}
public function kill_it() {
exit();
}
public function admin_page_url() {
return admin_url( $this->admin_base . '?page=' . self::MENU_SLUG );
}
public function page_link( $link, $post ) {
$post = get_post( $post );
if ( self::POST_TYPE == $post->post_type ) {
return $this->admin_page_url() . '&document=' . absint( $post->ID );
} else {
return $link;
}
}
protected function get_help_topics_html( $with_sort_handles = false ) {
if ( $with_sort_handles ) {
$this->filter_wp_list_pages = true;
}
$this->filter_wp_list_pages_sql = true;
$status = ( current_user_can( $this->get_cap( 'read_private_posts' ) ) ) ? 'private' : 'publish';
$defaults = array(
'post_type' => self::POST_TYPE,
'post_status' => $status,
'hierarchical' => true,
'echo' => false,
'title_li' => '',
);
$output = trim( wp_list_pages( apply_filters( 'cws_wp_help_list_pages', $defaults ) ) );
$this->filter_wp_list_pages = $this->filter_wp_list_pages_sql = false;
return $output;
}
public function render_listing_page() {
$document_id = $this->get_default_doc();
if ( isset( $_GET['document'] ) ) {
$document_id = absint( $_GET['document'] );
}
if ( $document_id ) : ?>