OLD | NEW |
1 /* | 1 /* |
2 * Copyright 2009, Google Inc. | 2 * Copyright 2009, Google Inc. |
3 * All rights reserved. | 3 * All rights reserved. |
4 * | 4 * |
5 * Redistribution and use in source and binary forms, with or without | 5 * Redistribution and use in source and binary forms, with or without |
6 * modification, are permitted provided that the following conditions are | 6 * modification, are permitted provided that the following conditions are |
7 * met: | 7 * met: |
8 * | 8 * |
9 * * Redistributions of source code must retain the above copyright | 9 * * Redistributions of source code must retain the above copyright |
10 * notice, this list of conditions and the following disclaimer. | 10 * notice, this list of conditions and the following disclaimer. |
(...skipping 18 matching lines...) Expand all Loading... |
29 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. | 29 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
30 */ | 30 */ |
31 | 31 |
32 | 32 |
33 // This file contains functions for importing COLLADA files into O3D. | 33 // This file contains functions for importing COLLADA files into O3D. |
34 #include "import/cross/precompile.h" | 34 #include "import/cross/precompile.h" |
35 | 35 |
36 #include "base/file_path.h" | 36 #include "base/file_path.h" |
37 #include "base/file_util.h" | 37 #include "base/file_util.h" |
38 #include "base/string_util.h" | 38 #include "base/string_util.h" |
| 39 #include "core/cross/class_manager.h" |
39 #include "core/cross/curve.h" | 40 #include "core/cross/curve.h" |
40 #include "core/cross/error.h" | 41 #include "core/cross/error.h" |
41 #include "core/cross/function.h" | 42 #include "core/cross/function.h" |
42 #include "core/cross/ierror_status.h" | 43 #include "core/cross/ierror_status.h" |
43 #include "core/cross/math_utilities.h" | 44 #include "core/cross/math_utilities.h" |
44 #include "core/cross/matrix4_axis_rotation.h" | 45 #include "core/cross/matrix4_axis_rotation.h" |
45 #include "core/cross/matrix4_composition.h" | 46 #include "core/cross/matrix4_composition.h" |
46 #include "core/cross/matrix4_scale.h" | 47 #include "core/cross/matrix4_scale.h" |
47 #include "core/cross/matrix4_translation.h" | 48 #include "core/cross/matrix4_translation.h" |
48 #include "core/cross/pack.h" | 49 #include "core/cross/pack.h" |
49 #include "core/cross/param_operation.h" | 50 #include "core/cross/param_operation.h" |
50 #include "core/cross/primitive.h" | 51 #include "core/cross/primitive.h" |
51 #include "core/cross/skin.h" | 52 #include "core/cross/skin.h" |
52 #include "core/cross/stream.h" | 53 #include "core/cross/stream.h" |
53 #include "import/cross/collada.h" | 54 #include "import/cross/collada.h" |
54 #include "import/cross/collada_conditioner.h" | 55 #include "import/cross/collada_conditioner.h" |
55 #include "import/cross/collada_zip_archive.h" | 56 #include "import/cross/collada_zip_archive.h" |
| 57 #include "import/cross/destination_buffer.h" |
56 #include "utils/cross/file_path_utils.h" | 58 #include "utils/cross/file_path_utils.h" |
57 | 59 |
58 #define COLLADA_NAMESPACE "collada" | 60 #define COLLADA_NAMESPACE "collada" |
59 #define COLLADA_NAMESPACE_SEPARATOR "." | 61 #define COLLADA_NAMESPACE_SEPARATOR "." |
60 | 62 |
61 // Macro to provide a uniform prefix for all string constants created by | 63 // Macro to provide a uniform prefix for all string constants created by |
62 // COLLADA. | 64 // COLLADA. |
63 #define COLLADA_STRING_CONSTANT(value) \ | 65 #define COLLADA_STRING_CONSTANT(value) \ |
64 (COLLADA_NAMESPACE COLLADA_NAMESPACE_SEPARATOR value) | 66 (COLLADA_NAMESPACE COLLADA_NAMESPACE_SEPARATOR value) |
65 | 67 |
(...skipping 74 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
140 Transform* parent, | 142 Transform* parent, |
141 ParamFloat* animation_input, | 143 ParamFloat* animation_input, |
142 const Options& options) { | 144 const Options& options) { |
143 return Collada::Import(pack, | 145 return Collada::Import(pack, |
144 UTF8ToFilePath(filename), | 146 UTF8ToFilePath(filename), |
145 parent, | 147 parent, |
146 animation_input, | 148 animation_input, |
147 options); | 149 options); |
148 } | 150 } |
149 | 151 |
| 152 void Collada::Init(ServiceLocator* service_locator) { |
| 153 ClassManager* class_manager= |
| 154 service_locator->GetService<o3d::ClassManager>(); |
| 155 class_manager->AddTypedClass<DestinationBuffer>(); |
| 156 } |
| 157 |
150 // Parameters: | 158 // Parameters: |
151 // pack: The pack into which the scene objects will be placed. | 159 // pack: The pack into which the scene objects will be placed. |
152 // Returns true on success. | 160 // Returns true on success. |
153 Collada::Collada(Pack* pack, const Options& options) | 161 Collada::Collada(Pack* pack, const Options& options) |
154 : service_locator_(pack->service_locator()), | 162 : service_locator_(pack->service_locator()), |
155 pack_(pack), | 163 pack_(pack), |
156 options_(options), | 164 options_(options), |
157 dummy_effect_(NULL), | 165 dummy_effect_(NULL), |
158 dummy_material_(NULL), | 166 dummy_material_(NULL), |
159 instance_root_(NULL), | 167 instance_root_(NULL), |
(...skipping 224 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
384 LOG_ASSERT(entity); | 392 LOG_ASSERT(entity); |
385 LOG_ASSERT(entity->GetType() == FCDEntity::MATERIAL); | 393 LOG_ASSERT(entity->GetType() == FCDEntity::MATERIAL); |
386 FCDMaterial* collada_material = down_cast<FCDMaterial*>(entity); | 394 FCDMaterial* collada_material = down_cast<FCDMaterial*>(entity); |
387 BuildMaterial(doc, collada_material); | 395 BuildMaterial(doc, collada_material); |
388 } | 396 } |
389 | 397 |
390 // Import the scene objects, starting at the root. | 398 // Import the scene objects, starting at the root. |
391 FCDSceneNode* scene = doc->GetVisualSceneInstance(); | 399 FCDSceneNode* scene = doc->GetVisualSceneInstance(); |
392 if (scene) { | 400 if (scene) { |
393 instance_root_ = CreateInstanceTree(scene); | 401 instance_root_ = CreateInstanceTree(scene); |
394 ImportTree(instance_root_, parent, animation_input); | 402 if (ImportTree(instance_root_, parent, animation_input)) { |
395 ImportTreeInstances(doc, instance_root_); | 403 if (ImportTreeInstances(doc, instance_root_)) { |
| 404 status = true; |
| 405 } |
| 406 } |
396 delete instance_root_; | 407 delete instance_root_; |
397 instance_root_ = NULL; | 408 instance_root_ = NULL; |
398 status = true; | |
399 } | 409 } |
400 } | 410 } |
401 } | 411 } |
402 return status; | 412 return status; |
403 } | 413 } |
404 | 414 |
405 namespace { | 415 namespace { |
406 | 416 |
407 Curve::Infinity ConvertInfinity(FUDaeInfinity::Infinity infinity) { | 417 Curve::Infinity ConvertInfinity(FUDaeInfinity::Infinity infinity) { |
408 switch (infinity) { | 418 switch (infinity) { |
(...skipping 380 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
789 } | 799 } |
790 | 800 |
791 // Recursively imports a tree of nodes from FCollada, rooted at the | 801 // Recursively imports a tree of nodes from FCollada, rooted at the |
792 // given node, into the O3D scene. | 802 // given node, into the O3D scene. |
793 // Parameters: | 803 // Parameters: |
794 // instance: The root NodeInstance from which to import. | 804 // instance: The root NodeInstance from which to import. |
795 // parent_transform: The parent Transform under which the tree will be placed. | 805 // parent_transform: The parent Transform under which the tree will be placed. |
796 // animation_input: The float parameter used as the input to the animation | 806 // animation_input: The float parameter used as the input to the animation |
797 // (if present). This is usually time. This can be null | 807 // (if present). This is usually time. This can be null |
798 // if there is no animation. | 808 // if there is no animation. |
799 void Collada::ImportTree(NodeInstance *instance, | 809 bool Collada::ImportTree(NodeInstance *instance, |
800 Transform* parent_transform, | 810 Transform* parent_transform, |
801 ParamFloat* animation_input) { | 811 ParamFloat* animation_input) { |
802 FCDSceneNode *node = instance->node(); | 812 FCDSceneNode *node = instance->node(); |
803 Transform* transform = BuildTransform(node, parent_transform, | 813 Transform* transform = BuildTransform(node, parent_transform, |
804 animation_input); | 814 animation_input); |
805 instance->set_transform(transform); | 815 instance->set_transform(transform); |
806 | 816 |
807 // recursively import the rest of the nodes in the tree | 817 // recursively import the rest of the nodes in the tree |
808 const NodeInstance::NodeInstanceList &children = instance->children(); | 818 const NodeInstance::NodeInstanceList &children = instance->children(); |
809 for (size_t i = 0; i < children.size(); ++i) { | 819 for (size_t i = 0; i < children.size(); ++i) { |
810 ImportTree(children[i], transform, animation_input); | 820 if (!ImportTree(children[i], transform, animation_input)) { |
| 821 return false; |
| 822 } |
811 } | 823 } |
| 824 return true; |
812 } | 825 } |
813 | 826 |
814 void Collada::ImportTreeInstances(FCDocument* doc, | 827 bool Collada::ImportTreeInstances(FCDocument* doc, |
815 NodeInstance *node_instance) { | 828 NodeInstance *node_instance) { |
816 FCDSceneNode *node = node_instance->node(); | 829 FCDSceneNode *node = node_instance->node(); |
817 // recursively import the rest of the nodes in the tree | 830 // recursively import the rest of the nodes in the tree |
818 const NodeInstance::NodeInstanceList &children = node_instance->children(); | 831 const NodeInstance::NodeInstanceList &children = node_instance->children(); |
819 for (size_t i = 0; i < children.size(); ++i) { | 832 for (size_t i = 0; i < children.size(); ++i) { |
820 ImportTreeInstances(doc, children[i]); | 833 if (!ImportTreeInstances(doc, children[i])) { |
| 834 return false; |
| 835 } |
821 } | 836 } |
822 | 837 |
823 Transform* transform = node_instance->transform(); | 838 Transform* transform = node_instance->transform(); |
824 for (size_t i = 0; i < node->GetInstanceCount(); ++i) { | 839 for (size_t i = 0; i < node->GetInstanceCount(); ++i) { |
825 FCDEntityInstance* instance = node->GetInstance(i); | 840 FCDEntityInstance* instance = node->GetInstance(i); |
826 FCDCamera* camera(NULL); | 841 FCDCamera* camera(NULL); |
827 FCDGeometryInstance* geom_instance(NULL); | 842 FCDGeometryInstance* geom_instance(NULL); |
828 | 843 |
829 LOG_ASSERT(instance != 0); | 844 LOG_ASSERT(instance != 0); |
830 // Import each node based on what kind of entity it is | 845 // Import each node based on what kind of entity it is |
831 // TODO(o3d): add more entity types as they are supported | 846 // TODO(o3d): add more entity types as they are supported |
832 switch (instance->GetEntityType()) { | 847 switch (instance->GetEntityType()) { |
833 case FCDEntity::CAMERA: | 848 case FCDEntity::CAMERA: |
834 // camera entity | 849 // camera entity |
835 camera = down_cast<FCDCamera*>(instance->GetEntity()); | 850 camera = down_cast<FCDCamera*>(instance->GetEntity()); |
836 BuildCamera(doc, camera, transform, node); | 851 BuildCamera(doc, camera, transform, node); |
837 break; | 852 break; |
838 case FCDEntity::GEOMETRY: { | 853 case FCDEntity::GEOMETRY: { |
839 // geometry entity | 854 // geometry entity |
840 geom_instance = static_cast<FCDGeometryInstance*>(instance); | 855 geom_instance = static_cast<FCDGeometryInstance*>(instance); |
841 Shape* shape = GetShape(doc, geom_instance); | 856 Shape* shape = GetShape(doc, geom_instance); |
842 if (shape) { | 857 if (shape) { |
843 transform->AddShape(shape); | 858 transform->AddShape(shape); |
844 } | 859 } |
845 break; | 860 break; |
846 } | 861 } |
847 case FCDEntity::CONTROLLER: { | 862 case FCDEntity::CONTROLLER: { |
848 FCDControllerInstance* controller_instance = | 863 FCDControllerInstance* controller_instance = |
849 static_cast<FCDControllerInstance*> (instance); | 864 static_cast<FCDControllerInstance*> (instance); |
850 Shape* shape = GetSkinnedShape(doc, controller_instance, node_instance); | 865 FCDController* controller = |
851 if (shape) { | 866 static_cast<FCDController*>(controller_instance->GetEntity()); |
852 transform->AddShape(shape); | 867 if (controller) { |
| 868 if (controller->IsSkin()) { |
| 869 Shape* shape = GetSkinnedShape(doc, |
| 870 controller_instance, |
| 871 node_instance); |
| 872 if (shape) { |
| 873 transform->AddShape(shape); |
| 874 } else { |
| 875 return false; |
| 876 } |
| 877 } |
853 } | 878 } |
854 break; | 879 break; |
855 } | 880 } |
856 default: | 881 default: |
857 // do nothing | 882 // do nothing |
858 break; | 883 break; |
859 } | 884 } |
860 } | 885 } |
| 886 return true; |
861 } | 887 } |
862 | 888 |
863 // Converts an FCollada vertex attribute semantic into an O3D | 889 // Converts an FCollada vertex attribute semantic into an O3D |
864 // vertex attribute semantic. Returns the O3D semantic, or | 890 // vertex attribute semantic. Returns the O3D semantic, or |
865 // UNKNOWN_SEMANTIC on failure. | 891 // UNKNOWN_SEMANTIC on failure. |
866 static Stream::Semantic C2G3DSemantic(FUDaeGeometryInput::Semantic semantic) { | 892 static Stream::Semantic C2G3DSemantic(FUDaeGeometryInput::Semantic semantic) { |
867 switch (semantic) { | 893 switch (semantic) { |
868 case FUDaeGeometryInput::POSITION: return Stream::POSITION; | 894 case FUDaeGeometryInput::POSITION: return Stream::POSITION; |
869 case FUDaeGeometryInput::VERTEX: return Stream::POSITION; | 895 case FUDaeGeometryInput::VERTEX: return Stream::POSITION; |
870 case FUDaeGeometryInput::NORMAL: return Stream::NORMAL; | 896 case FUDaeGeometryInput::NORMAL: return Stream::NORMAL; |
(...skipping 440 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1311 } | 1337 } |
1312 } | 1338 } |
1313 } | 1339 } |
1314 | 1340 |
1315 // There's a BIG assumption here. We assume the first primitive on the shape | 1341 // There's a BIG assumption here. We assume the first primitive on the shape |
1316 // has vertex buffers that are shared on all the primitives under this shape | 1342 // has vertex buffers that are shared on all the primitives under this shape |
1317 // such that we only need to copy the first primitive's vertex buffers to | 1343 // such that we only need to copy the first primitive's vertex buffers to |
1318 // skin everything. This is actually what was BuildShape was doing at the | 1344 // skin everything. This is actually what was BuildShape was doing at the |
1319 // time this code was written. | 1345 // time this code was written. |
1320 const ElementRefArray& elements = shape->GetElementRefs(); | 1346 const ElementRefArray& elements = shape->GetElementRefs(); |
1321 if (elements.empty() || !elements[0]->IsA(Primitive::GetApparentClass())) { | 1347 if (elements.empty()) { |
1322 return NULL; | 1348 return NULL; |
1323 } | 1349 } |
| 1350 // check that they all use the same StreamBank and are all Primitives |
| 1351 for (unsigned ii = 0; ii < elements.size(); ++ii) { |
| 1352 if (!elements[ii]->IsA(Primitive::GetApparentClass())) { |
| 1353 O3D_ERROR(service_locator_) |
| 1354 << "Element in Shape '" << shape->name() << "' is not a Primitive."; |
| 1355 return NULL; |
| 1356 } |
| 1357 if (down_cast<Primitive*>(elements[ii].Get())->stream_bank() != |
| 1358 down_cast<Primitive*>(elements[0].Get())->stream_bank()) { |
| 1359 O3D_ERROR(service_locator_) |
| 1360 << "More than one StreamBank in Shape '" << shape->name() << "'."; |
| 1361 return NULL; |
| 1362 } |
| 1363 } |
1324 Primitive* primitive = down_cast<Primitive*>(elements[0].Get()); | 1364 Primitive* primitive = down_cast<Primitive*>(elements[0].Get()); |
1325 | 1365 |
1326 String controller_name = WideToUTF8(controller->GetName().c_str()); | 1366 String controller_name = WideToUTF8(controller->GetName().c_str()); |
1327 | 1367 |
1328 ParamArray* matrices = pack_->Create<ParamArray>(); | 1368 ParamArray* matrices = pack_->Create<ParamArray>(); |
1329 Skin* skin = pack_->Create<Skin>(); | 1369 Skin* skin = pack_->Create<Skin>(); |
1330 skin->set_name(controller_name); | 1370 skin->set_name(controller_name); |
1331 SkinEval* skin_eval = pack_->Create<SkinEval>(); | 1371 SkinEval* skin_eval = pack_->Create<SkinEval>(); |
1332 skin_eval->set_name(controller_name); | 1372 skin_eval->set_name(controller_name); |
1333 | 1373 |
(...skipping 71 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1405 // two issues come up | 1445 // two issues come up |
1406 // | 1446 // |
1407 // 1) If we serialize that VertexBuffer, POSITION and NORMAL are stored | 1447 // 1) If we serialize that VertexBuffer, POSITION and NORMAL are stored |
1408 // twice. Once in the SourceBuffer, again in the VertexBuffer. That's a lot | 1448 // twice. Once in the SourceBuffer, again in the VertexBuffer. That's a lot |
1409 // of data to download just to throw it away. | 1449 // of data to download just to throw it away. |
1410 // | 1450 // |
1411 // 2) If we want to instance the skin we'll need to make a new VertexBuffer | 1451 // 2) If we want to instance the skin we'll need to make a new VertexBuffer |
1412 // so we can store the skinned vertices for the second instance. But we'd | 1452 // so we can store the skinned vertices for the second instance. But we'd |
1413 // like to share the COLOR and TEXCOORDS. To do that they need to be in | 1453 // like to share the COLOR and TEXCOORDS. To do that they need to be in |
1414 // a separate VertexBuffer. | 1454 // a separate VertexBuffer. |
1415 StreamBank* stream_bank = primitive->stream_bank(); | 1455 StreamBank* old_stream_bank = primitive->stream_bank(); |
1416 SourceBuffer* buffer = pack_->Create<SourceBuffer>(); | 1456 StreamBank* new_stream_bank = pack_->Create<StreamBank>(); |
| 1457 new_stream_bank->set_name(String("skinned_") + old_stream_bank->name()); |
| 1458 Buffer* old_buffer = NULL; |
| 1459 SourceBuffer* source_buffer = pack_->Create<SourceBuffer>(); |
1417 VertexBuffer* shared_buffer = pack_->Create<VertexBuffer>(); | 1460 VertexBuffer* shared_buffer = pack_->Create<VertexBuffer>(); |
| 1461 DestinationBuffer* dest_buffer = pack_->Create<DestinationBuffer>(); |
1418 const StreamParamVector& source_stream_params = | 1462 const StreamParamVector& source_stream_params = |
1419 stream_bank->vertex_stream_params(); | 1463 old_stream_bank->vertex_stream_params(); |
1420 std::vector<Field*> new_fields(source_stream_params.size(), NULL); | 1464 std::vector<Field*> source_fields(source_stream_params.size(), NULL); |
| 1465 std::vector<Field*> dest_fields(source_stream_params.size(), NULL); |
1421 // first make all the fields. | 1466 // first make all the fields. |
1422 for (unsigned ii = 0; ii < source_stream_params.size(); ++ii) { | 1467 for (unsigned ii = 0; ii < source_stream_params.size(); ++ii) { |
1423 const Stream& source_stream = source_stream_params[ii]->stream(); | 1468 const Stream& source_stream = source_stream_params[ii]->stream(); |
1424 const Field& field = source_stream.field(); | 1469 const Field& field = source_stream.field(); |
| 1470 if (old_buffer == NULL) { |
| 1471 old_buffer = field.buffer(); |
| 1472 } else if (old_buffer != field.buffer()) { |
| 1473 O3D_ERROR(service_locator_) |
| 1474 << "More than 1 buffer used by StreamBank '" |
| 1475 << old_stream_bank->name().c_str() |
| 1476 << "' which the collada importer does not currently support"; |
| 1477 } |
1425 bool copied = false; | 1478 bool copied = false; |
1426 if (field.IsA(FloatField::GetApparentClass()) && | 1479 if (field.IsA(FloatField::GetApparentClass()) && |
1427 (field.num_components() == 3 || | 1480 (field.num_components() == 3 || |
1428 field.num_components() == 4)) { | 1481 field.num_components() == 4)) { |
1429 switch (source_stream.semantic()) { | 1482 switch (source_stream.semantic()) { |
1430 case Stream::POSITION: | 1483 case Stream::POSITION: |
1431 case Stream::NORMAL: | 1484 case Stream::NORMAL: |
1432 case Stream::BINORMAL: | 1485 case Stream::BINORMAL: |
1433 case Stream::TANGENT: { | 1486 case Stream::TANGENT: { |
1434 copied = true; | 1487 copied = true; |
1435 unsigned num_source_components = field.num_components(); | 1488 unsigned num_source_components = field.num_components(); |
1436 unsigned num_source_vertices = source_stream.GetMaxVertices(); | 1489 unsigned num_source_vertices = source_stream.GetMaxVertices(); |
1437 if (num_source_vertices != num_vertices) { | 1490 if (num_source_vertices != num_vertices) { |
1438 O3D_ERROR(service_locator_) | 1491 O3D_ERROR(service_locator_) |
1439 << "Number of vertices in stream_bank '" | 1492 << "Number of vertices in stream_bank '" |
1440 << stream_bank->name().c_str() | 1493 << old_stream_bank->name().c_str() |
1441 << "' does not equal the number of vertices in the Skin '" | 1494 << "' does not equal the number of vertices in the Skin '" |
1442 << skin->name().c_str() << "'"; | 1495 << skin->name().c_str() << "'"; |
1443 return NULL; | 1496 return NULL; |
1444 } | 1497 } |
1445 new_fields[ii] = buffer->CreateField(FloatField::GetApparentClass(), | 1498 source_fields[ii] = source_buffer->CreateField( |
1446 num_source_components); | 1499 FloatField::GetApparentClass(), num_source_components); |
| 1500 DCHECK(source_fields[ii]); |
| 1501 dest_fields[ii] = dest_buffer->CreateField( |
| 1502 FloatField::GetApparentClass(), num_source_components); |
| 1503 DCHECK(dest_fields[ii]); |
| 1504 if (!new_stream_bank->SetVertexStream( |
| 1505 source_stream.semantic(), |
| 1506 source_stream.semantic_index(), |
| 1507 dest_fields[ii], |
| 1508 0)) { |
| 1509 O3D_ERROR(service_locator_) |
| 1510 << "could not SetVertexStream on StreamBank '" |
| 1511 << new_stream_bank->name() << "'"; |
| 1512 return NULL; |
| 1513 } |
1447 } | 1514 } |
1448 } | 1515 } |
1449 } | 1516 } |
1450 if (!copied) { | 1517 if (!copied) { |
1451 // It's a shared field, copy it to the shared buffer. | 1518 // It's a shared field, copy it to the shared buffer. |
1452 new_fields[ii] = shared_buffer->CreateField(field.GetClass(), | 1519 source_fields[ii] = shared_buffer->CreateField(field.GetClass(), |
1453 field.num_components()); | 1520 field.num_components()); |
| 1521 new_stream_bank->SetVertexStream(source_stream.semantic(), |
| 1522 source_stream.semantic_index(), |
| 1523 source_fields[ii], |
| 1524 0); |
1454 } | 1525 } |
1455 } | 1526 } |
1456 | 1527 |
1457 if (!buffer->AllocateElements(num_vertices) || | 1528 if (!source_buffer->AllocateElements(num_vertices) || |
1458 !shared_buffer->AllocateElements(num_vertices)) { | 1529 !shared_buffer->AllocateElements(num_vertices) || |
| 1530 !dest_buffer->AllocateElements(num_vertices)) { |
1459 O3D_ERROR(service_locator_) | 1531 O3D_ERROR(service_locator_) |
1460 << "Failed to allocate destination vertex buffer"; | 1532 << "Failed to allocate destination vertex buffer"; |
1461 return NULL; | 1533 return NULL; |
1462 } | 1534 } |
1463 | 1535 |
1464 for (unsigned ii = 0; ii < source_stream_params.size(); ++ii) { | 1536 for (unsigned ii = 0; ii < source_stream_params.size(); ++ii) { |
1465 const Stream& source_stream = source_stream_params[ii]->stream(); | 1537 const Stream& source_stream = source_stream_params[ii]->stream(); |
1466 const Field& field = source_stream.field(); | 1538 const Field& field = source_stream.field(); |
1467 bool copied = false; | 1539 bool copied = false; |
1468 if (field.IsA(FloatField::GetApparentClass()) && | 1540 if (field.IsA(FloatField::GetApparentClass()) && |
1469 (field.num_components() == 3 || | 1541 (field.num_components() == 3 || |
1470 field.num_components() == 4)) { | 1542 field.num_components() == 4)) { |
1471 switch (source_stream.semantic()) { | 1543 switch (source_stream.semantic()) { |
1472 case Stream::POSITION: | 1544 case Stream::POSITION: |
1473 case Stream::NORMAL: | 1545 case Stream::NORMAL: |
1474 case Stream::BINORMAL: | 1546 case Stream::BINORMAL: |
1475 case Stream::TANGENT: { | 1547 case Stream::TANGENT: { |
1476 copied = true; | 1548 copied = true; |
1477 unsigned num_source_components = field.num_components(); | 1549 unsigned num_source_components = field.num_components(); |
1478 Field* new_field = new_fields[ii]; | 1550 Field* source_field = source_fields[ii]; |
1479 | 1551 |
1480 std::vector<float> data(num_vertices * num_source_components); | 1552 std::vector<float> data(num_vertices * num_source_components); |
1481 field.GetAsFloats(0, &data[0], num_source_components, | 1553 field.GetAsFloats(0, &data[0], num_source_components, |
1482 num_vertices); | 1554 num_vertices); |
1483 // TODO(o3d): Remove this matrix multiply. I don't think it is | 1555 // TODO(o3d): Remove this matrix multiply. I don't think it is |
1484 // needed. | 1556 // needed. |
1485 for (unsigned vv = 0; vv < num_vertices; ++vv) { | 1557 for (unsigned vv = 0; vv < num_vertices; ++vv) { |
1486 float* values = &data[vv * num_source_components]; | 1558 float* values = &data[vv * num_source_components]; |
1487 switch (field.num_components()) { | 1559 switch (field.num_components()) { |
1488 case 3: { | 1560 case 3: { |
(...skipping 20 matching lines...) Expand all Loading... |
1509 values[2], | 1581 values[2], |
1510 values[3])); | 1582 values[3])); |
1511 values[0] = result.getElem(0); | 1583 values[0] = result.getElem(0); |
1512 values[1] = result.getElem(1); | 1584 values[1] = result.getElem(1); |
1513 values[2] = result.getElem(2); | 1585 values[2] = result.getElem(2); |
1514 values[3] = result.getElem(3); | 1586 values[3] = result.getElem(3); |
1515 break; | 1587 break; |
1516 } | 1588 } |
1517 } | 1589 } |
1518 } | 1590 } |
1519 new_field->SetFromFloats(&data[0], num_source_components, 0, | 1591 source_field->SetFromFloats(&data[0], num_source_components, 0, |
1520 num_vertices); | 1592 num_vertices); |
1521 // Bind streams | 1593 // Bind streams |
1522 skin_eval->SetVertexStream(source_stream.semantic(), | 1594 skin_eval->SetVertexStream(source_stream.semantic(), |
1523 source_stream.semantic_index(), | 1595 source_stream.semantic_index(), |
1524 new_field, | 1596 source_field, |
1525 0); | 1597 0); |
1526 stream_bank->BindStream(skin_eval, | 1598 new_stream_bank->BindStream(skin_eval, |
1527 source_stream.semantic(), | 1599 source_stream.semantic(), |
1528 source_stream.semantic_index()); | 1600 source_stream.semantic_index()); |
1529 break; | 1601 break; |
1530 } | 1602 } |
1531 } | 1603 } |
1532 } | 1604 } |
1533 if (!copied) { | 1605 if (!copied) { |
1534 Field* new_field = new_fields[ii]; | 1606 Field* source_field = source_fields[ii]; |
1535 new_field->Copy(field); | 1607 source_field->Copy(field); |
1536 field.buffer()->RemoveField(&source_stream.field()); | |
1537 stream_bank->SetVertexStream(source_stream.semantic(), | |
1538 source_stream.semantic_index(), | |
1539 new_field, | |
1540 0); | |
1541 } | 1608 } |
1542 } | 1609 } |
| 1610 |
| 1611 // Set all primitives to use new stream bank. |
| 1612 for (unsigned ii = 0; ii < elements.size(); ++ii) { |
| 1613 down_cast<Primitive*>(elements[ii].Get())->set_stream_bank( |
| 1614 new_stream_bank); |
| 1615 } |
| 1616 pack_->RemoveObject(old_stream_bank); |
| 1617 if (old_buffer) { |
| 1618 source_buffer->set_name(String("source_") + old_buffer->name()); |
| 1619 dest_buffer->set_name(String("skinned_") + old_buffer->name()); |
| 1620 shared_buffer->set_name(String("shared_") + old_buffer->name()); |
| 1621 pack_->RemoveObject(old_buffer); |
| 1622 } |
1543 } | 1623 } |
1544 return shape; | 1624 return shape; |
1545 } | 1625 } |
1546 | 1626 |
1547 Texture* Collada::BuildTextureFromImage(FCDImage* image) { | 1627 Texture* Collada::BuildTextureFromImage(FCDImage* image) { |
1548 const fstring filename = image->GetFilename(); | 1628 const fstring filename = image->GetFilename(); |
1549 Texture* tex = textures_[filename.c_str()]; | 1629 Texture* tex = textures_[filename.c_str()]; |
1550 if (!tex) { | 1630 if (!tex) { |
1551 FilePath file_path = WideToFilePath(filename.c_str()); | 1631 FilePath file_path = WideToFilePath(filename.c_str()); |
1552 FilePath uri = file_path; | 1632 FilePath uri = file_path; |
(...skipping 1207 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2760 SetParamFromFCEffectParam(param_object, | 2840 SetParamFromFCEffectParam(param_object, |
2761 kMaterialParamNameShininess, | 2841 kMaterialParamNameShininess, |
2762 effect_standard->GetShininessParam()); | 2842 effect_standard->GetShininessParam()); |
2763 SetParamFromFCEffectParam(param_object, | 2843 SetParamFromFCEffectParam(param_object, |
2764 kMaterialParamNameSpecularFactor, | 2844 kMaterialParamNameSpecularFactor, |
2765 effect_standard->GetSpecularFactorParam()); | 2845 effect_standard->GetSpecularFactorParam()); |
2766 } | 2846 } |
2767 } | 2847 } |
2768 } | 2848 } |
2769 } // namespace o3d | 2849 } // namespace o3d |
OLD | NEW |