2012-09-13 11 views
6

Mam GUI z dwiema osiami. Pierwsze osie mają obraz o niskiej rozdzielczości.Matlab: Wyznaczanie czasu rzeczywistego ROI wybranego przy pomocy IMRECT

To, co chciałbym zrobić, to wybrać obszar na pierwszych osiach przy pomocy IMRECT, a następnie wyświetlić ten obszar jako obraz o wysokiej rozdzielczości na drugiej osi, przy ciągłej aktualizacji, kiedy przesuję prostokąt IMRECT.

Jedyny sposób, w jaki mogłem to zrobić, to "pętla for" z 0,1 pauzą, która trwa zaledwie minutę lub dwie, podczas gdy ja wybieram i zmieniam ROI z IMRECT, bardzo uciążliwy.

Moja myśl polegała na użyciu funkcji uruchamianej za każdym razem, gdy mysz poruszała się w obrębie pierwszych osi, za pomocą poleceń drukowania i getPosition w tej funkcji. Jednak nie jestem pewien, jak napisać taką funkcję (wyzwalanie ruchu myszy w osiach).

Każda pomoc będzie bardzo ceniona!

+1

Sprawdź również: http://stackoverflow.com/questions/10998739/scaleable-dragable-box-on-plot-to-can-select-data/10998803 # 10998803 –

Odpowiedz

4

Ogólnie należy przypisać oddzwonienie do numeru imrect. Na przykład:

x = imrect(); 
x.addNewPositionCallback(@(x)(disp('The rect has changed'))) 

Wywołanie zwrotne powinny uzyskać dodatkowe parametry, takie jak obraz i drugi osie poprzez wykorzystanie funkcji anonimowych.


Napisałem mały fragment kodu, który robi to, co chcesz. Powinieneś dodać kontrole graniczne, ponieważ nie zawracałem sobie głowy. Aktualizuje on CData zamiast uruchamiać imshow po przesunięciu prostokąta, więc jest całkiem gładki.

GUI

function Zoomer 
    figure(); 

    highResImage = imread('peppers.png'); 
    lowResImage = imresize(highResImage,0.5); 

    a1 = subplot(2,1,1); 
    a2 = subplot(2,1,2); 

    imshow(lowResImage,'Parent',a1); 
    initialPosition = [10 10 100 100]; 
    lowResRect = imrect(a1,initialPosition); 

    lowResRect.addNewPositionCallback(@(pos)Callback(pos,a2,highResImage)); 

    Callback(initialPosition , a2, highResImage); 
end 

function Callback(position,axesHandle, highResImage) 
    position = position * 2; 
    x1 = position(1); 
    y1 = position(2); 
    x2 = position(1) + position(3); 
    y2 = position(2) + position(4); 

    highResThumbnail = highResImage(round(y1:y2),round(x1:x2),:); 

    if isempty(get(axesHandle,'Children')) 
     imshow(highResThumbnail,'Parent',axesHandle); 
    else 
     imHandle = get(axesHandle,'Children'); 
     oldSize = size(get(imHandle,'CData')); 
     if ~isequal(oldSize, size(highResThumbnail)) 
      imshow(highResThumbnail,'Parent',axesHandle); 
     else 
      set(imHandle,'CData', highResThumbnail); 
     end  
    end 
end 
+0

Dzięki, Andrey. Mam to doskonale. Przez jakiś czas walczyłem, właśnie tego szukałem. Poprzedni wiersz kodu, który miałem do ograniczenia prostego prostokąta do rozmiaru obrazu, już nie działa. Czy masz szybkie rozwiązanie, aby ograniczyć prawidłowy wybór do osi? Dziękuję Ci bardzo! – user1668909

+0

@ user1668909, sprawdź http://stackoverflow.com/questions/10998739/scaleable-dragable-box-on-plots-that-can-select-data/10998803#10998803. Zwłaszcza funkcja 'makeConstraint' –

1

zblizonym funkcjonalność jak @ post Andrey jest z trzema różnicami:

  • Ustawianie axis granice zamiast 'CData'
  • Współczynnik powiększenie (które mogą być szybciej?) jest zmienna i zależy od rozmiaru prostokąta, ze względu na 'fit''IniitalMagnification'.
  • Dodany ConstraintFcn

byłoby:

function imZ = Zoom(im, s) 

f = figure; 
a1 = subplot(1,2,1); 
imshow(im,'InitialMagnification', 'fit'); 
a2 = subplot(1,2,2); 
imshow(im,'InitialMagnification', 'fit'); 

Ipos = [0 0 s]; 
rect = imrect(a1,Ipos); 
rect.setPositionConstraintFcn(@(p) Const(p,size(im))); 
rect.addNewPositionCallback(@(p) CB(p,a2)); 
CB(Ipos,a2); 

if nargout > 0 
    uiwait(f); 
    imZ = im(pm(2):pm(2)+pm(4),pm(1):pm(1)+pm(3),:); 
end 

    function p = Const(p,imS) 
     p(1:2) = max(1,p(1:2)); 
     p(1:2) = min(imS([2 1])-p(3:4),p(1:2)); 
    end 

    function CB(p,a) 
     pm = round(p); 
     axes(a);  
     axis([pm(1),pm(1)+pm(3),pm(2),pm(2)+pm(4)]); 
    end 
end 

które można nazwać jako:

Zoom(imread('peppers.png'),[100 100]); 
+0

Myślę, że jest to najlepsza odpowiedź tutaj. –

Powiązane problemy