自定义JPanel属性在repaint时为null但Timer执行时存在的问题排查
问题根源:创建了两个
Drawing实例 你代码里犯了一个极易忽略的低级错误:
- 先创建了
Drawing实例d,后续给这个实例设置了sceneRootNode - 但添加到窗口的是另一个全新的
Drawing实例(new Drawing())
窗口里实际渲染的是那个没被设置sceneRootNode的实例,所以paintComponent里打印的是null;而Timer里访问的是你设置过的d实例,所以能拿到正确的场景节点。
修复方案
把添加到窗口的代码改成使用已创建的d实例:
// 原代码 fr.getContentPane().add( new Drawing(), BorderLayout.CENTER ); // 修改后 fr.getContentPane().add( d, BorderLayout.CENTER );
额外补充的Swing注意点
- Swing组件是实例绑定的,每个组件实例都是独立的,操作不同实例的属性不会互相影响
- 虽然这次问题和线程无关,但要记住Swing的所有组件操作(包括属性设置、repaint触发)都应该在AWT事件调度线程(EDT)执行,你已经用
SwingUtilities.invokeLater和Swing Timer做到了这一点,这是正确的做法
内容的提问来源于stack exchange,提问作者user8112809
相关产品推荐
相关产品推荐

