青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品

天行健 君子當自強而不息

游戲中物件的定義與使用(8)

 

本篇是游戲中物件的定義與使用(7)的續篇。


Developing a Character ICS

Although developing a character’s inventory system might make you cringe at first,
let me reassure you that it’s not much different from developing a map inventory
control system. You have the ability to add and remove items, but you don’t have the
problem of dealing with the item coordinates on the map. Instead, a player’s ICS
keeps track of order, which means that players can rearrange the items as they see fit.


Of course, this ordering is just a matter of arranging the linked list, but what about
the items that can hold other items, such as backpacks? As long as you properly categorize
the items as containers in the MIL Editor, you don’t need to worry.


Speaking of categorizing, the real magic happens when you want to equip or use
an item. Because each item is categorized, the character ICS can quickly determine
what to do with the item in question. If the item is a weapon, the character ICS can
ask to equip the item. If it’s a healing item, the player can consume it. Beginning
to get the idea?

Finally, a character ICS should allow the player to examine objects, which is the reason
for the mesh and image parameters in the MIL Editor. Whenever the game’s
player examines the object, the specific mesh or image is loaded and displayed.
Now, turn your attention to putting together a character ICS and example by using
the ICS.

 

Defining the cCharICS Class

Interface:

//==================================================================================
// This structure contains char item information list.
//==================================================================================
typedef struct sCharItem
{
    
long    item_index;     // MIL item index
    long    quantity;       // quantity of item (ie coins)    

    sCharItem*   prev;
    sCharItem*   next;

    
long    index;           // map item index
    long    owner;

    sCharItem*   parent;     
// parent of a contained item
    
    sCharItem()
    {
        memset(
this, 0, sizeof(*this));
        owner = -1;
    }

    ~sCharItem()
    {
        delete next;   
    }
} *sCharItemPtr;

//==================================================================================
// This class encapsulate char inventory contrl system for character.
//==================================================================================
typedef class cCharIcs
{
private:
    
long         m_num_items;
    sCharItemPtr m_root_item;

private:
    
long    get_next_long(FILE* fp);
    
float   get_next_float(FILE* fp);

public:
    cCharIcs();
    ~cCharIcs();

    
bool load(const char* filename);
    
bool save(const char* filename);
    
void free();

    
void add(long item_index, long quantity, sCharItemPtr owner_item);
    
void remove(sCharItemPtr item);

    
long get_num_items();
    sCharItemPtr get_root_item();
    sCharItemPtr get_item(
long index);

    
void sort();
    
bool move_up(sCharItemPtr item);
    
bool move_down(sCharItemPtr item);
} *cCharIcsPtr;
 

Much like the cMapICS class, the cCharICS class uses a special structure (sCharItem) that
tracks the MIL item numbers and quantity and maintains a linked list. Unlike the
sMapItem structure, however, sCharItem doesn’t care about the item’s coordinates.

Implement:

//----------------------------------------------------------------------------
// Get numeric value from file.
//----------------------------------------------------------------------------
static void get_numeric_value(FILE* fp, char* buf, int size)
{
    
long pos;
    
int c;

    
// read until EOF or EOL or over buffer
    for(pos = 0; (c = fgetc(fp)) != EOF && c != 0x0a && pos != size-1; pos++)
    {
        
if((c >= '0' && c <= '9') || c == '.' || c == '-')
            buf[pos] = c;
    }

    buf[pos] = 0;
}

//----------------------------------------------------------------------------
// Constructor, initialize member data.
//----------------------------------------------------------------------------
cCharIcs::cCharIcs()
{
    memset(
this, 0, sizeof(*this));
}

//----------------------------------------------------------------------------
// Destructor, free allocated resource. 
//----------------------------------------------------------------------------
cCharIcs::~cCharIcs()
{
  free();
}

//----------------------------------------------------------------------------
// free allocate resource.
//----------------------------------------------------------------------------
void cCharIcs::free()
{
  m_num_items = 0;

  delete m_root_item;  
}

//----------------------------------------------------------------------------
// Load all char items from file.
//----------------------------------------------------------------------------
bool cCharIcs::load(const char* filename)
{
    free();     
// free a prior set

    FILE* fp;

    
if((fp = fopen(filename, "rb")) == NULL)
        
return false;    

    sCharItemPtr item;
    sCharItemPtr item_ptr = NULL;

    
// loop forever reading in items
    while(1)
    {
        
long item_index;

        
// get next item number (break if no more items, which is represented by a return value of -1).
        if((item_index = get_next_long(fp)) == -1)
            
break;

        
// create a new map item and link it in

        item = 
new sCharItem;

        
if(item_ptr == NULL)
            m_root_item = item;
        
else
        {
            item->prev = item_ptr;
            item_ptr->next = item;
        }

        item_ptr = item;

        item->item_index  = item_index;
        item->quantity    = get_next_long(fp);      
        item->owner       = get_next_long(fp);
        item->index       = m_num_items++;
    }

    fclose(fp);

    
// match objects that belong to others
    for(item_ptr = m_root_item; item_ptr != NULL; item_ptr = item_ptr->next)
    {
        
// check if this item belongs to another
        if(item_ptr->owner == -1)
            
continue;

        
// find matching parent item
        for(item = m_root_item; item != NULL; item = item->next)
        {
            
if(item_ptr->owner == item->index)
            {
                
// a match, point to parent and stop scanning for parents.
                item_ptr->parent = item;
                
break;
            }
        }
    }

    
return true;
}

//----------------------------------------------------------------------------
// Save all char items to file.
//----------------------------------------------------------------------------
bool cCharIcs::save(const char* filename)
{
    FILE* fp;

    
if((fp = fopen(filename, "wb")) == NULL)
        
return false;
     
    
long index = 0;

    
for(sCharItemPtr item = m_root_item; item != NULL; item = item->next)
    {
        item->index = index++;

        
// match child items to parents
        if(item->parent)
            item->owner = item->parent->index;
        
else
            item->owner = -1;

        fprintf(fp, "%lu\r\n%lu\r\n%ld\r\n", item->item_index, item->quantity, item->owner);
    }
    
    fclose(fp);

    
return true;
}

//----------------------------------------------------------------------------
// Add char item into list.
//----------------------------------------------------------------------------
void cCharIcs::add(long item_index, long quantity, sCharItemPtr owner_item)
{
    sCharItemPtr item = 
new sCharItem;

    
// fill the item structure
    item->item_index = item_index;
    item->quantity   = quantity;
    item->parent     = owner_item;

    
// insert into top of list

    item->next = m_root_item;

    
if(m_root_item)
        m_root_item->prev = item;

    m_root_item = item;
}

//----------------------------------------------------------------------------
// Remove char item from list.
//----------------------------------------------------------------------------
void cCharIcs::remove(sCharItemPtr item)
{    
    sCharItemPtr next_item;

    
// remove child objects first
    for(sCharItemPtr item_ptr = m_root_item; item_ptr != NULL; item_ptr = next_item)
    {
        next_item = item_ptr->next;

        
if(item_ptr->parent == item)
            remove(item_ptr);
    }

    
// remove from linked list and reset root if it's the current head of list.
    
    
if(item->prev)
        item->prev->next = item->next;
    
else
        m_root_item = item->next;

    
if(item->next)
        item->next->prev = item->prev;

    item->prev = item->next = NULL;
    delete item;
}

//----------------------------------------------------------------------------
// Return number of map items.
//----------------------------------------------------------------------------
long cCharIcs::get_num_items()
{
    
return m_num_items;
}

//----------------------------------------------------------------------------
// Return root map item.
//----------------------------------------------------------------------------
sCharItemPtr cCharIcs::get_root_item()
{
    
return m_root_item;
}

//----------------------------------------------------------------------------
// Return map item with specified index.
//----------------------------------------------------------------------------
sCharItemPtr cCharIcs::get_item(long index)
{
    sCharItemPtr item;

    
// loop until reached item index
    for(item = m_root_item; item != NULL && index != 0; item = item->next)
        index--;

    
return item;
}

//----------------------------------------------------------------------------
// Return long value from next line in file.
//----------------------------------------------------------------------------
long cCharIcs::get_next_long(FILE *fp)
{
    
char buf[1024];
    get_numeric_value(fp, buf, 
sizeof(buf));

    
if(strlen(buf) == 0)    // if there is no long value in file
        return -1;

    
return atol(buf);
}

//----------------------------------------------------------------------------
// Return float value from next line in file.
//----------------------------------------------------------------------------
float cCharIcs::get_next_float(FILE *fp)
{
    
char buf[1024];
    get_numeric_value(fp, buf, 
sizeof(buf));

    
return (float)atof(buf);
}

The cCharICS class, again, is much like its cMapICS counterpart, except for the addition
of three more public functions— sort, move_up, and move_down. You use these functions
to sort the character’s list of items. Their code is as follows:


//----------------------------------------------------------------------------
// Arrange char ics.
//----------------------------------------------------------------------------
void cCharIcs::sort()
{
    
// start at top of linked list and float each item up that has a lesser item_index,
    // break if past bottom of list.
    for(sCharItemPtr item = m_root_item; item != NULL; item = item->next)
    {
        
// keep floating up while previous item has a lesser item_index value or
        // until top of list has been rearched.
        for(sCharItemPtr prev_item = item->prev; prev_item != NULL; prev_item = item->prev)
        {
            
// break if no more to float up
            if(prev_item->item_index <= item->item_index)
                
break;

            
// swap element

            
if(prev_item->prev)
                prev_item->prev->next = item;

            
if((prev_item->next = item->next) != NULL)
                item->next->prev = prev_item;

            
if((item->prev = prev_item->prev) == NULL)
                m_root_item = item;
            
            prev_item->prev = item;
            item->next = prev_item;
        }
    }
}

//----------------------------------------------------------------------------
// Move one char item up.
//----------------------------------------------------------------------------
bool cCharIcs::move_up(sCharItemPtr item)
{
    sCharItemPtr prev_item = item->prev;

    
if(prev_item == NULL)
        
return FALSE;

    
// swap item and item before it

    
if(prev_item->prev)
        prev_item->prev->next = item;

    
if((prev_item->next = item->next) != NULL)
        item->next->prev = prev_item;

    
if((item->prev = prev_item->prev) == NULL)
        m_root_item = item;

    prev_item->prev = item;
    item->next = prev_item;

    
return TRUE;
}

//----------------------------------------------------------------------------
// Move one char item down.
//----------------------------------------------------------------------------
bool cCharIcs::move_down(sCharItemPtr item)
{
    sCharItemPtr next_item = item->next;

    
if(next_item == NULL)
        
return FALSE;

    
// swap item and item after it

    
if((item->next = next_item->next) != NULL)
        next_item->next->prev = item;

    
if((next_item->prev = item->prev) != NULL)
        item->prev->next = next_item;
    
else
        m_root_item = next_item;

    next_item->next = item;
    item->prev = next_item;

    
return TRUE;
}

Function 'sort' sorts the linked list of items based on each item’s MIL item number, from
lowest to highest. If, on the other hand, you want to specifically order the list yourself,
you can utilize the move_up and move_down functions, which take a pointer to a
sCharItem structure that is already contained in the list.

The move_up function moves the specified sItem structure up in the linked list, and
move_down moves the specified structure down in the linked list. Figure 15.10 illustrates
the concept of using the Arrange, move_up, and move_down functions on a sample
linked list of items.

The rest of the functions in cCharICS are identical in their functionality to the
cMapICS class, with the obvious exclusion of the item coordinates used when adding
an item to the list. Even the storage format for character items is identical to the
map item format, except for the coordinates.

 

Using the cCharICS Class

To demonstrate the use of the character ICS system, I created a demo application
named CharICS that maintains a list of items contained in the default.mil master
item list file. When you start the demo, you’ll see the
Inventory dialog box (shown in following snap). In the Inventory dialog box, the list
box contains an imaginary character’s inventory, which you can manipulate by
using the buttons on the dialog box.

To use the CharICS demo, follow these steps:


1. Click the Add Item button. The CharICS demo will add a random item from
the MIL to the inventory list.


2. Select an item from the list. Items are classified, so the Use and Equip buttons
are enabled or disabled depending on which item you select from the
list. Clicking Equip has no effect; it comes into play later when you deal with
characters. Clicking Use, however, removes an item if it is flagged as USEONCE.

3. Click the Drop button to drop an item (remove the item from the inventory
list) if it is flagged as CANDROP.


4. In order to arrange the items in the inventory, you can click an item and
then click either Sort Up or Sort Down. The selected item then moves up or
down in the list. To arrange the items by their item number in the list, click
Sort.


As a last, special treat, items that have matching meshes appear in the box on the
right in the demo. The 3-D object spins around slowly so that you have a full view
of all sides. Now, that’s cool!


posted on 2007-11-08 15:05 lovedday 閱讀(427) 評論(0)  編輯 收藏 引用

公告

導航

統計

常用鏈接

隨筆分類(178)

3D游戲編程相關鏈接

搜索

最新評論

青青草原综合久久大伊人导航_色综合久久天天综合_日日噜噜夜夜狠狠久久丁香五月_热久久这里只有精品
  • <ins id="pjuwb"></ins>
    <blockquote id="pjuwb"><pre id="pjuwb"></pre></blockquote>
    <noscript id="pjuwb"></noscript>
          <sup id="pjuwb"><pre id="pjuwb"></pre></sup>
            <dd id="pjuwb"></dd>
            <abbr id="pjuwb"></abbr>
            久久久免费精品| 久久精品最新地址| 欧美日韩一区在线视频| 一区二区三区视频在线播放| 亚洲精品在线二区| 欧美午夜片欧美片在线观看| 欧美一区二视频| 久久国产福利| 亚洲靠逼com| 亚洲午夜伦理| 精品成人国产| 亚洲精选一区| 国产一区二区三区四区在线观看| 免费不卡在线视频| 欧美日韩不卡在线| 久久久久se| 欧美激情日韩| 久久精品国产一区二区三| 免费亚洲婷婷| 亚洲一区二区三区视频播放| 欧美在线影院在线视频| 99精品视频一区二区三区| 亚洲欧美久久久| 日韩视频一区二区三区| 午夜欧美精品久久久久久久| 亚洲国内精品在线| 亚洲欧美一区二区原创| 99v久久综合狠狠综合久久| 午夜精品成人在线视频| 日韩视频在线观看一区二区| 欧美一进一出视频| 亚洲一级黄色片| 狼狼综合久久久久综合网| 午夜在线观看欧美| 欧美激情bt| 蜜桃av一区| 国产区精品在线观看| 亚洲精品免费电影| 在线免费观看日本一区| 亚洲欧美视频一区| 亚洲图片你懂的| 欧美大尺度在线| 老司机午夜免费精品视频| 国产精品永久免费在线| 亚洲精选国产| 日韩一级欧洲| 欧美激情aaaa| 亚洲国语精品自产拍在线观看| 国产亚洲欧美一区| 午夜视频一区| 欧美影院视频| 国产模特精品视频久久久久| 一区二区三区.www| 一区二区三区偷拍| 欧美日韩高清不卡| 亚洲区国产区| 亚洲精品影视| 欧美二区视频| 亚洲韩国精品一区| 99精品视频一区二区三区| 欧美h视频在线| 亚洲国产欧美在线人成| 亚洲免费观看视频| 欧美片网站免费| 国产精品天天看| 在线视频精品一区| 亚洲综合精品四区| 国产精品久久久久永久免费观看| 在线视频精品| 欧美一区二区三区免费视频| 国产欧美日韩视频一区二区三区| 亚洲一区免费视频| 久久久精品日韩| 亚洲高清一区二区三区| 欧美a级一区二区| 日韩视频在线一区二区三区| 亚洲一区日韩在线| 国产视频精品xxxx| 久热精品视频| 日韩一级免费| 久久国产精品色婷婷| 伊人激情综合| 欧美精品一区在线发布| 中文精品99久久国产香蕉| 久久精品99国产精品| 亚洲第一福利视频| 欧美日韩国产高清| 先锋影音国产精品| 亚洲国产精品99久久久久久久久| 99热在线精品观看| 国产欧美精品一区二区色综合| 久久久久久网| 日韩亚洲一区在线播放| 久久久久久夜| 一区二区三区毛片| 激情久久综艺| 欧美视频中文字幕| 久久婷婷av| 一片黄亚洲嫩模| 免费观看成人www动漫视频| 亚洲视频日本| 在线观看亚洲视频啊啊啊啊| 欧美日韩小视频| 久久精品导航| 亚洲一区二区三区国产| 亚洲国产高清高潮精品美女| 亚洲欧美精品伊人久久| 亚洲黄色免费电影| 国产亚洲一二三区| 欧美视频在线观看一区二区| 久久婷婷色综合| 亚洲女优在线| 一本色道久久综合亚洲精品不卡| 免费人成网站在线观看欧美高清| 亚洲一区二区三区777| 亚洲国产欧美国产综合一区| 国产婷婷色一区二区三区在线| 欧美日韩国产成人在线| 快播亚洲色图| 久久久久久久成人| 午夜久久久久| 亚洲欧美激情一区| 在线一区二区三区四区| 亚洲精品国产精品国自产在线| 久久女同精品一区二区| 午夜一区在线| 亚洲欧美乱综合| 夜夜躁日日躁狠狠久久88av| 亚洲国产精品va在看黑人| 国产日韩欧美一区在线| 国产精品入口夜色视频大尺度| 欧美人成免费网站| 欧美激情第二页| 欧美黄色网络| 欧美日韩成人网| 欧美精品一区二| 欧美人交a欧美精品| 欧美不卡高清| 欧美日韩高清在线一区| 欧美另类专区| 欧美日韩一区不卡| 欧美日韩中文字幕| 欧美三级视频在线播放| 欧美性一区二区| 国产精品久久久久久av福利软件 | 久久久国产精品一区二区三区| 亚洲在线不卡| 性亚洲最疯狂xxxx高清| 亚洲欧美日韩精品| 欧美一区二区视频97| 久久久久欧美精品| 欧美h视频在线| 91久久精品国产91久久性色| 日韩亚洲一区二区| 亚洲一区精彩视频| 久久av一区二区| 嫩模写真一区二区三区三州| 欧美精品一区二区在线播放| 国产精品vip| 国内成人精品2018免费看 | 欧美日韩ab| 国产精品免费一区二区三区观看 | 欧美日韩一区免费| 国产精品午夜春色av| 韩国精品一区二区三区| 91久久综合| 午夜在线电影亚洲一区| 鲁大师成人一区二区三区| 亚洲国产精品嫩草影院| 亚洲视频一区二区在线观看| 久久国产精品毛片| 欧美美女视频| 国产一区二区欧美| 日韩亚洲欧美中文三级| 午夜精品网站| 欧美顶级少妇做爰| 亚洲婷婷综合色高清在线 | 亚洲一区黄色| 欧美国产日韩一区二区三区| 国产精品美女在线| 亚洲国产美女| 久久精品盗摄| 亚洲精选国产| 久久在线免费| 国产日韩免费| 一区二区三区精品视频在线观看| 久久国产精品一区二区三区| 亚洲国产成人久久| 欧美在线播放一区| 国产精品观看| 日韩午夜电影在线观看| 另类欧美日韩国产在线| 一区二区三区视频在线| 欧美不卡高清| 永久免费视频成人| 欧美在线日韩精品| 一区二区久久久久| 欧美剧在线免费观看网站| 一区二区视频免费在线观看| 午夜精品一区二区三区四区|