Set A Cookie To URL Parameter, Pass Cookie From Page To Page To Alter Post
题
I have a function that makes the post multipage based on a URL Parameter with a specific value:
?content=multipage
The problem is that when a user clicks to the next page the URL parameter is stripped and the post resets to the onepage format.
If I manually add the URL parameter to the next page the post is multipage
From my research the best way to solve the problem is by setting a cookie when:
?content=multipage
That way this URL parameter gets passed on from page to page and it won't be visible in the address bar.
I tried multiple cookie setting methods, I found secookie ()
function that apparently should do the trick.
Here is my work so far:
function onepage() {
//**Removes shortcodes**//
function remove_shotcode($content) {
return str_replace('[/shortcode1]', '', $content);
return str_replace('[shortcode2]', '', $content);
}
add_filter( 'the_content', 'remove_shotcode');
/*
*Removes <!--nextpage-->
*@see http://wordpress.stackexchange.com/a/183587/26350
*/
add_action( 'the_post', function( $post )
{
if ( false !== strpos( $post->post_content, '<!--nextpage-->' ) )
{
// Reset the global $pages:
$GLOBALS['pages'] = [ $post->post_content ];
// Reset the global $numpages:
$GLOBALS['numpages'] = 0;
// Reset the global $multipage:
$GLOBALS['multipage'] = false;
}
});
}
//**IF Statement that should set the cookie**//
if ( empty( $_GET['content'] ) || "multipage" !== $_GET['content'] ) {
//**Only removes onepage() when content=multipage**//
add_action('wp','onepage');
//**Should set cookie only when content=multipage**//
setcookie( 'content', 'multipage', time()+3600, COOKIEPATH, COOKIE_DOMAIN );
}
The code that makes the post multipage is below:
//**PAGEBREAK SECTION - BEG**//
function pagebreak( $args = '' ) {
global $page, $numpages, $multipage, $more;
$defaults = array(
'before' => '<p class="post-nav-links">' . __( 'Pages:' ),
'after' => '</p>',
'link_before' => '',
'link_after' => '',
'aria_current' => 'page',
'next_or_number' => 'next',
'separator' => ' ',
'nextpagelink' => __( 'Next page' ),
'eog' => '<a href="http://127.0.0.1:10080/wordpress/">',
'previouspagelink' => __( 'Previous page' ),
'pagelink' => '%',
'echo' => 1,
);
$params = wp_parse_args( $args, $defaults );
/**
* Filters the arguments used in retrieving page links for paginated posts.
*
* @since 3.0.0
*
* @param array $params An array of arguments for page links for paginated posts.
*/
$r = apply_filters( 'wp_link_pages_args', $params );
$output = '';
if ( $multipage ) {
if ( 'number' == $r['next_or_number'] ) {
$output .= $r['before'];
for ( $i = 1; $i <= $numpages; $i++ ) {
$link = $r['link_before'] . str_replace( '%', $i, $r['pagelink'] ) . $r['link_after'];
if ( $i != $page || ! $more && 1 == $page ) {
$link = _wp_link_page( $i ) . $link . '</a>';
} elseif ( $i === $page ) {
$link = '<span class="post-page-numbers current" aria-current="' . esc_attr( $r['aria_current'] ) . '">' . $link . '</span>';
}
/**
* Filters the HTML output of individual page number links.
*
* @since 3.6.0
*
* @param string $link The page number HTML output.
* @param int $i Page number for paginated posts' page links.
*/
$link = apply_filters( 'wp_link_pages_link', $link, $i );
// Use the custom links separator beginning with the second link.
$output .= ( 1 === $i ) ? ' ' : $r['separator'];
$output .= $link;
}
$output .= $r['after'];
} elseif ( $more ) {
$output .= $r['before'];
$prev = $page - 1;
$next = $page + 1;
if ( $next <= $numpages ) {
if ( $prev ) {
$output .= $r['separator'];
}
$link = _wp_link_page( $next ) . $r['link_before'] . $r['nextpagelink'] . $r['link_after'] . '</a>';
/** This filter is documented in wp-includes/post-template.php */
$output .= apply_filters( 'wp_link_pages_link', $link, $next );
} elseif ( $next = $numpages ) {
$link = _wp_link_page( $next ) . $r['eog'] . $r['nextpagelink'] . $r['link_after'] . '</a>';
}
$output .= $r['after'];
}
}
/**
* Filters the HTML output of page links for paginated posts.
*
* @since 3.6.0
*
* @param string $output HTML output of paginated posts' page links.
* @param array $args An array of arguments.
*/
$html = apply_filters( 'wp_link_pages', $output, $args );
if ( $r['echo'] ) {
echo $html;
}
return $html;
}
/**
* Replace [nextpage] with <!--nextpage--> through the 'the_posts' filter.
*
* @see http://wordpress.stackexchange.com/a/183980/26350
*/
! is_admin() && add_filter( 'the_posts', function( $posts )
{
$posts = array_map( function( $p )
{
if ( false !== strpos( $p->post_content, '[pagebreak]' ) )
$p->post_content = str_replace( '[pagebreak]', '<!--nextpage-->', $p->post_content );
return $p;
}, $posts );
return $posts;
});
//**PAGEBREAK SECTION - END**//
I looked in the cookie list of my browser and apparently this does set the cookie content
to value multipage
.
However, it seems that it sets the cookie whether the URL has the URL parameter or not.
And when I go to the next page, the layout resets to onepage so I am assuming the site does not read the cookie.
Is it possible to store the ?content=multipage
in the cookie so that site becomes multipage
for that user or the ?content=multipage
has to be passed from page to page?
解决方案
I agree that passing the query string from one page to another page is the most reliable solution, and you can, for example, use filters like post_link
and term_link
to add the content
query string to post/category links.
However, it requires hooking to various filters like you can see here. And in addition, multi-page URLs like example.com/page/2?content=multipage
won't work without extra coding.
So it's probably better/easier for you to store the multi-page status in the browser's cookies, just as what you've attempted — the problem in your code is, that you're just setting the cookie, but nowhere reading it. And you can use $_COOKIE['content']
to read the cookie's value, just as you can see in the example below.
The Code/Solution
First off, remove this from your code:
//**IF Statement that should set the cookie**//
if ( empty( $_GET['content'] ) || "multipage" !== $_GET['content'] ) {
//**Only removes onepage() when content=multipage**//
add_action('wp','onepage');
setcookie( 'content', 'multipage', time()+3600, COOKIEPATH, COOKIE_DOMAIN );
}
And add the code after the //**PAGEBREAK SECTION - END**//
in your code:
add_action( 'init', 'set_check_content_cookie', 0 );
function set_check_content_cookie() {
if ( is_admin() ) {
return;
}
$is_multipage = false;
// If the query string "content" is not set, check if the "content" cookie value is exactly "multipage".
if ( ! isset( $_GET['content'] ) && isset( $_COOKIE['content'] ) && 'multipage' === $_COOKIE['content'] ) {
$is_multipage = true;
}
// If the query string "content" is set and its value is "multipage", set the cookie.
elseif ( isset( $_GET['content'] ) && 'multipage' === $_GET['content'] ) {
setcookie( 'content', 'multipage', time()+3600, COOKIEPATH, COOKIE_DOMAIN );
$is_multipage = true;
}
// Hook onepage() to `wp`, if applicable.
if ( ! $is_multipage ) {
add_action( 'wp', 'onepage' );
}
}
Note: You should remember that using this solution means that cookies must be enabled in the browser (i.e. supported and that the user is accepting cookies).