After 2 or 3 days of search, I still didn't find a solution to my problem.
I want to create a segmentation of the mouse without the shadow. The problem is that If I manage to remove the shadow I also remove the tail and the feets which is a problem. The shadow comes from the wall of the arena in which the mouse is.
I want to remove the shadow from a grayscale image but I have no clue how doing it. First I removed the background of the image and I obtain the following picture.
edit1 : Thank you for the answer it works well when the shadow doesn't touch the mouse. This is what I get otherwise :
from this original image :
I am extracting each frame from a tif file and apply your code for each frame. This is the code I use :
for k=1:1000
%reads image
I = imread('souris3.tif',k);
%first stage: perform thesholding and fill holes
seg = I >20000;
seg = imfill(seg,'holes');
%fixes the missing tail problem
%extract edges, and add them to the segmentation.
edges = edge(I);
seg = seg | edges;
%fill holes (again)
seg = imfill(seg,'holes');
%find all the connected components
CC = bwconncomp(seg,8);
%keeps only the biggest CC
numPixels = cellfun(@numel,CC.PixelIdxList);
[biggest,idx] = max(numPixels);
seg = zeros(size(edges));
seg(CC.PixelIdxList{idx}) = 1;
imshow(seg);
end
I choose 20000 for step with the command impixelinfo
because the image is in uint16
and it's the mean value of the mouse.
This is the link if you want to have the tif file :
Thank you for helping.
I suggest the following approach:
Code:
%reads image
I = rgb2gray(imread('mSWm4.png'));
%defines thersholds (you may want to tweak these thresholds, or find
%a way to calculate it automatically).
FIRST_STAGE_THRESHOLD = 70;
IM_BOUNDARY_RELEVANCE_THRESHOLD = 10;
%perform thesholding and fill holes, the tail is still missing
seg = I > FIRST_STAGE_THRESHOLD;
seg = imfill(seg,'holes');
%second stage fix the missing tail problem:
%extract edges from relevant areas (in which the matter is not too dark), and add them to the segmentation.
%the boundries of the image which are close enough to edges are also considered as edges
edges = edge(I);
imageBoundries = ones(size(I));
imageBoundries(2:end-1,2:end-1) = 0;
relevantDistFromEdges = bwdist(edges) > IM_BOUNDARY_RELEVANCE_THRESHOLD;
imageBoundries(bwdist(edges) > IM_BOUNDARY_RELEVANCE_THRESHOLD) = 0;
seg = seg | (edges | imageBoundries);
%fill holes (again) and perform noise cleaning
seg = imfill(seg,'holes');
seg = getBiggestCC(imopen(seg,strel('disk',1)));
getBiggestCC function:
function [ res ] = getBiggestCC(mask)
CC = bwconncomp(mask,8);
numPixels = cellfun(@numel,CC.PixelIdxList);
[~,idx] = max(numPixels);
res = zeros(size(mask));
res(CC.PixelIdxList{idx}) = 1;
end
results
results of each stage:
results image 1 results:
image 2 results:
Another view (segmentation is in red):