#target photoshop

//texture map creator script for L3tt3rM4pp3r After Effects plugin;
//usage: Create PSD file with one white symbol on black background per layer; 
//the script will analyze glyph data and create new symbol map - 
//PSD file with symbols placed from left to right, sorted by overall symbol area

function getAverageColorByLayer(inDoc, inLayerNum)
{
    app.preferences.rulerUnits = Units.PIXELS;

    for(var i=0; i<inDoc.colorSamplers.length; i++) 
    {
        inDoc.colorSamplers[i].remove();
    }
    for(var i=0; i<inDoc.layers.length; i++) 
    {
        inDoc.layers[i].visible=false;
    }
    inDoc.layers[inLayerNum].visible=true;   
    var CP = inDoc.colorSamplers.add([0.5*inDoc.width,0.5*inDoc.height]);
    sel=inDoc.selection.selectAll();    
    inDoc.layers[inLayerNum].applyAverage();
    var sColor = new SolidColor();
    sColor=CP.color;
    executeAction( charIDToTypeID('undo'), undefined, DialogModes.NO );
    inDoc.selection.deselect();
    return sColor;
} 


function calcLayerDensity (doc,inLayerNum)
{
    var density=0;
    var m_color=getAverageColorByLayer (doc, inLayerNum)  
    density=(m_color.rgb.red*1+m_color.rgb.blue*1+m_color.rgb.green*1)/3.0;        
    return Number(m_color.rgb.red); 
}


function sortGlyphs(a, b)
{
    if(a.density<b.density) return -1 
        if(a.density>b.density) return 1  
            return 0
    }



    function lm_Layer2Ramp()
    {
        //open source psd with symbols;
        //psd file with one symbol per layer is expected;
        //white symbol, black background

        var fontFile = File.openDialog("Open doc with symbol layers","PSD:*.psd");
        if (!fontFile)
        {
            alert("Could not open file.");
            return;
        }

        var sourceDoc=app.open(File(fontFile));
        sourceDoc.mode=RGBColor;
        var layerCount=sourceDoc.layers.length;    
        var g_TargetDocWidth=sourceDoc.width*layerCount;
        var g_TargetDocHeight=sourceDoc.height;
        var g_TargetGlyphWidth=sourceDoc.width;
        var g_TargetGlyphHeight=sourceDoc.height;
        var glyphs=[];
        
        //fill glyphs array; calculate densitiy per symbol
        for (i=0;i<layerCount;i++)
        {
            var m_density=calcLayerDensity (sourceDoc,i)

            glyph={id:i, density:Number(m_density)};

            glyphs.push(glyph);                
        }
        
        //sort glyphs by 'density' (by area of the symbol):
        glyphs=glyphs.sort(sortGlyphs);

        
        //create target document for symbol map and fill its base layer with black:
        targetDocName=sourceDoc.name.split(".")[0]+"_map_"+glyphs.length
        targetDoc=app.documents.add(UnitValue(Number(g_TargetDocWidth), "px"), UnitValue(Number(g_TargetDocHeight), "px"),72,targetDocName,NewDocumentMode.RGB);
        targetDoc.mode=RGBColor;
        app.activeDocument=targetDoc;
        var targetLayer= app.activeDocument.artLayers.add();
        targetLayer.name = "BackgroundLayer";
        targetLayer.blendMode = BlendMode.NORMAL;
        var fillColor = new SolidColor();
        fillColor.rgb.red = 0;
        fillColor.rgb.green = 0;
        fillColor.rgb.blue = 0;
        app.activeDocument.selection.selectAll();
        app.activeDocument.selection.fill(fillColor, ColorBlendMode.NORMAL, Number(100), false);
        
        //iterate thru glyph layers:
        for (i=0;i<layerCount;i++)
        {
            //select and solo layer of glyph[i]
            app.activeDocument=sourceDoc;
            for (j=0;j<layerCount;j++)
            {
                sourceDoc.layers[j].visible=false;          
            }
            sourceDoc.layers[Number(glyphs[i].id)].visible=true;

            //Copy glyph from sourceDoc to targetDoc, place according to sorted glyphs array:
            app.activeDocument.selection.selectAll();
            sourceDoc.selection.copy(true);       
            app.activeDocument=targetDoc;
            targetDoc.selection.select([
            [g_TargetGlyphWidth*i*1,0],
            [g_TargetGlyphWidth*i*1, g_TargetGlyphHeight],
            [g_TargetGlyphWidth*i*1+g_TargetGlyphWidth*1, g_TargetGlyphHeight],
            [g_TargetGlyphWidth*i*1+g_TargetGlyphWidth*1, 0],
            ], SelectionType.REPLACE, 0, false);
            targetDoc.paste (true);
        }
}
lm_Layer2Ramp();