单击框架面板时,我无法生成多个椭圆形状。我想要的是它将产生许多椭圆形状,这些形状将向下移动。其中一个要求是使用两个多线程。然而在我的情况下,我创建的程序是,它只会生成一个椭圆形状,并且位置随机变化。任何人都可以帮我一个。
package ovalrandomcolors;
import java.awt.Color;
import java.awt.Component;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.util.List;
import java.awt.Shape;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.geom.Ellipse2D;
import java.util.ArrayList;
import java.util.Collections;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.SwingUtilities;
public class OvalRandomColors extends JPanel{
private int ovalX = 50;
private int ovalY =50;
private int ovalPositionX = 250;
private int ovalPositionY = 250;
private Color color = Color.YELLOW;
public OvalRandomColors(){
setBackground(Color.DARK_GRAY);
}
@Override
public void paintComponent(Graphics g){
super.paintComponent(g);
g.setColor(color);
g.fillOval(ovalPositionX, ovalPositionY, ovalX, ovalY);
g.setColor(color);
g.fillOval(ovalPositionX, ovalPositionY, ovalX, ovalY);
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable(){
@Override
public void run() {
JFrame frame = new JFrame();
final OvalRandomColors oval = new OvalRandomColors();
oval.addMouseListener(new MouseAdapter(){
@Override
public void mouseClicked(MouseEvent e){
OvalWithThreading firstThread = new OvalWithThreading(oval);
OvalWithThreading secondThread = new OvalWithThreading(oval);
Thread first = new Thread(firstThread);
Thread second = new Thread(secondThread);
second.start();
first.start();
}
});
frame.add(oval);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setSize(500,700);
frame.setVisible(true);
}
});
}
public void updateOval(){
int r = (int)(Math.random() * 255);
int g = (int) (Math.random() * 255);
int b = (int)(Math.random() * 255);
color = new Color(r,g,b);
ovalPositionX = (int)(Math.random() * 78);
ovalPositionY = (int) (Math.random() * 245);
animateOval();
repaint();
}
public void animateOval(){
// ovalPositionX += 30;
ovalPositionY += 30;
}
public static class OvalWithThreading implements Runnable{
private final OvalRandomColors ovalShape;
public OvalWithThreading(OvalRandomColors oS){
this.ovalShape = oS;
}
@Override
public void run() {
for(;;){
ovalShape.updateOval();
try {
Thread.sleep(1000);
} catch (InterruptedException ex) {
Logger.getLogger(OvalRandomColors.class.getName()).log(Level.SEVERE, null, ex);
}
}
}
}
}
答案 0 :(得分:4)
让我们开始吧,Swing不是Thread
安全的,所以让另一个Timer
更新UI所依赖的对象状态需要一些严肃的考虑。通常情况下,我建议使用Swing SwingWorker
或List
来完成此操作,但这些并不是"要求"
为了渲染多个对象,您需要一些方法来存储它们,这样您就可以更新它们的状态并对它们进行渲染。最简单的解决方案是import java.awt.Dimension;
import java.awt.EventQueue;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Rectangle;
import java.awt.Shape;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.geom.Ellipse2D;
import java.awt.geom.Rectangle2D;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.concurrent.locks.ReentrantLock;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;
public class Test {
public static void main(String[] args) {
new Test();
}
public Test() {
EventQueue.invokeLater(new Runnable() {
@Override
public void run() {
try {
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
} catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
ex.printStackTrace();
}
JFrame frame = new JFrame("Testing");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add(new TestPane());
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
});
}
public class TestPane extends JPanel {
private ReentrantLock shapesLock = new ReentrantLock();
private List<Ellipse2D> shapes;
public TestPane() {
shapes = new ArrayList<>(25);
addMouseListener(new MouseAdapter() {
@Override
public void mouseClicked(MouseEvent e) {
shapesLock.lock();
try {
shapes.add(new Ellipse2D.Double(e.getX() - 5, e.getY() - 5, 10, 10));
} finally {
shapesLock.unlock();
}
}
});
Thread t = new Thread(new Runnable() {
private Map<Shape, Double> deltas = new HashMap<>();
@Override
public void run() {
while (true) {
try {
shapesLock.lock();
try {
Rectangle containerBounds = getBounds();
containerBounds.setLocation(0, 0);
Iterator<Ellipse2D> it = shapes.iterator();
while (it.hasNext()) {
Ellipse2D shape = it.next();
Rectangle2D bounds = shape.getBounds2D();
double y = bounds.getY();
Double delta = deltas.get(shape);
if (delta == null) {
delta = 0d;
}
y += delta;
shape.setFrame(bounds.getX(), y, bounds.getWidth(), bounds.getHeight());
if (containerBounds.contains(shape.getBounds())) {
delta = Math.min(delta + 0.25, 6d);
deltas.put(shape, delta);
} else {
it.remove();
}
}
} finally {
shapesLock.unlock();
}
repaint();
Thread.sleep(40);
} catch (InterruptedException ex) {
}
}
}
});
t.setDaemon(false);
t.start();
}
@Override
public Dimension getPreferredSize() {
return new Dimension(200, 200);
}
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2d = (Graphics2D) g.create();
shapesLock.lock();
try {
for (Ellipse2D shape : shapes) {
g2d.fill(shape);
}
} finally {
shapesLock.unlock();
}
g2d.dispose();
}
}
}
,您可以查看Collections Trail了解更多详情。
现在,如果你还需要管理颜色,你可以看看我如何管理每个形状的增量,并且应该给你一个想法
ViewPager.addOnPageChangeListener(new ViewPager.OnPageChangeListener() {
@Override
public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {
}
@Override
public void onPageSelected(int position) {
}
@Override
public void onPageScrollStateChanged(int state) {
if (i == 0) {
ImageView.setBackgroundResource(R.drawable.image1);
}
else if (i ==1) {
ImageView.setBackgroundResource(R.drawable.image2);
}
}
});