通过线程缩放图像 – JAVA
作者:互联网
假设我有一张图片.我将图像放在JPanel中,并在JFrame中添加JPanel.图像从框架的底部移动到框架的顶部,同时使用AffineTransform减小其尺寸.变量使用线程更改.
所以这是以下代码:
public class SplashScreen extends JFrame{
Image img1;
int w=1,h=1;
int x=0,y=0;
Thread th = new Thread(new Runnable() {
@Override
public void run() {
while(true){
w-=0.05;
h-=0.05;
y-=2;
x+=1;
if(y==-100){
new MainMenu_BlueJay().setVisible(true);
dispose();
}
repaint();
try {
Thread.sleep(10);
} catch (InterruptedException ex) {
Logger.getLogger(SplashScreen.class.getName()).log(Level.SEVERE, null, ex);
}
}
}
});
JPanel p = new JPanel();
public SplashScreen(){
setLayout(new BorderLayout());
p.setPreferredSize(new Dimension(900,600));
p.setBackground(Color.black);
p.setLayout(new GridLayout());
add(p);
setTitle("BlueJay");
setSize(900,600);
getContentPane().setBackground(Color.black);
setDefaultCloseOperation(EXIT_ON_CLOSE);
setLocationRelativeTo(null);
setVisible(true);
th.start();
requestFocus();
setFocusable(true);
}
@Override
public void paint(Graphics g) {
super.paint(g);
Graphics2D g2d = (Graphics2D) g;
img1 = new ImageIcon("images/Intro/BJ Production 2013.png").getImage();
AffineTransform at = new AffineTransform();
at.scale(w,h);
g2d.setTransform(at);
g2d.drawImage(img1, x, y, p);
}
public static void main(String[] args) {
new SplashScreen();
}
但是我从上面的代码得到的只是黑屏.怎么了?无论如何,如果我不使用AffineTransform功能(只是从下往上移动),图像会显示并移动但框架会快速闪烁(闪烁).
有任何想法解决这个问题所以我可以移动图像,同时减小其大小,并解决闪烁/快速闪烁帧?
解决方法:
您不应该覆盖JFrame的paint方法.如果你想绘制任何东西,你应该在扩展JPanel的类中绘制它,在那里覆盖paintComponent方法.
您不应该在绘画方法中加载图像.这非常低效.您应该只在ONCE中加载图像,可能在构造函数中.
你不应该调用Graphics2D #setTransform().看一下http://docs.oracle.com/javase/7/docs/api/java/awt/Graphics2D.html#setTransform%28java.awt.geom.AffineTransform%29的JavaDoc,它明确指出
警告:永远不应该使用此方法在现有变换之上应用新的坐标变换
你应该考虑你的w和h值.它们应该是绘制图像的大小,还是用作图像的缩放因子?将它们设置为AffineTransform的缩放因子将不具有将图像缩放到所需大小的效果.目前,它们被声明为int值,所以像w- = 0.05这样的东西无论如何都没有意义.
您应该清楚地了解如何描述图像应该执行的动画.
人们可以总结一下:
你不应该编写代码并假设它是“正确的”只是因为没有编译错误;-)
但是,以下代码段可能是迈向目标的第一步:
package stackoverflow;
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Image;
import javax.swing.ImageIcon;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.SwingUtilities;
public class SplashScreen extends JFrame
{
public static void main(String[] args)
{
SwingUtilities.invokeLater(new Runnable()
{
@Override
public void run()
{
new SplashScreen();
}
});
}
private PaintPanel paintPanel;
public SplashScreen()
{
setTitle("BlueJay");
setDefaultCloseOperation(EXIT_ON_CLOSE);
getContentPane().setBackground(Color.BLACK);
getContentPane().setLayout(new BorderLayout());
paintPanel = new PaintPanel();
getContentPane().add(paintPanel, BorderLayout.CENTER);
setSize(900,600);
setLocationRelativeTo(null);
setFocusable(true);
requestFocus();
setVisible(true);
startAnimation();
}
void startAnimation()
{
Thread thread = new Thread(new Runnable()
{
int x = 100;
int y = 100;
int w = 0;
int h = 0;
@Override
public void run()
{
try
{
Thread.sleep(500);
}
catch (InterruptedException ex)
{
Thread.currentThread().interrupt();
return;
}
while (true)
{
if (y == 200)
{
// new MainMenu_BlueJay().setVisible(true);
dispose();
}
x += 2;
y += 1;
w += 1;
h += 1;
paintPanel.setImageCoordinates(x, y, w, h);
repaint();
try
{
Thread.sleep(10);
}
catch (InterruptedException ex)
{
Thread.currentThread().interrupt();
return;
}
}
}
});
thread.start();
}
}
class PaintPanel extends JPanel
{
private final Image image;
private int imageX, imageY;
private int imageW, imageH;
PaintPanel()
{
image = new ImageIcon("Clipboard02.jpg").getImage();
imageX = 0;
imageY = 0;
imageW = 0;
imageH = 0;
}
void setImageCoordinates(int imageX, int imageY, int imageW, int imageH)
{
this.imageX = imageX;
this.imageY = imageY;
this.imageW = imageW;
this.imageH = imageH;
repaint();
}
@Override
protected void paintComponent(Graphics gr)
{
super.paintComponent(gr);
Graphics2D g = (Graphics2D) gr;
float scalingX = (float) imageW / image.getWidth(null);
float scalingY = (float) imageH / image.getHeight(null);
g.scale(scalingX, scalingY);
int ix = (int)(imageX / scalingX);
int iy = (int)(imageY / scalingY);
g.drawImage(image, ix, iy, null);
}
}
标签:java,swing,paint,repaint,thread-sleep 来源: https://codeday.me/bug/20190624/1280356.html