I want to add custom image sizes to the media uploader:

media uploader

In order to do this, I use the following code (comments are there for convenience):

// this function adds the custom image sizes to the media uploader
function my_insert_custom_image_sizes( $sizes ) {
    // get the custom image sizes
    global $_wp_additional_image_sizes;
    // if there are none, just return the built-in sizes
    if ( empty( $_wp_additional_image_sizes ) )
        return $sizes;

    // add all the custom sizes to the built-in sizes
    foreach ( $_wp_additional_image_sizes as $id => $data ) {
        // take the size ID (e.g., 'my-name'), replace hyphens with spaces,
        // and capitalise the first letter of each word
        if ( !isset($sizes[$id]) )
            $sizes[$id] = ucfirst( str_replace( '-', ' ', $id ) );

    return $sizes;

// define the init function next, which sets up all the necessary stuff
function custom_image_setup () {
    add_theme_support( 'post-thumbnails' );
    add_image_size( 'my-size1', 250, 250 );
    add_image_size( 'my-size2', 350, 350 );
    add_image_size( 'my-size3', 450, 450 );
    add_filter( 'image_size_names_choose', 'my_insert_custom_image_sizes' );

// attach that init function to the 'after_setup_theme' hook
// so it runs on each page load once your theme's been loaded
add_action( 'after_setup_theme', 'custom_image_setup' );

This code works fine. Beside one issue: When uploading an image, if it is smaller than the dimensions of the smallest custom image size, then this error appears: Invalid argument supplied for foreach().

I presume the problem comes from the my_insert_custom_image_sizes function. So basically, when no custom image is made, the error appears. How can I fix this? I have a feeling the problem is something simple that I overlooked but I'm lost...

If you want to replicate this error, just paste the above code in functions and upload an image that is smaller than 250x250 in pixels.

UPDATE: After some further research, it appears that the error is related to the foreach in my JPEG compression function:

// Set JPEG compression quality
add_filter('jpeg_quality', create_function('$quality', 'return 100;'));
add_action('added_post_meta', 'ad_update_jpeg_quality', 10, 4);

function ad_update_jpeg_quality($meta_id, $attach_id, $meta_key, $attach_meta) {

    if ($meta_key == '_wp_attachment_metadata') {

        $post = get_post($attach_id);

        if ($post->post_mime_type == 'image/jpeg') {

            $pathinfo = pathinfo($attach_meta['file']);
            $uploads = wp_upload_dir();
            $dir = $uploads['basedir'] . '/' . $pathinfo['dirname'];

            foreach ($attach_meta['sizes'] as $size => $value) {

                $image = $dir . '/' . $value['file'];
                $resource = imagecreatefromjpeg($image);

                if ($size == 'large') {
                    // set the jpeg quality for 'large' size
                    imagejpeg($resource, $image, 35);
                } elseif ($size == 'medium') {
                    // set the jpeg quality for the 'medium' size
                    imagejpeg($resource, $image, 35);
                } elseif ($size == 'small') {
                    // set the jpeg quality for the 'small' size
                    imagejpeg($resource, $image, 40);
                } else {
                    // set the jpeg quality for the rest of sizes
                    imagejpeg($resource, $image, 90);


Any ideas what is wrong with it?

  • That error should come with a .php file name and a line number. What are those?
    – s_ha_dum
    Commented Dec 2, 2012 at 16:16
  • Mind my stupidity, please check the update to my question. Commented Dec 2, 2012 at 16:26
  • Try adding (array) before $attach_meta['sizes'] in your foreach statement Commented Dec 2, 2012 at 16:30
  • @MatthewBoynes Can you please post an answer with the suggested fix? Commented Dec 2, 2012 at 16:32

1 Answer 1


Invalid argument supplied for foreach means that the X in foreach X as ... is not an array. You can prevent this error by type casting; add (array) before the argument in the foreach statement. This will turn your variable into an array, essentially. In your code, the change would be...

foreach ( (array) $attach_meta['sizes'] as $size => $value ) {

Now keep in mind that this won't fix the real issue here, which is that your code is expecting $attach_meta['sizes'] to be an array and it is not. You may want to refactor your code to handle that scenario.

  • This did prevent the code from displaying any errors, thank you kindly for taking the time to write this. Although I cannot figure out what I would need to change in my original code to handle this scenario, do you? Commented Dec 2, 2012 at 16:48
  • Frankly, I don't know. I couldn't actually replicate your issue. For me, $attach_meta['sizes'] was always an array, even if empty. I'm using 3.5RC1, so it's possible that this was a bug that's been fixed in my version and still exists in whatever version you're using. [shrug]. Commented Dec 2, 2012 at 17:06
  • I ended up going with if (is_array($attach_meta['sizes'])) which solved the issue. I will accept this as the correct answer as it hinted ways to the solution... Commented Dec 3, 2012 at 13:12

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Not the answer you're looking for? Browse other questions tagged or ask your own question.