保卫萝卜~场景的思路以及数据的存储。

     学习要写笔记,记录自己的步骤。
一、场景构建Tiled
     关于Tiled网上有一大堆的教程,这个比较好用,特别是构建塔防类的游戏极其简单,我也是爽了一把。
场景的资源目录结构比较好做,根据场景id进行区分目录。
场景对应目录:
 
  然后使用Tiled构建基本的场景
 
 
     这里有
     1、两个图块层(底图层、路径层)       2、三个对象层(可行路径对象格、障碍对象格、建筑对象格)
格子使用80X80,跟资源的大小刚好合适……导出.tmx文件,加入舞台就能看到成果了,顿时觉得比较爽。
Cocos2dx已经封装的 TMXTiledMap类使用起来也是顺手至极啊。
 
     TMXTiledMap::create(tmxUrl)
 
创建一个TMXTiledMap对象直接addChild至场景就可以看到效果,如果要获得对象层的数据,通过name就能获得。通过处理对象层的数据(坐标,宽高,类型、等属性)就可以搞定场景建筑搭建,怪物行走路径,鼠标可点击区域等,通过格子矩形的判断就能实现场景逻辑部分。
 
  对Tiled的了解不是很多,但是够用就行……
 
二、数据管理SQLite
 
     数据大概是游戏的命脉啊,可惜自己的数值功力有限,只能设计个自己能用的数据库了,借助于SQLite实现对数据的管理。
SQLite是一款轻型的数据库,是遵守ACID的关系型数据库管理系统,它包含在一个相对小的C库中。
 
下载sqlite文件
下载网址:http://www.sqlite.org/download.html
 
 
 
  这是最新版本。如下图把解压后的三个文件导入项目中就可以开心的使用了。
 
 
ok,关于创建SQLite数据库的工具也有一大堆,不过我还是喜欢使用   Navicat_Premium_9.1.11 用的爽就行~
 
 
OK,这样创建好数据库DB文件就好啦,下面使用辅助类就可以完美的 增、删、查、改!
 
三、自封装DB数据类
 
     关于封装SQLite的类也是有很多的,但是适用自己的才是最好的,封装起来也是比较简单的,不过鉴于自己的c++水平有限……(拿来主义)……在以前在网上找了个工具类,
后来自己也修改了下,改成自己适用的,贡献下自己修改后的DBUtil类。

#ifndef __DBUtil__
#define __DBUtil__
#include <string>
#include "cocos2d.h"
#include "sqlite3.h" using namespace std;
USING_NS_CC;
class DBUtil{
public: /************************************************************
封装 sqlite3操作
************************************************************/
//用来创建一个db数据库 db为数据库的名字
// 打开数据库
static void initDB(const char *url); //用来判断表格是否存在
// name:表示表名
static bool tableIsExist(string table_name); //用来创建一个表名为name的表格,创建时会先匹配时否有该表的存在如果存在则不创建
//创建表
static void createTable(string sql,string table_name); //用来删除一张表名为name的表格,删除时会先匹配是否有该表的存在如果不存在则不执行删除操作
//删除表名
static void deleteTable(string sql,string table_name); //用来向表中插入一条数据
//插入一条数据
static void insertData(string sql); //用来向表中删除一条数据
//删除一条数据
static void deleteData(string sql); //用来向表中修改一条数据
// 修改一条数据
static void updateData(string sql); //获取表的全部数据
// 返回记录的条数
static int getAllData(string table_name,std::function<void(std::map<string,string>)> callback); //读取一条记录的信息
/*
* 此方法是查询方法,pSender()
*/
static void getDataInfo(string sql,std::function<void(std::map<string,string>)> callback); //关闭打开的数据库
static void closeDB();
}; #endif

DBUtil.h

#include "DBUtil.h"

sqlite3 *pDB = NULL;//数据库指针
char * errMsg = NULL;//错误信息
std::string sqlstr;//SQL指令
int result;//sqlite3_exec返回值
unsigned int _count=;
std::map<unsigned int,std::function<void(std::map<string,string>)>> _keyMap; void DBUtil::initDB(const char *db)
{
//打开一个数据库,如果该数据库不存在,则创建一个数据库文件
result = sqlite3_open(db, &pDB);
if( result != SQLITE_OK )
log( "打开数据库失败,错误码:%d ,错误原因:%s\n" , result, errMsg );
} //tableIsExist的回调函数
int isExisted( void * para, int n_column, char ** column_value, char ** column_name )
{
bool *isExisted_=(bool*)para;
*isExisted_=(**column_value)!='';
return ;
} bool DBUtil::tableIsExist( string table_name )
{
if (pDB!=NULL)
{
//判断表是否存在
bool tableIsExisted;
sqlstr = "select count(type) from sqlite_master where type='table' and name ='"+table_name+"'";
result =sqlite3_exec(pDB,sqlstr.c_str(),isExisted,&tableIsExisted,&errMsg);
return tableIsExisted;
}
return false;
} void DBUtil::createTable( string sql,string table_name )
{
if (!tableIsExist(table_name))
{
//创建表,设置ID为主键,且自动增加
result = sqlite3_exec(pDB,sql.c_str(),NULL,NULL,&errMsg);
if( result != SQLITE_OK )
log( "创建表失败,错误码:%d ,错误原因:%s\n" , result, errMsg );
} } void DBUtil::deleteTable( string sql,string table_name )
{
if (tableIsExist(table_name))
{
result = sqlite3_exec(pDB,sql.c_str(),NULL,NULL,&errMsg);
if( result != SQLITE_OK )
log( "创建表失败,错误码:%d ,错误原因:%s\n" , result, errMsg );
}
} //@示例语句sqlstr=" insert into MyTable_1( name ) values ( 'data',..... ) ";
void DBUtil::insertData( string sql ){
result = sqlite3_exec( pDB, sql.c_str() , NULL, NULL, &errMsg );
if(result != SQLITE_OK )
log( "插入记录失败,错误码:%d ,错误原因:%s\n" , result, errMsg );
} //@示例语句sqlstr="delete from MyTable_1 where ID = 2";
void DBUtil::deleteData( string sql )
{
result=sqlite3_exec( pDB, sql.c_str() , NULL, NULL, &errMsg );
if(result != SQLITE_OK )
log( "插入记录失败,错误码:%d ,错误原因:%s\n" , result, errMsg );
} //@示例语句 sqlstr="update MyTable_1 set name='data' where ID = 3";
void DBUtil::updateData( string sql )
{
result = sqlite3_exec( pDB, sql.c_str() , NULL, NULL, &errMsg );
if(result != SQLITE_OK )
log( "插入记录失败,错误码:%d ,错误原因:%s\n" , result, errMsg );
} //getDataCount的回调函数
int loadRecordCount( void *para, int n_column, char ** column_value, char ** column_name )
{
std::map<string,string> data;
int index;
for( index = ; index < n_column; index ++ )
{
data.insert(std::pair<string,string>( column_name[index], column_value[index] ));
}
auto num = *(unsigned int *)para;
auto callback = _keyMap.at(num);
if( callback != nullptr )
{
callback(data);
}
return ;
} int DBUtil::getAllData(string table_name,std::function<void(std::map<string,string>)> callback)
{
string sql = "select * from "+table_name;
_count++;
_keyMap.insert(std::pair<unsigned int,std::function<void(std::map<string,string>)>>(_count,callback));
int count=sqlite3_exec( pDB, sql.c_str() , loadRecordCount, &_count, &errMsg );
return count;
} //getDataInfo的回调函数
int loadRecord( void * para, int n_column, char ** column_value, char ** column_name )
{
std::map<string,string> data;
int index;
for( index = ; index < n_column; index ++ )
{
string str1 = column_name[index];
if( column_value[index] == NULL )
{
log("DBUtil Get Data Value Failure! Table Name Is '%s'",str1.c_str());
continue;
}
string str2 = column_value[index];
data.insert(std::pair<string,string>(str1,str2));
}
auto num = *(unsigned int *)para;
auto callback = _keyMap.at(num);
if( callback != nullptr )
{
_keyMap.erase(num);
callback(data);
}
return ;
} void DBUtil::getDataInfo( string sql,std::function<void(std::map<string,string>)> callback )
{
_count++;
_keyMap.insert(std::pair<unsigned int,std::function<void(std::map<string,string>)>>(_count,callback));
sqlite3_exec( pDB, sql.c_str() , loadRecord, &_count, &errMsg );
} void DBUtil::closeDB()
{
sqlite3_close(pDB);
}

DBUtil.cpp

  这样在数据初始化的时候就可以直接传入表中怪物ID 直接初始化数据
 
四、总结
 
     有场景编辑器,有数据库,我觉得我终于可以完成我想要的效果了~~开心一把。哈哈哈,不过自己空闲时间也不多啊 惆怅……。
好想做*******,可惜C++懂得不多……
 

Cocos2d-x 3.2 学习笔记(十五)保卫萝卜 场景与数据的更多相关文章

  1. python3.4学习笔记(十五) 字符串操作(string替换、删除、截取、复制、连接、比较、查找、包含、大小写转换、分割等)

    python3.4学习笔记(十五) 字符串操作(string替换.删除.截取.复制.连接.比较.查找.包含.大小写转换.分割等) python print 不换行(在后面加上,end=''),prin ...

  2. (转载)西门子PLC学习笔记十五-(数据块及数据访问方式)

    一.数据块 数据块是在S7 CPU的存储器中定义的,用户可以定义多了数据块,但是CPU对数据块数量及数据总量是有限制的. 数据块与临时数据不同,当逻辑块执行结束或数据块关闭,数据块中的数据是会保留住的 ...

  3. (C/C++学习笔记) 十五. 构造数据类型

    十五. 构造数据类型 ● 构造数据类型概念 Structured data types 构造数据类型 结构体(structure), 联合体/共用体 (union), 枚举类型(enumeration ...

  4. MySQL学习笔记十五:优化(2)

    一.数据库性能评测关键指标 1.IOPS:每秒处理的IO请求次数,这跟磁盘硬件相关,DBA不能左右,但推荐使用SSD. 2.QPS:每秒查询次数,可以使用show status或mysqladmin ...

  5. Java基础学习笔记十五 集合、迭代器、泛型

    Collection 集合,集合是java中提供的一种容器,可以用来存储多个数据. 在前面的学习中,我们知道数据多了,可以使用数组存放或者使用ArrayList集合进行存放数据.那么,集合和数组既然都 ...

  6. angular学习笔记(十五)-module里的'服务'

    本篇介绍angular中的模块:module 在笔记(二)http://www.cnblogs.com/liulangmao/p/3711047.html里已经讲到过模块,这篇主要讲模块的 '服务' ...

  7. Java学习笔记十五:Java中的成员变量和局部变量

    Java中的成员变量和局部变量 一:成员变量: 成员变量在类中定义,用来描述对象将要有什么 成员变量可以被本类的方法使用,也可以被其他类的方法使用,成员变量的作用域在整个类内部都是可见的 二:局部变量 ...

  8. MYSQL进阶学习笔记十五:MySQL 的账号权限赋予!(视频序号:进阶_33,34)

    知识点十六:MySQL的账号权限赋予(33) 一.MySQL权限简介 关于mysql的权限简单的理解就是mysql允许你做你全力以内的事情,不可以越界.比如只允许你执行select操作,那么你就不能执 ...

  9. 数据结构和算法学习笔记十五:多路查找树(B树)

    一.概念 1.多路查找树(multi-way search tree):所谓多路,即是指每个节点中存储的数据可以是多个,每个节点的子节点数也可以多于两个.使用多路查找树的意义在于有效降低树的深度,从而 ...

  10. JavaScript权威设计--JavaScript脚本化文档Document与CSS(简要学习笔记十五)

    1.Document与Element和TEXT是Node的子类. Document:树形的根部节点 Element:HTML元素的节点 TEXT:文本节点   >>HtmlElement与 ...

随机推荐

  1. Struts2中获取servlet API的几种方式

    struts2是一个全新的MVC框架,如今被广大的企业和开发者所使用,它的功能非常强大.这给我们在使用servlet 纯java代码写项目的时候带来了福音.但是一般来说,我们的项目不到一定规模并不需要 ...

  2. 【整理】--C++变量概述

    1.变量概述及特殊变量初始化 a.引用 b.常量 c.静态 d.静态常量(整型) e.静态常量(非整型) 初始化:常量和引用,必须通过参数列表进行初始化. 静态成员变量的初始化也颇有点特别,是在类外初 ...

  3. (转)使用Node.js+Socket.IO搭建WebSocket实时应用

    Web领域的实时推送技术,也被称作Realtime技术.这种技术要达到的目的是让用户不需要刷新浏览器就可以获得实时更新.它有着广泛的应用场景,比如在线聊天室.在线客服系统.评论系统.WebIM等. W ...

  4. Webstorm 2016内置web服务器配置

    运行three.js的官方的例子.本来想用IIS来运行,运行不了.所以用webstorm,用鼠标右键的方式,来运行,如下图 但是有一天,我把IIS配置好了,可以在IIS中运行了(只是把build文件夹 ...

  5. 使用WatiN进行UI自动化测试

    Watin是一个UI自动化测试工具,支持ie/firefox,官方网站:http://watin.org/. 主要有以下特点: 支持主要的html元素,见:http://watin.org/docum ...

  6. [后端人员耍前端系列]Bootstrap篇:30分钟快速掌握Bootstrap

    一.引言 很久没有写过博客了,但是最近这段时间都没有闲着,接触了很多方面.比如一些前端框架和组件.还有移动开发React-Native.以及对.NET框架设计的一些重新认识.这些内容在接下来的时间都会 ...

  7. 【转】yahoo前端优化军规

    雅虎给出了前端优化的34条法则(包括Yslow规则22条) 详细说明,下载转发 ponytail 的译文(来自帕兰映像). Minimize HTTP Requests 减少http请求 图片.css ...

  8. dojo的发展历史

    dojo的开始要从2004年初开始说起,那时dojo之父 Alex Russell 在Informatica公司内从事一个名为netWindows的项目,这个项目的目的是在浏览器环境下提供创建窗口化界 ...

  9. 浅谈Excel开发:三 Excel 对象模型

    前一篇文章介绍了Excel中的菜单系统,在创建完菜单和工具栏之后,就要着手进行功能的开发了.不论您采用何种方式来开发Excel应用程序,了解Excel对象模型尤其重要,这些对象是您与Excel进行交互 ...

  10. 浅谈Excel开发:二 Excel 菜单系统

    在开始Excel开发之前,需要把架子搭起来.最直接的那就是Excel里面的菜单了,他向用户直观的展现了我们的插件具有哪些功能.菜单出来之后我们就可以实现里面的事件和功能了.Excel菜单有两种形式,一 ...