场景信息
//info.cpp文件 存储场景信息
int MAPWIDTH = 1200;
int MAPHEIGHT = 650;
//info.h文件 存储全局变量
#ifndef INFO_H //全局变量
#define INFO_H
#define SCENEWIDTH 1920
#define SCENEHEIGHT 1200
extern int MAPWIDTH;
extern int MAPHEIGHT;
#endif // INFO_H
游戏客户区 ,由QGraphicsItem、QGraphicsScene、QGraphicsView 图形视图框架搭建
//gamewindow.h
#ifndef GAMEWINDOW_H
#define GAMEWINDOW_H
#include
#include
#include
#include
#include
#include
#include "info.h" #include "player.h" class Player; class GameWindow : public QGraphicsView { Q_OBJECT friend class Player; public: GameWindow(QWidget *parent = 0); void mousePressEvent(QMouseEvent *event); public: QGraphicsScene *scene; //场景 Player *player; bool canArrive(qreal x, qreal y); bool canArrive(QPointF pos); void moveto(qreal x, qreal y); void moveto(QPointF pos); QTimer *timer; //用于移动 protected: void fixClientFor(qreal x, qreal y, bool right, bool down); private slots: void move_use_timer(); }; #endif// GAMEWINDOW_H
实现文件
#include
#include
#include "gamewindow.h"
GameWindow::GameWindow(QWidget *parent)
:QGraphicsView(parent)
{
setHorizontalScrollBarPolicy(Qt::ScrollBarAlwaysOff); //关闭显示
setVerticalScrollBarPolicy(Qt::ScrollBarAlwaysOff);
horizontalScrollBar()->setRange(0, SCENEWIDTH); //设置滚动条
verticalScrollBar()->setRange(0, SCENEHEIGHT);
horizontalScrollBar()->setValue(0);
verticalScrollBar()->setValue(0);
player = new Player;
timer = 0;
}
void GameWindow::mousePressEvent(QMouseEvent *event)
{
if (event->button() == Qt::RightButton)
{
moveto(mapToScene(event->pos()));
}
}
bool GameWindow::canArrive(qreal x, qreal y)
{
return !(x > SCENEWIDTH || x < 0 || y > SCENEHEIGHT || y < 0);
}
bool GameWindow::canArrive(QPointF pos)
{
return canArrive(pos.x(), pos.y());
}
void GameWindow::fixClientFor(qreal x, qreal y, bool right, bool down)
{
qreal cx = horizontalScrollBar()->value();
qreal cy = verticalScrollBar()->value();
qreal x = sx - cx;
qreal y = sy - cy;
//横向
if (x > MAPWIDTH * 2/3 && right)
{
horizontalScrollBar()->setValue(x - MAPWIDTH * 2/3);
}
if (x < MAPWIDTH /3 && !right)
{
horizontalScrollBar()->setValue(x - MAPWIDTH /3);
}
//纵向
if (y > MAPHEIGHT * 2/3 && down)
{
verticalScrollBar()->setValue(y - MAPHEIGHT * 2/3 );
}
if (y < MAPHEIGHT / 3 && !down)
{
verticalScrollBar()->setValue(y - MAPHEIGHT /3 );
}
}
void GameWindow::move_use_timer()
{
qreal partx = player->arrivepos.x() - player->cpos.x(); //x,y分量
qreal party = player->arrivepos.y() - player->cpos.y();
qreal s = sqrt(partx*partx + party*party); //直线路程
if (s < 5)
{
if (timer->isActive())
{
timer->stop();
delete timer;
timer = 0;
}
}
else
{
qreal movex = partx/s* 5; //每次计时移动距离
qreal movey = party/s* 5;
if (canArrive(player->cpos.x() + movex, player->cpos.y() + movey))
{
player->cpos.setX(player->cpos.x() + movex);
player->cpos.setY(player->cpos.y() + movey);
player->itempix->setPos(player->cpos);
}
else
{
if (timer->isActive())
{
timer->stop();
delete timer;
timer = 0;
}
}
}
fixClientFor(player->cpos.x(), player->cpos.y(), partx > 0, party > 0);
}
void GameWindow::moveto(qreal x, qreal y)
{
player->arrivepos.setX(x);
player->arrivepos.setY(y);
if (!timer)
{
timer = new QTimer;
timer->start(50);
connect(timer, SIGNAL(timeout()), this, SLOT(move_use_timer()));
}
}
void GameWindow::moveto(QPointF pos)
{
moveto(pos.x(), pos.y());
}
主窗口
#ifndef MAINWINDOW_H
#define MAINWINDOW_H
#include
#include "gamewindow.h"
#include "info.h"
class GameWindow;
namespace Ui {
class MainWindow;
}
class MainWindow : public QMainWindow
{
Q_OBJECT
public:
explicit MainWindow(QWidget *parent = 0);
~MainWindow();
void paintEvent(QPaintEvent *);
Ui::MainWindow *ui;
GameWindow *client; //视窗
QGraphicsScene *scene; //场景
};
#endif // MAINWINDOW_H
主窗口实现文件
#include "mainwindow.h"
#include "ui_mainwindow.h"
MainWindow::MainWindow(QWidget *parent) :
QMainWindow(parent),
ui(new Ui::MainWindow)
{
ui->setupUi(this);
scene = new QGraphicsScene(this);
client = new GameWindow(this);
client->scene = scene;
client->setScene(scene);
client->setFixedHeight(MAPHEIGHT); //视口
client->setFixedWidth(MAPWIDTH);
scene->setSceneRect(0, 0, SCENEWIDTH, SCENEHEIGHT); //场景
scene->addPixmap(QPixmap(":/pic/back"));
client->show();
client->player->itempix = scene->addPixmap(*client->player->pix);
client->player->setPos(MAPWIDTH/2, MAPHEIGHT/2);
}
MainWindow::~MainWindow()
{
delete ui;
}
void MainWindow::paintEvent(QPaintEvent *)
{
client->setFixedHeight(this->height()); // 重绘时重置大小(窗口大小可能被改变)
client->setFixedWidth(this->width());
MAPWIDTH = this->width();
MAPHEIGHT = this->height();
}
资源 :/pic/1.png
资源 :/pic/back.jpg 由于上传大小问题,建议把这个图片改成png格式
玩家类
#ifndef PLAYER_H
#define PLAYER_H
#include
#include
#include "info.h"
#include "mainwindow.h"
class Player : public QWidget
{
Q_OBJECT
public:
Player(QWidget * parent = 0);
~Player() {}
void setPos(qreal x, qreal y);
QPixmap * pix; //角色图组指针
QGraphicsPixmapItem *itempix;
QPointF cpos, arrivepos; //角色坐标,到达目标坐标
QTimer *timer; //用于移动
qreal speed; //速度
};
#endif // PLAYER_H
玩家类实现
#include "player.h"
//Player
Player::Player(QWidget * parent) : QWidget(parent)
{
timer = 0;
speed = 5;
pix = new QPixmap(":/pic/1");
}
void Player::setPos(qreal x, qreal y)
{
cpos.setX(x);
cpos.setY(y);
itempix->setPos(cpos);
}
主函数
#include "info.h"
#include "mainwindow.h"
#include
int main(int argc, char *argv[])
{
QApplication a(argc, argv);
MainWindow mainw;
mainw.setMinimumSize(MAPWIDTH, MAPHEIGHT);
mainw.show();
return a.exec();
}