Java JComponent不显示文本-Swing正在折磨我!
我是一名高中AP计算机科学的学生,正在用Java做一个独立的研究项目。我选择为初学钢琴的学生编写一个应用程序,在这个应用程序中,计算机会显示键盘的图片,并突出显示一个音符。然后,用户选择与突出显示的键对应的注释名称,计时器计数为零,然后报告用户的分数 我的视图即将完成,但在屏幕上显示计时器时遇到问题 计时器由模型创建并在单独的线程中运行,每秒指示控制器更新计时器,计时器在视图中调用一个方法,该方法在对象TimerUpdateComponent中设置一个值,然后验证以显示新文本 至少,这是理论。计时器工作得很好——就像我问的那样,每秒都会打印到控制台上——但是当我运行视图时,什么也没有出现。因此,我想我会像大师那样做并找出区别,我直接从Horstmann和Cornell的[I]Core Java-Volume I[/I]复制了这段代码,它应该在面板中央显示字符串“Hello,World!”:Java JComponent不显示文本-Swing正在折磨我!,java,user-interface,swing,Java,User Interface,Swing,我是一名高中AP计算机科学的学生,正在用Java做一个独立的研究项目。我选择为初学钢琴的学生编写一个应用程序,在这个应用程序中,计算机会显示键盘的图片,并突出显示一个音符。然后,用户选择与突出显示的键对应的注释名称,计时器计数为零,然后报告用户的分数 我的视图即将完成,但在屏幕上显示计时器时遇到问题 计时器由模型创建并在单独的线程中运行,每秒指示控制器更新计时器,计时器在视图中调用一个方法,该方法在对象TimerUpdateComponent中设置一个值,然后验证以显示新文本 至少,这是理论。计
public void paintComponent(Graphics g){<br>
Graphics2D g2 = (Graphics2D) g;<br>
String message = "Hello, World!";<br>
Font f = new Font("Serif",Font.BOLD,36);<br>
g2.setFont(f);
//measure the size of the message
FontRenderContext context = g2.getFontRenderContext();
Rectangle2D bounds = f.getStringBounds(message, context);
//set (x,y) to top-left corner of text
double x = (getWidth() - bounds.getWidth())/2;
double y = (getHeight() - bounds.getHeight())/2;
//add ascent to y to reach the baseline
double ascent = -bounds.getY();
double baseY = y + ascent;
//draw the message
g2.drawString(message, (int)x, (int)y);
g2.setPaint(Color.LIGHT_GRAY);
//draw the baseline
g2.draw(new Line2D.Double(x, baseY,x - bounds.getWidth(), baseY));
//draw the enclosing rectangle
Rectangle2D rect = new Rectangle2D.Double(x,y,bounds.getWidth(), bounds.getHeight());
g2.draw(rect);
}
}
public组件(图形g){
图形2d g2=(图形2d)g;
String message=“你好,世界!”;
Font f=新字体(“衬线”,字体粗体,36);
g2.setFont(f);
//测量消息的大小
FontRenderContext上下文=g2.getFontRenderContext();
矩形2D边界=f.getStringBounds(消息、上下文);
//将(x,y)设置为文本的左上角
双x=(getWidth()-bounds.getWidth())/2;
双y=(getHeight()-bounds.getHeight())/2;
//将上升添加到y以达到基线
双上升=-bounds.getY();
双基y=y+上升;
//传达信息
g2.抽绳(信息,(整数)x,(整数)y);
g2.setPaint(颜色:浅灰色);
//画基线
绘制(newline2d.Double(x,baseY,x-bounds.getWidth(),baseY));
//绘制封闭矩形
Rectangle2D rect=新的Rectangle2D.Double(x,y,bounds.getWidth(),bounds.getHeight());
g2.绘制(rect);
}
}
令我惊讶的是,这段代码也没有显示字符串!我认为字符串可能太大,无法容纳相当小的面板,因此它只显示空白,但我尝试将字体大小更改为10,但这也不起作用
所以现在我真的是:咬:咬。我能想到的唯一一件事是这本书已经过时了(Sun是否从2008年起改变了Swing的工作方式?我对此表示怀疑。)或者犯了一个惊人的编码错误(在第八版?),所以我创建了一个单独的文件,并从书中复制了整个.java文件,它工作得很好
请帮帮我
另外,这里是我的原始方法体,以防您想查看: String message = time/60+":"+time%60;<br>
Graphics2D g2 = (Graphics2D) g;<br>
FontRenderContext context = g2.getFontRenderContext();<br>
Rectangle2D bounds = g2.getFont().getStringBounds(message, context);<br>
double x = (getWidth() - bounds.getWidth()) / 2;<br>
double y = (getHeight() - bounds.getHeight() / 2);<br>
g2.drawString(message,(int)x,(int)y);<br>
String message=time/60+:“+time%60
图形2d g2=(图形2d)g
FontRenderContext上下文=g2.getFontRenderContext()
Rectangle2D bounds=g2.getFont().getStringBounds(消息、上下文)
双x=(getWidth()-bounds.getWidth())/2
双y=(getHeight()-bounds.getHeight()/2)
g2.抽绳(信息,(整数)x,(整数)y)
您可能应该在绘制文本之前设置文本的绘制。另外,确保在每次更新时使用SwingUtilities.invokeLater()调用组件上的repaint,在第一次重新绘制后,您将在灰色背景上绘制灰色文本
但是为什么不在每次定时器启动时使用JLabel和call setText,而自己完成所有这些呢?关键短语是
计时器在单独的线程上运行
您只能从事件调度线程更新Swing GUI,该线程运行GUI
解决方案是使用
SwingUtilities.invokeLater()
运行更新代码。我将绘制颜色更改为红色,但仍然没有得到任何结果。我没有使用JLabel,因为我可能希望格式化文本、更改大小、颜色等,而且JLabel限制太多。那么,您的非工作文件与书本中的工作文件有什么不同?如果您添加一些println/日志,从pain方法中转储组件的宽度和高度,它们是什么?