· 8 years ago · Feb 21, 2018, 05:07 AM
1//ImageJ macro making a movie (stack) of zooming on selected rectangle (ROI)
2//v2 Eugene Katrukha katpyxa at gmail.com
3//v2a Andrey Aristov: aaristov at pasteur.fr
4requires("1.48h");
5
6//check if there is rectangular selection
7if(selectionType() ==0)
8{
9 sTitle=getTitle();
10 sMovieTitle=sTitle+"_zoom_movie";
11 setBatchMode(true);
12
13 //ROI parameters
14 Roi.getBounds(nX, nY, nW, nH);
15 //print(nX);
16 //print(nY);
17 //print(nW);
18 //print(nH);
19
20 //Dialog
21 Dialog.create("Zoom-in parameters:");
22 Dialog.addNumber("Zoom Step (0 to 1)",0.95);
23 Dialog.addNumber("Add static number of frames in the end:", 5);
24 minMax=newArray("min","max");
25 Dialog.addChoice("Zoom to min/max ROI size:", minMax);
26 sScaleChoice=newArray("Specified below","same as ROI");
27 Dialog.addChoice("Final movie dimensions (px):", sScaleChoice);
28 Dialog.addNumber("Final movie width:", 512);
29 Dialog.addNumber("Final movie width:", 512);
30 Dialog.addCheckbox("Add scalebar:", false);
31 Dialog.addNumber("Pixel size, um:", 0.04);
32
33 Dialog.show();
34 zoomStep=Dialog.getNumber();
35 nFramesLast=Dialog.getNumber();
36 sChoice=Dialog.getChoice();
37 sSizeChoice=Dialog.getChoice();
38 nFinalW=Dialog.getNumber();
39 nFinalH=Dialog.getNumber();
40 addScaleBar = Dialog.getCheckbox();
41 px=Dialog.getNumber();
42
43 //print(nFinalW);
44 //print(nFinalH);
45
46 imageH=getHeight();
47 imageW=getWidth();
48 rawID=getImageID();
49
50
51 nCenterX=nX+0.5*nW;
52 //print("CenterX");
53 //print(nCenterX);
54 nCenterY=nY+0.5*nH;
55 //print("CenterY");
56 //print(nCenterY);
57
58 nScaleX=nW/imageW;
59 nScaleY=nH/imageH;
60
61
62 //adjust roi x/y ratio to image x/y ratio
63 //depending on user choice
64 if(startsWith(sChoice, "min"))
65 nScaleFin=minOf(nScaleX,nScaleY);
66 else
67 nScaleFin=maxOf(nScaleX,nScaleY);
68
69 nW=nScaleFin*imageW;
70 nH=nScaleFin*imageH;
71 //print("New nW");
72 //print(nW);
73 //print("New nH");
74 //print(nH);
75 nX=nCenterX-(nW*0.5);
76 nY=nCenterY-(nH*0.5);
77 //print(nX);
78 //print(nY);
79
80 //distance from (0,0) to left top corner of selsction
81 length=sqrt(nX*nX+nY*nY);
82 //print("length");
83 //print(length);
84 if(nX==0)
85 angle=3.14/2;
86 else
87 angle=atan(nY/nX);
88 //print("angle");
89 //print(angle);
90
91 //final movie size
92 if(startsWith(sSizeChoice,"same as"))
93 {
94 nFinalW=nW;
95 nFinalH=nH;
96 }
97 else
98 {
99 nMovieScaleX=nW/nFinalW;
100 nMovieScaleY=nH/nFinalH;
101 nMovieFinalScale = minOf(nMovieScaleX,nMovieScaleY);
102 nFinalW=nW/nMovieFinalScale;
103 nFinalH=nH/nMovieFinalScale;
104 }
105 //print(nFinalW);
106 //print(nFinalH);
107
108
109
110 bNotFirstIt=false;
111
112 dCount =0;
113 //for(nScale=1;nScale>=nScaleFin;nScale=nScale-nScaleStep)
114 nScale=1;
115
116 newW=imageW;
117 newH=imageH;
118 dLen = length;
119 ddLen = 0;
120 run("Set Scale...", "distance=1 known="+px+" pixel=1 unit=um");
121 //run("32-bit");
122
123 while(newW>nW){
124 //for(dCount =0;dCount<=nFrames;dCount++)
125 //{
126 selectImage(rawID);
127 //change viewport position/scale
128 //print("dlen");
129 //print(dLen);
130
131 offsetX=ddLen*cos(angle);
132 offsetY=ddLen*sin(angle);
133
134 run("Specify...", "width="+toString(newW)+" height="+toString(newH)+" x="+toString(offsetX)+" y="+toString(offsetY));
135 run("Duplicate...", "title="+sTitle+toString(nScale));
136 unscaledID=getImageID();
137 run("Scale...", "x=- y=- width="+toString(nFinalW)+" height="+toString(nFinalH)+" interpolation=Bicubic average create");
138 scaledID=getImageID();
139 selectImage(unscaledID);
140 close();
141 selectImage(scaledID);
142
143 run("Enhance Contrast...", "saturated=0.3");
144
145 if(addScaleBar){
146 trueSize = newW*px;//um
147
148 w = floor(trueSize/2);
149 if(w>300){
150 width = 300;
151 }
152 else if(w>100){
153 width = 100;
154 }
155 else if(w>30){
156 width = 30;
157 }
158 else if(w>10){
159 width = 10;
160 }
161 else if(w>3){
162 width = 3;
163 }
164 else {
165 width = 1;
166 }
167
168
169 run("Scale Bar...", "width="+width+" height=8 font=24 color=White background=None location=[Lower Right] bold");
170
171 }
172
173 //not a first frame, let's add to existing movie stack
174 if(bNotFirstIt)
175 {
176 sCurrTitle=sTitle+"x"+toString(nScale);
177 rename(sCurrTitle);
178 run("Concatenate...", " title=["+sMovieTitle+"] image1=["+sMovieTitle+"] image2=["+sCurrTitle+"]");
179 }
180 //first frame, let's make accumulating stack out of it
181 else
182 {
183 rename(sMovieTitle);
184 sMovieID=getImageID();
185 bNotFirstIt=true;
186 }
187 //nScale=nScale-nScaleStep;
188 //nScale=nScaleFin+(1-nScaleFin)/2/(dCount+1);
189
190 dLen=dLen*zoomStep;
191 ddLen = length-dLen+length*nScaleFin;
192
193
194 newW=newW*zoomStep;
195 newH=newH*zoomStep;
196
197 }
198
199 //adding static frames part
200 nScale=nScaleFin;
201 for(nAddFrames=1;nAddFrames<=nFramesLast;nAddFrames++)
202 {
203 selectImage(rawID);
204 //offsetX=length*cos(angle);
205 //offsetY=length*sin(angle);
206 //newW=imageW*nScale;
207 //newH=imageH*nScale;
208 run("Specify...", "width="+toString(newW/zoomStep)+" height="+toString(newH/zoomStep)+" x="+toString(offsetX)+" y="+toString(offsetY));
209 run("Duplicate...", "title="+sTitle+toString(nScale));
210 unscaledID=getImageID();
211 run("Scale...", "x=- y=- width="+toString(nFinalW)+" height="+toString(nFinalH)+" interpolation=Bilinear average create");
212 scaledID=getImageID();
213 selectImage(unscaledID);
214 close();
215 selectImage(scaledID);
216
217 run("Enhance Contrast...", "saturated=0.3");
218
219 if(addScaleBar){
220 run("Scale Bar...", "width="+width+" height=8 font=24 color=White background=None location=[Lower Right] bold");
221 }
222 sCurrTitle=sTitle+"x"+toString(nScale);
223 rename(sCurrTitle);
224 run("Concatenate...", " title=["+sMovieTitle+"] image1=["+sMovieTitle+"] image2=["+sCurrTitle+"]");
225
226 }
227 setBatchMode(false);
228}
229//no rectangular ROI selection, error
230else
231{
232 exit("Please choose rectangular selection (ROI) first.");
233}