Scripts for Manipulation and Analysis of High Energy Diffraction Images (GE2 files)
# Miscellaneous Diffraction Image Processing Commands | |
# This file defines aliases for several common image processing | |
# functions for GE2 diffraction images. This uses ImageMagick | |
# program, which is typically available on all Linux and Mac | |
# systems - http://www.imagemagick.org/script/index.php | |
# USAGE: | |
# Copy the contents of this file to the bottom of ~/.bashrc | |
# Run from terminal: source ~/.bashrc | |
# After this, following commands should be available | |
# 1. Convert TIFF to GE. Saves input.ge2 | |
# tiff2ge input.tiff | |
# 2. Convert GE to TIFF. Saves input.tiff (Note: The produced TIFF may seem to have very low | |
# intensity. That is because, GE2 has 16-bit depth. So the intensity | |
# can go from 0 to 65000. Detectors at APS and CHESS generally max out | |
# at 16000 counts. So even high intensity points have only 25% intensity. | |
# You can stretch the intensity range of the TIFF using ImageMagick - | |
# convert -normalize original.tiff bright_output.tiff). If the GE2 file has | |
# multiple frames, TIFF is multipage. You can split TIFF into individual frames | |
# using - convert multipage.tiff frame_%05d.tiff | |
# ge2tiff input.ge2 | |
# 3. Maximum over frames (saves a single frame with maximum intensity. Name: input-max.[ge2 | tiff]) | |
# max_over_frames input.[ge2 | tiff] | |
# 4. Mean over frames (saves a single frame with mean intensity. | |
# Good for creating a dark frame from a sequence. Name: input-mean.[ge2 | tiff]) | |
# mean_over_frames input.[ge2 | tiff] | |
# 5. Extract a single frame from a multi-frame image. Saves multiframe_frame_num.[ge2 | tiff] | |
# extract_frame multiframe.[ge2 | tiff] frame_num | |
# 6. Subtract dark frame from a (single or multi-frame) image. Saves input-dark-subtracted.[ge2 | tiff] | |
# subtract_dark input.[ge2 | tiff] dark_image.[ge2 | tiff] | |
# 7. Show FF data in a parent directory. This lists all ge2 files inside | |
# subdirectories. The output format is such that the GE2 list can be | |
# used e.g. in a heXRD config file. | |
# show_ff_data path/to/parent/directory | |
# | |
# Convert TIFF/PNG etc to GE2 (single or multi frame, works on multiple files) | |
function tiff2ge() { | |
for var in "$@" | |
do | |
echo "Processing : tiff2ge : $var" | |
filename=$(basename "$var") | |
extension="${filename##*.}" | |
filename="${filename%.*}" | |
convert "$var" -endian LSB -depth 16 -size 2048x2048 gray:"$filename".ge2.tmp | |
dd if="$filename".ge2.tmp of="$filename".ge2 obs=8192 seek=1 | |
rm -f "$filename.ge2.tmp" | |
done | |
} | |
# Convert GE2 image to tiff | |
function ge2tiff() { | |
for var in "$@" | |
do | |
echo "Processing : ge2tiff : $var" | |
filename=$(basename "$var") | |
extension="${filename##*.}" | |
filename="${filename%.*}" | |
convert -endian LSB -depth 16 -size 2048x2048+8192 gray:"$var" "$filename".tiff | |
done | |
} | |
# Max over all frames | |
function max_over_frames() { | |
for var in "$@" | |
do | |
filename=$(basename "$var") | |
extension="${filename##*.}" | |
filename="${filename%.*}" | |
if [ ${extension^^} == "TIF" ] || [ ${extension^^} == "TIFF" ] | |
then | |
echo "Processing : max over : $extension : $var" | |
convert "$var" -evaluate-sequence max "$filename"-max."$extension" | |
elif [ ${extension^^} == "GE2" ] | |
then | |
echo "Processing : max over : $extension : $var" | |
convert -endian LSB -depth 16 -size 2048x2048+8192 gray:"$var" \ | |
-endian LSB -depth 16 -size 2048x2048 -evaluate-sequence max gray:"$filename"."$extension".max | |
dd if="$filename"."$extension".max of="$filename"-max."$extension" obs=8192 seek=1 | |
rm -f "$filename"."$extension".max | |
fi | |
done | |
} | |
# Mean over all frames | |
function mean_over_frames() { | |
for var in "$@" | |
do | |
filename=$(basename "$var") | |
extension="${filename##*.}" | |
filename="${filename%.*}" | |
if [ ${extension^^} == "TIF" ] || [ ${extension^^} == "TIFF" ] | |
then | |
echo "Processing : max over : $extension : $var" | |
convert "$var" -evaluate-sequence mean "$filename"-mean."$extension" | |
elif [ ${extension^^} == "GE2" ] | |
then | |
echo "Processing : max over : $extension : $var" | |
convert -endian LSB -depth 16 -size 2048x2048+8192 gray:"$var" \ | |
-endian LSB -depth 16 -size 2048x2048 -evaluate-sequence mean gray:"$filename"."$extension".mean | |
dd if="$filename"."$extension".mean of="$filename"-mean."$extension" obs=8192 seek=1 | |
rm -f "$filename"."$extension".mean | |
fi | |
done | |
} | |
# Extract a specific frame from multi-frame image | |
function extract_frame() { | |
filename=$(basename "$1") | |
extension="${filename##*.}" | |
filename="${filename%.*}" | |
if [ ${extension^^} == "TIF" ] || [ ${extension^^} == "TIFF" ] | |
then | |
echo "Processing : extract frame $2 : $extension : $1" | |
convert "$1"[$2] "$filename"_"$2"."$extension" | |
elif [ ${extension^^} == "GE2" ] | |
then | |
echo "Processing : extract frame $2 : $extension : $1" | |
convert -endian LSB -depth 16 -size 2048x2048+8192 gray:"$1"["$2"] \ | |
-endian LSB -depth 16 -size 2048x2048 -evaluate-sequence max gray:"$filename"_"$2"."$extension".tmp | |
dd if="$filename"_"$2"."$extension".tmp of="$filename"_"$2"."$extension" obs=8192 seek=1 | |
rm -f "$filename"_"$2"."$extension".tmp | |
fi | |
} | |
# Subtract a dark frame from an image (not tested for multiframe) | |
function subtract_dark() { | |
filename=$(basename "$1") | |
extension="${filename##*.}" | |
filename="${filename%.*}" | |
if [ ${extension^^} == "TIF" ] || [ ${extension^^} == "TIFF" ] | |
then | |
echo "Processing : subtract dark : $extension : $2 from $1" | |
convert $1 null: $2 -compose difference -layers composite "$filename"-dark-subtracted."$extension" | |
#composite -compose difference $1 $2 "$filename"-dark-subtracted."$extension" | |
elif [ ${extension^^} == "GE2" ] | |
then | |
echo "Processing : subtract dark : $extension : $2 from $1" | |
convert -endian LSB -depth 16 -size 2048x2048+8192 gray:$1 \ | |
-endian LSB -depth 16 -size 2048x2048+8192 null: gray:$2 \ | |
-compose difference -layers composite -endian LSB -depth 16 -size 2048x2048+8192 "$filename"-dark-subtracted."$extension".tmp | |
#composite -compose difference -endian LSB -depth 16 -size 2048x2048+8192 gray:"$1" \ | |
# -endian LSB -depth 16 -size 2048x2048+8192 gray:"$2" \ | |
# -endian LSB -depth 16 -size 2048x2048+8192 "$filename"-dark-subtracted."$extension".tmp | |
dd if="$filename"-dark-subtracted."$extension".tmp of="$filename"-dark-subtracted."$extension" obs=8192 seek=1 | |
rm -f "$filename"-dark-subtracted."$extension".tmp | |
fi | |
} | |
# Display file numbers from an ff directory | |
function show_ff_data() { | |
# Find all directories with name ff and loop over them | |
find "$@" -not -empty -name "ff" -print | while read f; do | |
# Show directory name | |
echo "$f" | |
# Get size of all contents in the directory (in bytes) | |
tot_byte_size=$(du -b "$f") | |
# By default du prints the folder name too. Strip that. | |
tot_byte_size=($tot_byte_size) | |
tot_byte_size=${tot_byte_size[0]} | |
# Estimate number of FF frames assuming one frame = 2048*2048*2 bytes | |
num_frames_estimate=$( echo $tot_byte_size / 8388608 | bc ) | |
# Get size of all contents in a human readable unit (M, G, T) | |
tot_file_size=$(du -h "$f") | |
tot_file_size=($tot_file_size) | |
# Print total size and frame number estimate | |
echo Total size = ${tot_file_size[0]}, Estimated frames = $num_frames_estimate | |
# List the contents of the folders | |
filenames1=$(eval ls \'"$f"\' | tr '\n' ' ') | |
filelist='' | |
# Clean up the filenames assuming ff_%5d.ge2 format | |
for filename in $filenames1 | |
do | |
filenum1=${filename:3:5} | |
filenum=$(echo $filenum1 | sed 's/^0*//') | |
filelist+=", $filenum" | |
done | |
filelist1=${filelist:2} | |
# Print comma separated list of file numbers | |
echo $filelist1 | |
done | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment