Macro to batch convert DM3 to TIFF

metadata
macro
Tags: #<Tag:0x00007fd5439132d0> #<Tag:0x00007fd543912308>

#1

Hi,
I have been working a little bit on a macro to batch convert DM3 to TIFF. This is what it does:

  • Gets as input a folder (and sub folders) and a export file type.
  • Batch converts ALL the DM3 to the file type.
    • The Images obtain a Scale bar which is always around 1/3 of the width of the image, with nice numbers, such as 1, 2, 5, 10, 20, 50, 100, 200, 500…
    • The diffractions obtain the same scale bar but with 1/nm instead of nm units.
    • The EELS obtain NO scale bar. Instead, they are saved as 2 different documents:
      • A 2-column text file, with the Energy and counts
      • A image which lets you see how the spectrum looks like when digging in the folder, BUT just for that. This image is not calibrated nor has good quality, is just for easy seeking.

This macro is made up with pieces of several other macros/plugins, and I hope all of them are correctly refereed on it.

The macro requires CSI Spectrum reader, because it is the only way I found to get the data from the DM3.

If anyone has time and wants to dig in the macro, to find possible improvements, I would be happy.

Right now it makes what I need, it is a little bit slow (needs like 0.3s for each image) but it is enought for me.

I do not know how to attach files, so I just post it here:

// This macro batch processes .dm3 images saved with Gatan software
// for Transmission Electron Microscope (TEM) imaging. It adds scale bar to each image
// and converts them from .dm3 to different types of image
// the diffractions obtain a scalebar with 1/nm , and the EELS are saved
//as crappy image for track, and 2-column txt file
// global author: Oliver Dieste, 21.01.2016, JRC-ITU (Karlsruhe)

// last modification: 27.01.2016, 14:24

//REQUIRES CSI DM3 Reader plugin http://code.google.com/p/cornell-spectrum-imager/wiki/Home


// partially copied from: Amirhossein Khalajhedayati, 12/10/2013, University of California Irvine, USA
// Some other parts of this code were obtained from multiple resources on the web. 

requires("1.33n");
dir = getDirectory("Choose a directory that contains dm3 files");
//i removed the output place, I prefer to have the tif where the dm3 are

format = getFormat();
start = getTime();
setBatchMode(true);
print("\\Clear")
//start the process: lets find the images in the folder and SUBFOLDERS
find(dir);


//print a count of the time
print("Processing time:   " + (getTime() - start) / 1000 + " Seconds");

//END
/////////////////////////////////////////

function find(dir) {
print("Entering "+dir);
    //showStatus("enter " + dir);
    //this function iterates in the sub-folders to find the dm3 files
    // copied from the ListFilesRecursively macro
    list = getFileList(dir);

    for (i = 0; i < list.length; i++) {
        if (endsWith(list[i], "/")) {
	//if you find a dir, go deep on it
           // print("Entering "+dir+list[i]);
	find("" + dir + list[i]);
        } 
	else if (endsWith(list[i], "dm3")) {
            //if you find a dm3, convert it!
            convert_image(list[i], dir);
           showProgress(i, list.length);
        }
    }
}

function convert_image(file_dm3, dir_dm3) {
imagestart=getTime();
>
   //partially borrowed from ser2tiff plugin
   //by J Kaelber at National University of Singapore on 20 July 2012
	
   //this function converts the image
    path = dir_dm3 + file_dm3;
	outputDirectory = dir_dm3;
    outFile = outputDirectory + file_dm3;
	IJ.redirectErrorMessages();

    open(path);
    getPixelSize(unit, pixelWidth, pixelHeight);

    //we check if it is EELS with the signal value
    eels = getTag("ImageTags.Meta Data.Signal");

   //if it is not EELS
    if (eels != " EELS") {
        //now we check if image or diffraction
        modo = getTag("ImageTags.Microscope Info.Operation Mode");
        if (modo != " IMAGING") {
            //for diffraction change scale unit
            run("Set Scale...", "unit=1/nm");
	}
        //for both images and diffraction create a scale bar
        //and save the images
        crea_bar(pixelWidth);
        // windows does not like tiff with 16bit. 
  
    run("8-bit");

        saveAs(format, outFile);
        close();

}

   //if it is EELS
    else {

   //by saving here we obtain a shitty image, just to get the icon when
   //looking through the files 
        //saveAs(format, outFile);
        close();
        run("CSI DM3 Reader", "load=[&path]");
        //spectrum needs to be centered and calibrated
        //we get the drift of the tube, the offset energy and the dispersion
        //from the values recorded on the file
        drift = parseFloat(getTag("EELS.Acquisition.Spectrometer.Drift tube voltage"));
        offset = parseFloat(getTag("EELS.Acquisition.Spectrometer.Prism offset"));
        dispersion = parseFloat(getTag("EELS.Acquisition.Spectrometer.Dispersion"));
        energy = newArray(2048);
        //this is width of the profile, where it starts and where it ends.
        energy_width = dispersion * 2048;
        // TODO: check what is wrong with the spectra where OFFSET exist , p.e. for M4,5 lines
        //when using -3500eV, sometimes you get up to 11 eV of difference
        inicio = drift - offset - floor(energy_width / 10);
        fin = inicio + dispersion * 2048;

        run("Select All");
        // evilly copied from the macro of 
        // Version 1.0, 24-Sep-2010 Michael Schmid

        //this part gets the profile, saves it in variables x and y, and save them in
        //a 2-column txt file
        run("Plot Profile");

        Plot.getValues(x, y);

	saveAs(format, outFile);
        str = "Energy(eV)\tCounts\n"; // header 
        for (i = 0; i < x.length; i++) {
            energy[i] = inicio + dispersion * i;
            str += "" + energy[i] + "\t" + y[i] + "\n";
        }
        File.saveString(str, outFile + ".txt");
        close();
    }
print (file_dm3+" READY");
}

function getFormat() {
    //choose the output format

    formats = newArray("TIFF", "JPEG", "GIF", "PNG",
        "PGM", "BMP", "FITS", "Text Image", "ZIP", "Raw");
    Dialog.create("Output format");
    Dialog.addChoice("Convert to: ", formats, "TIFF");
    Dialog.show();
    return Dialog.getChoice();
}

function getTag(tag) {
    //get the needed tag

    info = getImageInfo();
    index1 = indexOf(info, tag);
    if (index1 == -1) return "";
    index1 = indexOf(info, "=", index1);
    if (index1 == -1) return "";
    index2 = indexOf(info, "\n", index1);
    value = substring(info, index1 + 1, index2);
    return value;
}

function crea_bar(ancho) {

    //function that prints the scalebar with certain width

    //first calculate the ideal width


    baseWidth = floor(300 * ancho);
    scaleValues = newArray(1, 2, 5);
    factor = 1;
    j = 0;
    for (t = 0; t < 20; t++) {
        scaleWidth = scaleValues[j] * factor;
        if (baseWidth > scaleWidth) {
            j++;
            if (j >= scaleValues.length) {
                j = 0;
                factor *= 10;
            }
        } else {
            t = 20;
        }
    }
    //then print it

  run("Scale Bar...", "width=&scaleWidth height=8 font=50 color=White background=Black location=[Lower Right] bold");
    return;
}

that´s it.

Regards,


#2

Thanks for sharing, @Oliver_Dieste! This is a nice, detailed example of processing all files in a directory.

Note that there are some general-purpose bare-bones examples available from the Templates menu of the Script Editor:

And a very similar example for doing batch conversion with Bio-Formats:

  • batchConvert.txt – batch convert files in a folder to TIFF using Bio-Formats

Batch convert/save as one file format to TIFF?
#3

Hi,

I write this question here because is related and noone else is talking about dm3.

In dm3 files, there is a lot of info, which can be obtainey by getimageinfo() (like i did in the dm3totiff mqcro up there).

Question: does anyone a way to 1) change that info, and/or 2) save a dm3 file.

I could not find anythink related. The point is that i am writting a macro to batch-change specimen info (in case you have been taking images for one whole day…before realizing that the specimen was not correctly set).
I guess this is going to be easier to do it on digitalmicrograph, but first i wanted to try on imagej

Best regards.


#4

In general, there are many fewer plugins which support saving to proprietary image file formats such as DM3, versus open formats like TIFF, OME-TIFF, ICS, NRRD, etc. In particular, the Bio-Formats Exporter only supports open formats.

For details on why, see this paper:

So yes, you will probably need to use Gatan’s tools to do it…


#5

Ok, thank you ! Definitely that’s what i will do.

Regards.


#6

I was having a problem converting my dm3 images to TIFF through DigitalMicrograph. My TEM diffraction patterns are dull. And, when I tried to convert them using ImageJ, the scale bar was missing.

Thank you so much Oliver for sharing this with us! This will help me so much!

Best Regards!


#7

Hi @Uchechi_Okeke , I am glad I could help someone :slight_smile:

Just in case you find it useful, I have a small update (just to write down apperture and some other details on the small image of the EELS spectra, so it is easier to read them directly) and another macro to convert the STEM files (.ser ) to tiff as well. Watch out, that this one does not work perfectly: sometimes the EDS wont be converted correctly, but at least it helps a little:

_DM3_convert.txt:

// This macro batch processes .dm3 images saved with Gatan software
// for Transmission Electron Microscope (TEM) imaging. It adds scale bar to each image
// and converts them from .dm3 to different types of image
// the diffractions obtain a scalebar with 1/nm , and the EELS are saved
// as crappy image for track, and 2-column txt file
// global author: Oliver Dieste, 21.01.2016, JRC-ITU (Karlsruhe)

// last modification: 12.09.2016 10:07

//REQUIRES CSI DM3 Reader plugin http://code.google.com/p/cornell-spectrum-imager/wiki/Home
//for the processing of EELS files. 


// partially copied from: Amirhossein Khalajhedayati, 12/10/2013, University of California Irvine, USA
// Some other parts of this code were obtained from multiple resources on the web. 

requires("1.33n");
dir = getDirectory("Choose a directory that contains dm3 files");
//i removed the output place, I prefer to have the tif where the dm3 are

format = getFormat();
bitdepth=getDepth();
start = getTime();
setBatchMode(true);
print("\\Clear")
//start the process: lets find the images in the folder and SUBFOLDERS
find(dir);


//print a count of the time
print("Processing time:   " + (getTime() - start) / 1000 + " Seconds");

//END
/////////////////////////////////////////

function find(dir) {
print("Entering "+dir);
    //showStatus("enter " + dir);
    //this function iterates in the sub-folders to find the dm3 files
    // copied from the ListFilesRecursively macro
    list = getFileList(dir);

    for (i = 0; i < list.length; i++) {
        if (endsWith(list[i], "/")) {
	//if you find a dir, go deep on it
           // print("Entering "+dir+list[i]);
	find("" + dir + list[i]);
        } 
	else if (endsWith(list[i], "dm3")) {
            //if you find a dm3, convert it!
            convert_image(list[i], dir);
           showProgress(i, list.length);
        }
    }
}

function convert_image(file_dm3, dir_dm3) {
imagestart=getTime();

    //partially borrowed from ser2tiff plugin
    //by J Kaelber at National University of Singapore on 20 July 2012
	
    //this function converts the image
    path = dir_dm3 + file_dm3;
	outputDirectory = dir_dm3;
    outFile = outputDirectory + file_dm3;
	IJ.redirectErrorMessages();

    open(path);
    getPixelSize(unit, pixelWidth, pixelHeight);

    //we check if it is EELS with the signal value
    eels = getTag("ImageTags.Meta Data.Signal");

    //if it is not EELS
    if (eels != " EELS") {
        //now we check if image or diffraction
        modo = getTag("ImageTags.Microscope Info.Operation Mode");
        if (modo != " IMAGING") {
            //for diffraction change scale unit
            run("Set Scale...", "unit=1/nm");
	}
        //for both images and diffraction create a scale bar
        //and save the images
        crea_bar(pixelWidth);
        // windows does not like tiff with 16bit. 
	   // But I let you choose 
  if(bitdepth==16){
    run("16-bit");}
else {
	
run("8-bit");}

        saveAs(format, outFile);
        close();

}

    //if it is EELS
    else {

        //by saving here we obtain a shitty image, just to get the icon when
        //looking through the files 
        //saveAs(format, outFile);
        close();
        run("CSI DM3 Reader", "load=[&path]");
        //spectrum needs to be centered and calibrated
        //we get the drift of the tube, the offset energy and the dispersion
        //from the values recorded on the file
        drift = parseFloat(getTag("ImageTags.EELS.Acquisition.Spectrometer.Drift tube voltage"));
        offset = parseFloat(getTag("ImageTags.EELS.Acquisition.Spectrometer.Prism offset"));
        dispersion = parseFloat(getTag("ImageTags.EELS.Acquisition.Spectrometer.Dispersion"));
	aperture=parseFloat(getTag("ImageTags.EELS.Acquisition.Spectrometer.Aperture label"));
	magnification=parseFloat(getTag("ImageTags.Microscope Info.Indicated Magnification"));
	exp_time=parseFloat(getTag("ImageTags.DataBar.Exposure Time"));
	sum_spectra=parseFloat(getTag("ImageTags.Acquisition.Parameters.Objects.0.Parameter 1"));
		
        energy = newArray(2048);
        //this is width of the profile, where it starts and where it ends.
        energy_width = dispersion * 2048;
        // TODO: check what is wrong with the spectra where OFFSET exist , p.e. for M4,5 lines
        //when using -3500eV, sometimes you get up to 11 eV of difference
        inicio = drift - offset - floor(energy_width / 10);
        fin = inicio + dispersion * 2048;

        run("Select All");
        // evilly copied from the macro of 
        // Version 1.0, 24-Sep-2010 Michael Schmid

        //this part gets the profile, saves it in variables x and y, and save them in
        //a 2-column txt file
        run("Plot Profile");
drawString("Aperture: "+aperture+" mm", 330, 30);
drawString("Camera length: "+magnification+" mm", 330, 40);
drawString("Exposure time: "+exp_time+" s", 330, 50);
drawString("Number of spectra: "+sum_spectra, 330, 60);
drawString("Dispersion: "+dispersion+" ev/ch", 330, 70);
drawString("Start: "+inicio+" eV", 330, 80);
drawString("End: "+fin+" eV", 330, 90);

        Plot.getValues(x, y);

	saveAs(format, outFile);
        str = "Energy(eV)\tCounts\n"; // header 
        for (i = 0; i < x.length; i++) {
            energy[i] = inicio + dispersion * i;
            str += "" + energy[i] + "\t" + y[i] + "\n";
        }
        File.saveString(str, outFile + ".txt");
        close();
    }
print (file_dm3+" READY");
}

function getFormat() {
    //choose the output format

    formats = newArray("TIFF", "JPEG", "GIF", "PNG",
        "PGM", "BMP", "FITS", "Text Image", "ZIP", "Raw");
    Dialog.create("Output format");
    Dialog.addChoice("Convert to: ", formats, "TIFF");
    Dialog.show();
    return Dialog.getChoice();
}

function getDepth(){
    //choose the output bit depth

    bits = newArray("8", "16");
    Dialog.create("Output bitdepth");
    Dialog.addChoice("Choose bit depth: ", bits, "8");
    Dialog.show();
    return Dialog.getChoice();
}

function getTag(tag) {
    //get the needed tag

    info = getImageInfo();
    index1 = indexOf(info, tag);
    if (index1 == -1) return "";
    index1 = indexOf(info, "=", index1);
    if (index1 == -1) return "";
    index2 = indexOf(info, "\n", index1);
    value = substring(info, index1 + 1, index2);
    return value;
}

function crea_bar(ancho) {

    //function that prints the scalebar with certain width

    //first calculate the ideal width


    baseWidth = floor(300 * ancho);
    scaleValues = newArray(1, 2, 5);
    factor = 1;
    j = 0;
    for (t = 0; t < 20; t++) {
        scaleWidth = scaleValues[j] * factor;
        if (baseWidth > scaleWidth) {
            j++;
            if (j >= scaleValues.length) {
                j = 0;
                factor *= 10;
            }
        } else {
            t = 20;
        }
    }
    //then print it

    run("Scale Bar...", "width=&scaleWidth height=8 font=50 color=White background=Black location=[Lower Right] bold");
    return;
}

_SER2TIFF.txt:

//This macro is adapted from the batch conversion macro in ij macro source repository
//by J Kaelber at National University of Singapore on 20 July 2012
dir = getDirectory("Choose a directory that contains SER files");
//i removed the output place, I prefer to have the tif where the dm3 are

// This macro batch processes .ser images saved with Gatan software
// for Transmission Electron Microscope (TEM) imaging. It adds scale bar to each image
// and converts them from .ser to different types of image
// the EDS obtains a crappy tif image to make it easy to find them on folders
// and a TXT file with two columns. 
// global author: Oliver Dieste, 19.10.2016, JRC-ITU (Karlsruhe)

//REQUIRES CSI DM3 Reader plugin http://code.google.com/p/cornell-spectrum-imager/wiki/Home
//for the processing of EDS files (tia spectrum reader).


format = getFormat();
start = getTime();
setBatchMode(true);
print("\\Clear")
//start the process: lets find the images in the folder and SUBFOLDERS
find(dir);


//print a count of the time
print("Processing time:   " + (getTime() - start) / 1000 + " Seconds");

//END
/////////////////////////////////////////

function find(dir) {
print("Entering "+dir);
    //showStatus("enter " + dir);
    //this function iterates in the sub-folders to find the SER files
    // copied from the ListFilesRecursively macro
    list = getFileList(dir);
    for (i = 0; i < list.length; i++) {
        if (endsWith(list[i], "/")) {
	//if you find a dir, go deep on it
           // print("Entering "+dir+list[i]);
	find("" + dir + list[i]);
        } 
	else if (endsWith(list[i], "ser")) {
            //if you find a ser, convert it!
            convert_image(list[i], dir);
           showProgress(i, list.length);
        }
    }
}

function convert_image(file_ser, dir_ser) {     
	serpath= dir_ser+file_ser;
	
	// this next line is to test the file but doesnt work       
	// IJ.redirectErrorMessages();
	
	
	if(endsWith(file_ser,"_1.ser")){
		run("TIA Reader", ".ser-reader...=&serpath");
	
		//  this part is adapted from the source poposed by @author Frederick Ding
	
		getPixelSize(unit, pw, ph);
		crea_bar(pw);
	
		// if the tiff are not in 8-bit, windows wont recognize them
		run("8-bit");
		//save it
		saveAs(format, dir_ser+file_ser+"stem");
		}
	
	//if it is not am image (ending with _1) then it´s a EDS
	else{
	
        		run("CSI TIA Reader", "load=[&serpath]");
		//IJ.redirectErrorMessages();
       	 	run("Select All");
       	 	// evilly copied from the macro of 
       	 	// Version 1.0, 24-Sep-2010 Michael Schmid
	
      	  	//this part gets the profile, saves it in variables x and y, and save them in
     	   	//a 2-column txt file
     	   	run("Plot Profile");
	
       	 	Plot.getValues(x, y);
      	  	saveAs(format, dir_ser+file_ser+"EDS");
     	   	str = "Energy(eV)\tCounts\n"; // header 
     	   	j=1;
		//this macro fails to get the correct values for some spectra
		//dont know the reason. Have go to deeper on it.
		while(j<x.length){
			str += "" + x[j] + "\t" + y[j] + "\n";
			j++;
      	  		}
	        	File.saveString(str, dir_ser+file_ser+"EDS" + ".txt");
		close();
		}

        	print (file_ser+" READY");
	}
 
  function getFormat() {
       formats = newArray("TIFF", "JPEG", "GIF", "PNG",
          "PGM", "BMP", "FITS", "Text Image", "ZIP", "Raw");
       Dialog.create("Output format");
       Dialog.addChoice("Convert to: ", formats, "TIFF");
       Dialog.show();
       return Dialog.getChoice();

}
function crea_bar(ancho) {

    //function that prints the scalebar with certain width

    //first calculate the ideal width


    baseWidth = 300 * ancho;
    scaleValues = newArray(1, 2, 3, 4, 5);
	oldWidth=1;
    factor = 1;
    j = 0;
    for (t = 0; t < 20; t++) {
        scaleWidth = scaleValues[j] * factor;
        if (baseWidth > scaleWidth) {
            j++;
	oldWidth=scaleWidth;
            if (j >= scaleValues.length) {
                j = 0;
                factor *= 10;
            }
        } else {
	scaleWidth=oldWidth;
	if(scaleWidth>ancho*512){
	scaleWidth=scaleWidth/2;}
	
            t = 20;
        }
    }
    //then print it

    run("Scale Bar...", "width=&scaleWidth height=8 font=50 color=White background=Black location=[Lower Right] bold");
    return;
}

As you can seen, the ser2tiff is not correctly commented as dm3 is, but i think it is more or less clear what it does.

In case anyone has some improvement over any of these scripts, please let me know, I am using them quite intensively now but they are not yet perfect :slight_smile:

Best regards,


#8

Hi everybody,

I know I am talking about something with a very small public, but just in case someone is interested…

I improved a little bit the macros that I created for the conversion of DM3 ( TEM, DIFF and EELS) and SER (EDS and STEM) images to a normal, readable format.

Now I blended both conversions into one Macro file, called _TEM_Convert.tx (imaginative name, isn´t it?).

If anyone would use it, and finds an error on it, please let me know.

// This macro batch processes .dm3 images saved with Gatan software
// for Transmission Electron Microscope (TEM) imaging. It adds scale bar to each image
// and converts them from .dm3 to different types of image
// the diffractions obtain a scalebar with 1/nm , and the EELS are saved
// as crappy image for track, and 2-column txt file
// global author: Oliver Dieste, 21.01.2016, JRC-ITU (Karlsruhe)

// last modification: 5.12.2017 11:17

//REQUIRES CSI DM3 Reader plugin http://code.google.com/p/cornell-spectrum-imager/wiki/Home
//for the processing of EELS files and EDS 


// partially copied from: Amirhossein Khalajhedayati, 12/10/2013, University of California Irvine, USA
// Some other parts of this code were obtained from multiple resources on the web. 

requires("1.33n");
//choose directory, format, depth and if you want to overwrite or not
dir = getDirectory("Choose a directory that contains the files");
datos=newArray("","","","","");
datos=getPreguntas();
format = datos[0];
bitdepth = datos[1];
overwrite = datos[2];
dm3=datos[3];
ser=datos[4];
start = getTime();

setBatchMode(true);


print("\\Clear")
print(overwrite);
//start the process: lets find the images in the folder and SUBFOLDERS
find(dir);
//print a count of the time
print("Processing time:   " + (getTime() - start) / 1000 + " Seconds");
//END
/////////////////////////////////////////
function find(dir) {
 print("Entering " + dir);
 //showStatus("enter " + dir);
 //this function iterates in the sub-folders to find the dm3 files
 // copied from the ListFilesRecursively macro
 list = getFileList(dir);
 for (i = 0; i < list.length; i++) {
  if (endsWith(list[i], "/")) {
   //if you find a dir, go deep on it
   find("" + dir + list[i]);
  } else if (endsWith(list[i], "dm3") && dm3) {
   //if you find a dm3, firts check if image exists.
   //if exists and we dont want to overwrite, skip it
   figure = replace(list[i], ".dm3", "." + format);
   if (File.exists(dir + figure) && !overwrite) {
       tabWindow("_dm3_", figure,"SKIPPED");
   } else {
    convert_image(list[i], dir, "dm3");
   }
  } else if (endsWith(list[i], "ser") && ser) {
   //if you find a ser,firts check if image exists.
   //if exists and we dont want to overwrite, skip it
   figure = replace(list[i], ".ser", "." + format);
   if (File.exists(dir + figure) && !overwrite) {
       tabWindow("_ser_", figure,"SKIPPED");
   } else {
    convert_image(list[i], dir, "ser");
   }
  }
  showProgress(i, list.length);
 }
}

function convert_image(file_image, dir_image, formato) {
 //this function converts the image
 imagestart = getTime();

 //partially borrowed from ser2tiff plugin
 //by J Kaelber at National University of Singapore on 20 July 2012
 path = dir_image + file_image;

 if (formato == "dm3") {
// #######################################//
 open(path);
// close();
  //run("CSI DM3 Reader", "load=[&path]");
  getPixelSize(unit, pixelWidth, pixelHeight);

  //we check if it is EELS with the signal value
  eels = getTag("ImageTags.Meta Data.Signal");

  //if it is not EELS
  if (eels != " EELS") {
// ********************************************************//
   //now we check if image or diffraction
   modo = getTag("ImageTags.Microscope Info.Imaging Mode");
   if (modo != " IMAGING") {
    //for diffraction change scale unit
    run("Set Scale...", "unit=1/"+unit);
   tipo="DIFF";
   }
else{   tipo="TEM";}
   //for both images and diffraction create a scale bar
   //and save the images
width=getWidth;
   crea_bar(pixelWidth,width);
  }

  else {
// ********************************************************//
  //if it is EELS

   //spectrum needs to be centered and calibrated
   //we get the drift of the tube, the offset energy and the dispersion
   //from the values recorded on the file
   drift = parseFloat(getTag("ImageTags.EELS.Acquisition.Spectrometer.Drift tube voltage"));
   offset = parseFloat(getTag("ImageTags.EELS.Acquisition.Spectrometer.Prism offset"));
   dispersion = parseFloat(getTag("ImageTags.EELS.Acquisition.Spectrometer.Dispersion"));
   aperture = parseFloat(getTag("ImageTags.EELS.Acquisition.Spectrometer.Aperture label"));
   magnification = parseFloat(getTag("ImageTags.Microscope Info.Indicated Magnification"));
   exp_time = parseFloat(getTag("ImageTags.DataBar.Exposure Time"));
   sum_spectra = parseFloat(getTag("ImageTags.Acquisition.Parameters.Objects.0.Parameter 1"));

   run("Select All");
   // evilly copied from the macro of 
   // Version 1.0, 24-Sep-2010 Michael Schmid

   //this part gets the profile, saves it in variables x and y, and save them in
   //a 2-column txt file
   run("Plot Profile");
   Plot.getValues(x, y);
   energy = newArray(x.length);
   //this is width of the profile, where it starts and where it ends.
   energy_width = 2 * dispersion * x.length;
   // TODO: check what is wrong with the spectra where OFFSET exist , p.e. for M4,5 lines
   //when using -3500eV, sometimes you get up to 11 eV of difference
   inicio = drift - offset - floor(energy_width / 10);
   // this is just in case the spectrum starts in negative values, for the floor to be over, not under
   if (inicio < 0) {
    inicio = inicio + 1;
   }
   fin = inicio + energy_width;

   drawString("Aperture: " + aperture + " mm", 330, 30);
   drawString("Camera length: " + magnification + " mm", 330, 40);
   drawString("Exposure time: " + exp_time + " s", 330, 50);
   drawString("Number of spectra: " + sum_spectra, 330, 60);
   drawString("Dispersion: " + dispersion + " ev/ch", 330, 70);
   drawString("Start: " + inicio + " eV", 330, 80);
   drawString("End: " + fin + " eV", 330, 90);

   str = "Energy(eV)\tCounts\n"; // header 
   for (i = 0; i < x.length; i++) {
   energy[i] = inicio + 2 * dispersion * i;
    str += "" + energy[i] + "\t" + y[i] + "\n";
   }
  File.saveString(str, path + ".txt");
  tipo="EELS";
  }
 } else if (formato == "ser") {
// #######################################//
  run("TIA Reader", ".ser-reader...=&path");
  IJ.redirectErrorMessages();
  getPixelSize(unit, pw, ph);
  width = getWidth;
  height = getHeight;
  if (width == height) {
   // then it is an image
   //  this part is adapted from the source poposed by @author Frederick Ding
   crea_bar(pw,width);
   tipo="STEM";
  } else {
   // ********************************************************//
   //if it is not am image (not square) then it´s a EDS
close();
  run("CSI TIA Reader", "load=[&path]");
   run("Select All");
saveAs("Text Image", path);
   run("Plot Profile");
    tipo="EDS";
  }
 }
   if (bitdepth == 16) {
    run("16-bit");
   } else {
    run("8-bit");
   }

   saveAs(format, path);
   tabWindow(tipo, file_image,"READY");
   close();
}

function tabWindow (tipo, image,estado) {
momento=(getTime() -start)/ 1000;
print( tipo+ "\t\t " +image+"\t\t "+estado +"\t "+momento+" s.");
}


function getPreguntas() {
 //choose the output format


 formats = newArray("tif", "jpg", "gif", "png",
  "pgm", "bmp", "fits", "txt", "zip", "raw");
 bits = newArray("8", "16");
questions=newArray("","","","","");
Dialog.create("questions");
Dialog.addChoice("Convert to: ", formats, "tif");
Dialog.addChoice("Choose bit depth: ", bits, "8");
Dialog.addCheckbox("Overwrite images? ", false);
Dialog.addCheckbox("Convert TEM/DIFF/EELS? ", true);
Dialog.addCheckbox("Convert STEM/EDS? ", true);
 Dialog.show();
questions[0]=Dialog.getChoice();
questions[1]=Dialog.getChoice();
questions[2]=Dialog.getCheckbox();
questions[3]=Dialog.getCheckbox();
questions[4]=Dialog.getCheckbox();
 return questions;
}

function getTag(tag) {
 //get the needed tag

 info = getImageInfo();
 index1 = indexOf(info, tag);
 if (index1 == -1) return "";
 index1 = indexOf(info, "=", index1);
 if (index1 == -1) return "";
 index2 = indexOf(info, "\n", index1);
 value = substring(info, index1 + 1, index2);
 return value;
}

function crea_bar(ancho, pixel) {

 //function that prints the scalebar with certain width

 //first calculate the ideal width
// it is a third of the size of one pixel times the number of pixels
 baseWidth = ancho* pixel/3;
 scaleValues = newArray(1, 2, 3, 4, 5);
 oldWidth = 1;
 factor = 1;
 j = 0;
 for (t = 0; t < 20; t++) {
  scaleWidth = scaleValues[j] * factor;
  if (baseWidth > scaleWidth) {
   j++;
   oldWidth = scaleWidth;
   if (j >= scaleValues.length) {
    j = 0;
    factor *= 10;
   }
  } else {
   scaleWidth = oldWidth;
   if (scaleWidth > baseWidth) {
    scaleWidth = scaleWidth / 2;
   }

   t = 20;
  }
 }
 //then print it

 run("Scale Bar...", "width=&scaleWidth height=8 font=50 color=White background=Black location=[Lower Right] bold");
 return;
}