2011-06-19 52 views
5

Tôi có một ứng dụng máy tính để bàn java nhỏ cần có khả năng thêm và xóa các trường động bằng cách nhấp vào nút "+" và "-" tương ứng. Tôi đã nhận được điều này để làm việc bằng cách gọi revalidate() và sau đó repaint() trên tất cả các thùng chứa cha mẹ tất cả các con đường lên đến JFrame trong ActionListener.Java Swing revalidate() và repaint() vấn đề

Điều này dường như đã thực hiện thủ thuật, nhưng đôi khi nó không hoạt động và JPanels không thay đổi kích thước chính xác. Điều này xảy ra không thường xuyên và dường như ngẫu nhiên và khiến tôi tin rằng đó có thể là vấn đề tương tranh. Tôi đã cố gắng tung ra các thùng chứa cha mẹ từ thread gửi sự kiện nhưng điều này đã không giải quyết được vấn đề.

Đây có phải là vấn đề tương tranh hay tôi đang sủa nhầm cây không? Bất cứ ai có bất kỳ ý tưởng những gì đang xảy ra và làm thế nào nó có thể được giải quyết?

nhiều đánh giá cao

-SwingNoob

+0

@john, một ['LayoutManager'] (http://download.oracle.com/javase/tutorial/uiswing/layout/using.html) chịu trách nhiệm về các thành phần của nó. được nói, hoàn toàn không có lý do gì để gọi 'repaint()' hoặc 'revalidate()' khi thêm/xóa các thành phần khỏi một thùng chứa. – mre

+1

Lỗi liên tục thường đề xuất các vấn đề tương tranh, nhưng tôi không nghĩ rằng bất kỳ ai sẽ có thể cung cấp cho bạn câu trả lời chắc chắn dựa trên thông tin được trình bày. –

+1

@mre: Vui lòng làm rõ nhận xét của bạn vì trong kinh nghiệm của tôi và từ bài đọc của tôi, người ta phải gọi là 'revalidate' và 'repaint' trên Container khi xóa các mục và' revalidate' và đôi khi 'repaint' khi thêm thành phần. –

Trả lời

1

Ra mắt container từ thread AWT/EDT là không đủ.

Bạn cần thực thi mọi thay đổi bố cục cho vùng chứa trên chuỗi AWT/EDT.

Vì vậy, nếu bạn đảm bảo rằng việc thêm và xóa của bạn được thực hiện theo cách đó, hãy xác thực lại() hoặc vẽ lại() không cần thiết.

+2

'AWT' thread? Bạn không có nghĩa là 'EDT'? – mre

+0

Tôi cũng gọi nó là awt (từ năm 1999) – bestsss

3

mà không được trả lời cho câu hỏi OP của nice example, vấn đề OP là có thể về LayoutManager và một cái gì đó unknow trong mã OP của

1/nếu bạn thêm một JComponent mới cho container sau đó bạn phải gọi

validate(); 
repaint(); //lay with LayoutManager required that 

2/nếu loại bỏ và sau đó thêm một JComponents từ/đến các container sau đó bạn phải gọi

revalidate(); 
repaint(); // lay with LayoutManager required that 

3/trông giống như val phủ như xác nhận lại idate quá,

+0

Tôi không chắc chắn nếu gọi 'repaint()' là cần thiết. Tôi đã viết một số mã mẫu, và có vẻ như việc gọi 'validate()' là tất cả những gì được yêu cầu, cho dù bạn đang loại bỏ hay thêm các thành phần. Nhưng, tất nhiên, điều này có thể hoàn toàn tình huống.:) – mre

+0

@mre đồng ý nếu bạn sẽ loại bỏ hoặc chỉ thêm một JComponents, nếu có số lượng JComponents, quan điểm của tôi bạn có thể có nguy cơ với chỉ với kiến ​​trúc MVC GUI nghiêm ngặt, nếu không ý tưởng không an toàn byteCode cho một dòng ... :-), có repaint rất lười đến GC, đó là giả kim thuật không được mô tả – mKorbel