I have an image and I want to covert it to logical image includes the line is black and background is white. Of course, it is possible to make that with using threshold meth
This is a classic Breadth First Search (BFS) problem. You can think of your starting point marked in your example as an entry point into a maze where your job is find a way out of the maze. The basic driving force behind BFS is that it uses a queue. At the starting point, you add this point to queue. Then, while the queue is not empty, dequeue the point off the queue, then check any of its neighbours to see if you have:
Should you have any points that have satisfied both (1) and (2), you add these points to the queue by enqueueing them. Once you're finished adding points to the queue, you go back and dequeue another point and repeat the algorithm until your queue is empty.
For your line tracing algorithm, what you would do is that for each point that you have dequeued, you would mark the image in a colour... let's say you'd mark this in red. Once you dequeue the point, add those points that you haven't visited and that are valid vessel points to your queue then go back and dequeue another point, then repeat the logic. You'd continue with this until your queue is empty. The good thing about BFS is that it allows you to explore multiple paths at the same time and should you reach a dead end, we stop searching this path and allow the other paths we haven't explored to continue being explored.
Here's some sample code that I wrote. To make things simple, I read your image from StackOverflow, converted the image to black and white and skeletonized the image. You unfortunately need to convert this into logical for this algorithm to work. I understand that you don't desire this, but I'm assuming that you will have multiple instances of these traces, and so if you mark a point that is within one continuous vessel, this algorithm will mark all points that belong to this vessel.
In any case, I skeletonized so that the thickness of the vessel is 1 pixel thick to make things easier. I have also created a colour version of the skeletonized image so that we can colour in the pixels we have explored in red. The first thing that the code does after this is that it shows you the skeletonized image, and it waits for you to click somewhere along the vessel. This is done with ginput. The code will find the closest point with respect to where you have clicked, and it makes this the starting point. This is done by simply finding the minimum Euclidean distance with the point you clicked with every valid point that is in the vessel.
Once we find this starting point, we add this as the first entry into our queue and begin our BFS algorithm. As a bonus, I also wrote code to save the progress as an animated GIF. Every 20 frames, an image gets written to this animated GIF file. In addition, I show you what the line tracing looks like at every 20 frames. This continues until we run out of points, or when the queue is empty, and then the algorithm stops. The animated GIF also gets stored in the same directory where you ran the code. I also wrote what the final completed image looks like as it will inevitably be the case where when we stop the algorithm, it doesn't happen at a multiple of 20 frames, and so you should definitely write the last and final frame to file, which should be the completely marked vessel image.
Without further ado, here's the code:
% // Read in the image from StackOverflow
im = imread('http://i.stack.imgur.com/3t4Dx.png');
%// Skeletonize the image to simplify problem
im = bwmorph(~im2bw(im), 'skel', 'inf');
%// Make a colour version so that we can mark pixels we have visited in
%// red
im_colour = 255*uint8(cat(3,im,im,im));
%// Get a starting point from the user
imshow(im);
[col,row] = ginput(1);
close all;
%// Find the closest point on the vessel where we have clicked and
%// add to the queue as a starting point
[rows,cols] = find(im);
[~,ind] = min((row-rows).^2 + (col-cols).^2);
queue = [rows(ind), cols(ind)];
%// Variable that stores all the locations we have visited so far
mask = false(size(im));
%// To save animated GIF to file
filename = 'linetracing.gif';
figure;
%// Counter that keeps track of how many points we have processed so far
%// This also allows us to write the line tracing algorithm output at
%// certain iteration numbers to output
n = 1;
%// While the queue is not empty
while ~isempty(queue)
%// Dequeue
pt = queue(1,:);
queue(1,:) = [];
%// If this is not a valid vessel point, mark as visited and continue
if im(pt(1),pt(2)) == 0
mask(pt(1),pt(2)) = true;
%// If we have visited this point, continue
elseif mask(pt(1),pt(2))
continue;
else
%// We haven't visited this point yet
%// Mark this as visited
mask(pt(1),pt(2)) = true;
%// Colour the image at this point
im_colour(pt(1),pt(2),:) = [255;0;0];
%// We will write the progress of our line tracing every 20 frames
%// If we are at the first frame, we need to initialize our GIF
%// writing. Loop the GIF animation forever when viewing it
if n == 1
[imind,cm] = rgb2ind(im_colour,256);
imshow(im_colour);
imwrite(imind, cm, filename, 'Loopcount', inf);
%// For every 20th frame, add the progress to our GIF
elseif mod(n,20) == 0
[imind,cm] = rgb2ind(im_colour,256);
imshow(im_colour);
imwrite(imind, cm, filename, 'WriteMode', 'append');
end
%// Increment counter
n = n + 1;
%// Find neighbouring points that surround current point
%// and only select those that we haven't visited
[c,r] = meshgrid(pt(2)-1:pt(2)+1,pt(1)-1:pt(1)+1);
ind = sub2ind(size(im), r, c);
locs = im(ind);
r = r(locs);
c = c(locs);
%// Enqueue
queue = [queue; r(:) c(:)];
end
end
%// Write the very last frame in case we don't get to do that. Only
%//happens if the count is not a multiple of 20.
imshow(im_colour);
[imind,cm] = rgb2ind(im_colour,256);
imwrite(imind, cm, filename, 'WriteMode', 'append');
Here's an example run of this code as an animated GIF. I made the starting point around the same as where you have marked your example in your post.
Hopefully this will get you started. Good luck!