Read and process multiple .TIFF files using MATLAB - matlab

I have problem on read and process multiple tiff file using MATLAB since I am beginner in MATLAM software. I have 300 of tiff images with same dimension. I want to loop the process, however, I cannot get it. Until now, I only change the file-name every time to read and process. I still don't get where should start. Can anyone help me. Here I attach my coding.
filename=('brd06330_s0239.tif');
fileinfo=imfinfo(filename);
Nfiles=numel(fileinfo);
Cloud=cell(Nfiles,1);
for n=1:Nfiles
A=imread(filename);
[rimg cimg]=size(A);
% Read by band (for this task only use band 1)
B1Channel = A(:, :, 1);
% A=imread(filename);
% [rimg cimg]=size(A);
%for channel 1
W_countB1 = sum(sum(B1Channel == 0)) % W= water
NW_countB1 = sum(sum(B1Channel > 0)) % NW= non water (cloud and land)
end
%save in text format(excel)
d=[W_countB1,NW_countB1]
colname={W_countB1,NW_countB1}
xlswrite('brd06330_s0239',d)

try dir('*.tif'), that will get you a list of all TIFFs in your directory, then you can loop the whole thing like you wanted.
it would look something like:
files=dir('*.tif');
for i=1:length(files)
A=imread(file(i).name);
%//... whatever you want to do with your TIFFs
end
hope that helps.

Related

How to build filenames in a nested loop

I am trying to access 4k images and crop some ROI based areas (4 ROI in my case) and store them in some directory. So far everything is working okay except the loops handling of the filename.
Below is my code attached. I am accessing N 4k images, crop and resize them to my desired resolution. In the end, when I tried to save the data the images got overwritten.
N=2;
for img = 1:N
x = gTruth.LabelData.crack{img,1}
for i=1:4
Cells = x(i,1:4)
baseFileName = theFiles(img).name;
fullFileName = fullfile(myFolder, baseFileName);
fprintf(1, 'Now reading %s\n', fullFileName);
imageArray = imread(fullFileName);
CroP = imcrop(imageArray,Cells);
imshow(CroP);
B = imresize(CroP,[256 256]);
imshow(B);
imwrite(B,strcat('C:\Users\USER\Desktop\Directory\imagefile_00',num2str(i),'.png'));
end
end
My question is that after loop i runs, it saves 4 images and for img again it saves four values. Now when the code runs it saves only last 4 images and not 8. I should get a i*N number of total images, but I'm getting only 4 and rest are overwritten.
How can I adapt my program to save all files?
imwrite(B,strcat('C:\Users\USER\Desktop\Directory\imagefile_00',num2str(i),'.png'));
is where the problem is. You use num2str(i) to change the number, and i=[1,2,3,4]. Thus, you cannot create a file which is outside numbers 1 to 4. Taking you want something based on img as well, you can use e.g.
imwrite(B,strcat('C:\Users\USER\Desktop\Directory\imagefile_',num2str(img),num2str(i),'.png'));
which will create a file named imagefile_11 for the first image and first region, imagefile_12 for the first image, second region, imagefile_324 for the 32nd image, fourth region etc. Change according to your needs of course.
Example in action:
>> i=3;img=1;
>> strcat('C:\Users\USER\Desktop\Directory\imagefile_',num2str(img),num2str(i),'.png')
ans =
C:\Users\USER\Desktop\Directory\imagefile_13.png
>> i=1;img=2;
>> strcat('C:\Users\USER\Desktop\Directory\imagefile_',num2str(img),num2str(i),'.png')
ans =
C:\Users\USER\Desktop\Directory\imagefile_21.png
Free advice:
i and j are the imaginary unit. It's, in my opinion, preferable not to use them as loop indices.
Your desktop is most likely not the best place to save stuff. Make a folder in for example your Documents folder with an apt name, e.g. C:\Users\USER\Documents\ROIfrom4k\
The declarations of x and Cells would benefit from a closing semicolon on the line, so as to prevent them from outputting to the console, slowing down the program and clogging the command window. The orange wiggles MATLAB puts there are not for festivity, they present a useful warning. (Not to be confused with red wiggles, those present an serious error, because of which MATLAB cannot run at all.)

Faster way to load .csv files in folder and display them using imshow in MATLAB

I have a piece of MATLAB code that works fine, but I wanted to know is there any faster way of performing the same task, where each .csv file is a 768*768 dimension matrix
Current code:
for k = 1:143
matFileName = sprintf('ang_thresholded%d.csv', k);
matData = load(matFileName);
imshow(matData)
end
Any help in this regard will be very helpful. Thank You!
In general, its better to separate the loading, computational and graphical stuff.
If you have enough memory, you should try to change your code to:
n_files=143;
% If you know the size of your images a priori:
matData=zeros( 768, 768,n_files); % prealocate for speed.
for k = 1:n_files
matFileName = sprintf('ang_thresholded%d.csv', k);
matData(:,:,k) = load(matFileName);
end
seconds=0.01;
for k=1:n_Files
%clf; %Not needed in your case, but needed if you want to plot more than one thing (hold on)
imshow(matData(:,:,k));
pause(seconds); % control "framerate"
end
Note the use of pause().
Here is another option using Matlab's data stores which are designed to work with large datasets or lots of smaller sets. The TabularTextDatastore is specifically for this kind of text based data.
Something like the following. However, note that since I don't have any test files it is sort of notional example ...
ttds = tabularTextDatastore('.\yourDirPath\*.csv'); %Create the data store
while ttds.hasdata %This turns false after reading the last file.
temp = read(ttds); %Returns a Matlab table class
imshow(temp.Variables)
end
Since it looks like your filenames' numbering is not zero padded (e.g. 1 instead of 001) then the file order might get messed up so that may need addressed as well. Anyway I thought this might be a good alternative approach worth considering depending on what else you want to do with the data and how much of it there might be.

Fast way of exporting the same figure n-times

I am trying to put together an animation in matlab. For this i am showing pictures containing a description of whats currently happening in the animation. So i am writing out pictures of my figures and later on put these together to an avi file again using matlab. For the description parts to "show up" long enough i use a simple loop in which the current figure is saved n-times. Unfortunatelly this process, though matlab does not have to calculate anything new, is the slowest one.
As the loop i use the following (h_f being the figure handle):
for delay = 1:80
export_fig (h_f,['-r' num2str(resolution)], ['C:\Users\Folder\Name_', '_' num2str(7700+delay) '.png'])
end
I just want to ask if there is any faster way. right now it kind of feels like matlab replots the fig each time before exporting it. So is there a way of plotting the figure once and simultaneously export it n-times?
Thanks for the help :)
If they are all really identical, then you can just copy the first file into the subsequent files. Your time will be limited by the speed of your disk drive and the size of your image files.
% Define some of the flags as variables. This'll make it clearer
% what you're doing when you revisit the code in a year.
% Flag for the resolution
resFlag = sprintf('-r%u', resolutions);
% Base folder
folder = 'C:\Users\Folder\';
% First file number
startnum = 7701;
% This is the pattern all the filenames will use
nameToken = 'Name_%u.png';
% First filename
firstFile = fullfile(folder, sprintf(nameToken, startnum));
% Export the first file
export_fig(h_f, resFlag, firstFile);
numCopies = 80;
% Copy the file
for delay = 2:numCopies
% Make a new filename
currentFile = fullfile(folder, sprintf(nameToken, startnum + delay));
% Copy the first file into the current filename.
copyfile(firstFile, currentFile);
end

How to create a 3d surface from 2d images?

I've been working on modyfing dicom images so I can later 3d print them. The problem is that once I've modified the individual slices to turn them into an .stl file, the software I'm using (Osirix) prompts an error that asks for volumic data. If I try to render the .stl without modifying it first in MAtlab I get no error message.
I need an example of code for Matlab that can stack 2d images into a 3d surface so I can later import it to an .stl file. Can anyone help me?
One way could be to stack 2D images into a 3D cube of images.
Solution 1.
The following solution is based in the following assumptions:
1) that the size of all 2d images are the same: n1 by n2
2) that you know the number of images (slices): n3
3) that the images are uint8
You could create a 3D cube beforehand with:
allImgs = uint8(zeros(n1, n2, n3));
Then to fill the first slice with aSlice image, do:
allImgs(:, :, 1) = aSlice;
For the second, do:
allImgs(:, :, 2) = anotherSlice;
and so forth.
If you have a function (like getMeASlice())that gets the slices for you, you could efficiently call this from a for loop and fill it up:
for k = 1:n3
allImgs(:, :, k) = getMeASlice(your_params);
end
Solution 2.
You could concatenate slices as you go. Say that you read a slice:
aSlice = imread('cameraman.tif');
and then you later on your code you read another slice and want to stack it to your existing one, you could do:
aSlice = cat(3, aSlice, imread('anotherimage.jpg'));
which concatenates your new slice in the third dimension. And you could keep doing this as long as you need.
However, note the following. Concatenating is very slow compared to preallocating a variable and adding things (populating) such variable. For instance, if you compare the following two scripts, the second one is much slower:
n1=256; n2=256; n3=200;
allImgs = uint8(zeros(n1, n2, n3));
aSlice = imread('cameraman.tif');
tic;
for k=1:n3
allImgs(:,:,1)=aSlice;
end
fprintf(['Total time is: ' num2str(toc) '\n']);
tic;
allImgs=aSlice;
for k=2:n3
allImgs=cat(3, allImgs, aSlice);
end
fprintf(['Total time is: ' num2str(toc) '\n']);
Gives the following in my computer:
Total time is: 0.0085632
Total time is: 0.89103
Let me know if this helps or not.

How to make an animation from multiple results?

I have some calculation with matrices and have set my loop to run for (let's say) 50 times.
I also assigned a color to each value so I can get a picture in the end of these matrices based on their values.
What I don't know is - how to make an animation from this multiple images I get in each turn.
Is it possible?!
The following code is what I have used previously to produce an .avi file
n = 15;
p = randperm(n);
figure('Color','white');
fcount = 0;
for k = 1:n-1
% produce the plot
[idx,idx] = min(p(k:n));
p(idx+k-1) = p(k);
p(k) = k;
plot(p,'*')
% Make sure plot updates before we capture the contents
pause(0.1)
F(k) = getframe(gcf); %#ok
end
movie2avi(F,'so1.avi','fps',2,'quality',100);
However, there seems to be some issues with the avi codec now for use with Windows XP, for example see this thread.
http://www.mathworks.com/matlabcentral/newsreader/view_thread/271172
I had the same problem; the avi file produced with the default Indeo codec would not run in Windows Media Player. Using a different codec, such as
movie2avi(F,'so1.avi','fps',2,'quality',100,'compression','Cinepak');
solved the problem. You may need to experiment to find a working combination.
Hth, Darren
I'm not sure what you're trying to do. One option is to use the MS-GIF animator, although 50 images is a bit much. See http://en.wikipedia.org/wiki/Microsoft_GIF_Animator for info. Considering the number of images, you might want to create a powerpoint document.