Skip to main content
CatoPbx
Inspiring
November 12, 2025
Answered

Script to draw vector circles in Photoshop 27.0.0

  • November 12, 2025
  • 2 replies
  • 86 views

I tried the following script as a .jsx file. I want to draw a vector circle on a layer of the active document in Photoshop 27.0.0. The script runs without any errors, but it fills the whole layer with color (red) rather than drawing a vector circle.

// Draw a vector circle as a Shape Layer

// Parameters
var doc = app.activeDocument;
var radius = 200; // pixels
var centerX = doc.width / 2;
var centerY = doc.height / 2;

// Make a new shape layer with an ellipse path
var desc = new ActionDescriptor();
var ref = new ActionReference();
ref.putClass(stringIDToTypeID("contentLayer"));
desc.putReference(charIDToTypeID("null"), ref);

var desc2 = new ActionDescriptor();
var desc3 = new ActionDescriptor();

// Shape color
var colorDesc = new ActionDescriptor();
colorDesc.putDouble(charIDToTypeID('Rd  '), 255);
colorDesc.putDouble(charIDToTypeID('Grn '), 0);
colorDesc.putDouble(charIDToTypeID('Bl  '), 0);
desc3.putObject(charIDToTypeID('Clr '), charIDToTypeID('RGBC'), colorDesc);

// Shape geometry (ellipse)
var shapeDesc = new ActionDescriptor();
shapeDesc.putUnitDouble(charIDToTypeID('Top '), charIDToTypeID('#Pxl'), centerY - radius);
shapeDesc.putUnitDouble(charIDToTypeID('Left'), charIDToTypeID('#Pxl'), centerX - radius);
shapeDesc.putUnitDouble(charIDToTypeID('Btom'), charIDToTypeID('#Pxl'), centerY + radius);
shapeDesc.putUnitDouble(charIDToTypeID('Rght'), charIDToTypeID('#Pxl'), centerX + radius);

desc3.putObject(charIDToTypeID('Shp '), charIDToTypeID('Elps'), shapeDesc);
desc2.putObject(charIDToTypeID('Type'), stringIDToTypeID('solidColorLayer'), desc3);
desc.putObject(charIDToTypeID('Usng'), stringIDToTypeID('contentLayer'), desc2);

executeAction(charIDToTypeID('Mk  '), desc, DialogModes.NO);

 

Correct answer Stephen Marsh

@CatoPbx - It's drawing a solid fill layer, not a vector ellipse shape layer... Try this:

 

#target photoshop

// Open doc check
if (app.documents.length > 0) {

    // Options
    var autoRevealAll = true; // Set to false to disable automatic reveal-all behavior
    var radius = 200; // Circle radius in pixels

    // Variables
    var doc = app.activeDocument;
    var docWidth = doc.width.as('px');
    var docHeight = doc.height.as('px');
    var centerX = docWidth / 2;
    var centerY = docHeight / 2;
    var top = centerY - radius;
    var left = centerX - radius;
    var bottom = centerY + radius;
    var right = centerX + radius;

    // Check if the ellipse extends beyond the doc bounds
    var needsRevealAll = left < 0 || top < 0 || right > docWidth || bottom > docHeight;

    // Create the ellipse shape layer
    var idMk = charIDToTypeID("Mk  ");
    var desc270 = new ActionDescriptor();
    var idnull = charIDToTypeID("null");
    var ref9 = new ActionReference();
    var idcontentLayer = stringIDToTypeID("contentLayer");
    ref9.putClass(idcontentLayer);
    desc270.putReference(idnull, ref9);
    var idUsng = charIDToTypeID("Usng");
    var desc271 = new ActionDescriptor();

    // Fill color
    var idType = charIDToTypeID("Type");
    var desc272 = new ActionDescriptor();
    var idClr = charIDToTypeID("Clr ");
    var desc273 = new ActionDescriptor();
    desc273.putDouble(stringIDToTypeID("redFloat"), 255);
    desc273.putDouble(stringIDToTypeID("greenFloat"), 0);
    desc273.putDouble(stringIDToTypeID("blueFloat"), 0);
    desc272.putObject(idClr, charIDToTypeID("RGBC"), desc273);
    desc271.putObject(idType, stringIDToTypeID("solidColorLayer"), desc272);

    // Ellipse bounds and center placement
    var idShp = charIDToTypeID("Shp ");
    var desc274 = new ActionDescriptor();
    desc274.putInteger(stringIDToTypeID("unitValueQuadVersion"), 1);
    desc274.putUnitDouble(charIDToTypeID("Top "), charIDToTypeID("#Pxl"), top);
    desc274.putUnitDouble(charIDToTypeID("Left"), charIDToTypeID("#Pxl"), left);
    desc274.putUnitDouble(charIDToTypeID("Btom"), charIDToTypeID("#Pxl"), bottom);
    desc274.putUnitDouble(charIDToTypeID("Rght"), charIDToTypeID("#Pxl"), right);
    desc271.putObject(idShp, charIDToTypeID("Elps"), desc274);

    // Create the ellipse
    desc270.putObject(idUsng, idcontentLayer, desc271);
    executeAction(idMk, desc270, DialogModes.NO);

    // Conditional reveal all
    if (autoRevealAll && needsRevealAll) {
        if (confirm("The ellipse extends beyond the document bounds!" + "\n" + "Reveal all to fit the entire shape?")) {
            executeAction(charIDToTypeID("RvlA"), new ActionDescriptor(), DialogModes.NO);
        }
    }
}

2 replies

Stephen Marsh
Community Expert
Stephen MarshCommunity ExpertCorrect answer
Community Expert
November 13, 2025

@CatoPbx - It's drawing a solid fill layer, not a vector ellipse shape layer... Try this:

 

#target photoshop

// Open doc check
if (app.documents.length > 0) {

    // Options
    var autoRevealAll = true; // Set to false to disable automatic reveal-all behavior
    var radius = 200; // Circle radius in pixels

    // Variables
    var doc = app.activeDocument;
    var docWidth = doc.width.as('px');
    var docHeight = doc.height.as('px');
    var centerX = docWidth / 2;
    var centerY = docHeight / 2;
    var top = centerY - radius;
    var left = centerX - radius;
    var bottom = centerY + radius;
    var right = centerX + radius;

    // Check if the ellipse extends beyond the doc bounds
    var needsRevealAll = left < 0 || top < 0 || right > docWidth || bottom > docHeight;

    // Create the ellipse shape layer
    var idMk = charIDToTypeID("Mk  ");
    var desc270 = new ActionDescriptor();
    var idnull = charIDToTypeID("null");
    var ref9 = new ActionReference();
    var idcontentLayer = stringIDToTypeID("contentLayer");
    ref9.putClass(idcontentLayer);
    desc270.putReference(idnull, ref9);
    var idUsng = charIDToTypeID("Usng");
    var desc271 = new ActionDescriptor();

    // Fill color
    var idType = charIDToTypeID("Type");
    var desc272 = new ActionDescriptor();
    var idClr = charIDToTypeID("Clr ");
    var desc273 = new ActionDescriptor();
    desc273.putDouble(stringIDToTypeID("redFloat"), 255);
    desc273.putDouble(stringIDToTypeID("greenFloat"), 0);
    desc273.putDouble(stringIDToTypeID("blueFloat"), 0);
    desc272.putObject(idClr, charIDToTypeID("RGBC"), desc273);
    desc271.putObject(idType, stringIDToTypeID("solidColorLayer"), desc272);

    // Ellipse bounds and center placement
    var idShp = charIDToTypeID("Shp ");
    var desc274 = new ActionDescriptor();
    desc274.putInteger(stringIDToTypeID("unitValueQuadVersion"), 1);
    desc274.putUnitDouble(charIDToTypeID("Top "), charIDToTypeID("#Pxl"), top);
    desc274.putUnitDouble(charIDToTypeID("Left"), charIDToTypeID("#Pxl"), left);
    desc274.putUnitDouble(charIDToTypeID("Btom"), charIDToTypeID("#Pxl"), bottom);
    desc274.putUnitDouble(charIDToTypeID("Rght"), charIDToTypeID("#Pxl"), right);
    desc271.putObject(idShp, charIDToTypeID("Elps"), desc274);

    // Create the ellipse
    desc270.putObject(idUsng, idcontentLayer, desc271);
    executeAction(idMk, desc270, DialogModes.NO);

    // Conditional reveal all
    if (autoRevealAll && needsRevealAll) {
        if (confirm("The ellipse extends beyond the document bounds!" + "\n" + "Reveal all to fit the entire shape?")) {
            executeAction(charIDToTypeID("RvlA"), new ActionDescriptor(), DialogModes.NO);
        }
    }
}
CatoPbx
CatoPbxAuthor
Inspiring
November 13, 2025

Thank you - works great!

Stephen Marsh
Community Expert
Community Expert
November 13, 2025
quote

Thank you - works great!


By @CatoPbx


You're welcome!

Genius
November 12, 2025

Did you write this?

CatoPbx
CatoPbxAuthor
Inspiring
November 13, 2025

No, Google search provided me with this answer when I searched on the above title.