Main Page | Namespace List | Class Hierarchy | Alphabetical List | Compound List | File List | Namespace Members | Compound Members | File Members

PrimitiveDrawRequestBuilder.cpp

Go to the documentation of this file.
00001 //------------------------------------------------------------------------------
00002 // Lamp : Open source game middleware
00003 // Copyright (C) 2004  Junpei Ohtani ( Email : junpee@users.sourceforge.jp )
00004 //
00005 // This library is free software; you can redistribute it and/or
00006 // modify it under the terms of the GNU Lesser General Public
00007 // License as published by the Free Software Foundation; either
00008 // version 2.1 of the License, or (at your option) any later version.
00009 //
00010 // This library is distributed in the hope that it will be useful,
00011 // but WITHOUT ANY WARRANTY; without even the implied warranty of
00012 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00013 // Lesser General Public License for more details.
00014 //
00015 // You should have received a copy of the GNU Lesser General Public
00016 // License along with this library; if not, write to the Free Software
00017 // Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA
00018 //------------------------------------------------------------------------------
00019 
00020 /** @file
00021  * プリミティブ描画リクエストビルダ実装
00022  * @author Junpee
00023  */
00024 
00025 #include "LampBasic.h"
00026 #include "Graphics/PrimitiveRenderer/PrimitiveDrawRequestBuilder.h"
00027 #include "Graphics/PrimitiveRenderer/PrimitiveDrawRequest.h"
00028 #include "Graphics/Model/CharacterModel.h"
00029 
00030 namespace Lamp{
00031 
00032 //------------------------------------------------------------------------------
00033 // ポイントの構築
00034 void PrimitiveDrawRequestBuilder::buildPoint(PrimitiveDrawRequest* request){
00035     request->setVertexCount(12);
00036     request->enableColor(true);
00037     // X軸
00038     request->setPosition(0, Vector3::zero);
00039     request->setColor(0, Color4c(255, 255, 255, 255));
00040     request->setPosition(1, Vector3::unitX);
00041     request->setColor(1, Color4c(255, 255, 255, 64));
00042     request->setPosition(2, Vector3::zero);
00043     request->setColor(2, Color4c(255, 255, 255, 255));
00044     request->setPosition(3, -Vector3::unitX);
00045     request->setColor(3, Color4c(255, 255, 255, 64));
00046     // Y軸
00047     request->setPosition(4, Vector3::zero);
00048     request->setColor(4, Color4c(255, 255, 255, 255));
00049     request->setPosition(5, Vector3::unitY);
00050     request->setColor(5, Color4c(255, 255, 255, 64));
00051     request->setPosition(6, Vector3::zero);
00052     request->setColor(6, Color4c(255, 255, 255, 255));
00053     request->setPosition(7, -Vector3::unitY);
00054     request->setColor(7, Color4c(255, 255, 255, 64));
00055     // Z軸
00056     request->setPosition(8, Vector3::zero);
00057     request->setColor(8, Color4c(255, 255, 255, 255));
00058     request->setPosition(9, Vector3::unitZ);
00059     request->setColor(9, Color4c(255, 255, 255, 64));
00060     request->setPosition(10, Vector3::zero);
00061     request->setColor(10, Color4c(255, 255, 255, 255));
00062     request->setPosition(11, -Vector3::unitZ);
00063     request->setColor(11, Color4c(255, 255, 255, 64));
00064 }
00065 //------------------------------------------------------------------------------
00066 // 軸ポイントの構築
00067 void PrimitiveDrawRequestBuilder::buildAxisPoint(PrimitiveDrawRequest* request){
00068     request->setVertexCount(12);
00069     request->enableColor(true);
00070     // X軸
00071     request->setPosition(0, Vector3::zero);
00072     request->setColor(0, Color4c(255, 0, 0, 255));
00073     request->setPosition(1, Vector3::unitX);
00074     request->setColor(1, Color4c(255, 0, 0, 64));
00075     request->setPosition(2, Vector3::zero);
00076     request->setColor(2, Color4c(255, 0, 0, 255));
00077     request->setPosition(3, -Vector3::unitX);
00078     request->setColor(3, Color4c(255, 0, 0, 64));
00079     // Y軸
00080     request->setPosition(4, Vector3::zero);
00081     request->setColor(4, Color4c(0, 255, 0, 255));
00082     request->setPosition(5, Vector3::unitY);
00083     request->setColor(5, Color4c(0, 255, 0, 64));
00084     request->setPosition(6, Vector3::zero);
00085     request->setColor(6, Color4c(0, 255, 0, 255));
00086     request->setPosition(7, -Vector3::unitY);
00087     request->setColor(7, Color4c(0, 255, 0, 64));
00088     // Z軸
00089     request->setPosition(8, Vector3::zero);
00090     request->setColor(8, Color4c(0, 0, 255, 255));
00091     request->setPosition(9, Vector3::unitZ);
00092     request->setColor(9, Color4c(0, 0, 255, 64));
00093     request->setPosition(10, Vector3::zero);
00094     request->setColor(10, Color4c(0, 0, 255, 255));
00095     request->setPosition(11, -Vector3::unitZ);
00096     request->setColor(11, Color4c(0, 0, 255, 64));
00097 }
00098 //------------------------------------------------------------------------------
00099 // 軸の構築
00100 void PrimitiveDrawRequestBuilder::buildAxis(PrimitiveDrawRequest* request){
00101     request->setVertexCount(6);
00102     request->enableColor(true);
00103     // X軸
00104     request->setPosition(0, Vector3::zero);
00105     request->setColor(0, Color4c(255, 0, 0, 255));
00106     request->setPosition(1, Vector3::unitX);
00107     request->setColor(1, Color4c(255, 0, 0, 64));
00108     // Y軸
00109     request->setPosition(2, Vector3::zero);
00110     request->setColor(2, Color4c(0, 255, 0, 255));
00111     request->setPosition(3, Vector3::unitY);
00112     request->setColor(3, Color4c(0, 255, 0, 64));
00113     // Z軸
00114     request->setPosition(4, Vector3::zero);
00115     request->setColor(4, Color4c(0, 0, 255, 255));
00116     request->setPosition(5, Vector3::unitZ);
00117     request->setColor(5, Color4c(0, 0, 255, 64));
00118 }
00119 //------------------------------------------------------------------------------
00120 // 矢印の構築
00121 void PrimitiveDrawRequestBuilder::buildArrow(PrimitiveDrawRequest* request){
00122     request->setVertexCount(10);
00123     request->enableColor(true);
00124     request->setPosition(0, Vector3::zero);
00125     request->setColor(0, Color4c(255, 255, 255, 255));
00126     request->setPosition(1, Vector3::unitZ);
00127     request->setColor(1, Color4c(255, 255, 255, 255));
00128 
00129     float width = 0.25f;
00130     request->setPosition(2, Vector3::unitZ);
00131     request->setColor(2, Color4c(255, 255, 255, 255));
00132     request->setPosition(3, Vector3(width, width, 0.5f));
00133     request->setColor(3, Color4c(255, 255, 255, 64));
00134 
00135     request->setPosition(4, Vector3::unitZ);
00136     request->setColor(4, Color4c(255, 255, 255, 255));
00137     request->setPosition(5, Vector3(width, -width, 0.5f));
00138     request->setColor(5, Color4c(255, 255, 255, 64));
00139 
00140     request->setPosition(6, Vector3::unitZ);
00141     request->setColor(6, Color4c(255, 255, 255, 255));
00142     request->setPosition(7, Vector3(-width, width, 0.5f));
00143     request->setColor(7, Color4c(255, 255, 255, 64));
00144 
00145     request->setPosition(8, Vector3::unitZ);
00146     request->setColor(8, Color4c(255, 255, 255, 255));
00147     request->setPosition(9, Vector3(-width, -width, 0.5f));
00148     request->setColor(9, Color4c(255, 255, 255, 64));
00149 
00150 }
00151 //------------------------------------------------------------------------------
00152 // グリッドの構築
00153 void PrimitiveDrawRequestBuilder::buildGrid(
00154     PrimitiveDrawRequest* request, int division, int subDivision){
00155     int totalDivision = division * subDivision;
00156     int lineCount = totalDivision + 1;
00157     request->setVertexCount(lineCount * 4);
00158     request->enableColor(true);
00159     float scale = 1.f / totalDivision;
00160     for(int i = 0; i < lineCount; i++){
00161         int offset = i * 4;
00162         float value = i * scale - 0.5f;
00163         request->setPosition(offset + 0, Vector3(value, 0.f, -0.5f));
00164         request->setPosition(offset + 1, Vector3(value, 0.f, 0.5f));
00165         request->setPosition(offset + 2, Vector3(-0.5f, 0.f, value));
00166         request->setPosition(offset + 3, Vector3(0.5f, 0.f, value));
00167         Color4c color;
00168         if((i % subDivision) == 0){ color.set(255, 255, 255, 255); }
00169         else{ color.set(255, 255, 255, 64); }
00170         for(int j = 0; j < 4; j++){ request->setColor(offset + j,color); }
00171     }
00172 }
00173 //------------------------------------------------------------------------------
00174 // 平面の構築
00175 void PrimitiveDrawRequestBuilder::buildPlane(PrimitiveDrawRequest* request){
00176     request->setVertexCount(10);
00177     request->enableColor(true);
00178     request->setPosition(0, Vector3(0.f, 0.f, 0.f));
00179     request->setColor(0, Color4c(255, 255, 255, 255));
00180     request->setPosition(1, Vector3(0.f, 0.f, 1.f));
00181     request->setColor(1, Color4c(255, 255, 255, 192));
00182 
00183     request->setPosition(2, Vector3(0.5f, 0.5f, 0.f));
00184     request->setColor(2, Color4c(255, 255, 255, 192));
00185     request->setPosition(3, Vector3(-0.5f, 0.5f, 0.f));
00186     request->setColor(3, Color4c(255, 255, 255, 192));
00187 
00188     request->setPosition(4, Vector3(-0.5f, 0.5f, 0.f));
00189     request->setColor(4, Color4c(255, 255, 255, 192));
00190     request->setPosition(5, Vector3(-0.5f, -0.5f, 0.f));
00191     request->setColor(5, Color4c(255, 255, 255, 192));
00192 
00193     request->setPosition(6, Vector3(-0.5f, -0.5f, 0.f));
00194     request->setColor(6, Color4c(255, 255, 255, 192));
00195     request->setPosition(7, Vector3(0.5f, -0.5f, 0.f));
00196     request->setColor(7, Color4c(255, 255, 255, 192));
00197 
00198     request->setPosition(8, Vector3(0.5f, -0.5f, 0.f));
00199     request->setColor(8, Color4c(255, 255, 255, 192));
00200     request->setPosition(9, Vector3(0.5f, 0.5f, 0.f));
00201     request->setColor(9, Color4c(255, 255, 255, 192));
00202 }
00203 //------------------------------------------------------------------------------
00204 // 球の構築
00205 void PrimitiveDrawRequestBuilder::buildSphere(PrimitiveDrawRequest* request,
00206     float radius, int horizontalDivision, int verticalDivision){
00207     Assert(radius > 0.f);
00208     Assert(horizontalDivision > 2);
00209     Assert(verticalDivision > 2);
00210     int offset;
00211     // 頂点の構築
00212     int vertexCount = (verticalDivision - 1) * horizontalDivision + 2;
00213     request->setVertexCount(vertexCount);
00214     offset = 0;
00215     // 上
00216     request->setPosition(offset, Vector3(0.f, radius, 0.f));
00217     offset++;
00218     // 下
00219     request->setPosition(offset, Vector3(0.f, -radius, 0.f));
00220     offset++;
00221     // 中
00222     for(int i = 1; i < verticalDivision; i++){
00223         float yValue = Math::cos(Math::PI * i / verticalDivision) * radius;
00224         float scale = Math::sin(Math::PI * i / verticalDivision) * radius;
00225         for(int j = 0; j < horizontalDivision; j++){
00226             float radian = Math::doublePI * j / horizontalDivision;
00227             request->setPosition(offset, Vector3(
00228                 Math::cos(radian) * scale, yValue, Math::sin(radian) * scale));
00229             offset++;
00230         }
00231     }
00232     Assert(offset == vertexCount);
00233 
00234     // インデックスの構築
00235     int indexCount = (verticalDivision - 2) * horizontalDivision * 4 +
00236         horizontalDivision * 6;
00237     request->setVertexIndexCount(indexCount);
00238     offset = 0;
00239     // ふた
00240     for(int i = 0; i < horizontalDivision; i++){
00241         request->setVertexIndex(offset, 0);
00242         offset++;
00243         request->setVertexIndex(offset, i + 2);
00244         offset++;
00245     }
00246     // 中間
00247     int verticalCount = verticalDivision - 1;
00248     for(int i = 1; i < verticalCount; i++){
00249         int upOffset = horizontalDivision * (i - 1) + 2;
00250         int downOffset = upOffset + horizontalDivision;
00251         for(int j = 0; j < horizontalDivision; j++){
00252             int leftUp = upOffset + j;
00253             request->setVertexIndex(offset, leftUp);
00254             offset++;
00255             int rightUp = leftUp + 1;
00256             if(j == (horizontalDivision - 1)){ rightUp -= horizontalDivision; }
00257             request->setVertexIndex(offset, rightUp);
00258             offset++;
00259             request->setVertexIndex(offset, leftUp);
00260             offset++;
00261             request->setVertexIndex(offset, downOffset + j);
00262             offset++;
00263         }
00264     }
00265     // 底
00266     int bottomOffset = (verticalDivision - 2) * horizontalDivision + 2;
00267     for(int i = 0; i < horizontalDivision; i++){
00268         int leftUp = i + bottomOffset;
00269         request->setVertexIndex(offset, leftUp);
00270         offset++;
00271         request->setVertexIndex(offset, 1);
00272         offset++;
00273         request->setVertexIndex(offset, leftUp);
00274         offset++;
00275         int rightUp = leftUp + 1;
00276         if(i == (horizontalDivision - 1)){ rightUp -= horizontalDivision; }
00277         request->setVertexIndex(offset, rightUp);
00278         offset++;
00279     }
00280     Assert(offset == indexCount);
00281 }
00282 //------------------------------------------------------------------------------
00283 // 箱の構築
00284 void PrimitiveDrawRequestBuilder::buildBox(
00285     PrimitiveDrawRequest* request, float width, float height, float depth){
00286     Assert(width > 0.f);
00287     Assert(height > 0.f);
00288     Assert(depth > 0.f);
00289     // 頂点の構築
00290     float halfWidth = width * 0.5f;
00291     float halfHeight = height * 0.5f;
00292     float halfDepth = depth * 0.5f;
00293     request->setVertexCount(8);
00294     request->setPosition(0, Vector3(-halfWidth, -halfHeight, -halfDepth));
00295     request->setPosition(1, Vector3(-halfWidth,  halfHeight, -halfDepth));
00296     request->setPosition(2, Vector3( halfWidth,  halfHeight, -halfDepth));
00297     request->setPosition(3, Vector3( halfWidth, -halfHeight, -halfDepth));
00298     request->setPosition(4, Vector3( halfWidth,  halfHeight,  halfDepth));
00299     request->setPosition(5, Vector3(-halfWidth,  halfHeight,  halfDepth));
00300     request->setPosition(6, Vector3(-halfWidth, -halfHeight,  halfDepth));
00301     request->setPosition(7, Vector3( halfWidth, -halfHeight,  halfDepth));
00302 
00303     // インデックスの構築
00304     const int indexCount = 24;
00305     u_short indices[indexCount] = {
00306         0, 1, 1, 2, 2, 3, 3, 0, 4, 5, 5, 6,
00307         6, 7, 7, 4, 0, 6, 1, 5, 2, 4, 3, 7 };
00308     request->setVertexIndexCount(indexCount);
00309     for(int i = 0; i < indexCount; i++){
00310         request->setVertexIndex(i, indices[i]);
00311     }
00312 }
00313 //------------------------------------------------------------------------------
00314 // 円柱の構築
00315 void PrimitiveDrawRequestBuilder::buildCylinder(
00316     PrimitiveDrawRequest* request, float radius, float height, int division){
00317     Assert(radius > 0.f);
00318     Assert(height > 0.f);
00319     Assert(division > 2);
00320     // 頂点の構築
00321     request->setVertexCount(division * 2);
00322     for(int i = 0; i < division; i++){
00323         float radian = Math::doublePI * i / division;
00324         float xValue = Math::cos(radian) * radius;
00325         float zValue = Math::sin(radian) * radius;
00326         int offset = i * 2;
00327         request->setPosition(offset + 0, Vector3(xValue, 0.f, zValue));
00328         request->setPosition(offset + 1, Vector3(xValue, height, zValue));
00329     }
00330 
00331     // インデックスの構築
00332     request->setVertexIndexCount(division * 6);
00333     for(int i = 0; i < division; i++){
00334         int offset = i * 6;
00335         int leftUp = i * 2;
00336         int leftDown = leftUp + 1;
00337         request->setVertexIndex(offset + 0, leftUp);
00338         request->setVertexIndex(offset + 1, leftDown);
00339         request->setVertexIndex(offset + 2, leftUp);
00340         request->setVertexIndex(offset + 4, leftDown);
00341         if(i == (division - 1)){
00342             request->setVertexIndex(offset + 3, 0);
00343             request->setVertexIndex(offset + 5, 1);
00344         }else{
00345             request->setVertexIndex(offset + 3, leftUp + 2);
00346             request->setVertexIndex(offset + 5, leftDown + 2);
00347         }
00348     }
00349 }
00350 //------------------------------------------------------------------------------
00351 // コーンの構築
00352 void PrimitiveDrawRequestBuilder::buildCone(
00353     PrimitiveDrawRequest* request, float radius, float height, int division){
00354     Assert(radius > 0.f);
00355     Assert(height > 0.f);
00356     Assert(division > 2);
00357     // 頂点の構築
00358     request->setVertexCount(division + 1);
00359     request->setPosition(0, Vector3(0.f, height, 0.f));
00360     for(int i = 0; i < division; i++){
00361         float radian = Math::doublePI * i / division;
00362         float xValue = Math::cos(radian) * radius;
00363         float zValue = Math::sin(radian) * radius;
00364         request->setPosition(i + 1, Vector3(xValue, 0.f, zValue));
00365     }
00366 
00367     // インデックスの構築
00368     request->setVertexIndexCount(division * 4);
00369     for(int i = 0; i < division; i++){
00370         int offset = i * 4;
00371         request->setVertexIndex(offset + 0, 0);
00372         request->setVertexIndex(offset + 1, i + 1);
00373         request->setVertexIndex(offset + 2, i + 1);
00374         if(i == (division - 1)){ request->setVertexIndex(offset + 3, 1); }
00375         else{ request->setVertexIndex(offset + 3, i + 2); }
00376     }
00377 }
00378 //------------------------------------------------------------------------------
00379 // ボーンの構築
00380 void PrimitiveDrawRequestBuilder::buildBone(
00381     PrimitiveDrawRequest* request, CharacterModel* model){
00382     Assert(model != NULL);
00383     int boneCount = model->getBoneCount();
00384     Assert(boneCount != 0);
00385     model->buildBoneMatrix();
00386     // ルートボーン以外に対して一本の線が引かれる
00387     int vertexCount = (boneCount - 1) * 2;
00388     request->setVertexCount(vertexCount);
00389     request->enableColor(true);
00390     int offset = 0;
00391     for(int i = 0; i < boneCount; i++){
00392         Bone* bone = model->getBone(i);
00393         // ボーン位置算出行列は deform * invertPose.invert()
00394         Matrix34 matrix = bone->getInversePoseMatrix();
00395         matrix.invertTransformation();
00396         matrix = bone->getDeformMatrix() * matrix;
00397         Vector3 position = matrix * Vector3::zero;
00398         int childCount = bone->getBoneCount();
00399         for(int j = 0; j < childCount; j++){
00400             Bone* child = bone->getBone(j);
00401             // ボーン位置算出行列は deform * invertPose.invert()
00402             Matrix34 childMatrix = child->getInversePoseMatrix();
00403             childMatrix.invertTransformation();
00404             childMatrix = child->getDeformMatrix() * childMatrix;
00405             Vector3 childPosition = childMatrix * Vector3::zero;
00406             request->setPosition(offset, position);
00407             request->setColor(offset, Color4c::white);
00408             offset++;
00409             request->setPosition(offset, childPosition);
00410             request->setColor(offset, Color4c(255, 255, 255, 64));
00411             offset++;
00412         }
00413     }
00414     Assert(vertexCount == offset)
00415 }
00416 //------------------------------------------------------------------------------
00417 } // End of namespace Lamp
00418 //------------------------------------------------------------------------------

Generated on Wed Mar 16 10:29:34 2005 for Lamp by doxygen 1.3.2