I've been having fun with my new EyeFi card, I found a setting where I can upload to an FTP Server with resized photos. I think it'd be neat if I could upload small images to a folder, and have a small script and template build a light gallery with PHP.

How hard is it, and what functions would I need to use/learn, to create such a script? I recognise I'd need to check a directory for contents, and load each one onto a webpage. Those are the two purposes I foresee.

I'm thinking of uploading higher quality to another directory, with the same light gallery. However, there'd be an option to download the directory as a zip archive. It's not something I'm really interested in including - I'm just pursuing the idea - but I believe it's possible, right? .
Why not just use the fully-functional Cemetech Photos module? I have a really impressively complete second version, even better than the one I have installed here on Cemetech, that I made for a class project. I don't think I ever got around to officially releasing it, but I'd be happy to give it to you if you need. More eye candy:


(aww, can't find any more screenies, have a feature list:)

Photos Section (http://www.cemetech.net/projects/photos.php)
:: Photos can be individually added, or it can read Apache folder listings
:: Allows album creation with titles, description, and arbitrary levels of recursion
:: Generates static thumbnails for any images added from Cemetech
:: Permission control to allow just yourself, all users, or selected users to view items with album or photo granularity
:: Photos are easy to browse using keyboard arrows keys, or clicking on a photo advances to the next in the album
Oh, that's right. I think you sent me the zip for one of the versions.

I wouldn't need any of the edit buttons (reorder, delete, set thumbnail, rotate) though. I'm sure I could remove those. Does the gallery look for photos in a directory, or do they have to be added to a database (either textual or MySQL?)

For the sake of learning though, what functions are required for a really light web gallery? No database, just a directory of images and a page to list and display them.
Basically you'd just need PHP's readdir() function and not a whole lot else.
I can't figure out readdir().
Code:
readdir(resource dir_handle) //readdir arguments
resource opendir ( string $path [, resource $context ] ) //opendir arguments

if ($handle = opendir('/path/to/files')) {
    echo "Directory handle: $handle\n";
    echo "Files:\n";

    /* This is the correct way to loop over the directory. */
    while (false !== ($file = readdir($handle))) {
        echo "$file\n";


PHP.net gives no word on where $handle comes from, but when I copy and paste into a file on my site, it works, with the exception I replaced /n with <br> so I'd have new lines (didn't give them to me \n from the example). From the example, I've been able to get the loop to spit out an image as well by using


Code:
$dir = 'res/img/about/';

if ($handle = opendir($dir)) {
    echo "Directory handle: $handle<br>";
    echo "Files:<br>";

    /* This is the correct way to loop over the directory. */
    while (false !== ($file = readdir($handle))) {
        echo "$file<br>";
        echo('<img src="' . $dir . $file . '"><br>');
    }
}


I'm assuming I need to also close the directory? How would I avoid the .. & . at the end? Those aren't files in the directory at all, just the one image. Hopefully sometime soon I'll formulate a fuller directory and add some styles to give it a look.

Update: Got rid of the .. & . by reading another example.
Update: Thanks to help in IRC $handle makes sense, updated my page to remove the first two echo functions.
I still don't think you totally understand the if ($handle = opendir(...)) thing. There's two things going on here. First, opendir() is returning a handle number. It's either zero, if opendir() failed, or a positive number, if opendir() succeeded. Secondly, if (anything) is shorthand for if (anything != 0), so it's comparing $handle to zero and only trying to use it is opendir() succeeded. You could also think of it like this:


Code:
$handle = opendir($dir);
if ($handle != 0) {
    echo "Directory handle: $handle<br />";
} else {
    echo "Opendir failed!<br />";
}
In addition, getimagesize() is a very handy function to determine whether a file is an image or not (and if so, what size it is). The GD functions can be used to generate thumbnails and the like if so required, though be wary of uploading very large images that you don't run out of memory when generating the thumbnails.
That makes clearer sense, Kerm.

Benryves, that'd be better than using size inside the image tag! I'll play with it today.
I mentioned the memory issue as I've had a few problems with people uploading files to websites directly from the camera - a 12 megapixel image will take up at least 34MB RAM to open with GD, and as our servers default to 32MB RAM limit per script that doesn't tend to work out too well.
That shouldn't be much of an issue I hope; The card can resize the images to a few presets before upload, so I plan to use that. That's good information for the full sizes if I end up uploading those as well.
If you need more specific resizing code, and you get stuck on making it yourself, there is code you can use for reference in the Photos module zip you think you have, or else the internet has plenty of examples of varying quality. Smile
FWIW, I tried to do this on my website, and went with a design of having a folder with all the larger images (the original size) and another folder with the scaled down ones. And then wrote a script to check if the small image exists, and if not, to resize it from the larger image. Then I abused tables for the output, and have 5 pictures (aspect-aware resized to 128x128) per row for the rest of the page. `getimages.sh' resizes the images and puts them in the other directory, and `index.sh' displays the page (`../page.sh' is just the template for every page).
Code:
#!/bin/bash
# file: index.sh

echo 'Content type: text/html'
echo ''

(
    echo '<table align="center"><tr>'
    ls scaled-down/ | sed -ne 's;.*\.\(png\|jpg\|gif\|bmp\);<td width="144px"><a href="big-images/&"><img src="scaled-down/&" /></a></td>;p' | sed -e '0~5 s;.*;&</tr><tr>;'
    echo '</tr></table>'
) | ../page.sh Gallery

Code:
#!/bin/bash

for file in `ls big-images/`; do
    if [ ! -f scaled-down/$file ]; then
        convert big-images/$file -resize 128x128 scaled-down/$file
    fi
done

As an example of what it looks like, here is a quick page I made to test it. (Sorry for the plug :/)
_player, I'd try to get into what that all does in detail if I wasn't already trying to learn PHP to at least some degree.

I've managed to make a fairly ugly looking gallery for now. It supports n amount of images, and viewing them full-size. It distinguishes between tall and wide images and makes them accordingly for the CSS. I still need to move the "15 images" at the bottom to the top, and when viewing full-size I need to add previous and next links. I've left my debugging/styling CSS in. Cyan hover for wide and blue hover for tall images. Helped me make sure the PHP and CSS were working well. I can likely take it down, but I'll wait. The color and such still have much work to go. I'll try to tie it in to my main site as much as possible, and likely end up using some form this for my new portfolio galleries.

Is it possible to obtain the next and previous files in a directory without a database?


Code:
<?php

$headerimage = '../res/img/AlexGlanvilleHeader.png';

echo('
<html>

<head>
        <meta http-equiv="Content-Type" content="text/html; charset=UTF-8" >
        <title>EyeFi Card Upload Gallery</title>
        <link rel="stylesheet" type="text/css" media="screen" title="Standard Style" href="eyefi.css" >
</head>

<body>

<img src="' . $headerimage . '"><hr>

<div class="gallery">

');

$dir = 'upload/';
$count = 0;


if(!$_GET['view']) {
   if ($handle = opendir($dir)) {

       /* This is the correct way to loop over the directory. */
       while (false !== ($file = readdir($handle))) {
          $count++;
          if ($file != "." && $file != "..") {
              list($width, $height, $type, $attr) = getimagesize($dir . $file);
            
            if($height>$width)
                 echo('
                    <a class="upload" href="?view=' . $file . '"><img src="' . $dir . $file . '" class="tall"></a>
                 ');
              
              if($height<$width)
                 echo('
                    <a class="upload" href="?view=' . $file . '"><img src="' . $dir . $file . '" class="wide"></a>
                 ');
                  
           }
       }
       echo('<br><br>' . $count . ' images.');
   }
} else {
   $view = $_GET['view'];
   echo('
      <div id="view">
         <span><a href="?">Index</a><br></span><img src="' . $dir . $view .'"></div>
   ');
}


?>

</div>

</html>


+2 Hours: Styled the gallery into my sites current theme. I didn't add any of the CSS style that causes horizontal scroll bars so, there's some of the background showing through, not sure how to remedy that. I did a really hackish job with the CSS, I plan to rewrite the HTML & CSS at some point so I didn't put much effort into it now.
Why don't you use self-closing tags like <img ... /> and <hr /> and <br />? Sad It makes me sad when they're missing.
Browsers these days more or less know when a tag doesn't need a close, I assume, so I leave them out. I also like to add things at the end and I'll end up getting <img ... / class="this">.
comicIDIOT wrote:
Browsers these days more or less know when a tag doesn't need a close, I assume, so I leave them out. I also like to add things at the end and I'll end up getting <img ... / class="this">.

It depends on whether you're using HTML (which doesn't close elements like img, br, hr) or XHTML (which does). The bigger issue with your code is that you omit a doctype, which means that the browser will use quirks mode rather than standards mode. This means that each browser will interpret your CSS differently (for example, IE uses a completely different box model where "width" directly corresponds to the width of the element on the page, whereas usually the width of the element on the page is the width plus padding and borders). As a result, your gallery looks atrocious in IE unless you bring up the developer tools and manually switch it into standards mode, at which point it mostly looks correct (you should also add img { border: none; } to your CSS as IE adds borders to images that are links by default).

See the W3C's recommended list of doctype declarations for suitable doctypes - HTML 4.01 Strict is probably best for the moment. The doctype should be the very first part of the page (no whitespace before it, like you currently have whitespace before your opening HTML tag).
I think I have a doctype on my main site, but not this one page.

Thanks for the image URL remainder, I'll fix that when I can.

The HTML was really an after thought. I didn't have HTML, head or body tags to begin with. Haha. I added the HTML as the gallery professed into a fully functional page.
What doctype are you going to be using, comic? Thanks as always to Benryves for his extensive knowledge on this subject, and I can personally vouch for the rendering pains when you don't have a valid doctype and IE uses its quirks mode.
I'll be copying the same DOCTYPE from my main site:
Code:
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.01 Transitional//EN" "http://www.w3.org/TR/html4/loose.dtd">


Back to the question, is it possible to create next and back buttons without a database? Would I have to load the list of images into an array?
You would need to keep track of the order of images somehow. An array that is populated with a list of images on every page load would indeed work.
  
Register to Join the Conversation
Have your own thoughts to add to this or any other topic? Want to ask a question, offer a suggestion, share your own programs and projects, upload a file to the file archives, get help with calculator and computer programming, or simply chat with like-minded coders and tech and calculator enthusiasts via the site-wide AJAX SAX widget? Registration for a free Cemetech account only takes a minute.

» Go to Registration page
» Goto page 1, 2, 3, 4, 5  Next
» View previous topic :: View next topic  
Page 1 of 5
» All times are UTC - 5 Hours
 
You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot vote in polls in this forum

 

Advertisement