Monday, February 4, 2013

Jumbo Digital Picture Frame

What do you do with a spare flat panel monitor?  If you are a Raspberry Pi hobbyist, you turn it into a jumbo size digital picture frame.  Photography is another of my hobbies and this is a great way to display my work.

Hardware Part 1 - Modify the Monitor Power Supply

This section requires some knowledge of power supplies and delicate soldering skills.  This step is totally optional and can be skipped.  I didn't want a second wire hanging from the picture frame for the Raspberry Pi power supply, so I tapped 5V off of the monitor's power supply.  You can power the Pi normally.  If you are really lucky you will have a monitor with a built in USB hub and you can power it from there.

I completely disassembled the monitor and located 5V and ground on the back side of the power supply where one of the connectors attached.  The wires in the lower right of this image show the power lines that I attached.

I shouldn't need to say this, but: DANGER.  Make sure the power supply is unplugged when you work on it.  Mains power can kill you!


Hardware Part 2 - The Control Panel

The monitor outputs 5V even if it is turned off, because it isn't really off - just in standby.  I added a power switch and LED as well as a push button to signal the Pi to shut down.  A simple script will monitor the pushpbutton and execute a halt when it is pressed.




If you only want to install the shutdown button, just connect it to a GPIO pin and to ground.  The pinouts that I used are shown here.  Don't be concerned about the inconsistency in the GPIO pin numbers.  This is explained below and is due to differences in the pin numbering used by the Raspberry Pi developers, the native pin numbers on the BCM chip, and the WiringPi library.



Hardware Part 3 -Build a case and put it all together

I used the plastic from the case to an old backup tape.  These are more flexible and a lot less brittle than most plastic CD cases.  I was able to use scissors to cut the plastic to fit the curved shape on the rear of the monitor.  Machine screws hold the case together tightly enough to keep the Raspberry Pi in place.  It is mounted so that the SD card extends a little bit below the monitor.  I would have liked to have it all hidden, but there wasn't room and this does make it easier to remove and insert the SD card.

Both the case and the control panel are held in place with Velcro   This allows me to peel the case loose so that I can plug a network cable in if needed.  Tie wraps are used to hold the HDMI cable and power cable neatly in place.  It is a very tight fit.

A added a short length of rope for hanging which is attached to the top two VESA mounting screws.  My frame is 21 inches and is quite a bit heavier than a typical painting, so I wanted something stronger than a typical picture hanger on the wall.   My work of art wouldn't be happy crashing to the floor.  I was very lucky and found a stud in the wall exactly where I wanted to mount the frame.  If you have to use drywall anchors, then I recommend using two about four inches apart and make the rope long enough to go over both.  If your walls are stucco, then I wish you luck.

System Preparation

Windows only recognizes the first partition on removable media and I wanted a large FAT partition to put the pictures on when the SD card is plugged in to my Windows laptop.  That means I had to use the /boot partition for this purpose.

  1. Load Raspbian as usual. Shut down the Pi and remove the sdcard.
  2. Install "Minitool Partition Wizard Home Edition" on a windows system with an sdcard slot. http://download.cnet.com/MiniTool-Partition-Wizard-Home-Edition/3000-2094_4-10962200.html
  3. Run the partition wizard and move the second partition (the system partition) all the way to the end of the disk space.  You could shrink the partition first but I didn't bother.
  4. Expand the first partition to fill the remaining space.
  5. Put the SD card back into the Pi, boot up, and log in.
  6. Update the apt database using:  sudo apt-get update
  7. Install the Linux Frame Buffer Interface using:  sudo apt-get install fbi
  8. Create a directory to hold the pictures that the frame will display:  sudo mkdir /boot/PICTURES 
  9. Create a new user named "slideshow" which is a member of the "video" group:  sudo adduser slideshow --ingroup video
  10. Change the inittab file to automatically log on the slideshow user:  sudo nano /etc/inittab   Find the line that begins 1:2345:respawn:/sbin/getty --noclear 38400 tty1  Comment out that line by placing a # in front of it and then add this line:  1:2345:respawn:/bin/login -f slideshow tty1 </dev/tty1 >/dev/tty1 2>&1
  11. Create a script to run the slideshow:  sudo nano /boot/slideshow.sh  which includes this one line: fbi -noverbose -m 1920x1080 -t 10 /boot/PICTURES/*.jpg   
  12. Some notes about the fbi command line:  The -m option specifies the resolution to use on the monitor.  This may need to be changed to display better for the monitor that you use.  The mode specified must be in the /etc/fb.modes  file.  I had to add the mode I needed, which is shown below.  The -t 10 option causes the program to run a slideshow with a 10 second period for each picture.  The -a option causes the program to automatically resize the images to fit the screen.  When I first tried this I was using 10 mega pixel images (about 3800 pixels across) and the Pi was taking 8-10 seconds to perform the resize.  To prevent this I removed the -a option and used FastStone Image Resizer to resize all the pictures for my slideshow to fit into a 1920x1080 screen.  You can find that utility here: http://www.faststone.org/FSResizerDownload.htm
  13. Make the script executable:  sudo chmod 775 /boot/slideshow.sh
  14. Edit the bash login script for the slideshow user:  sudo nano ~slideshow/.bashrc  and add this line to the end:   /boot/slideshow.sh
  15. Once all of the above has been done, you can reboot and the system will automatically run the slideshow.  You can stop it by pressing Control-C on the keyboard.
  16. Of course, you have to put some pictures in the pictures directory.  You can do this many ways, but I re-partitioned the sdcard so that I could plug it into my laptop and copy pictures directly to the sdcard.  The fbi command will support formats other than JPG, so don't feel that you are limited to that format.  You do need to realize that Linux is case sensitive with file names, so be sure to rename them all consistently. 

Here is the block that I added to the /etc/fb.modes file:


mode "1920x1080"
    geometry 1920 1080 1920 1080 32
    timings 0 0 0 0 0 0 0
    accel true
    rgba 8/16,8/8,8/0,0/0
endmode


The default fb.modes file did not include a 1920x1080 resolution so I had to find this example.  Fortunately it  works fine with my monitor.  More information about the fb.modes file can be found here:

Trigger Shutdown Script 

The drawing above shows the shutdown switch connected to GPIO-1.  I normally refer to the GPIO pins using the WiringPi numbering scheme.  However, I am not using WiringPi for this project.  We will access the GPIO pin via the /proc filesystem.  WiringPi GPIO-1 is GPIO-18 to the system.

Create a script to monitor the pin and perform a shutdown: sudo nano /etc/ini.d/wait-for-trigger.sh   
The contents of the script is this:


#!/bin/bash

# monitor GPIO pin 18 (wiringPi pin 1) for shutdown signal

# export GPIO pin 18 and set to input with pull-up
echo "18" > /sys/class/gpio/export
echo "in" > /sys/class/gpio/gpio18/direction
echo "high" > /sys/class/gpio/gpio18/direction

# wait for pin to go low
while [ true ]
do
if [ "$(cat /sys/class/gpio/gpio18/value)" == '0' ]
then
echo "SHUT DOWN NOW *****"
        halt &
        exit 1
fi
sleep 1
done


First, the GPIO pin is configured for input with a pull-up resistor enabled.  Then the scripts loops once a second and checks if the pin is pulled low from the push button being pressed.  If it is, then it executes the halt command and exits.

This script must be run at startup.  The easiest way to accomplish this is to add it to the end of the local startup script:  sudo nano /etc/rc.local
Add this line at the end of the file:
/etc/ini.d/wait-for-trigger.sh &
The & at the end of the line makes the command run in the background.  Without it, the local.rc script would not exit and the system would hang on startup.

All Completed:




32 comments:

  1. Can this be setup to pull pictures that are stored in NAS (freenas)?

    ReplyDelete
  2. Sure. FreeNAS supports NFS and SMB. I haven't used NFS in years, but it is fairly simple to install samba to support SMB (Windows file shares) and then mount a shared folder on the NAS. You could also pull files as needed using FTP or SCP, but I would go the samba route.

    ReplyDelete
  3. Would it be possible to add a push-button to somehow control the picture display? Rather than a slideshow automatically changing the photo every ten seconds, I'm interested in being able to choose what picture I want to display and being able to cycle through the directory of pictures manually and leave it on a picture as needed. (I realize I may have to worry about monitor burn-in if I leave it on one picture for too long)

    I want to use it as a title screen behind me in a video broadcast, on a screen that at other times I use for Skype interviews (from a different PC on a different input) but want to be able to switch to the title screen quickly. I'd have the Raspberry Pi as a constant title screen displayer on this input.

    ReplyDelete
  4. I have experimented a little with trying to call the fbi command using popen (from a C application.) However, the fbi app will fail when called that way. This means that there is no way to pass it key strokes to control it's operation.

    I was able to make a program that calls fbi once for each image displayed and the C application does all the rest of the logic (pause, backwards, forwards.) When the fbi app runs it blanks the screen then displays the image and this did not appeal to me for a slideshow. However, it would probably work fine for what you want. The program doesn't have to be in C - you could do it inthe language of your choice. Also, it doesn't have to run on the console. I edited the /etc/inittab to prevent login from running on /dev/tty1 and then call fbi with the option "-t 0" to make it appear on the console. Then you can control the display from an SSH session.

    ReplyDelete
  5. I have discovered that fbi has a memory leak. If left running for a few days it will exhaust all memory and cause the system to freeze. I will have to add a periodic reboot to the script.

    ReplyDelete
  6. Great, well explained project. You could of course use WinSCP to copy photos from Windows to the Pi card and no need to go through the re-partioning.
    I use this all the time to copy files to and fro, for backups and for working on / editing Python.

    ReplyDelete
    Replies
    1. Of course. But that is not possible if the system is not on the network. This one hangs on the wall in my office at work and I can not connect it to the network.

      Delete
  7. while testing this, I commented out the /boot/slideshow.sh line in the .bashrc file and now the PI boots to a command prompt logged in as slideshow user, who does not have SUDO rights. How can I edit the .bashrc file without SUDO rights ?

    ReplyDelete
    Replies
    1. Easiest way is to type logoff
      then login as the pi user, which does have sudo rights.

      Delete
  8. Great project, but mostly have to say the idea is far better....

    Have a similar config, just for the record, I'm usig qiv, since it:
    -doesnt have memory problems
    -you could have keypressses( back, pause, ff )
    -fast enough
    but keep in mind you have to start it through lighdm....

    I would rather be interested in how to connect the keystrokes (like buttons: N-next, B-back etc) to GPIO pins ?

    keep on, If you have any ideas how can we improve the PictureFrame, let me know.:)

    here is my 1st ver: www.daemons.hu/dpf --now going to replace the internal parts with pi and linux.

    ReplyDelete
  9. After trying steps 2 through 4 a number of times, the windows app always reports a bad card, but lets me try it again. The image boots fine otherwise. What am I doing wrong?

    Thanks!

    ReplyDelete
    Replies
    1. No way for me to answer that. I suggest starting over with a fresh load of the raspbian image onto the SD card.

      Delete
  10. Ted, this is an amazing article. I am a photographer and want to build a very similar style frame with a few modifications. I do not have the technical skills to modify this. Is that something you might be willing to help me with? I'd be happy to compensate you for your efforts. Thanks.

    ReplyDelete
    Replies
    1. Thanks. This is one the most popular posts on my blog.
      Unfortunately, I don't have any time to spare for the many requests that I receive via this blog, and compensation is (fortunately, for me) somewhat irrelevant. However, I am willing to answer questions and give advice. That I give away. It's one of the purposes for this blog. I can't always respond in a timely matter since this is just a hobby and real life has me busy full time.

      Delete
    2. PS - I am also a photographer (very amateur) and try to focus on wildlife and landscapes. You can see some of my work at http://thalephotos.com

      Delete
  11. Nice work! And thanks for the reply and offer. I will undoubtedly be in touch with you as I get into it.

    If I can return the favor - I know a little bit about photography. www.markandrewimages.com

    ReplyDelete
  12. Great guide. I implemented a solution based on this and made an excellent slide show for a booth at an expo without risking the loss/theft of an entire laptop. Thanks!

    ReplyDelete
    Replies
    1. Glad to be of help. That is a great application for this project. I have worked many trade shows and know what it's like. Never enough space and always worried about the hardware.

      Delete
  13. when i make a new user raspberry asks for new UNIX password
    Ive ried to enter something but the keyboard is not responding
    pls help

    ReplyDelete
    Replies
    1. The keyboard is actually responding, but the characters are no echoed back for security reasons (someone looking over your shoulder)
      Just enter a password and then enter it again when prompted and it will work.

      Delete
  14. Thank you! I found this useful ;)

    ReplyDelete
  15. Hi. Interesting project. I'm thinking of making a pattern generator for calibrating tvs and this seems like a possible easy way of doing that. Is it possible to change resolutions on the fly?

    ReplyDelete
    Replies
    1. Add the various resolutions that you need to the file /etc/fb.modes
      Then specify the resolution when you call fbi.
      Instead of photos, you would display your various patterns. It should be straightforward to make a shell script to do all this.

      Delete
  16. I'm working on a project (www.learnatec.co.uk) to teach primary school kids how to program and I found this really useful. Thanks.

    ReplyDelete
  17. This comment has been removed by a blog administrator.

    ReplyDelete
  18. An excellent little project, many congratulations. I am in the closing stages of completing my take on this but am a bit stuck on the hardware to shut down the pi.

    I am using GPIO 18 as you are but I am a little lost on the circuit. My thinking is that all I need is a push-to-make switch between GPIO 18 and GND which, when the circuit is closed, shuts the pi down using your software listed above. However, you mentioned "the GPIO pin is configured for input with a pull-up resistor enabled". Looking at internet tutorials on Pi input switches, there are resistors in such circuits which have confused my rather simple hardware brain.

    Could you elaborate on this circuit and let me know if it is any more complex than I have suggested above?

    Many thanks

    ReplyDelete
    Replies
    1. It really is as simple as it seems. Just a normally open push-button connecting GPIO 18 to ground. The Raspberry Pi has configurable pull-up or pull-down resistors internally, so none are needed externally. The line
      echo "high" > /sys/class/gpio/gpio18/direction
      turns on the pull-up resistor so that the gpio pin will read high until it is connected to ground. Also note that with the script I provide, the pin is only tested once per second, so you need to hold the button down for at least one second for the shutdown to be triggered.

      Delete
    2. Great, thanks. Just to confirm, am I connecting GPIO 18 to ground with the push to make switch, or to 3.3V?

      Delete
    3. Yes, connect to ground.
      It could also be done the opposite way - configure a pull-down resistor and a push button connecting to 3.3v. The script would then be changed to look for a high signal instead of a low.

      Delete
  19. Can you recommend a reliable HDMI to VGA converter?

    ReplyDelete
    Replies
    1. No. I have never used one. I use HDMI to DVI cables connected to a normal monitor. If you have a fairly recent monitor, you should be able to do this. If your monitor is old and only has VGA, then you must get a converter.

      Try searching the forum for a recommendation
      http://www.raspberrypi.org/forums/

      Delete
  20. Great write up. Exactly what I want to do.
    I'm getting "undefined symbol" errors with fbi so need to troubleshoot that before I can get it working

    ReplyDelete