Panda3D
|
00001 // Filename: cLwoSurfaceBlock.cxx 00002 // Created by: drose (26Apr01) 00003 // 00004 //////////////////////////////////////////////////////////////////// 00005 // 00006 // PANDA 3D SOFTWARE 00007 // Copyright (c) Carnegie Mellon University. All rights reserved. 00008 // 00009 // All use of this software is subject to the terms of the revised BSD 00010 // license. You should have received a copy of this license along 00011 // with this source code in a file named "LICENSE." 00012 // 00013 //////////////////////////////////////////////////////////////////// 00014 00015 #include "cLwoSurfaceBlock.h" 00016 #include "cLwoSurfaceBlockTMap.h" 00017 #include "lwoToEggConverter.h" 00018 00019 #include "lwoSurfaceBlockChannel.h" 00020 #include "lwoSurfaceBlockEnabled.h" 00021 #include "lwoSurfaceBlockImage.h" 00022 #include "lwoSurfaceBlockRepeat.h" 00023 #include "lwoSurfaceBlockVMapName.h" 00024 #include "dcast.h" 00025 00026 00027 //////////////////////////////////////////////////////////////////// 00028 // Function: CLwoSurfaceBlock::Constructor 00029 // Access: Public 00030 // Description: 00031 //////////////////////////////////////////////////////////////////// 00032 CLwoSurfaceBlock:: 00033 CLwoSurfaceBlock(LwoToEggConverter *converter, const LwoSurfaceBlock *block) : 00034 _converter(converter), 00035 _block(block) 00036 { 00037 _block_type = _block->_header->get_id(); 00038 _ordinal = _block->_header->_ordinal; 00039 _enabled = true; 00040 _opacity_type = LwoSurfaceBlockOpacity::T_additive; 00041 _opacity = 1.0; 00042 _transform = LMatrix4d::ident_mat(); 00043 _inv_transform = LMatrix4d::ident_mat(); 00044 _projection_mode = LwoSurfaceBlockProjection::M_uv; 00045 _axis = LwoSurfaceBlockAxis::A_y; 00046 _clip_index = -1; 00047 _w_wrap = LwoSurfaceBlockWrap::M_repeat; 00048 _h_wrap = LwoSurfaceBlockWrap::M_repeat; 00049 _w_repeat = 1.0; 00050 _h_repeat = 1.0; 00051 _tmap = (CLwoSurfaceBlockTMap *)NULL; 00052 00053 // Scan the chunks in the header. 00054 int num_hchunks = _block->_header->get_num_chunks(); 00055 for (int hi = 0; hi < num_hchunks; hi++) { 00056 const IffChunk *hchunk = _block->_header->get_chunk(hi); 00057 00058 if (hchunk->is_of_type(LwoSurfaceBlockChannel::get_class_type())) { 00059 const LwoSurfaceBlockChannel *bc = 00060 DCAST(LwoSurfaceBlockChannel, hchunk); 00061 _channel_id = bc->_channel_id; 00062 00063 } else if (hchunk->is_of_type(LwoSurfaceBlockEnabled::get_class_type())) { 00064 const LwoSurfaceBlockEnabled *ec = 00065 DCAST(LwoSurfaceBlockEnabled, hchunk); 00066 _enabled = ec->_enabled; 00067 } 00068 } 00069 00070 // Scan the chunks in the body. 00071 int num_chunks = _block->get_num_chunks(); 00072 for (int i = 0; i < num_chunks; i++) { 00073 const IffChunk *chunk = _block->get_chunk(i); 00074 00075 if (chunk->is_of_type(LwoSurfaceBlockTMap::get_class_type())) { 00076 const LwoSurfaceBlockTMap *lwo_tmap = DCAST(LwoSurfaceBlockTMap, chunk); 00077 if (_tmap != (CLwoSurfaceBlockTMap *)NULL) { 00078 nout << "Two TMAP chunks encountered within surface block.\n"; 00079 delete _tmap; 00080 } 00081 _tmap = new CLwoSurfaceBlockTMap(_converter, lwo_tmap); 00082 00083 } else if (chunk->is_of_type(LwoSurfaceBlockProjection::get_class_type())) { 00084 const LwoSurfaceBlockProjection *proj = DCAST(LwoSurfaceBlockProjection, chunk); 00085 _projection_mode = proj->_mode; 00086 00087 } else if (chunk->is_of_type(LwoSurfaceBlockAxis::get_class_type())) { 00088 const LwoSurfaceBlockAxis *axis = DCAST(LwoSurfaceBlockAxis, chunk); 00089 _axis = axis->_axis; 00090 00091 } else if (chunk->is_of_type(LwoSurfaceBlockImage::get_class_type())) { 00092 const LwoSurfaceBlockImage *image = DCAST(LwoSurfaceBlockImage, chunk); 00093 _clip_index = image->_index; 00094 00095 } else if (chunk->is_of_type(LwoSurfaceBlockWrap::get_class_type())) { 00096 const LwoSurfaceBlockWrap *wrap = DCAST(LwoSurfaceBlockWrap, chunk); 00097 _w_wrap = wrap->_width; 00098 _h_wrap = wrap->_height; 00099 00100 } else if (chunk->is_of_type(LwoSurfaceBlockWrap::get_class_type())) { 00101 const LwoSurfaceBlockWrap *wrap = DCAST(LwoSurfaceBlockWrap, chunk); 00102 _w_wrap = wrap->_width; 00103 _h_wrap = wrap->_height; 00104 00105 } else if (chunk->is_of_type(LwoSurfaceBlockVMapName::get_class_type())) { 00106 const LwoSurfaceBlockVMapName *vmap = DCAST(LwoSurfaceBlockVMapName, chunk); 00107 _uv_name = vmap->_name; 00108 00109 } else if (chunk->is_of_type(LwoSurfaceBlockRepeat::get_class_type())) { 00110 const LwoSurfaceBlockRepeat *repeat = DCAST(LwoSurfaceBlockRepeat, chunk); 00111 if (repeat->get_id() == IffId("WRPW")) { 00112 _w_repeat = repeat->_cycles; 00113 } else if (repeat->get_id() == IffId("WRPH")) { 00114 _h_repeat = repeat->_cycles; 00115 } 00116 } 00117 } 00118 00119 if (_tmap != (CLwoSurfaceBlockTMap *)NULL) { 00120 _tmap->get_transform(_transform); 00121 } 00122 00123 // Also rotate the transform if we specify some axis other than Y. 00124 // (All the map_* uv mapping functions are written to assume Y is 00125 // the dominant axis.) 00126 switch (_axis) { 00127 case LwoSurfaceBlockAxis::A_x: 00128 _transform = LMatrix4d::rotate_mat(90.0, 00129 LVecBase3d::unit_z(), 00130 CS_yup_left) * _transform; 00131 break; 00132 00133 case LwoSurfaceBlockAxis::A_y: 00134 break; 00135 00136 case LwoSurfaceBlockAxis::A_z: 00137 _transform = LMatrix4d::rotate_mat(-90.0, 00138 LVecBase3d::unit_x(), 00139 CS_yup_left) * _transform; 00140 break; 00141 } 00142 00143 _inv_transform.invert_from(_transform); 00144 } 00145 00146 //////////////////////////////////////////////////////////////////// 00147 // Function: CLwoSurfaceBlock::Destructor 00148 // Access: Public 00149 // Description: 00150 //////////////////////////////////////////////////////////////////// 00151 CLwoSurfaceBlock:: 00152 ~CLwoSurfaceBlock() { 00153 if (_tmap != (CLwoSurfaceBlockTMap *)NULL) { 00154 delete _tmap; 00155 } 00156 }