[solved]swing applet thread GUI 얼지 않는 spin 최신버전?

송효진의 이미지

swing 으로 applet 을 만들어보고 있는데요.

Thread 로 넘겨서 루프내에서 지속적으로 JProgressBar 값을 바꾸면 적용이 안되더군요.
InvokeAndWait 는 요점이 뭔지 모르겠고...(그냥 저 안에서 값을 바꾸는건 안되더군요.)
찾다찾다 spin 이라는 것을 찾았는데,
망한 프로젝트네요.
저런식의 프로젝트 또 있을까요?
아니면 Delphi 의 Application.ProcessMessage; 같은 역할을 하는 메소드가 있나요?
InvokeAndWait 로 애플릿 내의 패널 값을 바꾸는 방법을 소개해 주셔도 감지덕지 입니다.

감사합니다.

bookgekgom의 이미지

import java.awt.BorderLayout;
import java.awt.Container;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.BorderFactory;
import javax.swing.JFrame;
import javax.swing.JProgressBar;
import javax.swing.Timer;
import javax.swing.border.Border;
 
public class Main {
    int val;
 
    public Main() {
        JFrame f = new JFrame("JProgressBar Sample");
        f.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        Container content = f.getContentPane();
        final JProgressBar progressBar = new JProgressBar();
        progressBar.setValue(val);
        progressBar.setStringPainted(true);
        Border border = BorderFactory.createTitledBorder("Reading...");
        progressBar.setBorder(border);
        content.add(progressBar, BorderLayout.NORTH);
        f.setSize(300, 100);
        f.setVisible(true);
 
        Timer timer = new Timer(1000, new ActionListener() {
            public void actionPerformed(ActionEvent arg0) {
                progressBar.setValue(++val);
            }
        });
        timer.start();
    }
 
    public static void main(String args[]) {
        new Main();
    }
}

1 초에 1% 씩 올라가는 예제입니다.

이러면 안얼지 않나요?

타이머도 쓰레드 라서 괜찮을것 같은데....

아니면 원하시는게 저게 아닌가요?

---------------------------------------------------------------------------------------------------------------
루비 온 레일즈로 만들고 있는 홈페이지 입니다.

http://jihwankim.co.nr

여러 프로그램 소스들이 있습니다.

필요하신분은 받아가세요.

fender의 이미지

JProgressBar의 문제가 아니라, 말씀하신 'invokeAndWait/invokeLater'의 요점을 잘 모르시는 것이 문제입니다. 스윙에서 event dispatcher thread의 역할과 비동기적 작업을 올바르게 처리하는 방법에 대해 구글링 해보시면 될 듯 합니다.

----------------------------
[서명] 그놈 한국 사용자 모임 - 그놈에 대한 모든 것! - 게시판, IRC, 위키, 갤러리 등등...

----------------------------
[서명] 그놈 한국 사용자 모임 - 그놈에 대한 모든 것! - 게시판, IRC, 위키, 갤러리 등등...

송효진의 이미지

어렵네요.

		Timer timer2 = new Timer(500, new ActionListener() {
			public void actionPerformed(ActionEvent event) {
				try {
					SwingUtilities.invokeAndWait(new Runnable() {
					    public void run() {
				        	ProgressBar.setValue((int) CurrSize);
				        	ProgressBar.setString(Long.toString(CurrSize) + " / " + Long.toString(TotalSize));
					    }
					});
				} catch (Exception e) {
				}
			}
		});
		timer2.start();
 
		while(FResult == null) {
			try {
				Thread.sleep(100);
				System.out.println("A");
			} catch(Exception e) {
				FResult = "<script type='text/javascript'>alert('upload error. (" + e.getMessage() + ")');</script>";
			}
		}
		timer2.stop();
		return FResult;

루프를 돌고 리턴을 해야 해서 위쪽에 쓰레드를 하나 띄우고, 쓰레드가 FResult 를 채워주면 리턴해주도록 했습니다.
쓰레드 내에서는 ProgressBar 를 repaint() 해도 화면에 안나타서,
조언대로 위와 같이 타이머로도 해 봤습니다. (repaint() 도 넣어 봤습니다.)
안되네요.
타이머는 아래의 while() 루프가 없어야 할듯 합니다.

Application.ProgressMessage; 가 있으면 딱인데...

설계를 바꿔야 할까요?
설계를 바꾸면 리턴을 어떻게 할 수 있을까요?

emerge money
http://wiki.kldp.org/wiki.php/GentooInstallSimple - 명령어도 몇 개 안돼요~
http://xenosi.de/

fender의 이미지

여러 GUI 툴킷이 이벤트 처리와 화면 그리기 등을 담당하는 메인 스레드(EDT)를 하나 두고 필요한 작업을 큐에서 순서대로 처리하는 방식으로 구현되어 있습니다. 스윙도 예외가 아닌데, 이 경우 EDT에서 시간이 오래 걸리는 작업을 하거나 sleep을 쓰는 등으로 스레드를 지연시키면 그 시간 동안 GUI 관련 처리가 멈춰 버리기 때문에 화면이 굳어 버리는 것입니다.

또 대부분 이러한 방식의 경우 EDT를 제외한 다른 스레드에서 직접 화면과 관련된 작업을 하는 것(예컨대 프로그레스바를 진행시킨다던지)을 금지하고 있습니다.

따라서 이 경우 예를들어 네트워크 전송등과 같이 시간이 걸리는 작업을 비동기적으로 처리하면서 결과를 화면에 반영하고 싶은 경우,

(1) 별도의 스레드를 만들어서 작업을 처리한다.

(2) (1)의 스레드 안에서 적절한 시점(타이머나 sleep이용) 마다 화면을 업데이트 하는데,

(3) 업데이트시 자신이 EDT가 아니기 때문에 직접 호출해선 안되고 EDT의 큐에 작업을 '얹어주는' 방식으로 처리한다.

이런 순서를 따르면 됩니다. (3)을 해주는 것이 스윙에서는 SwingUtilities.invokeLater입니다.

이 부분은 GUI 프로그램에서는 기본이 되는 내용이기 때문에 좀 더 구글링 등을 통해 개념을 확실히 숙지하시는 것이 좋습니다.

----------------------------
[서명] 그놈 한국 사용자 모임 - 그놈에 대한 모든 것! - 게시판, IRC, 위키, 갤러리 등등...

----------------------------
[서명] 그놈 한국 사용자 모임 - 그놈에 대한 모든 것! - 게시판, IRC, 위키, 갤러리 등등...

bookgekgom의 이미지

while 문 자체도 하나의 쓰레드로 잡으면 될것 같은데요?

---------------------------------------------------------------------------------------------------------------
루비 온 레일즈로 만들고 있는 홈페이지 입니다.

http://jihwankim.co.nr

여러 프로그램 소스들이 있습니다.

필요하신분은 받아가세요.

송효진의 이미지

감사합니다.
조언을 바탕으로 저기에서의 리턴을 포기하고,
프로그래스바 갱신만 따로 타이머로 주고 해당 함수가 끝나도록 했습니다.

리턴값은 받아야 하는쪽에서 주기적으로 시도를 하게 고쳤습니다.
잘 되네요.^^

emerge money
http://wiki.kldp.org/wiki.php/GentooInstallSimple - 명령어도 몇 개 안돼요~
http://xenosi.de/

댓글 달기

Filtered HTML

  • 텍스트에 BBCode 태그를 사용할 수 있습니다. URL은 자동으로 링크 됩니다.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>
  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.

BBCode

  • 텍스트에 BBCode 태그를 사용할 수 있습니다. URL은 자동으로 링크 됩니다.
  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param>
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.

Textile

  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • You can use Textile markup to format text.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>

Markdown

  • 다음 태그를 이용하여 소스 코드 구문 강조를 할 수 있습니다: <code>, <blockcode>, <apache>, <applescript>, <autoconf>, <awk>, <bash>, <c>, <cpp>, <css>, <diff>, <drupal5>, <drupal6>, <gdb>, <html>, <html5>, <java>, <javascript>, <ldif>, <lua>, <make>, <mysql>, <perl>, <perl6>, <php>, <pgsql>, <proftpd>, <python>, <reg>, <spec>, <ruby>. 지원하는 태그 형식: <foo>, [foo].
  • Quick Tips:
    • Two or more spaces at a line's end = Line break
    • Double returns = Paragraph
    • *Single asterisks* or _single underscores_ = Emphasis
    • **Double** or __double__ = Strong
    • This is [a link](http://the.link.example.com "The optional title text")
    For complete details on the Markdown syntax, see the Markdown documentation and Markdown Extra documentation for tables, footnotes, and more.
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.
  • 사용할 수 있는 HTML 태그: <p><div><span><br><a><em><strong><del><ins><b><i><u><s><pre><code><cite><blockquote><ul><ol><li><dl><dt><dd><table><tr><td><th><thead><tbody><h1><h2><h3><h4><h5><h6><img><embed><object><param><hr>

Plain text

  • HTML 태그를 사용할 수 없습니다.
  • web 주소와/이메일 주소를 클릭할 수 있는 링크로 자동으로 바꿉니다.
  • 줄과 단락은 자동으로 분리됩니다.
댓글 첨부 파일
이 댓글에 이미지나 파일을 업로드 합니다.
파일 크기는 8 MB보다 작아야 합니다.
허용할 파일 형식: txt pdf doc xls gif jpg jpeg mp3 png rar zip.
CAPTCHA
이것은 자동으로 스팸을 올리는 것을 막기 위해서 제공됩니다.