Exit
  • Global community
    • Language:
      • Deutsch
      • English
      • Español
      • Français
      • Português
  • 日本語コミュニティ
  • 한국 커뮤니티
0

Script to insert file name to title field in file info

Explorer ,
Jul 11, 2024 Jul 11, 2024

Hi all

I need a script that can be run from a batch action that copies the name of the individual file and pastes it into the title field in file info.
Anyone have one?
Thanks

Dave Smith

TOPICS
Actions and scripting
799
Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines

correct answers 2 Correct answers

Explorer , Jul 11, 2024 Jul 11, 2024

Hi Stephen

This is what ChatGPT finally came up with. I deleted my copyright info in case someone else want to use it.

Your thoughts?

#target photoshop

function copyFileNameToTitle() {
if (app.documents.length > 0) {
var doc = app.activeDocument;
var fileName = doc.name.replace(/\.[^\.]+$/, ''); // Get the file name without extension

try {
// Ensure the XMP library is available
if (ExternalObject.AdobeXMPScript == undefined) {
ExternalObject.AdobeXMPScript = new ExternalObject("lib:AdobeXMPScript");
}

// Get

...
Translate
Community Expert , Jul 11, 2024 Jul 11, 2024
quote

Your thoughts?


By @dcsimages

 

I haven't tested it, however, I can see that it is also adding a copyright flag and a copyright text line, which you didn't previously mention so the scripts I posted don't include this.

 

You could try to graft those extra bits of code into the scripts I posted to directly process metadata. Let me know if you hit any roadblocks.

 

I would not open each JPEG into Photoshop to update metadata, whether it was for 9 or 91,000 images, it's too slow and contributes to

...
Translate
Adobe
Community Expert ,
Jul 11, 2024 Jul 11, 2024

@dcsimages 

 

What file formats are being processed? Adobe Bridge would be a better place to do this, especially if the files are JPEG.

 

Photoshop can also update metadata without having to open the file.

 

Do you really need to do this on an open file? Is the batch action performing other steps, or only the metadata?

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Explorer ,
Jul 11, 2024 Jul 11, 2024

Hi Stephen

They are jpeg files.  I have about 91000 files to process.

While I was waiting for an answer, I tried Chat GPT and after 5 iterations correcting errors, by telling it the error message, it was able to come up with a script that I can run by using an action and automate>batch.

What's the process using bridge and is the info written into the actual file and not a separate XML file?

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Community Expert ,
Jul 11, 2024 Jul 11, 2024

JPEG files need to be decompressed and recompressed, which degrades image quality when opening into Photoshop and resaving from Photoshop.

 

Both Bridge and Photoshop can "inject" the metadata directly into the file without decompressing/recompressing the image data. Apart from quality, it is much faster to update metadata than to work with image data, especially if you have 91,000 files!

 

Here is an old Bridge script that should still work with later versions:

 

// Filename to metadata title.jsx
// https://forums.adobe.com/message/3596812
#target bridge
   if( BridgeTalk.appName == "bridge" ) {
FT = MenuElement.create("command", "Add FileName to Description", "at the end of Tools");
}
FT.onSelect = function () {
var thumbs = app.document.selections;
if(!thumbs.length) return;
if (ExternalObject.AdobeXMPScript == undefined)  ExternalObject.AdobeXMPScript = new ExternalObject("lib:AdobeXMPScript");
for(var a in thumbs){
var selectedFile = thumbs[a].spec;
var FileName = decodeURI(selectedFile.name).replace(/\.[^\.]+$/, '')
      var myXmpFile = new XMPFile( selectedFile.fsName, XMPConst.UNKNOWN, XMPConst.OPEN_FOR_UPDATE);
  var myXmp = myXmpFile.getXMP();
var Desc=[];
var count =  myXmp.countArrayItems(XMPConst.NS_DC, "description");
for(var i = 1;i <= count;i++){
Desc.push(myXmp.getArrayItem(XMPConst.NS_DC, "description", i));
    }
Desc=Desc.toString() + " " + FileName;
        myXmp.deleteProperty(XMPConst.NS_DC, "description");
        myXmp.appendArrayItem(XMPConst.NS_DC, "description", Desc, 0, XMPConst.ALIAS_TO_ALT_TEXT);
        myXmp.setQualifier(XMPConst.NS_DC, "description[1]", "http://www.w3.org/XML/1998/namespace", "lang", "x-default");
        if (myXmpFile.canPutXMP(myXmp)) {
        myXmpFile.putXMP(myXmp);
         myXmpFile.closeFile(XMPConst.CLOSE_UPDATE_SAFELY);
         }
    }
}

 

If you wish to keep the filename extension of JPG/JPEG, then remove the following:

 

.replace(/\.[^\.]+$/, '')

 

https://prepression.blogspot.com/2017/11/downloading-and-installing-adobe-scripts.html

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Community Expert ,
Jul 11, 2024 Jul 11, 2024

This script adds the filename to both the Title and Description metadata, it is easy enough to remove the Description bits if needed:

 

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Community Expert ,
Jul 11, 2024 Jul 11, 2024

Another Bridge script:

 

/**
* @@@BUILDINFO@@@ FilenametoTitle.jsx !Version! Tue Nov 26 2019 09:07:36 GMT-0500
*/
/*
Utility Pack Scripts created by David M. Converse ©2018-19

Writes filename to Title metadata field.

/* Modified 30 March 2020 by Stephen Marsh to retain original filename in full */

/*
Licensed under the Apache License, Version 2.0 (the "License");
you may not use this file except in compliance with the License.
You may obtain a copy of the License at

    http://www.apache.org/licenses/LICENSE-2.0

Unless required by applicable law or agreed to in writing, software
distributed under the License is distributed on an "AS IS" BASIS,
WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
See the License for the specific language governing permissions and
limitations under the License.
*/

#target bridge

if (BridgeTalk.appName == 'bridge') {
    try {
        var FilenametoTitle = new Object; //id object for this script
        #include "prefsReader.jsxinc" //shared prefs read code

        //create menu
        if (useMenu == true) { //use Tools submenu
            if (MenuElement.find('utilPack') == null) { //submenu not yet created
                MenuElement.create('menu', 'Utility Script Pack', 'at the end of Tools', 'utilPack');
            }
            var ftCmd = MenuElement.create('command', 'Filename to Title', 'at the end of utilPack');
        }
        else { //do not use submenu
            var ftCmd = MenuElement.create('command', 'Filename to Title', 'at the end of Tools');
        }

        if (useCMenu == true) { //use contextual submenu
            if (MenuElement.find('cutilPack') == null) {
                MenuElement.create('menu', 'Utility Script Pack', 'after Thumbnail/Open', 'cutilPack');
            }
            var ftContCmd = MenuElement.create('command', 'Filename to Title', 'at the end of cutilPack'); //add to Contextual menu
        }
        else { //do not use contextual submenu
            var ftContCmd = MenuElement.create('command', 'Filename to Title', 'after Thumbnail/Open', this.menuID); //add to Contextual menu
        }
    }
    catch (e) {
        //alert(e + e.line);
    }
}

ftCmd.onSelect = function () {
    ftAddFilenameToTitle();
}

ftContCmd.onSelect = function () {
    ftAddFilenameToTitle();
}

function ftAddFilenameToTitle() {
    try {
        var ftThumbs = app.document.selections; //get selected thumbnails
        if (!ftThumbs.length) return; //nothing selected
        if (ExternalObject.AdobeXMPScript == undefined) ExternalObject.AdobeXMPScript = new ExternalObject('lib:AdobeXMPScript');
        for (var a in ftThumbs) { //loop through thumbs
            var ftTitle = ftThumbs[a].name; //get filename
            //remove filename after last dash character
            //to retain filename after dash, comment out lines 69-73
            //ftTitle = ftTitle.split('-');
            //if(ftTitle.length > 1){
            //    ftTitle.length--;
            //    }
            //ftTitle = ftTitle.join('-');
            //remove filename after last period character
            //ftTitle = ftTitle.split('.');
            //if(ftTitle.length > 1){
            //    ftTitle.length--;
            //    }
            //ftTitle = ftTitle.join('.');
            var ftMeta = ftThumbs[a].synchronousMetadata;
            var ftXMP = new XMPMeta(ftMeta.serialize());
            ftXMP.deleteProperty(XMPConst.NS_DC, 'title'); //delete old title
            ftXMP.appendArrayItem(XMPConst.NS_DC, 'title', ftTitle, 0, XMPConst.ALIAS_TO_ALT_TEXT); //write new title
            ftXMP.setQualifier(XMPConst.NS_DC, 'title[1]', 'http://www.w3.org/XML/1998/namespace', 'lang', 'x-default');
            var ftUpdatedPacket = ftXMP.serialize(XMPConst.SERIALIZE_OMIT_PACKET_WRAPPER | XMPConst.SERIALIZE_USE_COMPACT_FORMAT);
            ftThumbs[a].metadata = new Metadata(ftUpdatedPacket); //write to file
        }
    }
    catch (e) {
        //alert(e + e.line);
    }
}
Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Community Expert ,
Jul 11, 2024 Jul 11, 2024

Here is a Photoshop script that "injects" the filename as title metadata into all files at the root level of the selected folder, without having to process the image data:

 

 
If you wanted to do this on an open image via a batch action in Photoshop, then it could be as simple as:
 
#target photoshop
app.activeDocument.info.title = app.activeDocument.name.replace(/\.[^\.]+$/, '');
Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Explorer ,
Jul 11, 2024 Jul 11, 2024

Hi Stephen

This is what ChatGPT finally came up with. I deleted my copyright info in case someone else want to use it.

Your thoughts?

#target photoshop

function copyFileNameToTitle() {
if (app.documents.length > 0) {
var doc = app.activeDocument;
var fileName = doc.name.replace(/\.[^\.]+$/, ''); // Get the file name without extension

try {
// Ensure the XMP library is available
if (ExternalObject.AdobeXMPScript == undefined) {
ExternalObject.AdobeXMPScript = new ExternalObject("lib:AdobeXMPScript");
}

// Get the current XMP metadata
var xmp = new XMPMeta(doc.xmpMetadata.rawData);

// Remove existing title if any
xmp.deleteProperty(XMPConst.NS_DC, "title");

// Add new title as an array
xmp.appendArrayItem(XMPConst.NS_DC, "title", fileName, 0, XMPConst.ARRAY_IS_ORDERED);

// Set Copyright Status to "Copyrighted"
xmp.setProperty(XMPConst.NS_XMP_RIGHTS, "Marked", "True");

// Add Copyright description
xmp.setProperty(XMPConst.NS_DC, "rights", "Copyrighted by XXXXXXX ");

// Serialize the XMP data back to the document
doc.xmpMetadata.rawData = xmp.serialize(XMPConst.SERIALIZE_USE_COMPACT_FORMAT);
} catch (e) {
// Handle error
}
}
}

// Run the function
copyFileNameToTitle();

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Community Expert ,
Jul 11, 2024 Jul 11, 2024
quote

Your thoughts?


By @dcsimages

 

I haven't tested it, however, I can see that it is also adding a copyright flag and a copyright text line, which you didn't previously mention so the scripts I posted don't include this.

 

You could try to graft those extra bits of code into the scripts I posted to directly process metadata. Let me know if you hit any roadblocks.

 

I would not open each JPEG into Photoshop to update metadata, whether it was for 9 or 91,000 images, it's too slow and contributes to minor quality loss. Directly processing the metadata would be my best advice.

 

Yet another option is to use ExifTool to update the metadata, this would be my tool of choice for 91,000 images as it is CLI based (Windows OS would use double quotes " rather than ' single quotes as used on the Mac):

 

exiftool -overwrite_original_in_place '-title<${filename;s/\.[^.]*$//}' 'system path to top-level root folder or file'

 

or

 

exiftool -overwrite_original_in_place '-title<${filename;s/\.[^.]*$//}' -XMP-xmpRights:Marked=True -Photoshop:CopyrightFlag=True -XMP-dc:Rights='Copyrighted by XXXXXXX' -IFD0:Copyright='Copyrighted by XXXXXXX' -IPTC:CopyrightNotice='Copyrighted by XXXXXXX' 'system path to top-level root folder or file'

 

 

Here's another Bridge script, where I have added the copyright flag and string:

 

// https://imagesimple.wordpress.com/2011/08/24/cs5-filename-to-title-script/

#target bridge

if (BridgeTalk.appName == "bridge") {
    FT = MenuElement.create("command", "TEST - Add FileName to Title", "at the end of Tools");
}
FT.onSelect = function () {
    AddFilenameToTitle();
}
function AddFilenameToTitle() {
    var thumbs = app.document.selections;
    if (!thumbs.length) return;
    if (ExternalObject.AdobeXMPScript == undefined) ExternalObject.AdobeXMPScript = new
        ExternalObject("lib:AdobeXMPScript");
    for (var a in thumbs) {

        var selectedFile = thumbs[a].spec;

        var Title = decodeURI(selectedFile.name).replace(/\.[^\.]+$/, '');

        var myXmpFile = new XMPFile(selectedFile.fsName, XMPConst.UNKNOWN,
            XMPConst.OPEN_FOR_UPDATE);
        var myXmp = myXmpFile.getXMP();
        
        myXmp.deleteProperty(XMPConst.NS_DC, "title");
        myXmp.appendArrayItem(XMPConst.NS_DC, "title", Title, 0,
            XMPConst.ALIAS_TO_ALT_TEXT);
        myXmp.setQualifier(XMPConst.NS_DC, "title[1]",
            "http://www.w3.org/XML/1998/namespace", "lang", "x-default");

        myXmp.setProperty(XMPConst.NS_XMP_RIGHTS, "Marked", "True");

        myXmp.setProperty(XMPConst.NS_DC, "rights", "Copyrighted by XXXXXXX ");

        if (myXmpFile.canPutXMP(myXmp)) {
            myXmpFile.putXMP(myXmp);
            myXmpFile.closeFile(XMPConst.CLOSE_UPDATE_SAFELY);
        }
    }
}
Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Explorer ,
Jul 17, 2024 Jul 17, 2024

I ended up using exiftools.

Thanks.

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Explorer ,
Jul 19, 2024 Jul 19, 2024

Hi Stephen
Would it be possible to add to this code a line to also write the file name to the author title at the same time?
Having some issues with the site I'm uploading to consistantly picking up the document title field and this was a suggestion from a fellow user who uses the author title field instead.
exiftool -overwrite_original_in_place '-title<${filename;s/\.[^.]*$//}' 'system path to top-level root folder or file'

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines
Community Expert ,
Jul 19, 2024 Jul 19, 2024
LATEST

@dcsimages 

 

My previous example assumed that metadata entries were empty, in this new example, I explicitly removed any metadata in the target fields before writing to them. Additionally, I am writing to both the XMP and legacy IPTC fields for backwards/wider compatibility. Perhaps if you write to the XMP-dc:Title and IPTC:ObjectName you may not even need to use the additional XMP-photoshop:AuthorsPosition and IPTC:By-lineTitle as suggested by the other user.

 

exiftool -overwrite_original_in_place -XMP-dc:Title= -XMP-photoshop:AuthorsPosition= -IPTC:By-lineTitle= -IPTC:ObjectName= '-XMP-dc:Title<${filename;s/\.[^.]*$//}' '-XMP-photoshop:AuthorsPosition<${filename;s/\.[^.]*$//}' '-IPTC:By-lineTitle<${filename;s/\.[^.]*$//}' '-IPTC:ObjectName<${filename;s/\.[^.]*$//}' 'system path to top-level root folder or file'

 

A variation on the above is to first write to the title, and then copy the title to the other fields. This may run a little slower, so you may wish to test a small batch to see which will run faster:

 

exiftool -XMP-dc:Title= -XMP-photoshop:AuthorsPosition= -IPTC:By-lineTitle= -IPTC:ObjectName= '-XMP-dc:Title<${filename;s/\.[^.]*$//}' -execute '-XMP-photoshop:AuthorsPosition<${XMP-dc:Title}' '-IPTC:By-lineTitle<${XMP-dc:Title}' '-IPTC:ObjectName<${XMP-dc:Title}' -common_args -overwrite_original_in_place 'system path to top-level root folder or file'

 

(Windows OS would use double quotes " rather than ' single quotes as used on the Mac)

Translate
Report
Community guidelines
Be kind and respectful, give credit to the original source of content, and search for duplicates before posting. Learn more
community guidelines