-
Automating Importing photos and pairing to sequences
I am in the process of writing another script to automate my tedious workflow. I essentially have 2500 photos that need to be paired to sequences in the project that have similar names. They’re all broken into subfolders in the project and in the photos original location on the OS. The photos are named lastname_firstname and in my project the sequences are all named 00#Firstname Lastname for extended expression reasons. At this stage, I have the script seemingly recognizing matches and ready to import, but I am getting stuck on the importing to the original sequence stage. Any help is appreciated. Full disclosure, I was unfamiliar with the Levenshtein algorithm so I used ChatGPT to help generate this script, so there may very well be errors I am overlooking because of that.
// Function to calculate Levenshtein distance between two strings
function levenshteinDistance(a, b) {
if (a.length === 0) return b.length;
if (b.length === 0) return a.length;
var matrix = [];
// Initialize matrix
for (var i = 0; i <= b.length; i++) {
matrix[i] = [i];
}
for (var j = 0; j <= a.length; j++) {
matrix[0][j] = j;
}
// Calculate Levenshtein distance
for (var i = 1; i <= b.length; i++) {
for (var j = 1; j <= a.length; j++) {
if (b.charAt(i – 1) === a.charAt(j – 1)) {
matrix[i][j] = matrix[i – 1][j – 1];
} else {
matrix[i][j] = Math.min(
matrix[i – 1][j – 1] + 1,
matrix[i][j – 1] + 1,
matrix[i – 1][j] + 1
);
}
}
}
return matrix[b.length][a.length];
}
// Function to resize the footage layer to comp width
function resizeFootageToCompWidth(footageLayer, compWidth) {
var sourceRect = footageLayer.sourceRectAtTime(0, false);
var scaleFactor = compWidth / sourceRect.width;
footageLayer.scale.setValue([scaleFactor * 100, scaleFactor * 100]);
}
// Selecting the active folder in the project to search
var project = app.project;
var folder = project.activeItem;
var sequences = folder.items;
// Create an associative array to pair sequences with compositions
var sequenceComps = {};
// Prompt the user to select the photo folder
var footageFolder = Folder().selectDlg(“Select the footage folder”);
if (!footageFolder) {
alert(“No folder selected. Script aborted.”);
} else {
// Get a list of files in the selected footage folder
var footageFiles = footageFolder.getFiles();
// Set a threshold for similarity
var similarityThreshold = 5; // You may need to adjust this based on your needs
// Counter for the number of matches found
var matchCount = 0;
// Iterate through each file
for (var i = 0; i < footageFiles.length; i++) {
var fileName = footageFiles[i].name;
// Parse the firstname and lastname from the file name
var nameParts = fileName.split(“_”);
var lastname = nameParts[0];
var firstname = nameParts[1];
// Find the closest match in sequences
var bestMatch = null;
var minDistance = Infinity;
for (var j = 1; j < sequences.length; j++) {
var sequenceName = sequences[j];
var distance = levenshteinDistance(sequenceName, firstname + ” ” + lastname);
if (distance < minDistance && distance <= similarityThreshold) {
minDistance = distance;
bestMatch = sequenceName;
}
}
if (bestMatch !== null) {
// Check if the file is valid
if (footageFiles[i] instanceof File) {
// Check if we already have a composition for the sequence
var sequenceComp = sequenceComps[bestMatch];
// Import the image into the composition
var importedFootage = app.project.importFile(new ImportOptions(footageFiles[i]));
var footageLayer = sequenceComp.layers.add(importedFootage);
// Resize the image to comp width
var compWidth = sequenceComp.width; // You may need to adjust this based on your comp settings
resizeFootageToCompWidth(footageLayer, compWidth);
// Increment the match count
matchCount++;
} else {
alert(“Skipping non-image file: ” + fileName);
}
}
}
// Display the number of matches and total files found
alert(“Total files in folder: ” + footageFiles.length + “\nTotal matches found: ” + matchCount);
}