2010-07-29 13 views
6

Przenieśliśmy się z próby użycia OpenGL przez Penumbra do próby narysowania bezpośrednio na JPanelu za pomocą kontekstu Graphics.Stan wyścigu (?) Przy korzystaniu z Swinga

Byłoby wspaniale, gdyby nie kłopoty ... Skompilowałem kod, a ~ 1 raz na 25, grafika (to na przykład prostokąt) rysuje dobrze. Pozostałe ~ 24 razy, nie ma.

Oto mój kod:

(def main 
    (let [frame (JFrame. "This is a test.") 
     main-panel (JPanel. (GridBagLayout.)) 
     tpan (proxy [JPanel] [] (getPreferredSize [] (Dimension. 600 400)))] 

    (doto frame 
     (set-content-pane 
     (doto main-panel 
     (grid-bag-layout 
      :gridx 0 :gridy 0 
      tpan 
      :gridx 0 :gridy 1 
      xy-label))) 
     (pack-frame) 
     (set-visible)) 

    (draw-line tpan Color/RED 250 250 50 50))) 

Funkcja draw-line jest poniżej:

(defn draw-line [panel color x y w h] 
    (let [graphics (.getGraphics panel)] 
    (doto graphics 
     (.setColor color) 
     (.drawRect x y w h)))) 

nie mam pojęcia, co się dzieje. Początkowo myślałem, że to refreny, nad którymi pracowałem, ale potem wyjąłem je i nadal mam te problemy. Zresetowałem lein i slime/swank i emacs. Jestem dość zaintrygowany.

Jak zwykle, każda pomoc zostanie doceniona. Mam nadzieję, że to jest pytanie z odpowiedzią! Ostatnio wydaje mi się, że pytam o to, co niemożliwe:

Odpowiedz

5

Upewnij się, że zawsze jesteś na EDT. Jeśli widzisz, że GUI działa losowo, jest to zazwyczaj przyczyną. Warunki wyścigu są krytyczne dla huśtawki, ponieważ zaprojektowano je jako całkowicie jednowątkowe.

To, co możesz spróbować, aby zobaczyć, to znaleźć dowolną metodę, która współdziała z elementem swing i zlecić wydruk Thread.getCurrentThread(). ToString() (lub coś bardzo zbliżonego do tego).

Powinien zawsze wydrukować nazwę wątku, a zobaczysz gdzieś w nim litery AWT. Możesz nawet przechować ten wątek, testować go przy każdym wywołaniu Swing i twierdzić, że to nie to samo.

Właściwie nie wiem, dlaczego słońce nigdy nie zbudował „Debug” wersję JDK że dochodzenia kiedy takie rzeczy się (jak wtedy, gdy jakiś wątek huśtawka została wywołana z non-AWT wątku ...)

+0

Fantastyczne, dziękuję! Wszelkie sugestie dotyczące tego, od czego zacząć? (A, dla punktów bonusowych, jakikolwiek pomysł, w którym mógłbym zboczyć z EDT?) – Isaac

+0

Obawiam się, że nie wiem wystarczająco dużo o strukturze, z której korzystasz - nie rozpoznaję składni poza tym, że mogę powiedz, że jest to deklaracja. Jedną (denerwującą) rzeczą, którą możesz zrobić jest podklasowanie wszystkich kontrolek, których używasz, nadpisuj metody, których możesz użyć i wyprowadź z nich bieżący wątek. Inną możliwością jest wydrukowanie nazwy wątku i sprawdzenie, czy zawiera ona litery AWT. Po tym jednak po prostu nie wiem wystarczająco dużo o twoim kodzie. –

4

Powinieneś przesłonić paintComponent w panelu. (Wybór JPanel prawdopodobnie nie jest najlepszy - użyj JComponent i pewnych set-opaque na nim.)

Ponadto, sądzę, że powinieneś być na AWT EDT.

Powiązane problemy