void PrefabImporter::HandlePrefabSave(StringHash eventType, VariantMap& eventData) { using namespace PrefabSave; PrefabComponent* component = static_cast<PrefabComponent*>(eventData[P_PREFABCOMPONENT].GetPtr()); if (component->GetPrefabGUID() != asset_->GetGUID()) return; Node* node = component->GetNode(); if (!node) return; // flip temporary root children and components to not be temporary for save const Vector<SharedPtr<Component>>& rootComponents = node->GetComponents(); const Vector<SharedPtr<Node> >& children = node->GetChildren(); PODVector<Component*> tempComponents; PODVector<Node*> tempChildren; PODVector<Node*> filterNodes; for (unsigned i = 0; i < rootComponents.Size(); i++) { if (rootComponents[i]->IsTemporary()) { rootComponents[i]->SetTemporary(false); tempComponents.Push(rootComponents[i]); // Animated sprites contain a temporary node we don't want to save in the prefab // it would be nice if this was general purpose because have to test this when // breaking node as well if (rootComponents[i]->GetType() == AnimatedSprite2D::GetTypeStatic()) { AnimatedSprite2D* asprite = (AnimatedSprite2D*) rootComponents[i].Get(); if (asprite->GetRootNode()) filterNodes.Push(asprite->GetRootNode()); } } } for (unsigned i = 0; i < children.Size(); i++) { if (filterNodes.Contains(children[i].Get())) continue; if (children[i]->IsTemporary()) { children[i]->SetTemporary(false); tempChildren.Push(children[i]); } } // store original transform Vector3 pos = node->GetPosition(); Quaternion rot = node->GetRotation(); Vector3 scale = node->GetScale(); node->SetPosition(Vector3::ZERO); node->SetRotation(Quaternion::IDENTITY); node->SetScale(Vector3::ONE); component->SetTemporary(true); SharedPtr<File> file(new File(context_, asset_->GetPath(), FILE_WRITE)); node->SaveXML(*file); file->Close(); component->SetTemporary(false); // restore node->SetPosition(pos); node->SetRotation(rot); node->SetScale(scale); for (unsigned i = 0; i < tempComponents.Size(); i++) { tempComponents[i]->SetTemporary(true); } for (unsigned i = 0; i < tempChildren.Size(); i++) { tempChildren[i]->SetTemporary(true); } FileSystem* fs = GetSubsystem<FileSystem>(); fs->Copy(asset_->GetPath(), asset_->GetCachePath()); // reload it immediately so it is ready for use // TODO: The resource cache is reloading after this reload due to catching the file cache ResourceCache* cache = GetSubsystem<ResourceCache>(); XMLFile* xmlfile = cache->GetResource<XMLFile>(asset_->GetGUID()); cache->ReloadResource(xmlfile); VariantMap changedData; changedData[PrefabChanged::P_GUID] = asset_->GetGUID(); SendEvent(E_PREFABCHANGED, changedData); }
void SceneView3D::HandleDragEnterWidget(StringHash eventType, VariantMap& eventData) { using namespace DragEnterWidget; UIWidget* widget = static_cast<UIWidget*>(eventData[P_WIDGET].GetPtr()); if (widget != this) return; UIDragObject* dragObject = static_cast<UIDragObject*>(eventData[P_DRAGOBJECT].GetPtr()); Object* object = dragObject->GetObject(); if (!object) return; if (object->GetType() == Asset::GetTypeStatic()) { Asset* asset = (Asset*) object; AssetImporter* importer = asset->GetImporter(); if (!importer) return; StringHash importerType = importer->GetType(); if (importerType == PrefabImporter::GetTypeStatic()) { dragNode_ = scene_->CreateChild(asset->GetName()); PrefabComponent* pc = dragNode_->CreateComponent<PrefabComponent>(); pc->SetPrefabGUID(asset->GetGUID()); } else if (importerType == ModelImporter::GetTypeNameStatic()) { dragNode_ = scene_->CreateChild(); SharedPtr<File> file(new File(context_, asset->GetCachePath())); SharedPtr<XMLFile> xml(new XMLFile(context_)); if (!xml->Load(*file)) return; dragNode_->LoadXML(xml->GetRoot()); dragNode_->SetName(asset->GetName()); } else if (importerType == SpriterImporter::GetTypeNameStatic()) { AnimationSet2D* animationSet = GetSubsystem<ResourceCache>()->GetResource<AnimationSet2D>(asset->GetPath()); String animationName; if (animationSet && animationSet->GetNumAnimations()) { animationName = animationSet->GetAnimation(0)->GetName(); } dragNode_ = scene_->CreateChild(asset->GetName()); AnimatedSprite2D* sprite = dragNode_->CreateComponent<AnimatedSprite2D>(); if (!animationName.Length()) sprite->SetAnimationSet(animationSet); else sprite->SetAnimation(animationSet, animationName); } else if (importerType == TextureImporter::GetTypeNameStatic()) { dragNode_ = scene_->CreateChild(asset->GetName()); Sprite2D* spriteGraphic = GetSubsystem<ResourceCache>()->GetResource<Sprite2D>(asset->GetPath()); StaticSprite2D* sprite = dragNode_->CreateComponent<StaticSprite2D>(); sprite->SetSprite(spriteGraphic); } if (dragNode_.NotNull()) { Input* input = GetSubsystem<Input>(); IntVector2 pos = input->GetMousePosition(); UpdateDragNode(pos.x_, pos.y_); } //LOGINFOF("Dropped %s : %s on SceneView3D", asset->GetPath().CString(), asset->GetGUID().CString()); } }