cocos2d-x版本 2.0.4
cocos2d-x做android游戏在线更新资源。
费话不多说,直接上代码:
下载和解压是用android端java实现:
/**
*
* @return
* 100 没有sd卡
* 1 下载过程中出错
* 2 解压过程中出错
* 3 删除过程中出错
*/
public static int download()
{
//检查sd卡
if(!Environment.getExternalStorageState().equals(Environment.MEDIA_MOUNTED))
{
return 100;
}
//下载保存
try
{
saveToFile("http://192.168.0.14/data/Data.zip", Environment.getExternalStorageDirectory()+"/data.zip");
}
catch (IOException e)
{
e.printStackTrace();
return 1;
}
//解压
File zipFile = new File(Environment.getExternalStorageDirectory()+"/data.zip");
try
{
upZipFile(zipFile,Environment.getExternalStorageDirectory()+"/xydata/data/");
}
catch (ZipException e)
{
e.printStackTrace();
return 2;
}
catch (IOException e)
{
e.printStackTrace();
return 2;
}
//删除zip
try
{
deleteFile(zipFile);
}
catch(Exception e)
{
e.printStackTrace();
return 3;
}
return 0;
}
private static int BUFFER_SIZE = 8096; //缓冲区大小
/**
* 将HTTP资源另存为文件
*
* @param destUrl String
* @param fileName String
* @throws Exception
*/
public static void saveToFile(String destUrl, String fileName) throws IOException
{
FileOutputStream fos = null;
BufferedInputStream bis = null;
HttpURLConnection httpUrl = null;
URL url = null;
byte[] buf = new byte[BUFFER_SIZE];
int size = 0;
// 建立链接
url = new URL(destUrl);
httpUrl = (HttpURLConnection) url.openConnection();
// 连接指定的资源
httpUrl.connect();
// 获取网络输入流
bis = new BufferedInputStream(httpUrl.getInputStream());
// 建立文件
fos = new FileOutputStream(fileName);
System.out.println("正在获取链接[" + destUrl + "]的内容...\n将其保存为文件[" + fileName + "]");
// 保存文件
while ((size = bis.read(buf)) != -1)
{
fos.write(buf, 0, size);
}
fos.close();
bis.close();
httpUrl.disconnect();
}
/**
* 解压缩一个文件
*
* @param zipFile 要解压的压缩文件
* @param folderPath 解压缩的目标目录
* @throws IOException 当解压缩过程出错时抛出
*/
public static void upZipFile(File zipFile, String folderPath) throws ZipException, IOException
{
File desDir = new File(folderPath);
if (!desDir.exists())
{
desDir.mkdirs();
}
ZipFile zf = new ZipFile(zipFile);
for (Enumeration> entries = zf.entries(); entries.hasMoreElements();)
{
ZipEntry entry = ((ZipEntry) entries.nextElement());
InputStream in = zf.getInputStream(entry);
String str = folderPath + File.separator + entry.getName();
str = new String(str.getBytes("8859_1"), "GB2312");
File desFile = new File(str);
if (!desFile.exists())
{
File fileParentDir = desFile.getParentFile();
if (!fileParentDir.exists())
{
fileParentDir.mkdirs();
}
desFile.createNewFile();
}
OutputStream out = new FileOutputStream(desFile);
byte buffer[] = new byte[1024];
int realLength;
while ((realLength = in.read(buffer)) > 0)
{
out.write(buffer, 0, realLength);
}
in.close();
out.close();
}
}
//将SD卡文件删除
public static void deleteFile(File file)
{
if (file.exists())
{
if (file.isFile())
{
file.delete();
}
// 如果它是一个目录
else if (file.isDirectory())
{
// 声明目录下所有的文件 files[];
File files[] = file.listFiles();
for (int i = 0; i < files.length; i++)
{ // 遍历目录下所有的文件
deleteFile(files[i]); // 把每个文件 用这个方法进行迭代
}
}
file.delete();
}
}
流程就是先把zip包下载到sd卡中,再解压到指定目录,解压完成后zip就没了删之。
在c++里检测版本,在需要更新时通过jni调用download()方法,这里的方法都写成static的,纯是为了jni调用时省点事。
要是不会用通过jni在c++和java之间相互调用可以度娘、google,也可以参考cocos2dx\platform\android\jni目录下Java开头的几个类和samples\HelloCpp\proj.android\src\org\cocos2dx\lib里边的java文件结合着看看就明白了。
还要在AndroidManifest.xml中加sd卡中写文件和访问网络的权限如下:
现在sd卡的资源有了,下面解决调用问题,方法有2也直接上代码:
//方法1
unsigned long filesize;
CCImage image;
char* buffer = (char *)CCFileUtils::sharedFileUtils()->getFileData("/mnt/sdcard/to3/icon.png", "rb", &filesize);
if(image.initWithImageData((void*)buffer, filesize, CCImage::kFmtPng))
{
CCTexture2D *texture = new CCTexture2D();
texture->initWithImage(&image);
if( texture )
{
CCSprite *sprite = CCSprite::createWithTexture(texture);
if (sprite)
{
CCLog("111sprite != null");
this->addChild(sprite);
sprite->setPosition(ccp(200, 100));
}
else
{
CCLog("111sprite == null");
}
}
}
//方法2
bool flag = image.initWithImageFile("/mnt/sdcard/to3/icon.png", CCImage::kFmtPng);
if (flag)
{
CCTexture2D *texture2D = new CCTexture2D();
texture2D->initWithImage(&image);
CCSprite *sprite = CCSprite::createWithTexture(texture2D);
if (sprite)
{
CCLog("222sprite != null");
this->addChild(sprite);
sprite->setPosition(ccp(100, 100));
}
else
{
CCLog("222sprite == null");
}
}
方法1不只可以读图片,其他的 xml之类的文件也可以读,方法2只是读图片的。
/mnt/sdcard是sd卡的根目录,这里用于测试是写死的,由于手机厂商不同,这个路径也会不同,要通过jni(又是jni)获取Environment.getExternalStorageDirectory()
附图一张,图中的两小人就是上面的两个方法加进去的。
就到这里吧
有什么不对的地方请指正,谢谢!