10 Replies Latest reply on Apr 8, 2010 7:55 PM by Marketka1

    looking for scripter

    Marketka1

      I'm wildife biology student and I'm using Adobe Photoshop to quantify color of wild animals. I'm looking for someone who can help me to adjust a java script.

      The script automatizes random point selection in an image and gives an average color of the points.

      I need the script to do two more things for me:

      1. Save the RGB values from the random points into a spreadsheet so I can calculate stadard error OR provide the error along with the average RGB.

      2. Randomly select points in a highlighted area of the photo (now it randomly selects points in the whole image, but I need it to select just from the animal (not the background).

      If you know how to add either of these to the script, please let me know.

      Thank you,

      Marketa Zimova

        • 1. Re: looking for scripter
          c.pfaffenbichler Level 9

          Edit: Sorry, error on my side.

          • 2. Re: looking for scripter
            Michael L Hale Level 5

            Can you post the script that you need edited? I think it should not be too hard to export the samples to a csv file that Excel can read.

             

            I'm not sure that it will be possible to change it so it only samples just from the animal.

            • 3. Re: looking for scripter
              Marketka1 Level 1

              The script is posted bellow. I just copied and pasted it from jsx file. I dont know how post the actual file in here.

              It would be great if you know how to have it export the samples to csv file :it would really be awesome.

               

              And with the selection- I was just thinking if I could select an area with marquee tool or lasso and then if it could randomly sample just within that area. OR a really cool alternative to this would be if I could be deciding with each random point whether I want to keep that point and add it to a pool of points that I want to be saved in a csv file or not (e.g. if the random selected point was on the animal I would save it and if it was on the background I would delete it).

              Hope this makes sense.

              Thank you so much!

               

               

               

              // This script demonstrates how to create random selections in Photoshop and how to make an average of the colours

              // in the selection. You can also choose whether to sample the average colour for each selection made, or to sample

              // the average colour of all the selections.

               

              //Usage notes: this script will only work on RGB images and is designed to work on images containing only one layer.

              // ***** Be aware that it does edit the image in order to average the colour within a selection.   *****

               

              #target "photoshop"

               

              if(!app.documents.length > 0){

              alert("Please open an image first!")

              }

              else{

               

               

              //setup some defaults

              var noOfSelections = 1;

              var sizeOfSelection = 10;

              var avgOverAllSelections = false;

              var avgColour = new SolidColor;

               

              noOfSelections = Number(prompt("How many selections should be made?", noOfSelections, "Colour Evaluation Script"));

              sizeOfSelection = Number(prompt("What size should each selection be?", sizeOfSelection, "Colour Evaluation Script"));

              avgOverAllSelections = confirm("Sample colour for each selection (click Yes) or sample the colour over all selections (click No)?", true, "Colour Evaluation Script");

               

              //get the current ruler units then change it to pixels

              var origRulerUnits = app.preferences.rulerUnits;

              app.preferences.rulerUnits = Units.PIXELS;

               

              //gather some information about the document

              var myDoc = app.activeDocument;

              var docWidth = myDoc.width;

              var docHeight = myDoc.height;

               

              //clear any existing selection

              myDoc.selection.deselect();

               

              //make the new selection and measure the average colour

              for (i = 0; i < noOfSelections; i++){

               

              var xPosition = randomSelection(docWidth);

              var yPosition = randomSelection(docHeight);

               

              if(avgOverAllSelections == true){

              //make a selection, replace any existing selection

              myDoc.selection.select(new Array (new Array(xPosition, yPosition),new Array(xPosition + sizeOfSelection, yPosition), new Array(xPosition + sizeOfSelection, yPosition + sizeOfSelection), new Array(xPosition, yPosition + sizeOfSelection)), SelectionType.REPLACE, 0, false);

               

              //average the colour of the selection

              myDoc.activeLayer.applyAverage();

               

              placeColourSampler(xPosition + sizeOfSelection/2, yPosition + sizeOfSelection/2);

              //get the colour of the selection

              avgColour = getColourOfSelection();

              //show an alert that displays the values for the RGB components of the sampled colour

              alert("Red: " + Math.round(avgColour.rgb.red) + "\n" + "Green: " + Math.round(avgColour.rgb.green) + " \n" + "Blue: " + Math.round(avgColour.rgb.blue));

              //set the current foreground colour to be the one we just sampled

              app.foregroundColor = avgColour;

              //delete the colour sampler

              deleteSampler();

              }

              else{

              //make a selction, add it to the existing selections

              myDoc.selection.select(new Array (new Array(xPosition, yPosition),new Array(xPosition + sizeOfSelection, yPosition), new Array(xPosition + sizeOfSelection, yPosition + sizeOfSelection), new Array(xPosition, yPosition + sizeOfSelection)), SelectionType.EXTEND, 0, false);

               

              if(i == noOfSelections - 1){

              //this is the last selection now we can make the average of all the selections we have made

              myDoc.activeLayer.applyAverage();

              //get the colour of the selection

              avgColour = getColourOfSelection();

              //show an alert that displays the values for the RGB components of the sampled colour

              alert("Red: " + Math.round(avgColour.rgb.red) + "\n" + "Green: " + Math.round(avgColour.rgb.green) + " \n" + "Blue: " + Math.round(avgColour.rgb.blue));

              //set the current foreground colour to be the one we just sampled

              app.foregroundColor = avgColour;

              //delete the colour sampler

              deleteSampler();

              }

              }

               

              }

               

               

              //set the original ruler units back

              app.preferences.rulerUnits = origRulerUnits;

              }

               

               

              //create random number based on dimensions of image

              function randomSelection(seed){

               

              do {

               

              var random = Math.floor(Math.random()*seed + 1)

              }

              while (random > seed -10);

               

              return random;

              }

               

              //deletes the color sampler from the document

              function deleteSampler(){

               

              var idDlt = charIDToTypeID( "Dlt " );

                  var desc294 = new ActionDescriptor();

                  var idnull = charIDToTypeID( "null" );

                      var ref170 = new ActionReference();

                      var idClSm = charIDToTypeID( "ClSm" );

                      var idOrdn = charIDToTypeID( "Ordn" );

                      var idAl = charIDToTypeID( "Al  " );

                      ref170.putEnumerated( idClSm, idOrdn, idAl );

                  desc294.putReference( idnull, ref170 );

              executeAction( idDlt, desc294, DialogModes.NO );

               

               

              }

               

              //places a Colour Sampler at the specified coordinates

              function placeColourSampler(XCoord, YCoord){

               

              var idMk = charIDToTypeID( "Mk  " );

                  var descriptor1 = new ActionDescriptor();

                  var idnull = charIDToTypeID( "null" );

                      var reference1 = new ActionReference();

                      var idClSm = charIDToTypeID( "ClSm" );

                      reference1.putClass( idClSm );

                  descriptor1.putReference( idnull, reference1 );

                  var idPstn = charIDToTypeID( "Pstn" );

                      var samplerCoords = new ActionDescriptor();

                      var idHrzn = charIDToTypeID( "Hrzn" );

                      var idPxl = charIDToTypeID( "#Pxl" );

                      samplerCoords.putUnitDouble( idHrzn, idPxl, XCoord);

                      var idVrtc = charIDToTypeID( "Vrtc" );

                      var idPxl = charIDToTypeID( "#Pxl" );

                      samplerCoords.putUnitDouble( idVrtc, idPxl, YCoord );

                  var idPnt = charIDToTypeID( "Pnt " );

                  descriptor1.putObject( idPstn, idPnt, samplerCoords );

              executeAction( idMk, descriptor1, DialogModes.NO );

               

              }

               

              //gets the colour of a selection

              function getColourOfSelection(){

               

              //place a Colour Sampler in the middle of our selection

              placeColourSampler(xPosition + sizeOfSelection/2, yPosition + sizeOfSelection/2);

               

              var colourSamplers = myDoc.colorSamplers;

              var theColour = new SolidColor;

              theColour = colourSamplers[0].color;

               

              return theColour;

              }

              • 4. Re: looking for scripter
                c.pfaffenbichler Level 9
                And with the selection- I was just thinking if I could select an area with marquee tool or lasso and then if it could randomly sample just within that area.

                That should indeed be possible, but a bit complicated for me – Michael (or some of the other regulars) probably could accomplish it in a more concise fashion.

                 

                I wonder about the relevance of the measured colours, though …

                Have the photographs all been taken under standardized conditions regarding the spatial relation (and nature/intensity) of light-source/s, camera and subjects?

                And translating rgb-values to spectral information may be somewhat of a problem, too.

                • 5. Re: looking for scripter
                  Michael L Hale Level 5

                  With the script below you make a rough selection of the area you want sampled then run the script. It will ask how many samples to take, the size of each sample area in px. It then dupes the selection to a new layer, turns off the orginal layer, and takes the samples. If the random sample is in a transparent area it tries again. If it finds a color it prompts the position and color of the sample and asks if you want to keep that sample. When it has the requested number of approved samples it writes a csv file to the desktop.

                   

                  The selection can be make with any of the selections methods and doesn't need to be to accurate. But the better the selection the less background samples will be made.

                   

                  // script expects an open single layer document in RGB mode with a selection of the area to sample.
                  // the csv file is written to the desktop and the script will overwrite an existing samples.csv
                  
                  main();
                  function main(){
                       if( app.documents == 0 ) {
                            alert("No image to process");
                            return;
                       }
                       var doc = app.activeDocument;
                       if( doc.mode != DocumentMode.RGB ){
                            alert("Image must be in RGB mode to sample");
                            return;
                       }
                       if( !hasSelection( doc ) ){
                            alert("Please make a selection of target animal\rbefore running script");
                            return;
                       }
                       var numberOfSamples = Number(prompt("How many selections should be made?",10));
                       if(  numberOfSamples == NaN )  numberOfSamples = 1;
                       var sampleSize = Number(prompt("What size should each selection be?(NxN px)", 3));
                       if( sampleSize == NaN ) sampleSize = 3;
                       var originalLayer = doc.activeLayer;// make reference to current layer
                       executeAction( charIDToTypeID( "CpTL" ), undefined, DialogModes.NO );// dupe selection to new layer
                       var sampleLayer = doc.activeLayer;// make reference to that new layer
                       originalLayer.visible = false;// turn off original layer
                       var samples = [];// make array to hold samples
                       var bounds = sampleLayer.bounds;
                       var layerX = bounds[0].as('px');
                       var layerY = bounds[0].as('px');
                       var layerWidth = bounds[2].as('px') - bounds[0].as('px');
                       var layerHeight = bounds[3].as('px') - bounds[1].as('px');
                       // make requested number of samples
                       var s = 0;
                       while(  s < numberOfSamples ){
                            var sX = randomRange( layerX, layerX + layerWidth );
                            var sY = randomRange( layerY, layerY + layerHeight );
                            var cs = doc.colorSamplers.add( [ new UnitValue( sX, 'px' ), new UnitValue( sY, 'px' ) ] );
                            var sample = getSelectionColor( 0, sampleSize );
                            if( undefined != sample ){
                                 var keep = confirm("Sample at px "+sX+','+sY+ ' is R:'+sample.rgb.red+', G:'+sample.rgb.green+', B:'+sample.rgb.blue+'.\rKeep?',true);
                                 if( keep ){
                                      samples.push( getSelectionColor( 0, sampleSize ) );
                                      s++;
                                 }
                            }
                            cs.remove();
                       }
                       var sampleFile = new File('~/Desktop/samples.csv');
                       sampleFile.open('w');
                       sampleFile.writeln('red,green,blue');
                       for( var s = 0; s< samples.length;s++ ){
                            sampleFile.writeln( samples[s].rgb.red+','+samples[s].rgb.green+','+samples[s].rgb.blue );
                       }
                       sampleFile.close();
                       
                       function randomRange( minVal, maxVal ){
                            return minVal+Math.floor(Math.random()*( maxVal-minVal ));
                       }
                       ///////////////////////////////////////////////////////////////////////////////
                       // Function: hasSelection
                       // Description: Detremines if there is a selection
                       // Usage: alert(hasSelection()) 
                       // Input:
                       // Return:  true or false
                       // Dependencies:
                       /////////////////////////////////////////////////////////////////////////////////
                        function hasSelection(doc) { 
                            var res = false; 
                            var as = doc.activeHistoryState; 
                            doc.selection.deselect(); 
                            if (as != doc.activeHistoryState) { 
                                 res = true; 
                                 doc.activeHistoryState = as; 
                            } 
                            return res; 
                       }
                       // adapted from scirpt by jugenjury at adobefourms
                       function getSelectionColor( s, A ){
                            var origRulerUnits = app.preferences.rulerUnits;
                            app.preferences.rulerUnits = Units.PIXELS;
                            try{
                                 if ( undefined == s ) { s=0; }
                                 if ( undefined == A ) { A=1; }
                                 var CP = app.activeDocument.colorSamplers;
                                 var sampleSize = A;
                                 var r=((A-1)/2);
                                 var x=Math.round(CP[s].position[0]-r);
                                 var y=Math.round(CP[s].position[1]-r);
                                 activeDocument.selection.select([[x, y], [x+sampleSize, y], [x+sampleSize, y+sampleSize], [x, y+sampleSize]], SelectionType.REPLACE, 0, false);
                                 activeDocument.activeLayer.applyAverage();
                                 var re = RegExp( '[123456789]' );
                                 var sColor = new SolidColor();
                                 if ( activeDocument.mode == DocumentMode.GRAYSCALE ) {
                                      var gv = re.exec(activeDocument.channels[0].histogram.toString() ).index/2;
                                      sColor.gray.gray = 100 * (gv/255);
                                 }
                                 if ( activeDocument.mode == DocumentMode.RGB ) {
                                      sColor.rgb.red = re.exec(activeDocument.channels[0].histogram.toString() ).index/2;
                                      sColor.rgb.green = re.exec( activeDocument.channels[1].histogram.toString() ).index/2;
                                      sColor.rgb.blue = re.exec( activeDocument.channels[2].histogram.toString() ).index/2;
                                 }
                                 if ( activeDocument.mode == DocumentMode.LAB ) {
                                      var lv = re.exec(activeDocument.channels[0].histogram.toString() ).index/2;
                                      sColor.lab.l = 100 * ( lv/255 );
                                      sColor.lab.a = ( re.exec( activeDocument.channels[1].histogram.toString() ).index/2 ) - 128;
                                      sColor.lab.b = ( re.exec( activeDocument.channels[2].histogram.toString() ).index/2 ) -128;
                                 }
                                 if ( activeDocument.mode == DocumentMode.CMYK ) {
                                      var cv = re.exec(activeDocument.channels[0].histogram.toString() ).index/2;
                                      sColor.cmyk.cyan = 100 * (1-(cv/255));
                                      cv = re.exec(activeDocument.channels[1].histogram.toString() ).index/2;
                                      sColor.cmyk.magenta = 100 * (1-(cv/255));
                                      cv = re.exec(activeDocument.channels[2].histogram.toString() ).index/2;
                                      sColor.cmyk.yellow = 100* (1-(cv/255));
                                      cv = re.exec(activeDocument.channels[3].histogram.toString() ).index/2;
                                      sColor.cmyk.black = 100 * (1-(cv/255));
                                 }
                                 executeAction( charIDToTypeID('undo'), undefined, DialogModes.NO );
                                 activeDocument.selection.deselect();
                                 return sColor;
                                 app.preferences.rulerUnits = origRulerUnits;
                            }catch(e){
                                 app.preferences.rulerUnits = origRulerUnits;
                            }
                       }
                  }
                  
                  1 person found this helpful
                  • 6. Re: looking for scripter
                    Marketka1 Level 1

                    Wow, this is truly amazing. Thank you so much!

                     

                    May I have one more request for you please????

                     

                    The problem is that when it shows the sample selection on the animal it only shows a little target- is there a way to actually show the true size of the selection? I know this seems like a pain but I need to see the whole sample area to see what's included in the sample- the animals I'm studying are snowshoe hares- and they are always hiding under trees and in bushes and so the twigs and other objects are always in the way. Therefore it would be great to see if the sample area include purely the hare's coat or also some twigs (I dont want twigs).

                     

                    I really appreciate your help. May I write your name in the acknowledgement section of my thesis and article?

                    Marketa

                    • 7. Re: looking for scripter
                      Michael L Hale Level 5

                      This might be a little better at showing where the sample area is in the image. The problem is that the 'marching ants' don't march while the prompt is showing so it is still easy to miss.

                       

                      // script expect  an open single layer document in RGB mode with a selection of the area to sample.
                      // the csv file is written to the desktop and the script will overwrite an existing samples.csv
                      
                      main();
                      function main(){
                           if( app.documents == 0 ) {
                                alert("No image to process");
                                return;
                           }
                           var doc = app.activeDocument;
                           if( doc.mode != DocumentMode.RGB ){
                                alert("Image must be in RGB mode to sample");
                                return;
                           }
                           if( !hasSelection( doc ) ){
                                alert("Please make a selection of target animal\rbefore running script");
                                return;
                           }
                           var numberOfSamples = Number(prompt("How many selections should be made?",10));
                           if(  numberOfSamples == NaN )  numberOfSamples = 1;
                           var sampleSize = Number(prompt("What size should each selection be?(NxN px)", 3));
                           if( sampleSize == NaN ) sampleSize = 3;
                           var originalLayer = doc.activeLayer;// make reference to current layer
                           executeAction( charIDToTypeID( "CpTL" ), undefined, DialogModes.NO );// dupe selection to new layer
                           var sampleLayer = doc.activeLayer;// make reference to that new layer
                           originalLayer.visible = false;// turn off original layer
                           var samples = [];// make array to hold samples
                           var bounds = sampleLayer.bounds;
                           var layerX = bounds[0].as('px');
                           var layerY = bounds[0].as('px');
                           var layerWidth = bounds[2].as('px') - bounds[0].as('px');
                           var layerHeight = bounds[3].as('px') - bounds[1].as('px');
                           // make requested number of samples
                           var s = 0;
                           while(  s < numberOfSamples ){
                                var sX = randomRange( layerX, layerX + layerWidth );
                                var sY = randomRange( layerY, layerY + layerHeight );
                                var cs = doc.colorSamplers.add( [ new UnitValue( sX, 'px' ), new UnitValue( sY, 'px' ) ] );
                                var sample = getSelectionColor( 0, sampleSize );
                                if( undefined != sample ){
                                     samples.push( sample );
                                     s++;
                                }
                                cs.remove();
                           }
                           var sampleFile = new File('~/Desktop/samples.csv');
                           sampleFile.open('w');
                           sampleFile.writeln('red,green,blue');
                           for( var s = 0; s< samples.length;s++ ){
                                sampleFile.writeln( samples[s].rgb.red+','+samples[s].rgb.green+','+samples[s].rgb.blue );
                           }
                           sampleFile.close();
                           
                           function randomRange( minVal, maxVal ){
                                return minVal+Math.floor(Math.random()*( maxVal-minVal ));
                           }
                           ///////////////////////////////////////////////////////////////////////////////
                           // Function: hasSelection
                           // Description: Detremines if there is a selection
                           // Usage: alert(hasSelection()) 
                           // Input:
                           // Return:  true or false
                           // Dependencies:
                           /////////////////////////////////////////////////////////////////////////////////
                            function hasSelection(doc) { 
                                var res = false; 
                                var as = doc.activeHistoryState; 
                                doc.selection.deselect(); 
                                if (as != doc.activeHistoryState) { 
                                     res = true; 
                                     doc.activeHistoryState = as; 
                                } 
                                return res; 
                           }
                           // adapted from scirpt by jugenjury at adobefourms
                           function getSelectionColor( s, A ){
                                var origRulerUnits = app.preferences.rulerUnits;
                                app.preferences.rulerUnits = Units.PIXELS;
                                try{
                                     if ( undefined == s ) { s=0; }
                                     if ( undefined == A ) { A=1; }
                                     var CP = app.activeDocument.colorSamplers;
                                     var sampleSize = A;
                                     var r=((A-1)/2);
                                     var x=Math.round(CP[s].position[0]-r);
                                     var y=Math.round(CP[s].position[1]-r);
                                     activeDocument.selection.select([[x, y], [x+sampleSize, y], [x+sampleSize, y+sampleSize], [x, y+sampleSize]], SelectionType.REPLACE, 0, false);
                                     activeDocument.activeLayer.applyAverage();
                                     var re = RegExp( '[123456789]' );
                                     var sColor = new SolidColor();
                                     if ( activeDocument.mode == DocumentMode.GRAYSCALE ) {
                                          var gv = re.exec(activeDocument.channels[0].histogram.toString() ).index/2;
                                          sColor.gray.gray = 100 * (gv/255);
                                     }
                                     if ( activeDocument.mode == DocumentMode.RGB ) {
                                          sColor.rgb.red = re.exec(activeDocument.channels[0].histogram.toString() ).index/2;
                                          sColor.rgb.green = re.exec( activeDocument.channels[1].histogram.toString() ).index/2;
                                          sColor.rgb.blue = re.exec( activeDocument.channels[2].histogram.toString() ).index/2;
                                     }
                                     if ( activeDocument.mode == DocumentMode.LAB ) {
                                          var lv = re.exec(activeDocument.channels[0].histogram.toString() ).index/2;
                                          sColor.lab.l = 100 * ( lv/255 );
                                          sColor.lab.a = ( re.exec( activeDocument.channels[1].histogram.toString() ).index/2 ) - 128;
                                          sColor.lab.b = ( re.exec( activeDocument.channels[2].histogram.toString() ).index/2 ) -128;
                                     }
                                     if ( activeDocument.mode == DocumentMode.CMYK ) {
                                          var cv = re.exec(activeDocument.channels[0].histogram.toString() ).index/2;
                                          sColor.cmyk.cyan = 100 * (1-(cv/255));
                                          cv = re.exec(activeDocument.channels[1].histogram.toString() ).index/2;
                                          sColor.cmyk.magenta = 100 * (1-(cv/255));
                                          cv = re.exec(activeDocument.channels[2].histogram.toString() ).index/2;
                                          sColor.cmyk.yellow = 100* (1-(cv/255));
                                          cv = re.exec(activeDocument.channels[3].histogram.toString() ).index/2;
                                          sColor.cmyk.black = 100 * (1-(cv/255));
                                     }
                                     executeAction( charIDToTypeID('undo'), undefined, DialogModes.NO );
                                     app.refresh();
                                     var keep = confirm("Sample at px "+sX+','+sY+ ' is R:'+sColor.rgb.red+', G:'+sColor.rgb.green+', B:'+sColor.rgb.blue+'.\rKeep?',true);
                                     activeDocument.selection.deselect();
                                     if( keep == true )return sColor;
                                     app.preferences.rulerUnits = origRulerUnits;
                                }catch(e){
                                     app.preferences.rulerUnits = origRulerUnits;
                                }
                           }
                      }
                      
                      • 8. Re: looking for scripter
                        Michael L Hale Level 5

                        Here is another version. It puts a stroke around the selection so it is easier to see. You might want to edit the color.

                         

                        And yes you can include my name in the acknowledgement section if you wish.

                         

                        // script expect  an open single layer document in RGB mode with a selection of the area to sample.
                        // the csv file is written to the desktop and the script will overwrite an existing samples.csv
                        
                        main();
                        function main(){
                             if( app.documents == 0 ) {
                                  alert("No image to process");
                                  return;
                             }
                             var doc = app.activeDocument;
                             if( doc.mode != DocumentMode.RGB ){
                                  alert("Image must be in RGB mode to sample");
                                  return;
                             }
                             if( !hasSelection( doc ) ){
                                  alert("Please make a selection of target animal\rbefore running script");
                                  return;
                             }
                             var numberOfSamples = Number(prompt("How many selections should be made?",10));
                             if(  numberOfSamples == NaN )  numberOfSamples = 1;
                             var sampleSize = Number(prompt("What size should each selection be?(NxN px)", 3));
                             if( sampleSize == NaN ) sampleSize = 3;
                             var originalLayer = doc.activeLayer;// make reference to current layer
                             executeAction( charIDToTypeID( "CpTL" ), undefined, DialogModes.NO );// dupe selection to new layer
                             var sampleLayer = doc.activeLayer;// make reference to that new layer
                             originalLayer.visible = false;// turn off original layer
                             var samples = [];// make array to hold samples
                             var bounds = sampleLayer.bounds;
                             var layerX = bounds[0].as('px');
                             var layerY = bounds[0].as('px');
                             var layerWidth = bounds[2].as('px') - bounds[0].as('px');
                             var layerHeight = bounds[3].as('px') - bounds[1].as('px');
                             // make requested number of samples
                             var s = 0;
                             while(  s < numberOfSamples ){
                                  var sX = randomRange( layerX, layerX + layerWidth );
                                  var sY = randomRange( layerY, layerY + layerHeight );
                                  var cs = doc.colorSamplers.add( [ new UnitValue( sX, 'px' ), new UnitValue( sY, 'px' ) ] );
                                  var sample = getSelectionColor( 0, sampleSize );
                                  if( undefined != sample ){
                                       samples.push( sample );
                                       s++;
                                  }
                                  cs.remove();
                             }
                             var sampleFile = new File('~/Desktop/samples.csv');
                             sampleFile.open('w');
                             sampleFile.writeln('red,green,blue');
                             for( var s = 0; s< samples.length;s++ ){
                                  sampleFile.writeln( samples[s].rgb.red+','+samples[s].rgb.green+','+samples[s].rgb.blue );
                             }
                             sampleFile.close();
                             
                             function randomRange( minVal, maxVal ){
                                  return minVal+Math.floor(Math.random()*( maxVal-minVal ));
                             }
                             ///////////////////////////////////////////////////////////////////////////////
                             // Function: hasSelection
                             // Description: Detremines if there is a selection
                             // Usage: alert(hasSelection()) 
                             // Input:
                             // Return:  true or false
                             // Dependencies:
                             /////////////////////////////////////////////////////////////////////////////////
                              function hasSelection(doc) { 
                                  var res = false; 
                                  var as = doc.activeHistoryState; 
                                  doc.selection.deselect(); 
                                  if (as != doc.activeHistoryState) { 
                                       res = true; 
                                       doc.activeHistoryState = as; 
                                  } 
                                  return res; 
                             }
                             // adapted from scirpt by jugenjury at adobefourms
                             function getSelectionColor( s, A ){
                                  var origRulerUnits = app.preferences.rulerUnits;
                                  app.preferences.rulerUnits = Units.PIXELS;
                                  try{
                                       if ( undefined == s ) { s=0; }
                                       if ( undefined == A ) { A=1; }
                                       var CP = app.activeDocument.colorSamplers;
                                       var sampleSize = A;
                                       var r=((A-1)/2);
                                       var x=Math.round(CP[s].position[0]-r);
                                       var y=Math.round(CP[s].position[1]-r);
                                       activeDocument.selection.select([[x, y], [x+sampleSize, y], [x+sampleSize, y+sampleSize], [x, y+sampleSize]], SelectionType.REPLACE, 0, false);
                                       activeDocument.activeLayer.applyAverage();
                                       var re = RegExp( '[123456789]' );
                                       var sColor = new SolidColor();
                                       if ( activeDocument.mode == DocumentMode.GRAYSCALE ) {
                                            var gv = re.exec(activeDocument.channels[0].histogram.toString() ).index/2;
                                            sColor.gray.gray = 100 * (gv/255);
                                       }
                                       if ( activeDocument.mode == DocumentMode.RGB ) {
                                            sColor.rgb.red = re.exec(activeDocument.channels[0].histogram.toString() ).index/2;
                                            sColor.rgb.green = re.exec( activeDocument.channels[1].histogram.toString() ).index/2;
                                            sColor.rgb.blue = re.exec( activeDocument.channels[2].histogram.toString() ).index/2;
                                       }
                                       if ( activeDocument.mode == DocumentMode.LAB ) {
                                            var lv = re.exec(activeDocument.channels[0].histogram.toString() ).index/2;
                                            sColor.lab.l = 100 * ( lv/255 );
                                            sColor.lab.a = ( re.exec( activeDocument.channels[1].histogram.toString() ).index/2 ) - 128;
                                            sColor.lab.b = ( re.exec( activeDocument.channels[2].histogram.toString() ).index/2 ) -128;
                                       }
                                       if ( activeDocument.mode == DocumentMode.CMYK ) {
                                            var cv = re.exec(activeDocument.channels[0].histogram.toString() ).index/2;
                                            sColor.cmyk.cyan = 100 * (1-(cv/255));
                                            cv = re.exec(activeDocument.channels[1].histogram.toString() ).index/2;
                                            sColor.cmyk.magenta = 100 * (1-(cv/255));
                                            cv = re.exec(activeDocument.channels[2].histogram.toString() ).index/2;
                                            sColor.cmyk.yellow = 100* (1-(cv/255));
                                            cv = re.exec(activeDocument.channels[3].histogram.toString() ).index/2;
                                            sColor.cmyk.black = 100 * (1-(cv/255));
                                       }
                                       executeAction( charIDToTypeID('undo'), undefined, DialogModes.NO );
                                       executeAction( charIDToTypeID( "CpTL" ), undefined, DialogModes.NO );// dupe selection to new layer
                                       applyInsideStroke();
                                       app.refresh();
                                       var keep = confirm("Sample at px "+sX+','+sY+ ' is R:'+sColor.rgb.red+', G:'+sColor.rgb.green+', B:'+sColor.rgb.blue+'.\rKeep?',true);
                                       app.activeDocument.activeLayer.remove();
                                       activeDocument.selection.deselect();
                                       if( keep == true )return sColor;
                                       app.preferences.rulerUnits = origRulerUnits;
                                  }catch(e){
                                       app.preferences.rulerUnits = origRulerUnits;
                                  }
                             }
                        
                             function applyInsideStroke( sColor ) {
                                  var sColor = new SolidColor;
                                  sColor.rgb.hexValue = '6dfe02';// edit stroke color here
                                  var desc = new ActionDescriptor();
                                       var ref = new ActionReference();
                                       ref.putProperty( charIDToTypeID('Prpr'), charIDToTypeID('Lefx') );
                                       ref.putEnumerated( charIDToTypeID('Lyr '), charIDToTypeID('Ordn'), charIDToTypeID('Trgt') );
                                  desc.putReference( charIDToTypeID('null'), ref );
                                       var effectDesc = new ActionDescriptor();
                                       effectDesc.putUnitDouble( charIDToTypeID('Scl '), charIDToTypeID('#Prc'), 100.000000 );
                                            var strokeDesc = new ActionDescriptor();
                                            strokeDesc.putBoolean( charIDToTypeID('enab'), true );
                                            strokeDesc.putEnumerated( charIDToTypeID('Styl'), charIDToTypeID('FStl'), charIDToTypeID('InsF') );
                                            strokeDesc.putEnumerated( charIDToTypeID('PntT'), charIDToTypeID('FrFl'), charIDToTypeID('SClr') );
                                            strokeDesc.putEnumerated( charIDToTypeID('Md  '), charIDToTypeID('BlnM'), charIDToTypeID('Nrml') );
                                            strokeDesc.putUnitDouble( charIDToTypeID('Opct'), charIDToTypeID('#Prc'), 100.000000 );
                                            strokeDesc.putUnitDouble( charIDToTypeID('Sz  '), charIDToTypeID('#Pxl'), 2.000000 );
                                                 var colorDesc = new ActionDescriptor();
                                                 colorDesc.putDouble( charIDToTypeID('Rd  '), sColor.rgb.red );
                                                 colorDesc.putDouble( charIDToTypeID('Grn '), sColor.rgb.green );
                                                 colorDesc.putDouble( charIDToTypeID('Bl  '), sColor.rgb.blue );
                                            strokeDesc.putObject( charIDToTypeID('Clr '), charIDToTypeID('RGBC'), colorDesc );
                                       effectDesc.putObject( charIDToTypeID('FrFX'), charIDToTypeID('FrFX'), strokeDesc );
                                  desc.putObject( charIDToTypeID('T   '), charIDToTypeID('Lefx'), effectDesc );
                                  executeAction( charIDToTypeID('setd'), desc, DialogModes.NO );
                             }
                        }
                        
                        2 people found this helpful
                        • 9. Re: looking for scripter
                          Marketka1 Level 1

                          Thank you, that is a good comment.

                          I'm using always the same camera, however light conditions are varying- we're photographing outdors and so we can't assure constant light.

                          We're using GretagMacbeth color chart and Pictocolor inCamera software to assure constant color across the images. I'm not very happy with its performance so far, sometimes it doesn't seem to assign accurate color profile. Maybe I'm just doing things wrong. Do you have any experience with that method?

                          M.

                          • 10. Re: looking for scripter
                            Marketka1 Level 1

                            Thank you so much Michael. It works great!!!!!