#include "widget.h"
#include "ui_widget.h"
#include <QPainter>
#include <QPixmap>
#include <QDebug>
#include <QKeyEvent>
#include <QTimerEvent>
#include <QTime>
#include <QMovie>
#include "enemyfish.h"
Widget::Widget(QWidget *parent) :
QWidget(parent),
ui(new Ui::Widget)
{
ui->setupUi(this);
this->setFixedSize( this->width (),this->height ()); //设置固定大小
setWindowTitle("PlaneWars");
myPlane = NULL;
//初始状态1
state = BEGIN_STATE;
Init();
}
Widget::~Widget()
{
delete ui;
}
//接收到我方战机受到攻击信号
void Widget::MyPlaneIsAttacked()
{
int life = myPlane->GetLife()-5; //降低5点生命力
myPlane->SetLife(life);
if(life <= 0) //玩家Over,进入状态3
{
state = END_STATE; //结束状态
Init();
}
}
//清空杂鱼和爆炸的内存空间
void Widget::DelFishAndExp()
{
QLinkedList<EnemyFish*>::iterator iter;
QLinkedList<Explosion*>::iterator iter1;
//清空敌方杂鱼列表
for(iter = fish_list.begin();iter!=fish_list.end();++iter)
{
EnemyFish *temp = *iter;
fish_list.removeOne(*iter);
delete temp;
}
//清空爆炸列表
for(iter1 = exp_list.begin();iter1!=exp_list.end();++iter1)
{
Explosion *temp1 = *iter1;
exp_list.removeOne(*iter1);
delete temp1;
}
}
//进入每个状态时的初始化
void Widget::Init()
{
if(state == RUNNING_STATE)
{
if(myPlane != NULL) //删除上一局剩下的飞机
{
delete myPlane; //删除我方飞机,同时会删除我方的子弹
DelFishAndExp(); //清空剩下的杂鱼和爆炸
}
myPlane = new MyPlane; //动态创造我方飞机
//设置显示字体颜色
QPalette pa;
pa.setColor(QPalette::WindowText,Qt::red);
ui->label->setPalette(pa);
ui->label_2->setPalette(pa);
ui->label_life->setPalette(pa);
ui->label_sco->setPalette(pa);
back.load(":/img/newback.bmp");
back.scaled(QSize(this->width(),this->height())); //缩放背景图片,以适应屏幕
back_spe = 0; //背景的移动的初始位置为0
ui->label_sco->setText(QString::number(myPlane->GetScore()));
ui->label_life->setText(QString::number(myPlane->GetLife()));
timer1 = startTimer(30); //用于响应飞机移动
timer2 = startTimer(20); //用于响应攻击
timer3 = startTimer(1000); //用于增加敌机
timer4 = startTimer(100); //用于绘制爆炸
max_fish_num = 20; //最大的敌方虾米数量
}
else if(state == BEGIN_STATE)
{
back.load(":/img/ready.bmp");
back = back.scaled(QSize(this->width(),this->height())); //缩放图片
}
else
{
back.load(":/img/gameover.bmp");
back = back.scaled(QSize(this->width(),this->height())); //缩放图片
}
}
//重绘事件:
void Widget::paintEvent(QPaintEvent *event)
{
QPainter painter;
painter.begin(this);
if(state == RUNNING_STATE)
{
ui->label_life->setText(QString::number(myPlane->GetLife()));
ui->label_sco->setText(QString::number(myPlane->GetScore()));
//绘制动态背景
painter.drawPixmap(0,back_spe,back);
painter.drawPixmap(0,back_spe-back.height(),back);
//绘制我方飞机
painter.drawPixmap(myPlane->pos,myPlane->img);
//绘制敌机
foreach(EnemyFish *temp_fish,fish_list)
painter.drawPixmap(temp_fish->pos,temp_fish->img);
//绘制我方子弹
foreach (MyBullet *temp_bul, myPlane->my_bulles)
painter.drawPixmap(temp_bul->pos,temp_bul->img);
//绘制爆炸
foreach(Explosion * temp_exp,exp_list)
{
if(temp_exp->GetCurPicNum()<=EXPLOSION_IMG_NUM)
painter.drawPixmap(temp_exp->GetPos(),*(temp_exp->exp_img_list[temp_exp->GetCurPicNum()-1]));
}
}
else
{
painter.drawPixmap(0,0,back);
}
painter.end();
}
void Widget::keyPressEvent(QKeyEvent *event) //???两个按键同时按下问题
{
if(state == RUNNING_STATE) //第二个阶段时
{
int fly_dir = 0;
//判断按下哪个按键,并打上标记
if(event->key() == Qt::Key_Up)
fly_dir = FLY_UP;
if(event->key() == Qt::Key_Down)
fly_dir = FLY_DOWN;
if(event->key() == Qt::Key_Left)
fly_dir = FLY_LEFT;
if(event->key() == Qt::Key_Right)
fly_dir = FLY_RIGHT;
myPlane->SetFlyDir(fly_dir,true); //给指定的方向打上标记
if(event->key() == Qt::Key_Space)
{
myPlane->FireBull(); //发射子弹
}
}
else
{
if(event->key() == Qt::Key_Return)
{
state = RUNNING_STATE;
Init();
}
}
}
//按键释放事件
void Widget::keyReleaseEvent(QKeyEvent *event)
{
if(state == RUNNING_STATE)
{
//判断释放哪个按键,并取消标记
int fly_dir = 0;
if(event->key() == Qt::Key_Up)
fly_dir = FLY_UP;
if(event->key() == Qt::Key_Down)
fly_dir = FLY_DOWN;
if(event->key() == Qt::Key_Left)
fly_dir = FLY_LEFT;
if(event->key() == Qt::Key_Right)
fly_dir = FLY_RIGHT;
myPlane->SetFlyDir(fly_dir,false); //给指定的方取消上标记
}
}
//定时器事件:主要用于移动飞机;判断战机和敌机、敌机和子弹是否发生碰撞;增加敌机数量;显示爆炸
void Widget::timerEvent(QTimerEvent *event)
{
if(event->timerId() == timer1) //移动飞机和子弹
{
//移动我方战机
for(int i = 1;i<=4;++i)
{
if(myPlane->GetFLyDir(i)) //上下左右:对应1 2 3 4
myPlane->Move(i);
}
//移动子弹
QLinkedList<MyBullet*>::iterator iter_bul;
for(iter_bul = myPlane->my_bulles.begin();iter_bul!=myPlane->my_bulles.end();++iter_bul)
{
MyBullet *temp_bul = *iter_bul;
temp_bul->Move(-1);
}
//移动敌方杂鱼机
QLinkedList<EnemyFish*>::iterator iter_fish;
for(iter_fish = fish_list.begin();iter_fish != fish_list.end();++iter_fish)
{
EnemyFish * temp_fish = *iter_fish;
temp_fish->Move(0);
}
this->update();
}
else if(event->timerId() == timer2) //判断是否发生碰撞
{
QLinkedList<EnemyFish*>::iterator iter;
QLinkedList<MyBullet*>::iterator iter_bul;
bool IsAttacked = false;
bool IsCon = false;
for(iter = fish_list.begin();iter!=fish_list.end();++iter) //遍历敌方所有杂鱼
{
EnemyFish *temp_fish = *iter;
IsAttacked = false; //初始未被攻击
QRect temp(temp_fish->pos,QSize(temp_fish->img.width(),temp_fish->img.height()));
for(iter_bul = myPlane->my_bulles.begin();iter_bul !=myPlane->my_bulles.end();++iter_bul) //遍历我方所有子弹
{
MyBullet *temp_bul = *iter_bul;
QRect temp_rec(temp_bul->pos,QSize(temp_bul->img.width(),temp_bul->img.height()));
IsAttacked = temp.intersects(temp_rec); //判断是否敌机是否受到我方子弹攻击
if(IsAttacked == true ) //子弹攻击到敌机
{
EneFishI