How to create an image from .txt file ?

I have some .txt files containing 3 columns of number (x,y,z). z is the luminosity of each point identified by the x,y coordinates. I should find a way to produce an image file (the format is not important, it may be a .jpg for example) in which the luminosity of each point identified by the first 2 columns of the .txt file (x and y coordinates) vary depending on the third column. How can I concert the coordinates and luminosity into an image? Thanks!

5 Comments

Have you ever considered the benefits of describing the relationship between the inputs and the desired image?
The problem is: the first 2 columns of the txt file are x and y coordinate. The third columns is made of numbers that express the luminosity of each point. I should find a way to create an image that has a certain luminosity in each point that vary along with the numbers in third column
Not sure what your edit was. Was there something in my solution below that didn't work?
Are the coordinates spaced on a grid? Is data given for every point on the grid? Are the coordinates positive integers? Should it be assumed that any unoccupied location is black, or should it be assumed that each given location is a point source and each unoccupied location should be interpolated according to inverse square of the distance from the closest point in each direction?
this is the .txt file. There are 3 columns. The first is x, the second is y and the third column is the luminosity and all the 3 columns are made of integer numbers.

Sign in to comment.

 Accepted Answer

Try this, assuming x, y, and z are all separate vectors that you got from dlmread(), importdata() or something similar.
numPoints = length(x);
% Let's assume x and y are columns and rows.
rows = max(y);
columns = max(x);
% Assume z is in the range 0-255 and can be handles by a uint8 image.
grayImage = zeros(rows, columns, 'uint8');
for k = 1 : numPoints
grayImage(y(k), x(k)) = z(k); % NOTE: y,x NOT x,y !!!
end

31 Comments

i will try as soon as possible this solution. I am waiting for my pc to be repaired.
however the x,y,z vector are made of 361920 elements. I did not success in creating the image. The error message is:Subscript indices must either be real positive integers or logicals.
It is difficult to offer suggestions when you have not responded to my questions
Did you try rounding x, y, and z so that they can be integers that they need to be to be indexes of grayImage?
Attach your X, Y, Z data. (I may not get to it though because I'm leaving for London tomorrow, and am/will be very busy)
this is the .txt file. There are 3 columns. The first is x, the second is y and the third column is the luminosity and all the 3 columns are made of integer numbers.
@Image Analyst: the algorithm you proposed me works. It was necessary to apply a slight modification... however, how can I associate a colormap to it?
@ImageAnalyst: I try this
I = dicomread(strcat('C:\Echo Images\Stelios\FDB.dcm\test', int2str(i) , '.dcm'));
data = dlmread('imgpositions.txt');
x=data(:,1)
y=data(:,2)
I(y,x)
pause(2)
figure
pause(2)
imshow(I)
And I get error
Subscript indices must either be real positive integers or logicals.
you know why?
Because x and y are floating point numbers, not integer row and column numbers. Also simply saying I(y,x), even if you did use ceil() or round() on y and x, does NOT change I at all.
And with that kind of indexing, you get where the x and y "stripes" intersect. See this demo:
m = reshape(1:81, 9, 9)
x = randi(9, 3, 1)
y = randi(9, 3, 1)
m2 = m(y, x)
Nevermind, I understand that indices cannot be fractures,negatives or zeros but I am trying to figure out a way to plot my images according to x,y (rows,columns) of my txt file. The values are fractures and negatives and zeros
I don't even know what that means. What does it mean to "plot" an image "according to x,y (rows,columns) of my txt file"? First of all (x,y) is (columns, rows), NOT (rows, columns). Do you just want a bar chart of the intensities at the few locations specified by your list of (x,y) locations?
You can say it resembles a bar chart but not intensities. All images have the same x value but they slightly differ on their y value. The differences among y coordinate of the global image are +-0.1,0.2mm. So as you may understood, some images must be positioned upper or lower than others related to y axis.
To position images differently, use image() and pass in 'XData' and 'YData' parameters.
Can you please give me a sample code?
img = imread('cameraman.tif');
image(img, 'XData', [0 1], 'YData', [0 1]);
colormap(gray(256));
hold on
for K = 1 : 5
xoff = randn(); yoff = randn();
image(img, 'XData', xoff+[0 1], 'YData', yoff+[0 1]);
end
hold off
set(gca, 'xlimmode', 'auto', 'ylimmode', 'auto')
Sorry, I don’t understand your example. What are [0 1]? X and Y coordinator values will be loaded by rows and columns of a txt file. Not random or 0,1
I tried the image line and I got the error "Expected input number 1, I, to be one of these types:
numeric, logical
Instead its type was matlab.graphics.primitive.Image. "
To be more clear. I have 15 images and each one of them must be in a position +-0.1,0.2 mm from the other. So some of the images will be upper than others.
The following code assumes that the pixel size of each image is the same, but does not assume that the images are the same size.
%build colormap
%replace the following line with your actual code
cmap = gray(256);
%how big is the first image?
%replace the following two lines with your actual code
width_of_first_image_in_mm = 143;
height_of_first_image_in_mm = 228;
%set imgs as a cell array containing all of your images
%replace the following line with your actual code
imgs = repmat({imread('cameraman.tif')}, 1, 15);
%set xoffs as the x offset of your images.
%remember, x corresponds to columns
%replace the following line with your actual code
xoffs = randn();
%set yoffs as the y offset of your images.
%remember, y corresponds to rows
%replace the following line with your actual code
yoffs = randn();
%now the display code
%display first image
img = imgs{1};
x1pix = size(img,2);
y1pix = size(img,1);
xoff = xoffs(1); yoff = yoffs(1);
xmm = width_of_first_image_in_mm;
ymm = height_of_first_image_in_mm;
xbounds = xoff+[0 xmm];
ybounds = yoff+[0 ymm];
image(img, 'XData', xbounds, 'YData', ybounds);
xrange = xbounds;
yrange = ybounds;
%configure axes
colormap(cmap);
axis equal
hold on
%display remaining images
for K = 2 : length(imgs)
img = imgs{K};
xpix = size(img, 2);
ypix = size(img, 1);
xoff = xoffs(K); yoff = yoffs(K);
%scale to known size of first image
xmm = xpix ./ x1pix .* width_of_first_image_in_mm;
ymm = ypix ./ y1pix .* height_of_first_image_in_mm;
xbounds = xoff+[0 xmm];
ybounds = yoff+[0 ymm];
image(img, 'XData', xbounds, 'YData', ybounds);
%keep running track of how far the images extend on the screen
xrange(1) = min(xrange(1), xbounds(1));
xrange(2) = max(xrange(2), xbounds(2));
yrange(1) = min(yrange(1), ybounds(1));
yrange(2) = max(yrange(2), ybounds(2));
end
%all done displaying.
%finish configuring axes
hold off
xlim(xbounds);
ylim(ybounds);
The above code displays everything with scaled mm, all the scales the same size. The scale is based upon how large the axes happens to come out.
If you need the display to come out as "real" mm, then it would be necessary to resize the figure so that data mm are forced to be screen mm. This computation is complicated a bit by the treatment of pixel size on high DPI displays, which uses a different scale factor for Windows (1 pixel = 1/96 inch) vs Mac (1 pixel = 1/72 inch), and scaling does not happen at all on Linux. So I am not going to bother writing the code for that unless you need it and you indicate your OS and your screen DPI (and your MATLAB release.)
Images are same size. Wouldn't be more easy to write the x,y values in a txt file and have them read by Matlab, instead of writing such a big code? My images are 15. Imagine having 100?
Since x value will be the same for all images. I need them to alter on the y value for about 0.1,0.2 mm up or down from a reference position. If we assume that the reference position in the center of the figure will be (0,0), then the next image will be (0,0.1) and the next (0,0.2) and the next (0,-0.3) and the next (0,-0.1) and so on so forth
Is there an algorithm for determining what x and y position to use given an interation number?
"Images are same size"
That simplifies code some, but not much really.
"instead of writing such a big code"
The code is so big because I had to point everything out to you to make it clear which values you had to provide according to your circumstances and which values I was providing for the sake of illustration.
"My images are 15. Imagine having 100?"
There would be no change in the code I posted, other than the sample input line
imgs = repmat({imread('cameraman.tif')}, 1, 15);
which you would replace with lines to read in your images into a cell array named imgs . That code would likely be a loop, and so would not get any larger for 100 images than for 15 images.
It gives me an error at line " xoff = xoffs(K); yoff = yoffs(K);" Index exceeds matrix dimensions. An easier way is to use a txt file with the x,y values that each image shall have. 15rows x 2 columns (x,y). Each image need to have a different x,y value from the reference value. As I explained earlier, if the reference value is (0,0) the next image will be (0,-0.2), same x but 2 mm lower in the y position from the reference state and so on so forth. No next image will have difference from the previous image. The y value difference will be determined from the reference position and not from the previous image.
I though another perspective of the task. If we assume that those 15 dicom images were captured with slight differences on the y position from the patient. Means that the patient moved or misalignments occurred. Then we can have a reference value for x,y and properly align all the rest 14 images to match the reference value. So we don't need to position them differently, but to imregister them on a single reference position no matter their misalignments. Am I clear?
Is this version of the code an acceptable length?
cmap = gray(256); %FIXME
width_mm = 143; %FIXME
height_mm = 228; %FIXME
imgs = repmat({imread('cameraman.tif')}, 1, 15); %FIXME
nimgs = length(imgs);
xoffs = randn(1, nimgs); %FIXME
yoffs = randn(1, nimgs); %FIXME
wb = [0 width_mm];
hb = [0 height_mm];
alp = 1/nimgs;
image(imgs{1}, 'XData', xoffs(1)+wb, 'YData', yoffs(1)+hb, 'AlphaData', alp );
colormap(cmap);
axis equal
hold on
for K = 2 : nimgs
image(imgs{K}, 'XData', xoffs(K)+wb, 'YData', yoffs(K)+hb, 'AlphaData', alp);
end
hold off
xlim([min(xoffs), width_mm+max(xoffs)]);
ylim([min(yoffs), height_mm+max(yoffs)]);
You might notice that the different images are not distinct, and that what you see is mostly a blurred version of the image. That is because 0.1 to 0.2 mm is a matter of a few pixels compared to the scale being used (which was arbitrarily chosen as roughly 5 1/2 inches by 9 inches, which is roughly human scale.)
Error in Line "image(imgs{1}, 'XData', xoffs(1)+wb, 'YData', yoffs(1)+hb, 'AlphaData', alp );"
Cell contents reference from a non-cell array object.
How did you initialize imgs? I tested the code before posting it, and in what I posted imgs is certainly a cell array.
.... As I explained in the comments on the longer version of the code that you thought was too long, implying that you did not need those comments.
imgs = repmat(dicomread(strcat('C:\Echo Images\Stelios\FDB.dcm\test', int2str(i) , '.dcm')));
I use this line and comes up with "Not enough input arguments"
Try this:
filename = fullfile('C:\Echo Images\Stelios\FDB.dcm\test', [int2str(i) , '.dcm']);
thisImage = dicomread(filename);
numHorizontalCopies = 2; % Whatever you want.
numVerticalCopies = 2; % Whatever you want.
imgs = repmat(thisImage, numVerticalCopies , numHorizontalCopies);
You are using a series of images. You should replace the assignment to imgs with code that reads in all of them images and assigns them as members of the cell array named imgs
Yeah. That worked. Thanks a lot. You've been really helpful.

Sign in to comment.

More Answers (1)

imgdata = load('Case06_RAW_100_01.txt'); %x y luminosity
luminosity = reshape( imgdata(:,3), 696, [] ) .';
However, we are now stuck in producing an image. luminosity is the total amount of energy emitted by an object or region, over all wavelengths, and gives no information about how we should convert into color. Portions might be emitting mostly in the microwave ranges, portions might have a dual peak in gamma radiation and ultraviolet, and a dull blue object might have the same luminosity as a bright red object since blue is higher energy.
If you want to get an idea of how the luminosities are distributed to verify whether the data has been read into the correct positions, then you can
imshow(luminosity, [])

3 Comments

in fact now i shoul associate a colormap, but how can i do that? (With a slight modification, the algorithm proposed by the user "imageAnalyst" works fine. But now: how can i associate a colormap?
imagesc(luminosity);
cmap = prism(64); %choose colormap and size
colormap(cmap); %activate it

Sign in to comment.

Categories

Find more on Images in Help Center and File Exchange

Community Treasure Hunt

Find the treasures in MATLAB Central and discover how the community can help you!

Start Hunting!