Making a patch a link in matlab? - matlab

I have asked several questions about making links on images in matlab, but I want to be able to make a patch a link. I tried the code I posted below but that didnt work. Any ideas on how to make this work?
patch([x2(i) x2(i+1) x2(i+1) x2(i)],[y3(j) y3(j) y3(j+1) y3(j+1)],[-0.01 -0.01 -0.01 -0.01],'r','FaceAlpha' ,.4,'EdgeColor','none','ButtonDownFcn', ['winopen(''' file(j,i) ''');']);
function [filePath] = file( x, y )
filePath = strcat('C:\Documents and Settings\Sentinelle\My Documents\Prostate_082_31\sl5_knt1\sl5_',num2str(x),'-',num2str(y),'.ps');
end

Here is a working example (just adjust the paths of files to something that actually exist):
BASE_DIR = 'C:\path\to\directory';
fcn = #(x,y) fullfile( BASE_DIR , sprintf('file_%d-%d.txt',x,y) );
patch([-1 -1 1 1], [-1 1 -1 1], 'r', ...
'ButtonDownFcn',{#(o,e,f)winopen(f), fcn(2,1)})
axis([-2 2 -2 2])
title('Click the shape to open file...')

Normally, callbacks are called with two input arguments, the handle to an object and a usually empty eventdata. This might lead to the error. Try this instead of ['winopen(''' file(j,i) ''');']:
#(u,v)winopen(#()file(j,i))

The problem is with the position of the patch it was positioned behind the image [-0.01 -0.01 -0.01 -0.01]. The links were being covered up by the image. I changed the code to [0 0 0 0] and this works how I want it to.
patch([x2(i) x2(i+1) x2(i+1) x2(i)],[y3(j) y3(j) y3(j+1) y3(j+1)],[0 0 0 0],'r','FaceAlpha' ,.4,'EdgeColor','none','ButtonDownFcn', ['winopen(''' file(j,i) ''');']);

Related

spurious lines using fimplicit on a modular function

I want to plot collections of repeating circular arcs and am having trouble with spurious lines showing up in the plots. For example, one of the plots I want is given by
a = #(x,y) ((mod(x,1) + 0.5).^2 + (mod(y,1) - 0.5).^2 - 1)
fimplicit(a,[-1,1],'MeshDensity',500)
but the output is incorrect as far as I can tell:
The implicit function is decidedly not zero on the verticle lines. I assume something funny is happening with the fimplicit algorithm and modular arithmetic. Any ideas how to get around this? Thanks!
That probably happens because your function is discontinuous at the lines x = k with k integer, as a surface plot reveals:
fsurf(a, [-2 2])
To verify that the discontinuity is the likely reason, consider the simpler example
f = #(x,y) (2*(x>=0)-1).*(2*(y>=0)-1);
This function is discontinuous at x = 0 and at y = 0. It jumps from 1 to −1 at x = 0 and at y = 0, but it never equals 0.
fsurf(f, [-2 2])
It can be seen that fimplicit is confused by the discontinuity, and thinks the function is 0 there:
fimplicit(f,[-2,2],'MeshDensity',500)
Looking at the source code of fimplicit, the actual work is seen to be done (on R2017b at least) by the class matlab.graphics.function.ImplicitFunctionLine in the second to last line. That class is a .p file, and is thus obfuscated, which means that unfortunately its source code cannot be seen.

Optimizing in Parallel in Matlab with Mosek

I'm trying to solve a cone program in Matlab by calling MOSEK while varying the bound on one of the constraints.
I would like to do so in parallel to take advantage of all the cores that I have. Here is a modified example to illustrate my point.
testBounds=[0.1, 0.15, 0.2, 0.25, 0.3];
clear prob;
[r, res] = mosekopt('symbcon');
prob.c = [0 0 0 1 1 1];
% Specify the non-conic part of the problem.
prob.a = sparse([1 1 2 0 0 0]);
prob.buc = 1;
prob.blx = [0 0 0 -inf -inf -inf];
prob.bux = inf*ones(6,1);
% Specify the cones.
prob.cones.type = [res.symbcon.MSK_CT_QUAD, res.symbcon.MSK_CT_RQUAD];
prob.cones.sub = [4, 1, 2, 5, 6, 3];
prob.cones.subptr = [1, 4];
for i=1:5
% Specify the changing bound
prob.blc = testBounds(i);
% Optimize the problem.
[r,res]=mosekopt('minimize',prob);
% Display the primal solution.
res.sol.itr.xx'
end
I tried to do this with parfor, but it isn't permitted. Unfortunately, MOSEK documentation doesn't go into detail about parallizing. How can I carry out the above in parallel?
The problem with your code is your use of the variable prob. While on an algorithmic level it is independent because each iteration of the loop uses it's own setting for blc and not uses any previous data, parfor does not support this use. Easiest solution is not to modify the variable prob but instead copy it in each iteration, making prob a broadcast and prob2 a local variable:
parfor ii=1:5
% Specify the changing bound
%copy broadcast variable prob to a temporary variable prob2
%this way the iteration has writing capabilities
prob2=prob
prob2.blc = testBounds(ii);
% Optimize the problem.
[r,res]=mosekopt('minimize',prob2);
% Display the primal solution.
res.sol.itr.xx'
end
Another issue with your code is the way you are returning data. parfor has no order when processing the data, thus just displaying it to the console will not give you any useful results. It's also slow. I don't know what exactly you need and what the datatypes are, thus I have not touched that part of the code. The code in my answer does the calculations but is not returning any results because res and r are both temporary variables.
N=5;
r = cell(1,N);
res = cell(1,N);
for ii=1:N
% Specify the changing bound
prob2=prob;
prob2.blc = testBounds(ii);
% Optimize the problem.
[r{ii},res{ii}]=mosekopt('minimize',prob2);
% Display the primal solution.
res{ii}.sol.itr.xx' %'// better not display at all during calculation
end
parfor does not allow for creation of variables within its bounds. Therefore I elected to preallocate r and res as cells, which can act the output storage. See the prob/ prob2 issue in #Daniel's answer

Linear Programming -- Minimizing t

I am trying to solve the following problem in matlab but facing some difficulty.
Min t
s.t.
t>= 0.0538λ_2 - 0.7071λ_1
t>= λ_1 - 0.3827λ_2
where 0<=λ_j<=1 for j=1,2
This is what I have so far:
f=[0;0;1]
A=[-0.7071 0.0538 -1;
1 -0.3827 -1]
B=[0;0]
ub=zeros(2,1)
lb=zeros(2,1)
linprog(f,A,B,[],[],lb,ub);
This problem is taken from a research paper and in that the author solved the above problem and found optimal value of t=−0.12698. I am not getting the correct answer with my implementation. Can someone help me please. Also how can I specify in linprog() that I want to use the simplex method.
This should give you the correct result:
f=[1;0;0];
A=[-1 -0.7071 0.0538;
-1 1 -0.3827] ;
B=[0;0] ;
ub=[inf 1 1] ;
lb=[-inf 0 0] ;
options = optimset('Algorithm','simplex');
xres = linprog(f,A,B,[],[],lb,ub,[],options);
Note that linprog expects your input in the format:
min x
s.t. Ax <=b
What I did here, is set the vector x = [t l1 l2], so the first entry in your result vector xres corresponds with t. You can set the algorithm using the optimset function.
Also, you set lower and upper bounds for 2 of the 3 variables only, so matlab gave me some warnings in that regard. To be on the safe side, it is usually best to set 'dummy' limits for the unrestricted variables (i.e. here I set the upper limit of t to inf, and the lower limit to -inf). That way, you make sure the right bounds apply to the right variables.
matrix A is incorrect set.
You need determined what variables where should be.
A=[-0.7071 0.0538 -1;
1 -0.3827 -1]
P.S. Sorry for my English.

Starting the graph lines at the same place

I'm trying to get the green line in the following Matlab code to start from the same point as the other two ones WITHOUT shifting the whole figure to the left, i.e the starting point shouldn't
be attached to the y axis. But I cannot figure out how to. If anyone could help explain how to do it, I'd greatly appreciate the help. :)
all_local = [ 1.0001 1.0001 1.0001 1.0001];
mix_diff_paragraphs = [ 0.59 0.93 0.97 1.0001];
mix_same_paragraphs = [ 0.35 0.55 0.80 1.0001];
axis manual
axis([1,4,0,2]);
y=[1 2 3 4];
h = plot(y+1,all_local,'-om',...
y+1,mix_diff_paragraphs,'-xb',...
y,mix_same_paragraphs,'-+g','LineWidth',2,'MarkerSize',8);
set(gca,'xtick', [1 2 3 4 5]);
set(gca,'XTickLabel',{0,300,500,1000,1500});
set(gca,'ytick', 0:0.2:1.2);
set(gca,'yticklabel', {'0', '0.2', '0.4', '0.6', '0.8','1',''});
legend('Location','BEST','Local users only','Local/Remote users alternate on Pargs.','Local/Remote users modify the same Parg.')
ylabel('Responsiveness');
xlabel('Thinking Period(msec)')
grid on;
That's quite a messy way to do what you did (I don't see why you'd want to change the tick labels without changing the actual x values), but this aside, just add (+1) to the green line:
h = plot(...
...
y+1 ...,'LineWidth',2,'MarkerSize',8);
and in the end add: xlim([1,5]);
If I understood correctly what you were trying to do...

crop an image according to what is different between 2 images

I have different images and I would like to crop them and keep only what is different between both. Here is the code I have so far.
video = VideoReader('frames.avi', 'Tag', 'my reader object');
frameFirst = read(video,1);
frameSecond = read(video, video.NumberOfFrames-1 );
imshowpair (frameSecond,frameFirst);
pause();
Well, it's tough to give you a good answer without much more detail. I think I understand what you're trying to do, and this might get you moving in the right direction. This code iterates through each pixel of the image (each pixel contains a 1x3 vector of RGB data ranging from 0 to 1), by row and column. If the difference in any of the elements of the 1x3 RGB vector exceeds some threshold (in this case, set to 0.1), we make that whole pixel black (set it to [0 0 0]). Else, we lust make it whatever the last frame was. To filter out all but those pixels that are identical, set the thresh value to 0. It goes like this:
thresh = 0.1
for ii = 1:size(frameFirst, 1)
for jj = 1:size(frameFirst, 2)
pixDiff = frameFirst{ii, jj} - frameSecond{ii, jj}
if (pixDiff(1) > thresh || pixDiff(2) > thresh || pixDiff(3) > thresh)
outputFrame = frameSecond{ii, jj};
else
outputFrame = [0 0 0];
end
end
end
I hope this does what you're looking for. Good luck!
Edit 1: Ok, I understand what you are looking for now. You need to have the indices of the bottom-right and top-left. If you already have those, just do this: frameOut = frameIn(xStart:xStop, yStart, yStop. If you need to find those points, that's harder. Let me know and I'll help you work it out.