12 KiB
filmless
Scripts and templates for making "filmless", cameraless analog films using free open-source software.
This is a collection of tools for printing and/or laser cutting non-film materials into 16mm-shaped strips of film. Use the Processing sketch to turn your video into valid scale 16mm images for printing on inkjet transparency or any kind of printable transparency sheets.
What this repo contains
- Laser cutting templates
- Scripts for exporting video to image sequences
- Processing sketch for generating pages of film strips
- Calibration sketch
1. Laser cutting templates
The laser cutting templates can be used on their own and without the other components. Use them to cut non-film materials into shapes that can be used in analog film machines.
The provided .svg and .dxf files can be opened in whichever application you use to control your laser cutter. With just these files you can cut twelve 33-frame strips of 16mm-sized film from any flat material that you can cut with your laser. Whether or not it will run through a projector depends on the material, but at least you can cut it! This has been tried with paper, vellum, acetate and inkjet transparency film.
Using the provided OpenSCAD file, scad/16mm_film.scad
, you can generate .dxf or .svg files of your own dimensions. Build strips of any number of frames and generate any number of strips. Just change the variables FRAME
and STRIP
at the top of the file or use the new Customizer feature in the latest version of OpenSCAD.
For more advanced tweaks, change the PITCH
variable from "long" to "short" to cut camera-sized short pitch film strips. You can also change the PERFS
variable from "single" to "double" for generating double perforated film strips.
2. Scripts for exporting video to image sequences
If you would like to generate images for printing and cutting, you will need Processing and optionally ffmpeg for generating image sequences from your video. Using the provided scripts/export.sh
script, you can quickly export an image sequence of .png files to your desktop that the processing sketch filmless_processing.pde
will turn into pages of film strips to be printed and cut.
Simply pass in a path to your video as the first and only argument, like so:
sh scripts/export.sh /path/to/my/video.mov
This will export the video in a .png sequence to a folder on your Desktop in a folder named "frames". This is the default directory that the filmless_processing.pde
sketch will look for an image sequence.
You can also export image sequences using your application of choice. This script simply allows you to do so from the command line without opening up an NLE or media export program. You can also generate image sequences with other Processing sketches.
Note: Processing can only read .tif files produced by the application, so unless you are using an image sequence generated by Processing save your files as .png or .jpeg.
3. A Processing sketch for generating pages of film strips
If you have installed Processing and the required libraries (read below) you can use this sketch to generate . Using the default settings, this will build a page of 12 strips, each 33 frames long that will comfortably fit on a letter-sized piece of 8.5" x 11" sheet of inkjet transparency film.
By including a path to a mono audio file, tested only with .wav files so far, you will build an optical soundtrack facsimile using the SoundtrackOptical library for Processing.
There are variables at the beginning of the sketch that you will need to change to properly generate pages from your images.
String DESKTOP = System.getProperty("user.home") + "/Desktop";
This line does not need to be used or changed, but will find the "Desktop" folder for the current user. This is useful if you wish to place your files in an easy-to-reach destination while generating files.
String SOURCE = DESKTOP + "/frames/";
The SOURCE
variable will point to the directory containing your image sequence. This can be changed completely or used as is if you place your image sequence in a folder named "frames" on your desktop and include the images.
String SOUND = DESKTOP + "/audio/audio.wav";
The SOUND
variable is optional. To include sound, use the path of a mono audio file. In the default setting, it will look for a file named "audio.wav" in a folder named "audio" on your Desktop. If you do not wish to use sound, change the line to this to generate a silent track: String SOUND = "";
String RENDER_PATH = DESKTOP + "/";
This variable controls the output location for the page_#.tif
files that will be produced by the sketch. These files can be LARGE (500MB to 2GB) so point this to a directory with a lot of space. Keep in mind, you will produce one of these pages for every 396 frames using the default settings, so a 4000 frame sequence will produce 11 pages. That as much as 22GB (or more) so plan accordingly.
String SOUNDTRACK_TYPE = "unilateral";
The soundtrack type refers to the style of soundtrack that's produced by the sketch. The soundtrack is produced using SoundtrackOptical and the options are unilateral
, variable area
, dual variable area
, maurer
, variable density
. Read more about these different types here.
int DPI = 1440;
The DPI is the target for printing. The maximum DPI you'll be able to print is dependent on your printer or image reproduction technology. The higher the DPI, the higher the theoretical resolution of your output. This variable will also determine your sound quality, as you will only be able to reproduce the number of samples the vertical resolution allows. If your printer can only draw 10,000 lines in 24 frames, your sample rate will effectively be 10Khz.
String PITCH = "long";
The pitch of the film refers to the distance between the perforations. Long pitch films are generally projection films, while short pitch films are for cameras. If you plan on contact printing your generated film, you should change the variable to short
.
Make sure that if you change this setting, you use the provided _long.svg
or _short.svg
(or .dxf files) or change the setting in the 16mm_film.scad
file when generating your own.
String FORMAT = "16mm";
FORMAT
refers to the image format that your film strips will use. Either 16mm
for standard 16mm or super16
for Super16.
Keep in mind: This sketch will scale your video frames to fit the size of the film frames. If you choose a standard 16mm format any frames provided to the script will be scaled to a ~4:3 aspect ratio. If you provide 1080P frames, they will be squashed from 16:9 to the square-ish 4:3 ratio. Conversely, if you choose the super16 format using String FORMAT = "super16";
your 4:3 frames will be stretched to 1.66:1.
Best practice would be to run the filmless_calibration.pde
sketch with your desired settings and look for this line in the logs: FRAME SIZE: 582x425
and then scale your video yourself to that size; optimizing the cropping or scaling before you export your frames for filmless_processing.pde
.
Another thing to note: Super16 and soundtracks occupy the same space on the filmstrip and the script will throw an error if you try to include both audio and a Super16 image format.
int PERFS = 1;
Refers to the number of perforations that will be printed as guides for your film. Can be either 1
or 2
. Similar to the conflict between Super16 and soundtracks, the second perforation on "double perf" film strips will occupy the same area that soundtracks and Super16 images do. If you intend to cut double perf film, use the proper .svg or .dxf file with 2 perforations per frame.
float PAGE_W = 8.5;
float PAGE_H = 11.0;
float SAFE_W = .25;
float SAFE_H = .5;
Change these only when printing on larger format sheets than standard US letter stock. The "SAFE_" variables refer to the areas on both sides of the width or height of the sheet which will not be printed on. Changing these to higher values will reduce the maximum amount of frames that are able to be printed on a single sheet. If you see the number of frames or strips change in the logs of the script, you should generate a new .svg or .dxf to match.
Using these default settings the script will generate 12 strips of 33 frames each, totally 396 frames per page.
color BACKGROUND = color(0);
The color that will fill the entire frame where there's no image or soundtrack data. The color()
method will accept grey values from 0
(black) to 255
(white) or will accept 8-bit RGB color values like color(255, 0, 0)
(red), color(0, 255, 0)
(green), color(0, 0, 255)
(blue) or anything in between those values.
boolean NEGATIVE = false;
Change this value from false
to true
to invert the colors of your images. Use this for contact printing or other experimental uses. Keep in mind: this will not perform the orange color mask inversion needed for color contact printing but will naively invert all color values.
boolean SHOW_PERFS = true;
Set to true
to print perfs for cutting registration. Set to false
to print nothing.
color PERFS_COLOR = color(255);
Set the color of the perforations, similar to BACKGROUND
. By default, they will be drawn white.
int SOUND_OFFSET = 25;
The sound offset is the number of frames before the image starts after the soundtrack starts. When set to 25
the image will start on the 26th frame, which is the standard for 16mm prints. Change this only if sync sound is not important.
4. Calibration sketch
The purpose of the calibration sketch filmless_calibration
is to generate a page to calibrate between your printer and laser cutter. The page it generates is easy on your ink cartridge while you determine if there is any stretch or squish happening to your generated pages of film strips before you commit to printing them out for cutting.
Hardware
- Laser cutter
- (optional) Printer
Dependencies
- Processing - [Download]
- Sound library for Processing - [Installation instructions]
- SoundtrackOptical library for Processing
- (optional) ffmpeg - [Download] or [Installation instructions]
- (optional) OpenSCAD - [Download]
- (optional) ImageMagick - [Download] or [Installation instructions]
Installing ffmpeg and/or ImageMagick
macOS
On a Mac, ffmpeg can be quickly and easily installed using the Homebrew package manager. Simply go to https://brew.sh and follow the instructions on the page. Then,
brew install ffmpeg
To install ImageMagick (which will include the program convert
):
brew install imagemagick
Linux
Install both ffmpeg and ImageMagick on Linux systems with either apt or yum.
apt install ffmpeg imagemagick
or
yum install ffmpeg imagemagick
Windows
The scripts are tested on macOS and Linux, but can be converted to work with Windows operating systems with few edits. Check the install links above for the Windows executables for ffmpeg and ImageMagick. Happy to accept pull requests for updates to the bash scripts to support all operating systems.