本帖最后由 barryhappy 于 2010-08-14 09:39:44 编辑

解决方案 »

  1.   


    //
    // Playing类 执行主要游戏操作
    class Playing implements ActionListener,MouseListener
    {
    static Resources resources = new Resources();
    public static Landmine gui;
    public Playing(Landmine in )
    {
    gui = in;
    } public void actionPerformed(ActionEvent event)
    {
    MyButton receive = (MyButton)event.getSource();
    if(receive.isBomb)
    {//如果翻到了雷。。
            for(int i=1; i<17; ++i)
            {//将所有的雷图标设为 “地雷”
            for(int j=1; j<17; ++j)
            {
                    if(gui.lei[i][j].isBomb)
                            gui.lei[i][j].setIcon(resources.bombIcon);
            }
    }
    receive.setIcon(resources.deadIcon);//将踩到的地雷图标设为 “衰”
    gui.timer.stop();                   //停止计时器
    JOptionPane.showMessageDialog(null,"小朋友,你挂了…","失败!",
                                  JOptionPane.INFORMATION_MESSAGE,
                                  resources.deadIcon);//提示失败
    int yourChose = JOptionPane.showConfirmDialog(null,"你可能是一不小心点错了,再来一局?" );
    if(yourChose == JOptionPane.OK_OPTION)
    {//点击“是”时
    replay();
    }
    else
    {//点击 “否” 或 “取消” 时退出程序
    System.exit(0);
    }
    }
    else if(receive.isClicked ==false)
    {//未翻到雷
    showBombNumber(receive);
    } }
    public static void showBombNumber(MyButton in)
    {//翻开点击的按钮
    int numberOfLandmine = 0;//记录雷的个数
    in.isClicked = true; //翻开标记设为真
    /*检测周围8个方块是否为雷*/
    if(gui.lei[in.num_x-1][in.num_y-1].isBomb == true) numberOfLandmine++;//左上
    if(gui.lei[in.num_x][in.num_y-1].isBomb == true) numberOfLandmine++; //上
    if(gui.lei[in.num_x+1][in.num_y-1].isBomb == true) numberOfLandmine++;//右上
    if(gui.lei[in.num_x+1][in.num_y].isBomb == true) numberOfLandmine++; //右
    if(gui.lei[in.num_x+1][in.num_y+1].isBomb == true) numberOfLandmine++;//右下
    if(gui.lei[in.num_x][in.num_y+1].isBomb == true) numberOfLandmine++; //下
    if(gui.lei[in.num_x-1][in.num_y+1].isBomb == true) numberOfLandmine++;//左下
    if(gui.lei[in.num_x-1][in.num_y].isBomb == true) numberOfLandmine++; //左
    in.setIcon(new ImageIcon("images/"+numberOfLandmine+".png"));//根据周围的雷数显示数字图标
    gui.numberOfClicked++;//翻开格子数+1
    if(gui.numberOfClicked==216)
    {//翻开216个格子时游戏成功,用户选择是否再来一局
    int yourChoice = JOptionPane.showConfirmDialog(null,"恭喜你成功了!再来一盘吗?");
    if(yourChoice == JOptionPane.OK_OPTION)
    replay();
    else
    System.exit(0);
    } if(numberOfLandmine==0)
    {//如果周围无雷,则将周围未翻开格子的全部翻开
    if(gui.lei[in.num_x-1][in.num_y-1].isClicked == false)
    showBombNumber(gui.lei[in.num_x-1][in.num_y-1]);
    if(gui.lei[in.num_x][in.num_y-1].isClicked == false)
    showBombNumber(gui.lei[in.num_x][in.num_y-1]);
    if(gui.lei[in.num_x+1][in.num_y-1].isClicked == false)
    showBombNumber(gui.lei[in.num_x+1][in.num_y-1]);
    if(gui.lei[in.num_x+1][in.num_y].isClicked == false)
    showBombNumber(gui.lei[in.num_x+1][in.num_y]);
    if(gui.lei[in.num_x+1][in.num_y+1].isClicked == false)
    showBombNumber(gui.lei[in.num_x+1][in.num_y+1]);
    if(gui.lei[in.num_x][in.num_y+1].isClicked == false)
    showBombNumber(gui.lei[in.num_x][in.num_y+1]);
    if(gui.lei[in.num_x-1][in.num_y+1].isClicked == false)
    showBombNumber(gui.lei[in.num_x-1][in.num_y+1]);
    if(gui.lei[in.num_x-1][in.num_y].isClicked == false)
    showBombNumber(gui.lei[in.num_x-1][in.num_y]);
    } }
    public static void replay()
    {//重新开始
    gui.dispose();  //释放框架资源
    gui.timer.stop();  //终止计时器
    Landmine ff = new Landmine();//重新创建一个主类的实例
    //这几条语句实现了重新开始————关闭上一个窗口,重新开启一个
    //但是这种方法会造成内存的浪费,一个改进的方法是不关闭当年窗口,而是将当前窗口重新初始化
    } public void mousePressed(MouseEvent e)
    {//当鼠标右键点击时自动调用此函数
    int mods = e.getModifiers();
    MyButton receive = (MyButton)e.getSource();
    if((mods & InputEvent.BUTTON3_MASK) != 0)
    {//鼠标右键
    if(receive.isClicked == false)
    {
    receive.isRight = receive.isRight ? false : true;//改变receive.isRight的值
    if(receive.isRight)
    {//如果添加标记,则剩余雷数-1,设置标签为“旗帜”
    gui.numberOfUnflaged--;
    receive.setIcon(resources.flagIcon);
    }
    else
    {//如果清除标记,则剩余雷数+1,设置标签为“未翻开”
    gui.numberOfUnflaged++;
    receive.setIcon(resources.smallIcon);
    }
    gui.numberOfUnflagedLabel.setText("剩余雷数:"+gui.numberOfUnflaged);
    //更新剩余雷数标签
    } }
    }
    public void mouseReleased(MouseEvent e){}
    public void mouseExited(MouseEvent e) {}
    public void mouseClicked(MouseEvent e){}
    public void mouseEntered(MouseEvent e){}
    }
    //
    // Help类,响应“关于”、“求救”
    class Help implements ActionListener
    {
    static Resources resources = new Resources();
    public static Landmine gui;
    public Help(Landmine in)
    {
    gui = in ;
    }
    public void actionPerformed(ActionEvent event)
    {
    if(event.getActionCommand()=="关于")
    JOptionPane.showMessageDialog(null,"扫雷1.2版。。小老头出品");
    if(event.getActionCommand()=="求救")
    help(); }
    public static void help()
    {//求救
    int stopNumber = (int)(Math.random() * gui.numberOfUnflaged + 1 );
    int count = 0;
    for(int i=1; i<17;++i )
    {
    for(int j=1; j<17; ++j)
    { if( gui.lei[i][j].isBomb &&  !gui.lei[i][j].isClicked && !gui.lei[i][j].isRight )
    {
    count++;
    }
    if(count == stopNumber)
    {
    gui.lei[i][j].setIcon(resources.badIcon);
    return;
    }
    }
    }
    }
    }
    //
    //      Keylistener类,响应键盘事件
    class Keylistener implements KeyListener
    {
            static Resources resources = new Resources();
            Landmine gui;
            public Keylistener(Landmine in)
            {
                    gui = in;
            }
            public void keyPressed(KeyEvent e)
            {//有键按下时自动执行该方法
                    if(e.getKeyCode() == KeyEvent.VK_UP)
                    {//按键为 向上 时,将所有未标记的地雷显示出
                            for(int i=1; i<17; ++i)
            {
            for(int j=1; j<17; ++j)
            {
                    if(gui.lei[i][j].isBomb && !gui.lei[i][j].isRight)
                            gui.lei[i][j].setIcon(resources.badIcon);
            }
    }
                    }
                    if(e.getKeyCode() == KeyEvent.VK_DOWN)
                    {//按键为 向下 时,将所有未标记的地雷恢复为未点击的图标
                            for(int i=1; i<17; ++i)
            {
            for(int j=1; j<17; ++j)
            {
                    if(gui.lei[i][j].isBomb && !gui.lei[i][j].isRight)
                            gui.lei[i][j].setIcon(resources.smallIcon);
            }
    }
                    }
            }
            public void keyReleased(KeyEvent e){}
            public void keyTyped(KeyEvent e){}
     } 
    //
    // 按钮类 MyBtton
    class MyButton extends JButton
    {
    public int num_x,num_y; //第几号方块
    public boolean isBomb; //是否为雷
    public boolean isClicked; //是否被点击
    public int BombFlag; //探雷标记
    public boolean isRight; //是否点击右键 public MyButton(int x, int y)
    {
    BombFlag = 0;
    num_x = x;
    num_y = y;
    isBomb = false;
    isClicked = true;
    isRight = false;
    }
    }
    //
    // 资源类 其他类中用到的图标,字体等
    class Resources
    {
    public static ImageIcon deadIcon;
    public static ImageIcon smallIcon;
    public static ImageIcon clockIcon;
    public static ImageIcon bombIcon;
    public static ImageIcon flagIcon;
    public static ImageIcon badIcon;
    public static ImageIcon bombIconForLabel;
    public static Font fontOne;
    public Resources()
    {
    deadIcon = new ImageIcon("images/dead.gif");
    smallIcon  = new ImageIcon("images/smallIcon.png");
    clockIcon = new ImageIcon("images/clock2.png");
    bombIcon = new ImageIcon("images/bomb.png");
    flagIcon = new ImageIcon("images/flag_2.png");
    badIcon = new ImageIcon("images/bad.gif");
    bombIconForLabel = new ImageIcon("images/bombForLabel.gif");
    fontOne = new Font("null",Font.BOLD,20);
    }
    }
      

  2.   

    改进了以前的几个小BUG,比如看不到雷~~~呵呵
      

  3.   

    支持楼主,如果有这种应用程序发布机制真的就非常好了,着重于讨论与版本升级~作为与sourceforge的呼应
    1,2,3的图片选画得不错啊下面两个按钮几乎看不到
    应该设一下点某个按钮周围全开的按键
      

  4.   

    哦,是类似windows自带扫雷的那种左右键齐按周围8格全开
      

  5.   

    翻开周围的方块类型有两种:一种是空白,一种是数字,空白的就继续翻开周围的,如果是数字则不作任何动作,被翻开的方块被标记成“Visited”,你可以维护一个列表,把空白的方块都放进去,对这个列表进行循环,最初的时候只有一个,翻开的过程中不断往里加,处理完一个就把他从列表中删除,直到列表中没有空白方块,不知道我这样描述是不是说清楚了。说白了就是一个图遍历的算法,可以认为是寻找连通图的算法。
      

  6.   

    嗯,就一个JAVA文件,分2个楼层贴的
      

  7.   

    ding.新生請多指教.一定多多支持的.
      

  8.   

    LZ呀 要不要再写个俄罗斯方块    话说 我只见过用VS写的  还没见过JAVA 版 不得不说LZ厉害呀