llcategory.cpp

Go to the documentation of this file.
00001 
00031 #include "linden_common.h"
00032 
00033 #include "llcategory.h"
00034 
00035 #include "message.h"
00036 
00037 const LLCategory LLCategory::none;
00038 
00042 
00043 // This is the storage of the category names. It's loosely based on a
00044 // heap-like structure with indices into it for faster searching and
00045 // so that we don't have to maintain a balanced heap. It's *VITALLY*
00046 // important that the CATEGORY_INDEX and CATEGORY_NAME tables are kept
00047 // in synch.
00048 
00049 // CATEGORY_INDEX indexes into CATEGORY_NAME at the first occurance of
00050 // a child. Thus, the first child of root is "Object" which is located
00051 // in CATEGORY_NAME[1].
00052 const S32 CATEGORY_INDEX[] =
00053 {
00054         1,      // ROOT
00055         6,      // object
00056         7,      // clothing
00057         7,      // texture
00058         7,  // sound
00059         7,  // landmark
00060         7,  // object|component
00061         7,  // off the end (required for child count calculations)
00062 };
00063 
00064 // The heap of names
00065 const char* CATEGORY_NAME[] =
00066 {
00067         "(none)",
00068         "Object",               // (none)
00069         "Clothing",
00070         "Texture",
00071         "Sound",
00072         "Landmark",
00073         "Component",    // object
00074         NULL
00075 };
00076 
00080 
00081 LLCategory::LLCategory()
00082 {
00083         // this is used as a simple compile time assertion. If this code
00084         // fails to compile, the depth has been changed, and we need to
00085         // clean up some of the code that relies on the depth, such as the
00086         // default constructor. If CATEGORY_DEPTH != 4, this code will
00087         // attempt to construct a zero length array - which the compiler
00088         // should balk at.
00089 //      static const char CATEGORY_DEPTH_CHECK[(CATEGORY_DEPTH == 4)?1:0] = {' '};      // unused
00090 
00091         // actually initialize the object.
00092         mData[0] = 0;
00093         mData[1] = 0;
00094         mData[2] = 0;
00095         mData[3] = 0;
00096 }
00097 
00098 void LLCategory::init(U32 value)
00099 {
00100         U8 v;
00101         for(S32 i = 0; i < CATEGORY_DEPTH; i++)
00102         {
00103                 v = (U8)((0x000000ff) & value);
00104                 mData[CATEGORY_DEPTH - 1 - i] = v;
00105                 value >>= 8;
00106         }
00107 }
00108 
00109 U32 LLCategory::getU32() const
00110 {
00111         U32 rv = 0;
00112         rv |= mData[0];
00113         rv <<= 8;
00114         rv |= mData[1];
00115         rv <<= 8;
00116         rv |= mData[2];
00117         rv <<= 8;
00118         rv |= mData[3];
00119         return rv;
00120 }
00121 
00122 S32 LLCategory::getSubCategoryCount() const
00123 {
00124         S32 rv = CATEGORY_INDEX[mData[0] + 1] - CATEGORY_INDEX[mData[0]];
00125         return rv;
00126 }
00127 
00128 // This method will return a category that is the nth subcategory. If
00129 // you're already at the bottom of the hierarchy, then the method will
00130 // return a copy of this.
00131 LLCategory LLCategory::getSubCategory(U8 n) const
00132 {
00133         LLCategory rv(*this);
00134         for(S32 i = 0; i < (CATEGORY_DEPTH - 1); i++)
00135         {
00136                 if(rv.mData[i] == 0)
00137                 {
00138                         rv.mData[i] = n + 1;
00139                         break;
00140                 }
00141         }
00142         return rv;
00143 }
00144 
00145 // This method will return the name of the leaf category type
00146 const char* LLCategory::lookupName() const
00147 {
00148         S32 i = 0;
00149         S32 index = mData[i++];
00150         while((i < CATEGORY_DEPTH) && (mData[i] != 0))
00151         {
00152                 index = CATEGORY_INDEX[index];
00153                 ++i;
00154         }
00155         return CATEGORY_NAME[index];
00156 }
00157 
00158 // message serialization
00159 void LLCategory::packMessage(LLMessageSystem* msg) const
00160 {
00161         U32 data = getU32();
00162         msg->addU32Fast(_PREHASH_Category, data);
00163 }
00164 
00165 // message serialization
00166 void LLCategory::unpackMessage(LLMessageSystem* msg, const char* block)
00167 {
00168         U32 data;
00169         msg->getU32Fast(block, _PREHASH_Category, data);
00170         init(data);
00171 }
00172 
00173 // message serialization
00174 void LLCategory::unpackMultiMessage(LLMessageSystem* msg, const char* block,
00175                                                                         S32 block_num)
00176 {
00177         U32 data;
00178         msg->getU32Fast(block, _PREHASH_Category, data, block_num);
00179         init(data);
00180 }
00181 

Generated on Thu Jul 1 06:08:21 2010 for Second Life Viewer by  doxygen 1.4.7