function res=Border_Image(D , Im, param)

thick = 12;
Mask = ones(256,256);

for i=1:thick
%    Mask(i,:)=0;
%    Mask(:,+i)=0;
%    Mask(257-i,:)=0;
   Mask(:,257-i)=0;
end

Mask = logical(Mask);

trueIm = double(Im);
maskedIm = trueIm .* Mask;

imPatches = im2col(maskedIm , param.patchSize , 'sliding');
maskPatches = im2col(Mask , param.patchSize , 'sliding');

Masks=maskPatches;
X=imPatches;
res=zeros(size(X));

dim = size(D , 1);
nAtoms = size(D , 2);
nSignals = size(X , 2);



for ii=1:nSignals
    
end





if ~isfield(param , 'IgnoreUnmasked'), param.IgnoreUnmasked = 0; end;

testErrorGoal = false; errorGoal = inf; 
if isfield(param , 'errorGoal'), 
	testErrorGoal = true; 
  	errorGoal = param.errorGoal * dim * (param.noiseSig.^2); 
end;
testMaxAtoms = false; maxAtoms = nAtoms;
if isfield(param , 'maxAtoms'), testMaxAtoms = true; maxAtoms = param.maxAtoms; end;
if (~testErrorGoal) && (~testMaxAtoms), error('At least one stopping criterion is needed!'); end;

allCoeffsList  = zeros(1 , nSignals * min(maxAtoms , ceil(0.2*nAtoms)));
allIndsList    = zeros(size(allCoeffsList));
allSignalsList = zeros(size(allCoeffsList));
totNcoeffs = 0;

% if param.IgnoreUnmasked
% 	sumUnmasked = sum(Masks , 1);
% 	patchesToIgnore = sumUnmasked == dim;
% else
% 	patchesToIgnore = [];
% end
% 
%     vec=0:7;
%     vecc=[vec,249+vec,2*249+vec,3*249+vec,4*249+vec,5*249+vec,6*249+vec,7*249+vec];

% Testing and processing signals
for cSignal = 1 : nSignals
    
	% process one signal
	
	% Get current mask
	m = Masks(: , cSignal);
	vm = find(m);
	
    % Copy the patch if it is not masked
    if (length(vm)==dim)
        res(:,cSignal)=X(:,cSignal);

    else
                      
	% Get current signal
	x = X(vm , cSignal);
	
	% Take the needed dictionary rows
	currD = D(vm , :);
	atomsNormFacts = sqrt(sum(currD.^2 , 1));
	currD = currD ./ repmat(atomsNormFacts , [size(currD , 1) 1]);
	
	% Update error goal
	currErrorGoal = errorGoal * length(vm) / dim;
	
	% Initialize coefficient and indices vectors
	residual = x;
	coeffsList = zeros(dim , 1);
	indsList = zeros(1 , dim);
	card = 0;
	
	% Make sure the initial signal in itself has enough energy, 
	% otherwise the zero signal is returned
% 	if ((testErrorGoal) && (sum(residual.^2) < currErrorGoal))
% 		continue; % simply move on to the next signal
% 	end
	
	% Repeat as long as stopping condition isn't filled
	while 1
		
		% Update cardinality
		card = card + 1;
		
		% Compute projections
		proj = currD' * residual;
		
		% Find the index of the largest absolute inner product
		maxProjInd = find(max(abs(proj))==abs(proj),1); 
				
		% Add this new atom to the list
		indsList(card) = maxProjInd;
		
		% If this is the first atom, keep its projection
		if (card == 1)
			coeffsList(card) = proj(maxProjInd);
		else
			% If not the first atom, do least-squares (LS) over all atoms in the representation
			coeffsList(1 : card) = currD(: , indsList(1 : card)) \ x;
		end
		
		% Compute new residual
		residual = x - currD(: , indsList(1 : card)) * coeffsList(1 : card);
		
		% Check if we can stop running
		if testErrorGoal % Error Treshold
			residNorm = sum(residual.^2);
			if residNorm < currErrorGoal, break; end;
		end
		
		if testMaxAtoms % Cardinality Threshold
			if (card >= maxAtoms), break; end;
		end
		
	end
	
	% We need to re-modify the coefficients, 
	% to undo the effects of the dictionary normalization
	if (card > 0)
		coeffsList(1 : card) = coeffsList(1 : card) ./ atomsNormFacts(indsList(1 : card))';
	end
		
	% Assign results
	allCoeffsList( totNcoeffs + (1 : card)) = coeffsList(1 : card);
	allIndsList(   totNcoeffs + (1 : card)) = indsList(1 : card);
	allSignalsList(totNcoeffs + (1 : card)) = cSignal;
	totNcoeffs = totNcoeffs + card;
    rec=zeros(64,1);

    % Computing the new patch
    for ii=1:card    

        rec=rec+coeffsList(ii).*D(:,ii);
    end
    res(:,cSignal)=rec;
    
    % Overwrite the existing sliding coefficients
%     X(:,cSignal)=rec;
    
%     nrow=floor(cSignal/249);
    
%     for ii=1:64
%        maskedIm(cSignal-7*nrow+vecc(i))=rec(i);
%        Mask(cSignal-7*nrow+vecc(i))=1;
%     end
%     
%     Masks = im2col(Mask , param.patchSize , 'sliding');
%     X = im2col(maskedIm , param.patchSize , 'sliding');
%     
    end
end

ResIm = Average_Overlapping_Patches(res, [256 256] , param.patchSize );
close all;
figure; imshow(ResIm , [0 255]); title('Reconstructed Image');


% Construct the sparse matrix
% resA = sparse(...
% 	allIndsList(1:totNcoeffs) , allSignalsList(1:totNcoeffs) , allCoeffsList(1:totNcoeffs) , ...
% 	nAtoms , nSignals);

% Create the output signals
% resX = D * resA;
% resX(: , patchesToIgnore) = X(: , patchesToIgnore);






