WordPress: adding a custom option box and developing file upload plugin

Hello Buddy,

One of my clients wanted to show thumbnail photo beside the post text as below. So, I had to make a plugin so that the admin can post the thumbnail when he is writing the post or can edit when editing the post. Take a look at the thumbnail’s position below.

Thus, recently I solved a plugin problem in one of my wordpress works although it was small. You know you may sometimes need to add a custom field in your wordpress posting/writing/editing area. To check what I am saying, take a look at the following image:

Adding such a box is extremely easy using the wordpress’s builtin add_meta function. But does file upload works i.e. if you upload the file, will it work? The answer is straight – “NO”. But why? The reason is also simple. If you want to upload a file, your form should have “enctype=”multipart/form-data” in the form opening such as

{code type=HTML}

{/code}

But the problem is – if you open the source code of text editor tool as following,

you will see that it does not have “enctype=”multipart/form-data” unfortunately. It looks exactly like this in my wordpress 2.7 version if I open the wp-admin/edit-form-advanced.php file at line # 520.

{code type=HTML}

{/code}

Not funny? Huh?

So, to cope up with this situation, I had to add “enctype=”multipart/form-data” in the form although I do not like changing the core files. Why do not I like to change the core files? The answer simple. Because whenever there is an update, the client have to update the file everytime. The client may not like it or may even forget it. Anyway, after change, it looks like this:

{code type=HTML}

{/code}

OK. Lemme show you step by step what to do if you want to add a file upload plugin.

Step One: Change the “wp-admin/edit-form-advanced.php” file

Open this file from the mentioned location and change the following line in the file:

{code type=HTML}

{/code}

to this line:

{code type=HTML}

{/code}

Step Two: Write you plugin

Here goes mine:

{code type=PHP}

/*
Plugin Name: Bag Thumbnail
Plugin URI: http://www.tanzilo.com/
Description: This plugin helps you to set thumbnail image of your bags.
Author: Tanzil Al Gazmir
Version: 1.0
Author URI: http://www.tanzilo.com/
*/

function init_bag_review_thumb_widget()
{

global $wpdb;

$result = mysql_list_tables(DB_NAME);
$current_table = array();
while($row = mysql_fetch_row($result))
{
$current_tables[] = $row[0];
}
$myNewDatabaseTable = $wpdb->prefix . ‘bag_thumb’;
if(!in_array($myNewDatabaseTable, $current_tables))
{

mysql_query(”
CREATE TABLE IF NOT EXISTS `” . $myNewDatabaseTable . “` (
`id` int(11) NOT NULL auto_increment,
`post_id` int(11) NOT NULL,
`image_name` varchar(255) NOT NULL,
PRIMARY KEY (`id`)
);
“);
}

/*
// Now I am going to delete all unnecessary thumb images by scanning the
// whole directory
*/
$sqlQuery = “SELECT image_name FROM ” .$wpdb->prefix . “bag_thumb; “;
$fileArray = $wpdb->get_col($sqlQuery);
$fileArray[] = ‘no_thumb.jpg’;

if ($handle = opendir(‘../bag_thumb/’))
{

// This is the correct way to loop over the directory.
while (false !== ($file = readdir($handle)))
{
if(is_file(‘../bag_thumb/’ . $file))
{
if(!in_array($file, $fileArray))
{
unlink(‘../bag_thumb/’ . $file);
}
}
}

closedir($handle);
}

}

// This function tells WP to add a new “meta box”
function add_bag_photo_box()
{

add_meta_box(

‘bag_photo’, // id of the

we’ll add
‘Add Bag Thumbnail Photo’, //title
‘add_bag_photo’, // callback function that will echo the box content
‘post’, // where to add the box: on “post”, “page”, or “link” page
‘normal’,
‘high’

);
}

// This function echoes the content of our meta box
function add_bag_photo()
{
echo


‘;
}

function bag_thumbnail_plugin_save_postdata()
{
$fileArray = array();
global $wpdb;

$file = $_FILES['bag_thumbnail_photo'];
$fileName = $_FILES['bag_thumbnail_photo']['name'];
$basename = ”;

if(!empty($fileName))
{
if(isAllowedExtension($_FILES['bag_thumbnail_photo']['name']))
{

$postID = $_POST['post_ID'];

# Do uploading here
$basename = basename( $_FILES['bag_thumbnail_photo']['name']);
$basename = str_replace(‘ ‘, ‘_’, $basename);
$basename = str_replace(‘-’, ‘_’, $basename);
$basename = strtolower($basename);
$basename = $_POST['post_ID'] . ‘_’ . $basename;
$target_path = ‘../bag_thumb/’;
$target_path = $target_path . $basename;

$sqlQuery = “DELETE FROM ” . $wpdb->prefix . “bag_thumb WHERE post_id=$postID;”;
$wpdb->query($sqlQuery);

move_uploaded_file($_FILES['bag_thumbnail_photo']['tmp_name'], $target_path);

// adding record in the database
$sqlQuery = “INSERT INTO ” .
$wpdb->prefix . “bag_thumb(post_id, image_name)
VALUES($postID, ‘$basename’)”;
$wpdb->query($sqlQuery);
}

}

}

function isAllowedExtension($fileName)
{
$allowedExtensions = array(“png”, “gif”, “jpg”, ‘jpeg’);
return in_array(end(explode(“.”, $fileName)), $allowedExtensions);
}

// This starts whenever the plugin is loaded
add_action(“plugins_loaded”, “init_bag_review_thumb_widget”);

// Hook things in, late enough so that add_meta_box() is defined
if (is_admin())
{
/* Use the admin_menu action to define the custom boxes */
add_action(‘admin_menu’, ‘add_bag_photo_box’);
}

/* Use the save_post action to do something with the data entered */
add_action(‘save_post’, ‘bag_thumbnail_plugin_save_postdata’);

?>
{/code}

Please notice that I dynamically delete any unnecessary file using the PHP’s unlink() function.

Step Three: get your image name from the database

I have placed the following code in my functions.php file.

{code type=PHP}

if(!function_exists('getBagThumbName'))
{
function getBagThumbName($postID)
{
global $wpdb;
$sqlQuery = 'SELECT image_name FROM ' . $wpdb->prefix . ‘bag_thumb WHERE post_id=’ . $postID . ‘;’;
$fileName = $wpdb->get_var($sqlQuery);
$fileName = trim($fileName);
$fileURL = get_option(‘siteurl’) . ‘/bag_thumb/’ . $fileName;
if(!empty($fileName))
{
return $fileURL;
}
else
{
return (get_option(‘siteurl’) . ‘/bag_thumb/no_thumb.jpg’);
}
}
}

?>
{/code}

Step Four: Link with the index.php or single.php or wherever you want

See how I placed the thumbnail image source in the code of index.php and single.php file.

{code type=PHP}

31 thoughts on “WordPress: adding a custom option box and developing file upload plugin

  1. Hello,

    I need to do that too, for a simple purpose, I have a select with some values that need to select and save the table wp_postmeta.

    Come to work more not know how it works, now I’m trying to work again.

    Only that I need more I’m starting my journey in the development of plugins.

    Thank you

  2. @ Murilo

    Wishing you all the best.

    I hope you will be a great plugin developer one day in near future.

    Thank you.

  3. Hello,

    Thanks, I develop my first plugin today, is already working better need it now, it makes use of add_action ( “save_post”, “the_save_post”);

    To save the data.

    Thanks to your blog soon added in my favorites

  4. @ Murilo

    It is very nice to hear that you have developed your first plugin successfully.

    Congrats!
    Keep up the good work dude!

  5. Hello,

    Many thanks for this!

    I’ve been searching extensively for a way to simplify uploading of files in the post page. (The current uploader is confusing for ordinary registered users on my site).

    I’m assuming your plugin can be adapted to upload ordinary files (e.g. doc, rtf etc). I’m a php beginner, though I think I can alter your code.

    Ideally, I’d really like it if selected registered users can upload files in the Comments section (similar to forums, so they don’t actually have to go the edit Write page). Though my WP and PHP knowledge is too limited for that.

    cheers

  6. @ snowcrash101

    wishing you all the best

    the more you play with PHP, the more & deeper you discover it.

    check the coding first so that you know where to made the changes.

    try hard and i am sure you can develop your desired output.

    wishes

  7. Had the same problem, but solved it with javascript. Add this to your plugins code where you add the form elements:

    var form = document.getElementById(“post”);
    form.enctype = “multipart/form-data”;

    Have fun!

  8. This is actually very simple. Instead of going through the hassle of developping a plugin in, I user custom fields which are supported by wordpress.

    For instance,
    1) I use article-image as the name of custom file and
    2) in the value box I put the full URL to the image to be displayed in that post. Then,
    3)I edited the single.php file of the theme to include something simple as ID, “thumbnail”, true); ?>

    Trust me, it’s much quicker!

  9. Hi thanks for this~ working on a project that requires some of the same functionality, I’ve tried using your Plugin on a wp2.8 and got this error:
    Warning: opendir(../bag_thumb/) [function.opendir]: failed to open dir: No such file or directory
    I noticed the folder is actually bag-thumb. oops
    Thank you for some good ideas *

  10. This was a very good tip on how to add uploads to the post form. However rather than changing the core wp file you can add the following javascript to your plugin. I have tested on my site and it works perfect.

    window.onload = function(){
    document.getElementById(‘post’).enctype = ‘multipart/form-data’;
    }

  11. hey keith does that not produce a JS error when on a page without a form? I did a similar thing using jQuery that way if there is no form no error ;)

  12. Thanks so much for the great post. Love to figure out how to add this file upload function to the profile form for registered users, store the file in a custom dir inside uploads dir. plus overwrite if user uploads newer file version, then ofcourse display the file that has been uploaded on the profile form page. Willing to help out? Looked for your contact info with no luck. Hope to hear from you soon.

    Jayson

    PS: Check out http://wpcoop.org, be a great addition to the membership.

  13. Thanks so much, let me play a bit more in the code, you have excellent structure, its just a matter of a few aspects. I will let you know what I end up with. Thanks again for your generosity.

  14. Don’t know how to hook with the post/page form head so i used the admin_head instead… I know it sucks, but it still works :)
    jQuery way to add the form enctype:

    function form_fix_js()
    {
    ?>

    jQuery(document).ready(function($){
    $(‘form#post’).attr({ encoding: ‘multipart/form-data’, enctype: ‘multipart/form-data’ });
    });

    <?
    }

    add_action('admin_head', 'form_fix_js');

  15. Hi

    IS there a way to add a wordpress standard file upload to a field on the new post page? ie one which will upload the file and create the thumbnails etc?

    I have a site where the client has to upload the media, then cancel and manually add the URLs to custom fields in the post.

    Thanks

    Lee

  16. hey guys

    love the idea of this plugin but as mentioned above I get this error and don’t know how to fix it:

    Warning: opendir(../bag_thumb/) [function.opendir]: failed to open dir: No such file or directory in /home/websitename/public_html/wp-content/plugins/bag-thumb/bag-thumb.php on line 47

    Any idea?

    Thanks

    Andy

  17. Sorry, did not mean for you to do it. Was wondering if it were possible with the existing script.

  18. 1. Definitely the best way to add enctype=”multipart/form-data” is to add it with jQuery. In my case, I made an upload control, that is added to the Post page, and the jQuery is executed there.

    2. You don’t need to do all that stuff directly on the database, unless you have a massive need to. Try:
    add_post_meta($post_id, ‘_your_option_name’, ‘your option value’)
    This will save it as a custom field attached to the post. Retrieve the value with
    get_post_meta($post_id, ‘_your_option_name’)

    3. You might find that hooking ‘save_post’ is going to fire your event twice, which might have an upload error on the second attempt (and, in your method, definitely go through a second series of database transactions) set a global flag and check for it.. eg,
    global $flag =0;
    if($flag == 0) {
    // do you code
    $flag = 1;
    }

    Cheers from New Zealand.

  19. Nice post,

    Thanks a lot for sharing this valuable plugin and your ideas. It’s really informative to the wordpress lovers. I am using few lines of your code to develop my own image gallery plugin.

    Thanks a lot……keep posting..
    Rohan

  20. Couple things I noticed. In the newest wordpress upgrade, you can add strings to the form code without editing core files. All you need to do is add:
    function post_edit_form_tag( ) {
    echo ‘ enctype=”multipart/form-data”‘;
    }
    to your functions.php of your theme.

    Also, I am getting the bad directory error that several other people have gotten. I’ve changed the name of the dir to “bag_thumb” and I’ve added the dir to every folder in my site. Still doesn’t work. What am I doing wrong?

    Thanks in advance, this plugin is very useful. Cheers.

Leave a Reply

Your email address will not be published. Required fields are marked *

You may use these HTML tags and attributes: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <strike> <strong>