Very Simple PHP Video Gallery (No Database, From Folder)

Welcome to a tutorial on how to create a simple responsive PHP video gallery. Once upon a time in the stone age of the Internet, we have to struggle with all kinds of funky 3rd party video plugins to even play a single video. Fast forward to today, things are really easy.

Creating a simple video gallery in PHP is as easy as:

  • Get a list of video files from the folder – $vids = glob("GALLERY/*.{webm,mp4,ogg}", GLOB_BRACE);
  • Output the HTML video tags – foreach ($vids as $v) { echo "<video controls src='". rawurlencode(basename($v)) ."'></video>"; }

Yep, let us build a video gallery based on that – Read on!

 

 

TABLE OF CONTENTS

 

DOWNLOAD & NOTES

Here is the download link to the example code, so you don’t have to copy-paste everything.

 

EXAMPLE CODE DOWNLOAD

Source code on GitHub Gist

Just click on “download zip” or do a git clone. I have released it under the MIT license, so feel free to build on top of it or use it in your own project.

 

SORRY FOR THE ADS...

But someone has to pay the bills, and sponsors are paying for it. I insist on not turning Code Boxx into a "paid scripts" business, and I don't "block people with Adblock". Every little bit of support helps.

Buy Me A Coffee Code Boxx eBooks

 

 

SIMPLE PHP VIDEO GALLERY

All right, let us now get into more details about the PHP video gallery.

 

TUTORIAL VIDEO

 

PART 1) VIDEO GALLERY PAGE

1a-gallery.php
<!-- (A) CLOSE FULLSCREEN VIDEO -->
<div id="vClose" onclick="vplay.toggle(false)">X</div>

<!-- (B) VIDEO GALLERY -->
<div class="gallery"><?php
  // (B1) GET ALL VIDEO FILES FROM THE GALLERY FOLDER
  $dir = __DIR__ . DIRECTORY_SEPARATOR . "gallery" . DIRECTORY_SEPARATOR;
  $vid = glob("$dir*.{webm,mp4,ogg}", GLOB_BRACE);
 
  // (B2) OUTPUT ALL VIDEOS
  if (count($vid) > 0) { foreach ($vid as $v) {
    printf("<video src='gallery/%s'></video>", rawurlencode(basename($v)));
  }}
?></div>

  1. <div id="vClose"> This “close” button will only show when a video is in fullscreen.
  2. As in the introduction – Get all video files in the gallery folder, and output them into <video> tags.

 

 

PART 2) CSS COSMETICS

1b-gallery.css
/* (A) GALLERY WRAPPER */
/* (A1) BIG SCREENS - 3 IMAGES PER ROW */
.gallery {
  display: grid;
  grid-template-columns: repeat(3, 1fr);
  grid-gap: 10px;
  max-width: 1200px;
  margin: 0 auto; /* horizontal center */
}
 
/* (A2) SMALL SCREENS - 2 IMAGES PER ROW */
@media screen and (max-width: 768px) {
  .gallery { grid-template-columns: repeat(2, 1fr); }
}
 
/* (B) GALLERY VIDEOS */
/* (B1) THUMBNAIL VIDEO */
.gallery video {
  width: 100%;
  height: 200px;
  object-fit: cover; /* fill | contain | cover | scale-down */
  cursor: pointer;
}
 
/* (B2) FULLSCREEN VIDEO */
.gallery video.full {
  position: fixed;
  top: 0; left: 0; z-index: 999;
  width: 100vw; height: 100vh;
  background: #000;
  object-fit: scale-down;
}

/* (C) EXIT FULLSCREEN */
#vClose {
  position: fixed; display: none;
  top: 0; right: 0; z-index: 9999;
  font-size: 20px; font-weight: 700;
  padding: 10px 15px;
  color: #fff;
  background: #741414;
  cursor: pointer;
}
#vClose.show { display: block; }

There’s quite a bit of CSS, but keep calm and let’s walk through the important mechanics:

  • (A1) display: grid and grid-template-columns: repeat(3, 1fr) pretty much does the “3 videos per row” layout magic.
  • (A2) On small screens, we change the layout to 2 videos per row.
  • (B1) width: 100% and height: 200px will automatically resize the videos, but the videos will be “out of proportion”. We use object-fit to change the resize behavior, change this and see for yourself; Pick one that you like.
  • (B2) On clicking a thumbnail video, we set it to fullscreen. Pretty much 100% viewport width and height, and a fixed position.
  • (C) The “close fullscreen video” button, place at the top right-hand corner.

 

 

PART 3) JAVASCRIPT

3-gallery.js
var vplay = {
  // (A) INIT - CLICK VIDEO TO GO FULL SCREEN
  init : () => { for (let v of document.querySelectorAll(".gallery video")) {
    v.onclick = () => {
      if (!v.classList.contains("full")) { vplay.toggle(v); }
    };
  }},
 
  // (B) TOGGLE FULLSCREEN
  toggle : e => {
    // (B1) TOGGLE CLOSE BUTTON
    document.getElementById("vClose").classList.toggle("show");
 
    // (B2) TOGGLE VIDEO
    let v = e===false ? document.querySelector(".gallery .full") : e ;
    v.classList.toggle("full");
    v.controls = e===false ? false : true ;
    if (e===false) { v.pause(); }
  }
};
window.onload = vplay.init;

A bit of Javascript to drive the “click to fullscreen video”.

  1. On window load, init() will attach “click to toggle fullscreen” on all gallery videos.
  2. To toggle the fullscreen video. Basically, add/remove the full CSS class on the selected video.

 

EXTRAS

That’s all for this project, and here is a small section on some extras and links that may be useful to you.

 

EXTRA) FILE NAME AS VIDEO CAPTION

3-gallery.js
// (B2) OUTPUT VIDEOS
if (count($vid) > 0) { foreach ($vid as $v) {
  $file = basename($v);
  $caption = substr($file, 0, strrpos($file, ".")); 
  printf("<div class='vWrap'>
    <video src='gallery/%s'></video>
    <div class='vCaption'>%s</div>
  </div>", rawurlencode($file), $caption);
}}

There is no database, but we can still use the file name as the caption.

 

 

EXTRA) SORTING THE VIDEOS

Sort by date – newest first
usort($vid, function ($file1, $file2) {
  return filemtime($file2) <=> filemtime($file1); 
});
Sort by date – oldest first
usort($vid, function ($file1, $file2) {
  return filemtime($file1) <=> filemtime($file2);
});
Sort by file name.
sort($vid); // ascending
rsort($vid); // descending

 

EXTRA) MULTIPLE CATEGORIES

<h1>CATEGORY A</h1>
<div class="gallery"><?php
  $vid = glob(FOLDER A);
  foreach ($vid as $v) { printf("<video ...>"); }
?></div>
 
<h1>CATEGORY B</h1>
<div class="gallery"><?php
  $vid = glob(FOLDER B);
  foreach ($vid as $v) { printf("<video ...>"); }
?></div>

Same old “get the list of files and output HTML”, just keep your video files in different folders.

 

EXTRA) READ ANOTHER FOLDER

$vid = array_merge(
  $vid, glob("ANOTHER-FOLDER*.{webm,mp4,ogg}", GLOB_BRACE)
);

This is an alternative to reading multiple folders, just use array_merge() to combine the results. But of course, this is only good as a “quick fix”, this is not good if you have a dozen folders.

 

VIDEO FORMAT SUPPORT & POSTER

  • Different browsers support different video formats, the safest format at the time of writing is H.264 MP4 – See the Wikipedia HTML5 Video link below for the full list.
  • Depending on the Internet connection and/or video format, some browsers may not even preload the video and show a thumbnail. You can set a poster image to show while the video is still loading – <video poster="IMAGE.JPG">.
  • Alternatively, you can “encourage” the browser to preload a fragment of the video by changing the preload behavior – <video preload="metadata">.

 

COMPATIBILITY CHECKS

This simple gallery will work on all modern browsers.

 

LINKS & REFERENCES

 

THE END

Thank you for reading, and we have come to the end of this guide. I hope that it has helped you with your project, and if you want to share anything with this guide, please feel free to comment below. Good luck and happy coding!

34 thoughts on “Very Simple PHP Video Gallery (No Database, From Folder)”

  1. #TROLL #ENTERTAINMENT Ignore this thread if you want useful comments only.

    Since your website may be visited by people who are more or less advanced in writing code, it is a good practice to put the complete code with all the extras at the end. Especially since you don’t tell us where to place extras in your code. But that’s just it. Brgs.

    1. Most are smart enough to read, start with the basics, and ask for help when in doubt. A few dumb ones blame others for their skill issues and think they have achieved something. But that’s just it. Brgs.

      https://code-boxx.com/faq/#help “Irrelavant, so what’s the question or request!?”

    2. @ W.S. TOH, As I see, there are also doomb ones who do not notice their character flaws. They are just beets and they were clearly not in the right queue before birth.

      WS: Keeping this for good entertainment. Trolls are cute, they take the free stuff and show gratitude with attacks. When told off that “it’s your fault” cannot solve problems, they desperately try to prove their superior intelligence and character. 😆

      Top Tip: See below for examples of how the smart ones ask questions and got answers.

      https://code-boxx.com/faq/#nobad “Feeding trolls are fun sometimes, but further comments with no value will be trashed. Cheers!”

  2. this is a super helpful script. i tried to add “file changed” date (of the video’s) to the output, guess should be simple but with my almost zero php knowledge i couldn’t get it to work. any hint would be appreciated!
    david

  3. Hi!
    Very usefull and easy to implement. I made it work on a local network and access to it with my android phone, chrome browser. It work very well.
    Not the same with Safari with iphone. Gallery doesn’t show nothing but doing randoms clicks it show videos.
    Any idea?

  4. Hi!

    I saw comment about viewing a poster instead od a video but is there an option to view “miniatures” at position i.e. 20s, not first frame?

Leave a Comment

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