一个简单的游戏框架:配置表方案

一个简单的游戏框架:配置表方案

代码:https://github.com/HushengStudent/myGameFramework

1、配置表格式

csv,逗号分隔,可以使用wps和Excel打开编辑,方便策划使用;

默认第一行为注释;

默认第二行为字段名+类型;二者以冒号隔开;

默认第一列为主键;

2、配置表导出方案

在编辑器下,读取配置表的内容,并把内容按规则转换成对应类型,然后把内容转换为对应的字节数组,写入到二进制文件,并生成对应的读表代码,在使用配置表的时候,根据生成的读表代码,自动加载对应的二进制文件,从而实现配置表解决方案;

(1)数据类型转换为byte[]

如:

        #region int

        private static int _intLength = 4;

        public static int INT_LENGTH { get { return _intLength; } }

        /// <summary>
        /// 以字节数组的形式返回指定的32位有符号整数值;
        /// </summary>
        /// <param name="value">要转换的数字;</param>
        /// <returns>长度为4的字节数组;</returns>
        public static byte[] GetBytes(int value)
        {
            return BitConverter.GetBytes(value);
        }

        /// <summary>
        /// 返回由字节数组中前四个字节转换来的32位有符号整数;
        /// </summary>
        /// <param name="value">字节数组;</param>
        /// <returns>由四个字节构成的32位有符号整数;</returns>
        public static int GetInt32(byte[] value)
        {
            return BitConverter.ToInt32(value, 0);
        }

        /// <summary>
        /// 返回由字节数组中指定位置的四个字节转换来的32位有符号整数;
        /// </summary>
        /// <param name="value">字节数组;</param>
        /// <param name="startIndex">value内的起始位置;</param>
        /// <returns>由四个字节构成的32位有符号整数;</returns>
        public static int GetInt32(byte[] value, int startIndex)
        {
            return BitConverter.ToInt32(value, startIndex);
        }

这样就能完成类型转换;

字符串在使用的时候,约定第一位为字符串的长度:

#region string

        /// <summary>
        /// 以UTF-8字节数组的形式返回指定的字符串;
        /// </summary>
        /// <param name="value">要转换的字符串;</param>
        /// <returns>UTF-8字节数组;</returns>
        public static byte[] GetBytes(string value)
        {
            return Encoding.UTF8.GetBytes(value);
        }

        /// <summary>
        /// 返回由UTF-8字节数组转换来的字符串;
        /// </summary>
        /// <param name="value">UTF-8字节数组;</param>
        /// <returns>字符串;</returns>
        public static string GetString(byte[] value)
        {
            if (value == null)
            {
                throw new Exception("Value is invalid.");
            }
            return Encoding.UTF8.GetString(value, 0, value.Length);
        }

        #endregion
protected static void ReadString(ref byte[] byteArr, ref int byteOffset, out string str)
        {
            int len;
            //第一位为长度;
            ReadInt32(ref byteArr, ref byteOffset, out len);
            str = Encoding.UTF8.GetString(byteArr, byteOffset, len);
            byteOffset += len;
        }
每读一次,就计算对应位置偏移;

(2)二进制文件的读取与生成

#region Txt

        /// <summary>
        /// 保存Txt;
        /// </summary>
        /// <param name="path"></param>
        /// <param name="contents"></param>
        public static void Write2Txt(string path, string[] contents)
        {
            File.WriteAllLines(path, contents);
        }
        /// <summary>
        /// 读取Txt;
        /// </summary>
        /// <param name="path"></param>
        /// <returns></returns>
        public static string[] ReadFromTxt(string path)
        {
            return File.ReadAllLines(path);
        }

        #endregion

        #region Bytes

        /// <summary>
        /// 保存Bytes;
        /// </summary>
        /// <param name="path"></param>
        /// <param name="bytes"></param>
        public static void Write2Bytes(string path, byte[] bytes)
        {
            File.WriteAllBytes(path, bytes);
        }
        /// <summary>
        /// 读取Bytes;
        /// </summary>
        /// <param name="path"></param>
        /// <returns></returns>
        public static byte[] ReadFromBytes(string path)
        {
            return File.ReadAllBytes(path);
        }

        #endregion

主要使用以上方法读取txt,修改txt,将txt转换为byte[],将byte[]写入文件;

之前有写过用MemoryStream写入字节流,然后调用GetBuff()获得byte[]数组,但是出错了;

扫描二维码关注公众号,回复: 2188409 查看本文章

备注
请注意,在缓冲区中包含分配的字节数,这可能是未使用。 例如,如果"test"的字符串写入到 MemoryStream 对象,从返回的缓冲区的长度 GetBuffer 为 256,而非 4,与未使用为 252 字节。 若要获取缓冲区中的数据,请使用 ToArray 方法; 但是, ToArray 在内存中创建数据的副本。

也可以是缓冲区 null。

(3)示例

道具Id,道具名字,道具描述
ItemId:INT,ItemName:STRING,ItemDes:STRING
1,屠龙刀,屠龙宝刀,武林至尊
2,倚天剑,倚天不出,谁与争锋
3,打狗棒,丐帮帮主信物

生成读表代码:

//------------------------------------------------------------------------------
// <auto-generated>
//     This code was generated by a tool.
//
//     Changes to this file may cause incorrect behavior and will be lost if
//     the code is regenerated.
// </auto-generated>
//------------------------------------------------------------------------------
 
using Framework; 
using System.Collections; 
using System.Collections.Generic; 
using UnityEngine; 
 
public class ItemTableDB : BaseTableDB<ItemTable>
{
    public static readonly ItemTableDB instance=new ItemTableDB();
}
 
// Generated from: ItemTable.csv
public class ItemTable : TableData
{

     public int ItemId;
     public string ItemName;
     public string ItemDes;
 
    public override int Key
    {
        get
        {
            return ItemId; 
        }
    }
 
    public override void Decode(byte[] byteArr, ref int bytePos)
    {

         ReadInt32(ref byteArr,ref bytePos,out ItemId);
         ReadString(ref byteArr,ref bytePos,out ItemName);
         ReadString(ref byteArr,ref bytePos,out ItemDes);
 
    }
 
}

BaseTable主要是读表代码,为了方便管理,提供Table基类,统一调用Load方法;

测试加载:

TableMgr.Instance.LoadTable("ItemTable",ItemTableDB.instance);
调用该方法,就会自动加载ItemTable,并读取对应的二进制文件,并且把文件数据加载到ItemTableDB.instance对象;

猜你喜欢

转载自blog.csdn.net/husheng0/article/details/80384093