PHP 5 – Sort by Folder

Recently, I needed to display a list of files with PHP. My only caveat was that I wanted to do so using newer methods of PHP 5 where possible.

I was delighted to find scandir. Problem was, scandir returns files mixed with folders and that would upset my flock of easily frightened Windows users.

So a quick… er medium… ok fine,  an exasperating search on Google and only outdated, complex and inefficient samples were to be found. PUFF!

So, here is the version I came up with.

Demo

Downloads

How it works

The most crucial part of all the code you will see inside the demo is the PHP getObjects() function. Without this everything else would be moot so lets go over it in a bit more detail.

function getObjects($path) {
    $path .= '/';
    $array = scandir($path); // returns an array of files and folders sorted alphabetically
    $array = array_diff($array, array('.', '..', '.DS_Store', 'Thumbs.db')); // filter out things we don't want

    $return_array = array();

    foreach($array as $item) {
        if(is_dir($path . $item)) {
            $return_array[$item] = getObjects($path . '/' . $item);
        }
    }

    $count = 0;
    foreach($array as $item) {
        if(!is_dir($path . $item)) {
            $return_array[$item] = $item;
            $count++;
        }
    }
    if($count == 0) {
        $return_array[''] = '';
    }

    return $return_array;
}

Line 3
Scandir returns an array of mixed folders and files for the path requested. This does not include sub directories.

Line 4
Filter out any undesirables. That means the current ‘.’ and parent directory ‘..’ although we don’t want any Mac ‘.DS_Store’ or WIndows ‘Thumbs.db’ files either.

Line 6
We create a new array called $return_array which will be built up with all the folders and files in the order we want them. Folders first, then files. Both alphabetically.

Line 8-12
Here we loop through each item in our filtered results from scandir. If the item is a directory we set the results of $return_array[$item] to a recursive call of the very same function we are already in. Traveling deeper each recursive call, that means we can handle seemingly infinite directory structures. Neat.

This first loop through only cares about directories which is exactly what puts them first in our $return_array. Files will come next.

Line 14
We set a variable $count to 0 to keep track of how many files we find in the next foreach loop.

Line 15-19
In this second loop we check to make sure the items are not directories and if so return those items while incrementing the $count variable.

Line 21-23
Now that we are finished looping for files we can check our $count variable. If 0 then set $return_array to ”. This can useful later in case we want to do something special for directories without files.

Line 25
Finally, we return whatever we have found. In most cases this means returning an $array to another instance of the function although ultimately the original one will return a completed array to the PHP call outside our function that started it all.

In the demo we can now loop through this nicely ordered array and write out some HTML and CSS, add a sprinkle of JavaScript and we have a real working web app.

Epilogue

Once you get your head around recursive loops things become much simpler. Plus you get to worry more about optimizing your code since each loop can be run so many times. It’s a good problem to have, really.

Anyway, I certainly hope this helps you in your next endeavor. I know I certainly would be lost without all the wonderful code and tutorials shared by others.

Cheers!


Gallery Progress II

Have I mentioned lately how much PHP rocks? Ah, yeah…

Today I researched and created the server side code for generating permanent thumbnails upon uploading. The beauty to this is that the server will only take a cpu hit on uploading (not often) instead of each view. The only downside is that it will eat into some of the space that you will be allocated. No big deal really as some of the thumbnails take up to 5k… ooooh.

Of course accomplishing this was much easier than I ever imagined and as usual I have PHP and Airor to thanks for that. Gosh, I’d hate to think what I would be doing now if Airor hadn’t shown me the light.

Did some preliminary work on beautifying the gallery viewer. Using lots of new CSS for the first time for extra fast, efficient and pixel perfect pages. Not to mention much easier to update.

Only the occasional client side JavaScript quirk for the image previews (nothing do to with generating thumbnails on the server) is bothering me now. I’m thinking that I can clean up the routines a bit and stop the function from rechecking itself so often. I’m guessing that sometimes it’s too fast and/or pulls the wrong value cause it’s programmed to be hyperactive.

Everything is going great. Time to go relax now.


Aha, gotcha!

Squished two bugs in the Lifestone forum. The first was an annoying yet harmless index not defined message. The second was a bug in the Page 1, 2 link code for longer threads. In certain situations with 10 replies, the paging code would not count the topic in it’s logic. This would cause the topic and 9 messages show up on the first page with no links to the second page which contained the 10th reply. I’m happy to say it’s all fixed now and thanks to Parr for spotting that one. :)

In other programming news, I’m happy to report that my super ultra magic secret project is coming along great. I can’t reveal too much about it yet but let me just say that it involves Flash, PHP and MySQL working in unison. It’s also surprisingly efficient and will help everyone in the Lifestone communicate better than ever before.

If you think you know what I’m working on send me an email with your idea to {email expired}. Close guesses will get their Lifestone accounts upgraded to beta level access which will let you play around with my new creation before it officially comes out for everyone.

Mystery adds so more more excitement than simply surprising you doesn’t it?