I am trying to separate out the different parts of my wordpress posts (at this point specifically the blockquote) so I can put them in different divs so I can put them on different parts of the page.
I have been able to remove the blockqoute and post the content without it, but couldn't put it back in
<div1>
<?php add_filter( 'the_content', 'rm_quotes' );
function rm_quotes($content) {
$content = preg_replace("~<blockquote>([\s\S]+?)</blockquote>~", "", $content);
return $content;
}
?>
</div1>
<div2>
<!-- This is where I want to put the <blockquote> -->
</div2>
Do a preg_match and put it into a variable called $quotes and then remove it from content with preg_replace. Now you can do whatever you want with the blockquotes that were removed.
example code:
preg_match('/<blockquote>([\s\S]+?)</blockquote>/', $content, $quotes);
var_dump($quotes);
Related
I'm trying to make a custom RSS feed with some alteration to the HTML content of each post.
Inside the template file rss-custom.php I have this:
<?php while (have_posts()) : the_post(); ?>
<?php echo processPostContent(); ?>
<?php endwhile; ?>
in functions.php, there are three replacements as follows :
function processPostContent() {
$post = get_post(get_the_ID());
$post_content = strval($post->post_content);
// replace h3 and h4 tags with h2
$post_content = preg_replace('/<(\/?)h((?![12])\d)/im', "<$1h2", $post_content);
// strip every attribute of <img> other than src
$post_content = preg_replace('/<img[^>]*(src="[^"]*")[^>]*>/im', "<img $1 />", $post_content);
// insert text after some closing tags
$post_content = preg_replace('/<\/(h2|p|figure)>/im', "</$1><p>Inserted</p>", $post_content);
return $post_content;
}
Then I get a strange result: out of 20 posts, only 7-8 of them will have been fully replaced. The remaining get the first two replacements but not the third one. Does anyone know why that is?
The solution, turns out, doesn't have anything to do with the loop nor preg_replace. Some posts' contents do not include any HTML tag, only plain text. That's why preg_replace didn't have any effect on them. When those contents are rendered in the RSS feed, however, <p> tags are automatically inserted. That's what led me to believe the third replacement was skipped.
First paragraph.
Second paragraph.
is turned to
<p>First paragraph.</p>
<p>Second paragraph.</p>
I want to remove a div added by a plugin to the content of WordPress posts. So the post has this structure:
<div class="post">
<div class="some-class">
<p>content</p>
</div>
</div>
I want to remove <div class="some-class"> and its closing </div> but leave the content. So it would be:
<div class="post">
<p>content</p>
</div>
using this filter:
add_filter( 'the_content', 'remove_class' , 100 );
function remove_class( $content ) {
$content = preg_replace('#<div[^>]*class="some-class"[^>]*>.*?</div>#is', '', $content);
return $content;
}
the content is also deleted, I just want the div and the closing div to be deleted. Any idea how?
this question is not duplicate of the other question because I want to remove a specific div not just all divs
You could just try to remove class attribute, so that only <div> is left, using code like this:
add_filter( 'the_content', 'remove_class' , 100 );
function remove_class( $content ) {
$content = preg_replace('/class=".*?"/', '', $content);
return $content;
}
#user7592255 you can try with jQuery like this:
$('p').unwrap();
If you can set an id or class on the p element you can target it more accurately
The content is removed because you replace the entire matched string with an empty string. Use a subpattern to capture the content of the <div> element and use it as replacement:
$content = preg_replace(
'#<div[^>]*class="some-class"[^>]*>(.*?)</div>#is',
'$1',
$content
);
However, be aware that it won't work properly if the content of <div class="some-class"> contains a <div> element.
There is no way to parse HTML using regex. The correct solution is to use an HTML parser (DOMDocument f.e.) to parse the HTML fragment and create its DOM, then operate the changes on the DOM and render it back to HTML.
I am calling in content in Wordpress via the below code. Eseentially, I am dividing the content of the post into three sections; 1. Before the tag, 2. After the tag and 3. Post gallery. The code I have so far works perfectly to get the content, however I am having an issue as all formatting tags (p in particular) are being stripped. Is there a way to retain these?
Thanks
<?php
// Fetch post content
$content = get_post_field( 'post_content', get_the_ID() );
// Get content parts
$content_parts = get_extended( $content );
?>
<p>
<?php echo $content_parts['main']; // Output content before <!--more--> ?>
</p>
<p class="read-more">
<?php echo strip_shortcodes($content_parts['extended']); // Output content after <!--more--> ?>
</p>
<button>Read More</button>
<?php $gallery = get_post_gallery_images( $post ); ?>
When you pull the post content using get_post_field, the autop filter is not applied:
http://codex.wordpress.org/Function_Reference/wpautop
You can apply all of the content filters yourself by adding this line after you set $content:
$content = apply_filters('the_content', $content);
This is a difficult question for me to word correctly, but I am trying to dynamically insert an ASIDE [specifically, just a "special thanks" note] between paragraphs. Initially I decided to drop this after the second paragraph by using substr_count(). I am floating this block, so if all it had to deal with was textual content there was no issue word-wrapping it. However, if it ran adjacent to an image or a PRE or anything else, it got wonky.
Anyway, what I want to do is detect when there is the first occurrence of TWO adjacent paragraphs and insert my aside between those. I.e.:
<p> Here is the first paragraph. </p>
<aside> INSERT THIS HERE </aside>
<p> Here is the second paragraph. </p>
Thoughts are appreciated.
Update: the substr_count() I am currently using.
Because I got voted down for not showing the original code, I'll post it below. I am using Wordpress but this isn't a WP specific question, as I'm taking the_content() as the string, counting the occurrences of P, and inserting the custom field there. This is ultimately not what I want to do, but I want to count two concurrent P's and insert this field between. It may be formatted strangely, as of course when I c/p from my editor stuff was all over the place.
$thanks = get_post_meta(get_the_ID(), 'thanks', true);
if (!$thanks) {
the_content();
}
else {
$show_after_p = 0;
$content = apply_filters('the_content', $post->post_content);
if(substr_count($content, '<p>') > $show_after_p) {
$contents = explode("</p>", $content);
$p_count = 0;
foreach($contents as $content)
{
echo $content;
if($p_count == $show_after_p)
{
?>
<aside class="thanks clearfix">
<p>
<?php echo '<span>Special thanks: </span>'.$thanks; ?>
</p>
</aside>
<?php }
echo "</p>";
$p_count++;
}
}
}
?>
Why not JS?
Well, javascript could definitely do this, but if I can do this in PHP then yahtzee.
use regular expression and preg_replace - search for: (closing of P){whitespaces (if any)}(opening P) and change whitespaces to your text.
something like that:
$content = preg_replace('#</p>\s*<p#', "</p><aside> INSERT THIS HERE </aside><p", $content);
Kudos to Jerzy Zawadzki for the inspiration. If you refer to the original code I segmented the content at the P tags using explode(). Now I am using preg_split() as follows:
$contents == preg_split('#</p>\s*<p>#', $content); // Thanks Jerzy
$i = 0;
foreach ( $contents as $content ) {
echo $content;
if ( $i == $show_after_p ) { // this is set to 0 right now
// insert aside here
}
echo "<p>";
$i++;
}
}
As far as I can tell, this busts up the content only at segments where there are concurrent paragraphs and no whitespace / images / other elements. At this first junction, I insert the aside. Then the content is appears as normal.
I am wanting to insert some code after each post in WordPress... I know you can do it after this for example, in single.php
<?php the_content(); ?>
However if I do that it puts it in the wrong place.. an example post is here: http://www.hardwareblog.com/348/computer-hardware/top-10-gadget-gift-ideas-to-avoid-this-christmas/ -- if I put it AFTER the code example above it will be placed AFTER the sociable & facebook links..... I want to put it BEFORE those, so it's RIGHT AFTER the post.
I did some checking & testing.. this code here from post-template.php
function the_content($more_link_text = null, $stripteaser = 0) {
$content = get_the_content($more_link_text, $stripteaser);
$content = apply_filters('the_content', $content);
$content = str_replace(']]>', ']]>', $content);
echo $content;
}
It seems the facebook & sociable code is inserted into the output within the apply_filters() function.... though I can't work out where.
Any help on what I am trying to do?
Here is an example of a filter on the content and the function:
function the_content_replacer($content)
{
//global $post, $posts;
//$content = str_replace(']]>', ']]>', $content);
$content .= "\n<div style=\"display:none;\">text here</div>";
//$content = preg_replace('/="http:\/\/cnn/i',
// '="http://example.com?http://cnn', $content, -1);
return $content;
}
add_filter('the_content', 'the_content_replacer', 1);
much more examples on this filter on http://wordpress.stackexchange.com ..........
You can just copy and paste the piece of content in the file "functions.php" in your theme and it will work.
You can also just drop it in the directory wp-content/mu-plugins if your run multisite so it works on all the blogs in your multisite environment.
the third parameters determines the importance of when applying the filter, see: https://wordpress.stackexchange.com/questions/2126/at-what-priority-does-add-filter-overwrite-core-functions
--> it is better to post all WordPress questions in http://wordpress.stackexchange.com !!!
--> if you use e.g.
$content .= "\n<div style=\"display:none;\">text here</div>";
it will not remove a closing paragraph tag (note the linebreak at the beginning of the string)