Hello,
I would like to add a field to the Wordpress publish section in order to treat a post as an ongoing event rather than just displaying the day it was published.
Basically the posts are being used to show theater plays and need to display within the archives for each month/year that they are being shown... for example:
Macbeth : 01/01/2013 - 01/12/2013
This play would be shown within all 12 months of 2013 in the archives
Cats : 01/05/2013 - 01/07/2013
Whereas this play would only be shown for May through to July in the archives.
I will also need someway of displaying the end date. Not all posts will span a date, so this needs to be optional.
I'm happy to use a plugin for this so long as it only does the above without any extras.
Appreciate your help.
Hariprasad Vijayan answers:
Hello,
I think you can do this with postmeta. I have created a demo for this. You can check it now. Add the following code in function.php
add_action( 'post_submitbox_misc_actions', 'event_date' );
add_action( 'save_post', 'save_event_date' );
function event_date() {
global $post;
if (get_post_type($post) == 'post') {
// values from meta field
$start_date = get_post_meta( $post_id, 'start_date', true );
$end_date = get_post_meta( $post_id, 'end_date', true );
echo '<div class="misc-pub-section misc-pub-section-last" style="border-top: 1px solid #eee;">';
wp_nonce_field( plugin_basename(__FILE__), 'custome_event_date' );
echo '<div class="misc-pub-section misc-pub-section-last">
<span id="timestamp">Start Date: <div class="timestamp"><select name="sm" id="sm">
<option value="01">Jan</option>
<option value="02">Feb</option>
<option value="03">Mar</option>
<option value="04">Apr</option>
<option value="05">May</option>
<option value="06">Jun</option>
<option selected="selected" value="07">Jul</option>
<option value="08">Aug</option>
<option value="09">Sep</option>
<option value="10">Oct</option>
<option value="11">Nov</option>
<option value="12">Dec</option>
</select><input type="text" autocomplete="off" maxlength="2" size="2" value="'.date("d").'" name="sd" id="sd"><input type="text" maxlength="4" size="4" value="'.date("Y").'" name="sy" id="sy">
</div>
</label>'
.'</span></div><div class="misc-pub-section misc-pub-section-last">
<span id="timestamp">End Date: <div class="timestamp"><select name="em" id="em">
<option value="01">Jan</option>
<option value="02">Feb</option>
<option value="03">Mar</option>
<option value="04">Apr</option>
<option value="05">May</option>
<option value="06">Jun</option>
<option selected="selected" value="07">Jul</option>
<option value="08">Aug</option>
<option value="09">Sep</option>
<option value="10">Oct</option>
<option value="11">Nov</option>
<option value="12">Dec</option>
</select><input type="text" autocomplete="off" maxlength="2" size="2" value="'.date("d").'" name="ed" id="ed"><input type="text" maxlength="4" size="4" value="'.date("Y").'" name="ey" id="ey">
</div>
</label>'
.'</span></div>';
}
}
function save_event_date($post_id) { // For saving values to meta field
if (!isset($_POST['post_type']) )
return $post_id;
if ( !wp_verify_nonce( $_POST['custome_event_date'], plugin_basename(__FILE__) ) )
return $post_id;
if ( defined('DOING_AUTOSAVE') && DOING_AUTOSAVE )
return $post_id;
if ( 'post' == $_POST['post_type'] && !current_user_can( 'edit_post', $post_id ) )
return $post_id;
else {
// Update information into meta field
$start_date = $_POST['sy'].$_POST['sm'].$_POST['sd']; // Date format should be YYYYMMDD - sy - Start year, sm - Start month, sd - Start date
$end_date = $_POST['ey'].$_POST['em'].$_POST['ed']; // Date format should be YYYYMMDD - ey - End year, em - End month, ed - End date
update_post_meta($post_id, 'start_date',$start_date, get_post_meta( $post_id, 'start_date', true ));
update_post_meta($post_id, 'end_date',$end_date, get_post_meta( $post_id, 'end_date', true ));
}
}
Above code will add additional option for selecting start date and end date. It will appear above post publish button. And the value save into wp_postmeta table while saving the post.
And You can use the following code to display the post
<?php
$args = array(
'meta_query' => array(
'relation' => 'AND',
array(
'key' => 'start_date',
'value' => date('Ymd'),
'type' => 'date',
'compare' => '<='
),
array(
'key' => 'end_date',
'value' => date('Ymd'),
'type' => 'date',
'compare' => '>='
)
)
);
?>
<?php
// The Query
$query = new WP_Query( $args );
// The Loop
if ( $query->have_posts() ) {
while ( $query->have_posts() ) {
$query->the_post();
echo get_the_title().'<br />';
}
} else {
// no posts found
}
/* Restore original Post Data */
wp_reset_postdata();
?>
This is just a demo. Please check it. Please ask if you need any help regarding this.
Good luck
leannekera comments:
Hi Hariprasad,
This is more what I am after however its not working. The dates do not save when published.
This is the site in question: http://coa.devclouds.co/
You will see at the top a button called "Timeline" once clicked it will display the months for each post archive.
I need to be able to set the date for each post so they can span a number of monthly archives.
For example; Post 1 starts: 01/02/2013 and ends: 01/04/2013
This means that post 1 will show in the archives for January, Febuary, March and April.
Many thanks for looking into this.
Hariprasad Vijayan comments:
Hi,
Its actually saving to meta, that code was not complete.Its just a demo. Not fetching the values from meta after publishing post. Input fields are not dynamic. I think the dates are saving correctly here. I think you can see values in wp_postmeta. But your requirement is little bit different. Let me check some other solution. Need some more time.. Thank you..
Hariprasad Vijayan comments:
Hi,
Where you want to display these posts? in archives.php? or in some other page?
Hariprasad Vijayan comments:
Are you using any plugin for listing timeline?
Hariprasad Vijayan comments:
If you are using "Smart Archives Reloaded" plugin for listing timeline, i think we can customize that plugin for your requirement. Let me know.
leannekera comments:
Hi Hariprasad,
We are not using any plugin to list the archives, however if you think using an edited version of "Smart Archives Reloaded" will make things easier I will be happy to.
The current posts are displaying in archives.php
Hariprasad Vijayan comments:
Hi,
I didn't get how you are listing archives in timeline. The structure of time line is slimier to "Smart Archives Reloaded" plugin display. Am not sure all functionality that you need. If you can use "Smart Archives Reloaded", we can customize it i think.
Add the following code in function.php to enable additional option for reading two dates near publish area.
<?php
add_action( 'post_submitbox_misc_actions', 'event_date' );
add_action( 'save_post', 'save_event_date' );
function event_date() {
global $post;
if (get_post_type($post) == 'post') {
// values from meta field
$start_date = get_post_meta( $post->ID, 'start_date', true );
$end_date = get_post_meta( $post->ID, 'end_date', true );
$sy = substr($start_date,0,4);
$sm = substr($start_date,4,2);
$sd = substr($start_date,6,2);
$ey = substr($end_date,0,4);
$em = substr($end_date,4,2);
$ed = substr($end_date,6,2);
$month_list = array('01'=>'Jan', '02'=>'Feb', '03'=>'Mar', '04'=>'Apr', '05'=>'May', '06'=>'Jun', '07'=>'Jul', '08'=>'Aug', '09'=>'Sep', '10'=>'Oct', '11'=>'Nov', '12'=>'Dec');
echo '<div class="misc-pub-section misc-pub-section-last" style="border-top: 1px solid #eee;">';
wp_nonce_field( plugin_basename(__FILE__), 'custome_event_date' );
echo '<div class="misc-pub-section misc-pub-section-last"><span id="timestamp">Start Date: <div class="timestamp"><select name="sm" id="sm">';
$opt = '';
foreach(array_keys($month_list) as $ml)
{
if($start_date)
{
if($sm == $ml)
{
$opt .= '<option selected="selected" value="'.$ml.'">'.$month_list[$ml].'</option>';
}
else
{
$opt .= '<option value="'.$ml.'">'.$month_list[$ml].'</option>';
}
}
else
{
if(date(m)== $ml)
{
$opt .= '<option selected="selected" value="'.$ml.'">'.$month_list[$ml].'</option>';
}
else
{
$opt .= '<option value="'.$ml.'">'.$month_list[$ml].'</option>';
}
}
}
echo $opt;
if($start_date){ $day = $sd; } else { $day = date("d"); }
if($start_date){ $year = $sy; } else { $year = date("Y"); }
echo '</select><input type="text" autocomplete="off" maxlength="2" size="2" value="'.$day.'" name="sd" id="sd"><input type="text" maxlength="4" size="4" value="'.$year.'" name="sy" id="sy">
</div>
</label>'
.'</span></div><div class="misc-pub-section misc-pub-section-last">
<span id="timestamp">End Date: <div class="timestamp"><select name="em" id="em">';
$opt = '';
foreach(array_keys($month_list) as $ml)
{
if($end_date)
{
if($em == $ml)
{
$opt .= '<option selected="selected" value="'.$ml.'">'.$month_list[$ml].'</option>';
}
else
{
$opt .= '<option value="'.$ml.'">'.$month_list[$ml].'</option>';
}
}
else
{
if(date(m)== $ml)
{
$opt .= '<option selected="selected" value="'.$ml.'">'.$month_list[$ml].'</option>';
}
else
{
$opt .= '<option value="'.$ml.'">'.$month_list[$ml].'</option>';
}
}
}
echo $opt;
if($start_date){ $day = $ed; } else { $day = date("d"); }
if($start_date){ $year = $ey; } else { $year = date("Y"); }
echo '</select><input type="text" autocomplete="off" maxlength="2" size="2" value="'.$day.'" name="ed" id="ed"><input type="text" maxlength="4" size="4" value="'.$year.'" name="ey" id="ey">
</div>
</label>'
.'</span></div>';
}
}
function save_event_date($post_id) { // For saving values to meta field
if (!isset($_POST['post_type']) )
return $post_id;
if ( !wp_verify_nonce( $_POST['custome_event_date'], plugin_basename(__FILE__) ) )
return $post_id;
if ( defined('DOING_AUTOSAVE') && DOING_AUTOSAVE )
return $post_id;
if ( 'post' == $_POST['post_type'] && !current_user_can( 'edit_post', $post_id ) )
return $post_id;
else {
// Update information into meta field
$start_date = $_POST['sy'].$_POST['sm'].$_POST['sd']; // Date format should be YYYYMMDD - sy - Start year, sm - Start month, sd - Start date
$end_date = $_POST['ey'].$_POST['em'].$_POST['ed']; // Date format should be YYYYMMDD - ey - End year, em - End month, ed - End date
update_post_meta($post_id, 'start_date',$start_date, get_post_meta( $post_id, 'start_date', true ));
update_post_meta($post_id, 'end_date',$end_date, get_post_meta( $post_id, 'end_date', true ));
}
}
?>
Change protected function load_data from generator.php file in plugin with following code(I tried this on Smart Archives Reloaded Version 2.0.5)
protected function load_data( $qv ) {
$qv = array_merge( $qv, array(
'ignore_sticky_posts' => true,
'nopaging' => true,
'cache_results' => false,
'suppress_filters' => false,
'months_with_posts' => true
) );
unset( $qv['year'], $qv['monthnum'] );
$rows = get_posts( $qv );
if ( empty( $rows ) )
return false;
$months = array();
foreach ( $rows as $row )
//$months[$row->year][] = $row->month;
query_posts( 'posts_per_page=-1' );
while ( have_posts() ) : the_post();
$start = get_post_meta( get_the_ID(), 'start_date', true );
$end = get_post_meta( get_the_ID(), 'end_date', true );
if($start)
{
$sy = substr($start,0,4);
$sm = substr($start,4,2);
$months[$sy][] = $sm;
}
if($end)
{
$ey = substr($end,0,4);
$em = substr($end,4,2);
$months[$ey][] = $em;
}
if($start && $end)
{
for($i=$sm;$i<=$em;$i++)
{
$months[$ey][] = $i;
}
}
endwhile;
krsort($months);
$this->months_with_posts = $months;
return true;
}
Use the following code in archive.php to display post
<?php
$args = array(
'meta_query' => array(
'relation' => 'AND',
array(
'key' => 'start_date',
'value' => get_the_date('Ymd'),
'type' => 'date',
'compare' => '<='
),
array(
'key' => 'end_date',
'value' => get_the_date('Ymd'),
'type' => 'date',
'compare' => '>='
)
)
);
?>
<?php
// The Query
$query = new WP_Query( $args );
// The Loop
if ( $query->have_posts() ) {
while ( $query->have_posts() ) {
$query->the_post();
echo get_the_title().'<br />';
}
} else {
// no posts found
}
/* Restore original Post Data */
wp_reset_postdata();
?>
Hope this will help you.. Let me know if you have any doubts on this.
leannekera comments:
Still no luck Hariprasad,
It appears to break the plugin. Screenshot attached.