Java 如何在俄罗斯方块游戏中保留底部的矩形?

Java 如何在俄罗斯方块游戏中保留底部的矩形?,java,swing,oop,graphics,Java,Swing,Oop,Graphics,我已经开始开发俄罗斯方块游戏。一切正常,但如何在底部保留矩形 这是Comp1类,在该类中检索随机形状并随计时器向下移动 package buildblock; import java.awt.*; import java.awt.event.ActionEvent; import java.awt.event.ActionListener; import java.util.Random; import java.util.logging.Level; import java.util.log

我已经开始开发俄罗斯方块游戏。一切正常,但如何在底部保留矩形

这是Comp1类,在该类中检索随机形状并随计时器向下移动

package buildblock;

import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.util.Random;
import java.util.logging.Level;
import java.util.logging.Logger;
import javax.swing.*;
import buildblock.tetris;
public class Comp1 extends JPanel implements ActionListener {

int curx=10;
int cury=30;
int nx=0;
int ny=0;
int p=1;
 Timer t;
boolean EndofLine=false;
JLabel l1=new JLabel("");
int value=0;
int coords[][][]=new int[3][3][2];
int shape[][][][]={
        {{{0,0},{0,0},{0,0}},{{0,0},{0,0},{0,0}},{{0,0},{0,0},{0,0}}},
        {{{0,0},{100,20},{0,0}},{{0,0},{100,40},{0,0}},{{80,60},{100,60},{0,0}}},
        {{{0,0},{100,20},{0,0}},{{80,40},{100,40},{120,40}},{{0,0},{0,0},{0,0}}},
        {{{0,0},{100,20},{0,0}},{{0,0},{100,40},{0,0}},{{0,0},{100,60},{0,0}}},
        {{{80,20},{100,20},{0,0}},{{0,0},{100,40},{0,0}},{{0,0},{100,60},{0,0}}},
        {{{0,0},{100,20},{0,0}},{{80,40},{100,40},{0,0}},{{80,60},{0,0},{0,0}}},
        {{{80,20},{0,0},{0,0}},{{80,40},{100,40},{0,0}},{{0,0},{100,60},{0,0}}},
         {{{80,20},{100,20},{0,0}},{{80,40},{100,40},{0,0}},{{0,0},{0,0},{0,0}}},
        };

Comp1(tetris Parent)
{
   setVisible(true);
   setSize(400,900);
   curx=(400-curx)/2;
   setLayout(new BorderLayout());
   timer();
}

public void getShape(int a)
{
     for(int i=0;i<3;i++)
    {
        for(int j=0;j<3;j++)
        {
            for(int k=0;k<2;k++)
            {
            coords[i][j][k]=shape[a][i][j][k];
             repaint();
            }
        }
    }
}

public void paint(Graphics g)
{
    super.paint(g);

    for(int i=0;i<3;i++)
    {
        for(int j=0;j<3;j++)
        {
            for(int k=0;k<2;k++)
            {
                if(coords[i][j][k]!=0)
                {
                    if(k==0)
                    {
                        curx=coords[i][j][k]+nx;
                    }
                    else
                    {
                        cury=coords[i][j][k]+ny;
                        drawRec(g,curx,cury,20,20);

                    }
                }
            }
        }
    }              
}

 public void drawRec(Graphics g,int newx,int newy,int w,int h)
 {
             g.drawRect(newx, newy, 20, 20);
             g.drawLine(curx+1,cury+20-1,curx+20-1,cury+20-1);       
 }

public void timer()
{
t=new Timer(150,this);
  t.start();
}

public int Random()
{
    Random r=new Random();
    int n=Math.abs(r.nextInt()%7+1);
    return n;
}

public void lineDown()
{
    ny=ny+10;
    repaint();
}

public void actionPerformed(ActionEvent e) 
{
    if(value!=250&&!EndofLine)
    {     
        value=value+5;
        if(p==0)
        {
            p=Random();
        }
        getShape(p);
        lineDown();
    }
    else
    {
        p=Random();
        ny=0;
        EndofLine=false;
        value=0;
    }
}
}
包构建块;
导入java.awt.*;
导入java.awt.event.ActionEvent;
导入java.awt.event.ActionListener;
导入java.util.Random;
导入java.util.logging.Level;
导入java.util.logging.Logger;
导入javax.swing.*;
导入buildblock.俄罗斯方块;
公共类Comp1扩展JPanel实现ActionListener{
int-curx=10;
int cury=30;
int nx=0;
int-ny=0;
int p=1;
定时器t;
布尔值EndofLine=false;
JLabel l1=新的JLabel(“”);
int值=0;
int coords[][]=新int[3][3][2];
整数形状[][]={
{{{0,0},{0,0},{0,0}},{{0,0},{0,0},{0,0}},{{0,0},{0,0},{0,0}}},
{{{0,0},{100,20},{0,0}},{{0,0},{100,40},{0,0}},{{80,60},{100,60},{0,0}}},
{{{0,0},{100,20},{0,0}},{{80,40},{100,40},{120,40}},{{0,0},{0,0},{0,0}}},
{{{0,0},{100,20},{0,0}},{{0,0},{100,40},{0,0}},{{0,0},{100,60},{0,0}}},
{{{80,20},{100,20},{0,0}},{{0,0},{100,40},{0,0}},{{0,0},{100,60},{0,0}}},
{{{0,0},{100,20},{0,0}},{{80,40},{100,40},{0,0}},{{80,60},{0,0},{0,0}}},
{{{80,20},{0,0},{0,0}},{{80,40},{100,40},{0,0}},{{0,0},{100,60},{0,0}}},
{{{80,20},{100,20},{0,0}},{{80,40},{100,40},{0,0}},{{0,0},{0,0},{0,0}}},
};
Comp1(俄罗斯方块父母)
{
setVisible(真);
设置大小(400900);
curx=(400 curx)/2;
setLayout(新的BorderLayout());
定时器();
}
公共形状(int a)
{

对于(int i=0;i我将创建一个“形状”列表已经落在俄罗斯方块底部的。此
列表将保存在你的
俄罗斯方块
类中,当当前落下的项目落在方块底部或已经落下的形状之一时,应停止并添加到落下列表中

其他一般提示:

根据个人经验,除非有必要,否则尽量远离大小大于2的数组;它们臃肿、混乱且难以维护。在您的情况下,有一个名为
Shape
的完美界面可供使用。请查看此代码

// java.awt.geom.Path2D implements java.awt.Shape
java.awt.geom.Path2D path = new Path2D.Double();
path.moveTo(0, 0);
path.lineTo(2, 0);
path.lineTo(2, 2);
path.lineTo(2, 0);
path.closePath();
path.transform(AffineTransform.getScaleInstance(20, 20));
这将创建一个
形状
,这是您的基本正方形!然后您就可以访问您不必自己实现的强大功能


PS:正如Andrew在评论中所建议的,“还要看看基于
Shape
的。它使用Java2D
Area
对象来测试交叉点。”

俄罗斯方块
类中列出包含所有已完成下落的形状的
列表。形状下落后,将其添加到已完成的数组中。您可能仍需要此数组进行碰撞检查。其他提示:1)要在Swing组件中正确地制作动画,最简单的方法是建立Swing
计时器,并从
ActionListener
.2
setSize(400900)的
actionPerformed(ActionEvent)
方法调用
repaint()
;最好覆盖
getPreferredSize()
面板的方法,然后
pack()
父容器。3)
public void paint(图形g){super.paint(g);…
应该是
public void paintComponent(图形g){super.paintComponent(g)你可以考虑在俄罗斯方块中只考虑7种形状,这样可以帮助你清理一些代码,而不是用4D数组来旋转我的头。使用一个类的形状比用一个混乱的4维看起来更容易。Dical array。另请看。它使用Java 2D
Area
对象来测试相交。我对Graphics2D或geom包的类没有太多研究,但现在发现这件事非常有趣和有用。通过测试这些方法和类,我发现如果我制作一个多边形数组来容纳所有的&形状,然后使用Shape类引用变量引用它们,这将比Path2D更便于平移或旋转。但我仍然无法在Path2D和Shape类之间进行选择。Agian需要您的建议,谢谢ug:)@Akaal您所引用的
Shape
类实际上是一个接口。许多类型的形状实现了是界面,其中包括
Path2D
Polygon
Rectangle
。你可以使用任何一个你喜欢的来构建你的俄罗斯方块。我刚才使用了
Path2D
,因为我对它们比较熟悉。