void Entity_constructPreferences(PreferencesPage& page) { page.appendCheckBox( "Show", "Light Radii", LightRadiiImportCaller(GlobalEntityCreator()), LightRadiiExportCaller(GlobalEntityCreator()) ); }
void DEntity::BuildInRadiant( bool allowDestruction ){ bool makeEntity = strcmp( m_Classname, "worldspawn" ) ? true : false; if ( makeEntity ) { NodeSmartReference node( GlobalEntityCreator().createEntity( GlobalEntityClassManager().findOrInsert( m_Classname.GetBuffer(), !brushList.empty() || !patchList.empty() ) ) ); for ( std::list<DEPair* >::const_iterator buildEPair = epairList.begin(); buildEPair != epairList.end(); buildEPair++ ) { Node_getEntity( node )->setKeyValue( ( *buildEPair )->key, ( *buildEPair )->value ); } Node_getTraversable( GlobalSceneGraph().root() )->insert( node ); for ( std::list<DBrush *>::const_iterator buildBrush = brushList.begin(); buildBrush != brushList.end(); buildBrush++ ) ( *buildBrush )->BuildInRadiant( allowDestruction, NULL, node.get_pointer() ); for ( std::list<DPatch *>::const_iterator buildPatch = patchList.begin(); buildPatch != patchList.end(); buildPatch++ ) ( *buildPatch )->BuildInRadiant( node.get_pointer() ); QER_Entity = node.get_pointer(); } else { for ( std::list<DBrush *>::const_iterator buildBrush = brushList.begin(); buildBrush != brushList.end(); buildBrush++ ) ( *buildBrush )->BuildInRadiant( allowDestruction, NULL ); for ( std::list<DPatch *>::const_iterator buildPatch = patchList.begin(); buildPatch != patchList.end(); buildPatch++ ) ( *buildPatch )->BuildInRadiant(); } }
// Add a new conversations entity button void ConversationDialog::onAddEntity() { // Obtain the entity class object IEntityClassPtr eclass = GlobalEntityClassManager().findClass(CONVERSATION_ENTITY_CLASS); if (eclass) { // Construct a Node of this entity type IEntityNodePtr node(GlobalEntityCreator().createEntity(eclass)); // Create a random offset node->getEntity().setKeyValue( "origin", RandomOrigin::generate(128) ); // Insert the node into the scene graph assert(GlobalSceneGraph().root()); GlobalSceneGraph().root()->addChildNode(node); // Refresh the widgets populateWidgets(); } else { // conversation entityclass was not found gtkutil::MessageBox::ShowError( (boost::format(_("Unable to create conversation Entity: class '%s' not found.")) % CONVERSATION_ENTITY_CLASS).str(), GlobalMainFrame().getTopLevelWindow() ); } }
scene::INodePtr Quake3MapReader::createEntity(const EntityKeyValues& keyValues) { // Get the classname from the EntityKeyValues EntityKeyValues::const_iterator found = keyValues.find("classname"); if (found == keyValues.end()) { throw FailureException("Quake3MapReader::createEntity(): could not find classname."); } // Otherwise create the entity and add all of the properties std::string className = found->second; IEntityClassPtr classPtr = GlobalEntityClassManager().findClass(className); if (classPtr == NULL) { rError() << "[mapdoom3]: Could not find entity class: " << className << std::endl; // greebo: EntityClass not found, insert a brush-based one classPtr = GlobalEntityClassManager().findOrInsert(className, true); } // Create the actual entity node IEntityNodePtr node(GlobalEntityCreator().createEntity(classPtr)); for (EntityKeyValues::const_iterator i = keyValues.begin(); i != keyValues.end(); ++i) { node->getEntity().setKeyValue(i->first, i->second); } return node; }
// Creates a new entity for the given entityclass ScriptSceneNode EntityInterface::createEntity(const ScriptEntityClass& eclass) { scene::INodePtr node = GlobalEntityCreator().createEntity(eclass); // Add the node to the buffer otherwise it will be deleted immediately, // as ScriptSceneNodes are using weak_ptrs. SceneNodeBuffer::Instance().push_back(node); return ScriptSceneNode(node); }
void AnimationPreview::setupSceneGraph() { RenderPreview::setupSceneGraph(); _entity = GlobalEntityCreator().createEntity( GlobalEntityClassManager().findClass(FUNC_STATIC_CLASS) ); // This entity is acting as our root node in the scene getScene()->setRoot(_entity); }
void ParticlePreview::setupSceneGraph() { RenderPreview::setupSceneGraph(); _entity = GlobalEntityCreator().createEntity( GlobalEntityClassManager().findClass(FUNC_EMITTER_CLASS)); _entity->enable(scene::Node::eHidden); // This entity is acting as our root node in the scene getScene()->setRoot(_entity); }
void Entity_killconnectSelected(){ if ( GlobalSelectionSystem().countSelected() == 2 ) { GlobalEntityCreator().connectEntities( GlobalSelectionSystem().penultimateSelected().path(), GlobalSelectionSystem().ultimateSelected().path(), 1 ); } else { globalErrorStream() << "entityKillConnectSelected: exactly two instances must be selected\n"; } }
/** * greebo: Creates a new entity with an attached curve * * @key: The curve type: pass either "curve_CatmullRomSpline" or "curve_Nurbs". */ void createCurve(const std::string& key) { UndoableCommand undo(std::string("createCurve: ") + key); // De-select everything before we proceed GlobalSelectionSystem().setSelectedAll(false); GlobalSelectionSystem().setSelectedAllComponents(false); std::string curveEClass = game::current::getValue<std::string>(GKEY_DEFAULT_CURVE_ENTITY); // Fallback to func_static, if nothing defined in the registry if (curveEClass.empty()) { curveEClass = "func_static"; } // Find the default curve entity IEntityClassPtr entityClass = GlobalEntityClassManager().findOrInsert( curveEClass, true ); // Create a new entity node deriving from this entityclass IEntityNodePtr curve(GlobalEntityCreator().createEntity(entityClass)); // Insert this new node into the scenegraph root GlobalSceneGraph().root()->addChildNode(curve); // Select this new curve node Node_setSelected(curve, true); // Set the model key to be the same as the name curve->getEntity().setKeyValue("model", curve->getEntity().getKeyValue("name")); // Initialise the curve using three pre-defined points curve->getEntity().setKeyValue( key, "3 ( 0 0 0 50 50 0 50 100 0 )" ); ITransformablePtr transformable = Node_getTransformable(curve); if (transformable != NULL) { // Translate the entity to the center of the current workzone transformable->setTranslation(GlobalXYWnd().getActiveXY()->getOrigin()); transformable->freezeTransform(); } }
void DifficultySettingsManager::saveSettings() { // Locates all difficulty entities DifficultyEntityFinder finder; GlobalSceneGraph().root()->traverse(finder); // Copy the list from the finder to a local list DifficultyEntityFinder::EntityList entities = finder.getEntities(); if (entities.empty()) { // Create a new difficulty entity std::string eclassName = game::current::getValue<std::string>(GKEY_DIFFICULTY_ENTITYDEF_MAP); IEntityClassPtr diffEclass = GlobalEntityClassManager().findClass(eclassName); if (diffEclass == NULL) { rError() << "[Diff]: Cannot create difficulty entity!\n"; return; } // Create and insert a new entity node into the scenegraph root IEntityNodePtr entNode = GlobalEntityCreator().createEntity(diffEclass); GlobalSceneGraph().root()->addChildNode(entNode); // Add the entity to the list entities.push_back(&entNode->getEntity()); } // Clear all difficulty-spawnargs from existing entities for (DifficultyEntityFinder::EntityList::const_iterator i = entities.begin(); i != entities.end(); i++) { // Construct a difficulty entity using the raw Entity* pointer DifficultyEntity diffEnt(*i); // Clear the difficulty-related spawnargs from the entity diffEnt.clear(); } // Take the first entity DifficultyEntity diffEnt(*entities.begin()); // Cycle through all settings objects and issue save call for (std::size_t i = 0; i < _settings.size(); i++) { _settings[i]->saveToEntity(diffEnt); } }
// Creates a new entity for the given entityclass ScriptSceneNode EntityInterface::createEntity(const std::string& eclassName) { // Find the eclass IEntityClassPtr eclass = GlobalEntityClassManager().findClass(eclassName); if (eclass == NULL) { rMessage() << "Could not find entity class: " << eclassName << std::endl; return ScriptSceneNode(scene::INodePtr()); } scene::INodePtr node = GlobalEntityCreator().createEntity(eclass); // Add the node to the buffer otherwise it will be deleted immediately, // as ScriptSceneNodes are using weak_ptrs. SceneNodeBuffer::Instance().push_back(node); return ScriptSceneNode(node); }
void Entity_constructPreferences( PreferencesPage& page ){ page.appendSpinner( "Names Display Distance (3D)", 512.0, 0.0, 200500.0, IntImportCallback( ShowNamesDistImportCaller( GlobalEntityCreator() ) ), IntExportCallback( ShowNamesDistExportCaller( GlobalEntityCreator() ) ) ); page.appendSpinner( "Names Display Ratio (2D)", 64.0, 0.0, 100500.0, IntImportCallback( ShowNamesRatioImportCaller( GlobalEntityCreator() ) ), IntExportCallback( ShowNamesRatioExportCaller( GlobalEntityCreator() ) ) ); page.appendCheckBox( "Entity Names", "= Targetnames", BoolImportCallback( ShowTargetNamesImportCaller( GlobalEntityCreator() ) ), BoolExportCallback( ShowTargetNamesExportCaller( GlobalEntityCreator() ) ) ); }
// Add a new objectives entity button void ObjectivesEditor::_onAddEntity() { if (_objectiveEClasses.empty()) { // Objective entityclass(es) not defined gtkutil::MessageBox::ShowError( _("Unable to create Objective Entity: classes not defined in registry."), GlobalMainFrame().getTopLevelWindow() ); return; } const std::string& objEClass = _objectiveEClasses.front(); // Obtain the entity class object IEntityClassPtr eclass = GlobalEntityClassManager().findClass(objEClass); if (eclass) { // Construct a Node of this entity type IEntityNodePtr node(GlobalEntityCreator().createEntity(eclass)); // Create a random offset node->getEntity().setKeyValue("origin", RandomOrigin::generate(128)); // Insert the node into the scene graph assert(GlobalSceneGraph().root()); GlobalSceneGraph().root()->addChildNode(node); // Refresh the widgets populateWidgets(); } else { // Objective entityclass was not found gtkutil::MessageBox::ShowError( (boost::format(_("Unable to create Objective Entity: class '%s' not found.")) % objEClass).str(), GlobalMainFrame().getTopLevelWindow() ); } }
void post( const scene::Path& path, scene::Instance& instance ) const { Entity* entity = Node_getEntity( path.top() ); if ( entity != 0 && ( instance.childSelected() || Instance_getSelectable( instance )->isSelected() ) ) { NodeSmartReference node( GlobalEntityCreator().createEntity( GlobalEntityClassManager().findOrInsert( m_classname, node_is_group( path.top() ) ) ) ); EntityCopyingVisitor visitor( *Node_getEntity( node ) ); entity->forEachKeyValue( visitor ); NodeSmartReference child( path.top().get() ); NodeSmartReference parent( path.parent().get() ); Node_getTraversable( parent )->erase( child ); if ( Node_getTraversable( child ) != 0 && Node_getTraversable( node ) != 0 && node_is_group( node ) ) { parentBrushes( child, node ); } Node_getTraversable( parent )->insert( node ); } }
/** * Create an instance of the given entity at the given position, and return * the Node containing the new entity. * * @returns: the scene::INodePtr referring to the new entity. */ scene::INodePtr createEntityFromSelection(const std::string& name, const Vector3& origin) { // Obtain the structure containing the selection counts const SelectionInfo& info = GlobalSelectionSystem().getSelectionInfo(); IEntityClassPtr entityClass = GlobalEntityClassManager().findOrInsert(name, true); // TODO: to be replaced by inheritance-based class detection bool isModel = (info.totalCount == 0 && name == "func_static"); // Some entities are based on the size of the currently-selected primitive(s) bool primitivesSelected = info.brushCount > 0 || info.patchCount > 0; if (!(entityClass->isFixedSize() || isModel) && !primitivesSelected) { throw EntityCreationException( (boost::format(_("Unable to create entity %s, no brushes selected.")) % name).str() ); } // Get the selection workzone bounds AABB workzone = GlobalSelectionSystem().getWorkZone().bounds; // Create the new node for the entity IEntityNodePtr node(GlobalEntityCreator().createEntity(entityClass)); GlobalSceneGraph().root()->addChildNode(node); // The layer list we're moving the newly created node/subgraph into scene::LayerList targetLayers; if (entityClass->isFixedSize() || (isModel && !primitivesSelected)) { selection::algorithm::deleteSelection(); ITransformablePtr transform = Node_getTransformable(node); if (transform != 0) { transform->setType(TRANSFORM_PRIMITIVE); transform->setTranslation(origin); transform->freezeTransform(); } GlobalSelectionSystem().setSelectedAll(false); // Move the item to the active layer targetLayers.insert(GlobalLayerSystem().getActiveLayer()); Node_setSelected(node, true); } else // brush-based entity { // Add selected brushes as children of non-fixed entity node->getEntity().setKeyValue("model", node->getEntity().getKeyValue("name")); // Take the selection center as new origin Vector3 newOrigin = selection::algorithm::getCurrentSelectionCenter(); node->getEntity().setKeyValue("origin", string::to_string(newOrigin)); // If there is an "editor_material" class attribute, apply this shader // to all of the selected primitives before parenting them std::string material = node->getEntity().getEntityClass()->getAttribute("editor_material").getValue(); if (!material.empty()) { selection::algorithm::applyShaderToSelection(material); } // If we had primitives to reparent, the new entity should inherit the layer info from them if (primitivesSelected) { scene::INodePtr primitive = GlobalSelectionSystem().ultimateSelected(); targetLayers = primitive->getLayers(); } else { // Otherwise move the item to the active layer targetLayers.insert(GlobalLayerSystem().getActiveLayer()); } // Parent the selected primitives to the new node selection::algorithm::ParentPrimitivesToEntityWalker walker(node); GlobalSelectionSystem().foreachSelected(walker); walker.reparent(); // De-select the children and select the newly created parent entity GlobalSelectionSystem().setSelectedAll(false); Node_setSelected(node, true); } // Assign the layers - including all child nodes (#2864) scene::AssignNodeToLayersWalker layerWalker(targetLayers); Node_traverseSubgraph(node, layerWalker); // Set the light radius and origin if (entityClass->isLight() && primitivesSelected) { AABB bounds(Doom3Light_getBounds(workzone)); node->getEntity().setKeyValue("origin", string::to_string(bounds.getOrigin())); node->getEntity().setKeyValue("light_radius", string::to_string(bounds.getExtents())); } // Flag the map as unsaved after creating the entity GlobalMap().setModified(true); // Check for auto-setting key values. TODO: use forEachClassAttribute // directly here. eclass::AttributeList list = eclass::getSpawnargsWithPrefix( *entityClass, "editor_setKeyValue" ); if (!list.empty()) { for (eclass::AttributeList::const_iterator i = list.begin(); i != list.end(); ++i) { // Cut off the "editor_setKeyValueN " string from the key to get the spawnarg name std::string key = i->getName().substr(i->getName().find_first_of(' ') + 1); node->getEntity().setKeyValue(key, i->getValue()); } } // Return the new node return node; }
void post( const scene::Path& path, scene::Instance& instance ) const { Entity* entity = Node_getEntity( path.top() ); if ( entity != 0 && ( instance.childSelected() || Instance_getSelectable( instance )->isSelected() ) ) { if( path.top().get_pointer() == m_world ){ /* do not want to convert whole worldspawn entity */ if( instance.childSelected() && !m_2world ){ /* create an entity from world brushes instead */ EntityClass* entityClass = GlobalEntityClassManager().findOrInsert( m_classname, true ); if( entityClass->fixedsize ) return; //is important to have retexturing here; if doing in the end, undo doesn't succeed; //don't do this extra now, as it requires retexturing, working for subgraph // if ( string_compare_nocase_n( m_classname, "trigger_", 8 ) == 0 ){ // Scene_PatchSetShader_Selected( GlobalSceneGraph(), GetCommonShader( "trigger" ).c_str() ); // Scene_BrushSetShader_Selected( GlobalSceneGraph(), GetCommonShader( "trigger" ).c_str() ); // } NodeSmartReference node( GlobalEntityCreator().createEntity( entityClass ) ); Node_getTraversable( GlobalSceneGraph().root() )->insert( node ); scene::Path entitypath( makeReference( GlobalSceneGraph().root() ) ); entitypath.push( makeReference( node.get() ) ); scene::Instance& entityInstance = findInstance( entitypath ); if ( g_pGameDescription->mGameType == "doom3" ) { Node_getEntity( node )->setKeyValue( "model", Node_getEntity( node )->getKeyValue( "name" ) ); } //Scene_parentSelectedBrushesToEntity( GlobalSceneGraph(), node ); Scene_parentSubgraphSelectedBrushesToEntity( GlobalSceneGraph(), node, path ); Scene_forEachChildSelectable( SelectableSetSelected( true ), entityInstance.path() ); } return; } else if( m_2world ){ /* ungroupSelectedEntities */ //condition is skipped with world = 0, so code next to this may create multiple worldspawns; todo handle this very special case? if( node_is_group( path.top() ) ){ parentBrushes( path.top(), *m_world ); Path_deleteTop( path ); } return; } EntityClass* eclass = GlobalEntityClassManager().findOrInsert( m_classname, node_is_group( path.top() ) ); NodeSmartReference node( GlobalEntityCreator().createEntity( eclass ) ); if( entity->isContainer() && eclass->fixedsize ){ /* group entity to point one */ char value[64]; sprintf( value, "%g %g %g", instance.worldAABB().origin[0], instance.worldAABB().origin[1], instance.worldAABB().origin[2] ); entity->setKeyValue( "origin", value ); } EntityCopyingVisitor visitor( *Node_getEntity( node ) ); // entity->forEachKeyValue( visitor ); NodeSmartReference child( path.top().get() ); NodeSmartReference parent( path.parent().get() ); // Node_getTraversable( parent )->erase( child ); if ( Node_getTraversable( child ) != 0 && node_is_group( node ) ) { /* group entity to group one */ parentBrushes( child, node ); } Node_getTraversable( parent )->insert( node ); entity->forEachKeyValue( visitor ); /* must do this after inserting node, otherwise problem: targeted + having model + not loaded b4 new entities aren't selectable normally + rendered only while 0 0 0 is rendered */ if( !entity->isContainer() && !eclass->fixedsize ){ /* point entity to group one */ AABB bounds( g_vector3_identity, Vector3( 16, 16, 16 ) ); if ( !string_parse_vector3( entity->getKeyValue( "origin" ), bounds.origin ) ) { bounds.origin = g_vector3_identity; } Brush_ConstructPlacehoderCuboid( node.get(), bounds ); Node_getEntity( node )->setKeyValue( "origin", "" ); } Node_getTraversable( parent )->erase( child ); } }
void Entity_createFromSelection( const char* name, const Vector3& origin ){ #if 0 if ( string_equal_nocase( name, "worldspawn" ) ) { gtk_MessageBox( GTK_WIDGET( MainFrame_getWindow() ), "Can't create an entity with worldspawn.", "info" ); return; } #else const scene::Node* world_node = Map_FindWorldspawn( g_map ); if ( world_node && string_equal( name, "worldspawn" ) ) { // GlobalRadiant().m_pfnMessageBox( GTK_WIDGET( MainFrame_getWindow() ), "There's already a worldspawn in your map!", "Info", eMB_OK, eMB_ICONDEFAULT ); UndoableCommand undo( "ungroupSelectedPrimitives" ); Scene_parentSelectedBrushesToEntity( GlobalSceneGraph(), Map_FindOrInsertWorldspawn( g_map ) ); //=no action, if no worldspawn (but one inserted) (since insertion deselects everything) //Scene_parentSelectedBrushesToEntity( GlobalSceneGraph(), *Map_FindWorldspawn( g_map ) ); = crash, if no worldspawn return; } #endif StringOutputStream command; command << "entityCreate -class " << name; UndoableCommand undo( command.c_str() ); EntityClass* entityClass = GlobalEntityClassManager().findOrInsert( name, true ); const bool isModel = entityClass->miscmodel_is || ( GlobalSelectionSystem().countSelected() == 0 && classname_equal( name, "func_static" ) && g_pGameDescription->mGameType == "doom3" ); const bool brushesSelected = Scene_countSelectedBrushes( GlobalSceneGraph() ) != 0; //is important to have retexturing here; if doing in the end, undo doesn't succeed; if ( string_compare_nocase_n( name, "trigger_", 8 ) == 0 && brushesSelected && !entityClass->fixedsize ){ //const char* shader = GetCommonShader( "trigger" ).c_str(); Scene_PatchSetShader_Selected( GlobalSceneGraph(), GetCommonShader( "trigger" ).c_str() ); Scene_BrushSetShader_Selected( GlobalSceneGraph(), GetCommonShader( "trigger" ).c_str() ); } if ( !( entityClass->fixedsize || isModel ) && !brushesSelected ) { globalErrorStream() << "failed to create a group entity - no brushes are selected\n"; return; } AABB workzone( aabb_for_minmax( Select_getWorkZone().d_work_min, Select_getWorkZone().d_work_max ) ); NodeSmartReference node( GlobalEntityCreator().createEntity( entityClass ) ); Node_getTraversable( GlobalSceneGraph().root() )->insert( node ); scene::Path entitypath( makeReference( GlobalSceneGraph().root() ) ); entitypath.push( makeReference( node.get() ) ); scene::Instance& instance = findInstance( entitypath ); if ( entityClass->fixedsize || ( isModel && !brushesSelected ) ) { //Select_Delete(); Transformable* transform = Instance_getTransformable( instance ); if ( transform != 0 ) { transform->setType( TRANSFORM_PRIMITIVE ); transform->setTranslation( origin ); transform->freezeTransform(); } GlobalSelectionSystem().setSelectedAll( false ); Instance_setSelected( instance, true ); } else { if ( g_pGameDescription->mGameType == "doom3" ) { Node_getEntity( node )->setKeyValue( "model", Node_getEntity( node )->getKeyValue( "name" ) ); } Scene_parentSelectedBrushesToEntity( GlobalSceneGraph(), node ); Scene_forEachChildSelectable( SelectableSetSelected( true ), instance.path() ); } // tweaking: when right click dropping a light entity, ask for light value in a custom dialog box // see SF bug 105383 if ( g_pGameDescription->mGameType == "hl" ) { // FIXME - Hydra: really we need a combined light AND color dialog for halflife. if ( string_equal_nocase( name, "light" ) || string_equal_nocase( name, "light_environment" ) || string_equal_nocase( name, "light_spot" ) ) { int intensity = g_iLastLightIntensity; if ( DoLightIntensityDlg( &intensity ) == eIDOK ) { g_iLastLightIntensity = intensity; char buf[30]; sprintf( buf, "255 255 255 %d", intensity ); Node_getEntity( node )->setKeyValue( "_light", buf ); } } } else if ( string_equal_nocase( name, "light" ) ) { if ( g_pGameDescription->mGameType != "doom3" ) { int intensity = g_iLastLightIntensity; if ( DoLightIntensityDlg( &intensity ) == eIDOK ) { g_iLastLightIntensity = intensity; char buf[10]; sprintf( buf, "%d", intensity ); Node_getEntity( node )->setKeyValue( "light", buf ); } } else if ( brushesSelected ) { // use workzone to set light position/size for doom3 lights, if there are brushes selected AABB bounds( Doom3Light_getBounds( workzone ) ); StringOutputStream key( 64 ); key << bounds.origin[0] << " " << bounds.origin[1] << " " << bounds.origin[2]; Node_getEntity( node )->setKeyValue( "origin", key.c_str() ); key.clear(); key << bounds.extents[0] << " " << bounds.extents[1] << " " << bounds.extents[2]; Node_getEntity( node )->setKeyValue( "light_radius", key.c_str() ); } } if ( isModel ) { const char* model = misc_model_dialog( GTK_WIDGET( MainFrame_getWindow() ) ); if ( model != 0 ) { Node_getEntity( node )->setKeyValue( entityClass->miscmodel_key() , model ); } } }
void ToggleShowLightRadii(){ GlobalEntityCreator().setLightRadii( !GlobalEntityCreator().getLightRadii() ); g_show_lightradii_item.update(); UpdateAllWindows(); }
void BuildDoorsX2(vec3_t min, vec3_t max, bool bSclMainHor, bool bSclMainVert, bool bSclTrimHor, bool bSclTrimVert, const char* mainTexture, const char* trimTexture, int direction) { int xy; if(direction == 0) xy = 0; else xy = 1; //----- Build Outer Bounds --------- vec3_t v1, v2, v3, v5, v6, v7, ve_1, ve_2, ve_3; VectorCopy(min, v1); VectorCopy(min, v2); VectorCopy(min, v3); VectorCopy(max, v5); VectorCopy(max, v6); VectorCopy(max, v7); v2[0] = max[0]; v3[1] = max[1]; v6[0] = min[0]; v7[1] = min[1]; float width = (max[xy] - min[xy])/2; if(direction == 0) { VectorCopy(v1, ve_1); VectorCopy(v3, ve_2); VectorCopy(v6, ve_3); } else { VectorCopy(v7, ve_1); VectorCopy(v1, ve_2); VectorCopy(v2, ve_3); } ve_1[xy] += width; ve_2[xy] += width; ve_3[xy] += width; //---------------------------------- scene::Node* newBrush1 = Brush_AllocNode(); scene::Node* newBrush2 = Brush_AllocNode(); AddFaceWithTexture(newBrush1, v1, v2, v3, "textures/common/caulk", FALSE); AddFaceWithTexture(newBrush1, v5, v7, v6, "textures/common/caulk", FALSE); AddFaceWithTexture(newBrush2, v1, v2, v3, "textures/common/caulk", FALSE); AddFaceWithTexture(newBrush2, v5, v7, v6, "textures/common/caulk", FALSE); if(direction == 0) { AddFaceWithTexture(newBrush1, v1, v3, v6, "textures/common/caulk", FALSE); AddFaceWithTexture(newBrush2, v5, v2, v7, "textures/common/caulk", FALSE); } else { AddFaceWithTexture(newBrush1, v1, v7, v2, "textures/common/caulk", FALSE); AddFaceWithTexture(newBrush2, v5, v6, v3, "textures/common/caulk", FALSE); } if(direction == 0) { AddFaceWithTextureScaled(newBrush1, v1, v7, v2, mainTexture, bSclMainVert, bSclMainHor, min[0], min[2], max[0], max[2]); AddFaceWithTextureScaled(newBrush1, v5, v6, v3, mainTexture, bSclMainVert, bSclMainHor, max[0], min[2], min[0], max[2]); AddFaceWithTextureScaled(newBrush2, v1, v7, v2, mainTexture, bSclMainVert, bSclMainHor, min[0], min[2], max[0], max[2]); AddFaceWithTextureScaled(newBrush2, v5, v6, v3, mainTexture, bSclMainVert, bSclMainHor, max[0], min[2], min[0], max[2]); // flip max/min to reverse tex dir AddFaceWithTextureScaled(newBrush1, ve_3, ve_2, ve_1, trimTexture, bSclTrimVert, bSclTrimHor, min[1], min[2], max[1], max[2]); AddFaceWithTextureScaled(newBrush2, ve_1, ve_2, ve_3, trimTexture, bSclTrimVert, bSclTrimHor, max[1], min[2], min[1], max[2]); } else { AddFaceWithTextureScaled(newBrush1, v1, v3, v6, mainTexture, bSclMainVert, bSclMainHor, min[1], min[2], max[1], max[2]); AddFaceWithTextureScaled(newBrush1, v5, v2, v7, mainTexture, bSclMainVert, bSclMainHor, max[1], min[2], min[1], max[2]); AddFaceWithTextureScaled(newBrush2, v1, v3, v6, mainTexture, bSclMainVert, bSclMainHor, min[1], min[2], max[1], max[2]); AddFaceWithTextureScaled(newBrush2, v5, v2, v7, mainTexture, bSclMainVert, bSclMainHor, max[1], min[2], min[1], max[2]); // flip max/min to reverse tex dir AddFaceWithTextureScaled(newBrush1, ve_1, ve_2, ve_3, trimTexture, bSclTrimVert, bSclTrimHor, min[0], min[2], max[0], max[2]); AddFaceWithTextureScaled(newBrush2, ve_3, ve_2, ve_1, trimTexture, bSclTrimVert, bSclTrimHor, max[0], min[2], min[0], max[2]); } //---------------------------------- scene::Node* pEDoor1 = GlobalEntityCreator().createEntity("func_door"); scene::Node* pEDoor2 = GlobalEntityCreator().createEntity("func_door"); if(direction == 0) { pEDoor1->m_entity->setkeyvalue("angle", "180"); pEDoor2->m_entity->setkeyvalue("angle", "360"); } else { pEDoor1->m_entity->setkeyvalue("angle", "270"); pEDoor2->m_entity->setkeyvalue("angle", "90"); } srand((unsigned)time(NULL)); char teamname[256]; sprintf(teamname, "t%i", rand()); pEDoor1->m_entity->setkeyvalue("team", teamname); pEDoor2->m_entity->setkeyvalue("team", teamname); pEDoor1->m_traverse->insert(newBrush1); pEDoor2->m_traverse->insert(newBrush2); GlobalSceneGraph().root()->m_traverse->insert(pEDoor1); GlobalSceneGraph().root()->m_traverse->insert(pEDoor2); // ResetCurrentTexture(); }
static bool Entity_create (const std::string& name, const Vector3& origin) { EntityClass* entityClass = GlobalEntityClassManager().findOrInsert(name, true); bool revert = false; const bool isModel = (name == "misc_model"); const bool isSound = (name == "misc_sound"); const bool isParticle = (name == "misc_particle"); const bool isStartingPositionActor = (name == "info_player_start") || (name == "info_human_start") || (name == "info_alien_start") || (name == "info_civilian_start"); const bool isStartingPositionUGV = (name == "info_2x2_start"); const bool isStartingPosition = isStartingPositionActor || isStartingPositionUGV; const bool brushesSelected = map::countSelectedBrushes() != 0; if (!(entityClass->fixedsize || isModel) && !brushesSelected) { throw EntityCreationException(std::string("Unable to create entity \"") + name + "\", no brushes selected"); } UndoableCommand undo("entityCreate -class " + name); AABB workzone(AABB::createFromMinMax(GlobalSelectionSystem().getWorkZone().min, GlobalSelectionSystem().getWorkZone().max)); NodeSmartReference node(GlobalEntityCreator().createEntity(entityClass)); Node_getTraversable(GlobalSceneGraph().root())->insert(node); scene::Path entitypath(makeReference(GlobalSceneGraph().root())); entitypath.push(makeReference(node.get())); scene::Instance& instance = findInstance(entitypath); // set all mandatory fields to default values // some will be overwritten later Entity *entity = Node_getEntity(node); entity->addMandatoryKeyValues(); if (entityClass->fixedsize || (isModel && !brushesSelected)) { selection::algorithm::deleteSelection(); Transformable* transform = Instance_getTransformable(instance); if (transform != 0) { transform->setType(TRANSFORM_PRIMITIVE); if (isStartingPosition) { const int sizeX = (int) ((entityClass->maxs[0] - entityClass->mins[0]) / 2.0); const int sizeY = (int) ((entityClass->maxs[1] - entityClass->mins[1]) / 2.0); const int sizeZ = (int) ((entityClass->maxs[2] - entityClass->mins[2]) / 2.0); const int x = ((int) origin.x() / UNIT_SIZE) * UNIT_SIZE - sizeX; const int y = ((int) origin.y() / UNIT_SIZE) * UNIT_SIZE - sizeY; const int z = ((int) origin.z() / UNIT_HEIGHT) * UNIT_HEIGHT + sizeZ; const Vector3 vec(x, y, z); transform->setTranslation(vec); } else { transform->setTranslation(origin); } transform->freezeTransform(); } GlobalSelectionSystem().setSelectedAll(false); Instance_setSelected(instance, true); } else { // Add selected brushes as children of non-fixed entity Scene_parentSelectedBrushesToEntity(GlobalSceneGraph(), node); Scene_forEachChildSelectable(SelectableSetSelected(true), instance.path()); } // TODO tweaking: when right click dropping a light entity, ask for light value in a custom dialog box if (name == "light" || name == "light_spot") { ui::LightDialog dialog; dialog.show(); if (!dialog.isAborted()) { std::string intensity = dialog.getIntensity(); Vector3 color = dialog.getColor(); entity->setKeyValue("light", intensity); entity->setKeyValue("_color", color.toString()); } else revert = true; } if (isModel) { ui::ModelAndSkin modelAndSkin = ui::ModelSelector::chooseModel(); if (!modelAndSkin.model.empty()) { entity->setKeyValue("model", modelAndSkin.model); if (modelAndSkin.skin != -1) entity->setKeyValue("skin", string::toString(modelAndSkin.skin)); } else revert = true; } else if (isSound) { // Display the Sound Chooser to get a sound from the user ui::SoundChooser sChooser; std::string sound = sChooser.chooseSound(); if (!sound.empty()) entity->setKeyValue("noise", sound); else revert = true; } else if (isParticle) { ui::ParticleSelector pSelector; std::string particle = pSelector.chooseParticle(); if (!particle.empty()) entity->setKeyValue("particle", particle); else revert = true; } return revert; }
void Entity_createFromSelection(const char* name, const Vector3& origin) { #if 0 if(string_equal_nocase(name, "worldspawn")) { gtk_MessageBox(GTK_WIDGET(MainFrame_getWindow()), "Can't create an entity with worldspawn.", "info"); return; } #endif EntityClass* entityClass = GlobalEntityClassManager().findOrInsert(name, true); bool isModel = string_equal_nocase(name, "misc_model") || string_equal_nocase(name, "misc_gamemodel") || string_equal_nocase(name, "model_static") || (GlobalSelectionSystem().countSelected() == 0 && string_equal_nocase(name, "func_static")); if(!(entityClass->fixedsize || isModel) && Scene_countSelectedBrushes(GlobalSceneGraph()) == 0) { globalErrorStream() << "failed to create a group entity - no brushes are selected\n"; return; } NodeSmartReference node(GlobalEntityCreator().createEntity(entityClass)); Node_getTraversable(GlobalSceneGraph().root())->insert(node); scene::Path entitypath(makeReference(GlobalSceneGraph().root())); entitypath.push(makeReference(node.get())); scene::Instance& instance = findInstance(entitypath); if(entityClass->fixedsize) { Select_Delete(); Transformable* transform = Instance_getTransformable(instance); if(transform != 0) { transform->setType(TRANSFORM_PRIMITIVE); transform->setTranslation(origin); transform->freezeTransform(); } GlobalSelectionSystem().setSelectedAll(false); Instance_setSelected(instance, true); } else { Scene_parentSelectedBrushesToEntity(GlobalSceneGraph(), node); Scene_forEachChildSelectable(SelectableSetSelected(true), instance.path()); } // tweaking: when right clic dropping a light entity, ask for light value in a custom dialog box // see SF bug 105383 if (g_pGameDescription->mGameType == "hl") { // FIXME - Hydra: really we need a combined light AND color dialog for halflife. if (string_equal_nocase(name, "light") || string_equal_nocase(name, "light_environment") || string_equal_nocase(name, "light_spot")) { int intensity = g_iLastLightIntensity; if (DoLightIntensityDlg (&intensity) == eIDOK) { g_iLastLightIntensity = intensity; char buf[30]; sprintf( buf, "255 255 255 %d", intensity ); Node_getEntity(node)->setKeyValue("_light", buf); } } } else if(g_pGameDescription->mGameType != "doom3" && string_equal_nocase(name, "light")) { int intensity = g_iLastLightIntensity; if (DoLightIntensityDlg (&intensity) == eIDOK) { g_iLastLightIntensity = intensity; char buf[10]; sprintf( buf, "%d", intensity ); Node_getEntity(node)->setKeyValue("light", buf); } } if(isModel) { const char* model = misc_model_dialog(GTK_WIDGET(MainFrame_getWindow())); if(model != 0) { Node_getEntity(node)->setKeyValue("model", model); } } }
void ShowLightRadiiExport( const BoolImportCallback& importer ){ importer( GlobalEntityCreator().getLightRadii() ); }
void BuildDoorsX2(vec3_t min, vec3_t max, bool bSclMainHor, bool bSclMainVert, bool bSclTrimHor, bool bSclTrimVert, const char* mainTexture, const char* trimTexture, int direction) { int xy; if(direction == 0) xy = 0; else xy = 1; //----- Build Outer Bounds --------- vec3_t v1, v2, v3, v5, v6, v7, ve_1, ve_2, ve_3; VectorCopy(min, v1); VectorCopy(min, v2); VectorCopy(min, v3); VectorCopy(max, v5); VectorCopy(max, v6); VectorCopy(max, v7); v2[0] = max[0]; v3[1] = max[1]; v6[0] = min[0]; v7[1] = min[1]; float width = (max[xy] - min[xy])/2; if(direction == 0) { VectorCopy(v1, ve_1); VectorCopy(v3, ve_2); VectorCopy(v6, ve_3); } else { VectorCopy(v7, ve_1); VectorCopy(v1, ve_2); VectorCopy(v2, ve_3); } ve_1[xy] += width; ve_2[xy] += width; ve_3[xy] += width; //---------------------------------- NodeSmartReference newBrush1(GlobalBrushCreator().createBrush()); NodeSmartReference newBrush2(GlobalBrushCreator().createBrush()); AddFaceWithTexture(newBrush1, v1, v2, v3, "textures/common/caulk", false); AddFaceWithTexture(newBrush1, v5, v7, v6, "textures/common/caulk", false); AddFaceWithTexture(newBrush2, v1, v2, v3, "textures/common/caulk", false); AddFaceWithTexture(newBrush2, v5, v7, v6, "textures/common/caulk", false); if(direction == 0) { AddFaceWithTexture(newBrush1, v1, v3, v6, "textures/common/caulk", false); AddFaceWithTexture(newBrush2, v5, v2, v7, "textures/common/caulk", false); } else { AddFaceWithTexture(newBrush1, v1, v7, v2, "textures/common/caulk", false); AddFaceWithTexture(newBrush2, v5, v6, v3, "textures/common/caulk", false); } if(direction == 0) { AddFaceWithTextureScaled(newBrush1, v1, v7, v2, mainTexture, bSclMainVert, bSclMainHor, min[0], min[2], max[0], max[2]); AddFaceWithTextureScaled(newBrush1, v5, v6, v3, mainTexture, bSclMainVert, bSclMainHor, max[0], min[2], min[0], max[2]); AddFaceWithTextureScaled(newBrush2, v1, v7, v2, mainTexture, bSclMainVert, bSclMainHor, min[0], min[2], max[0], max[2]); AddFaceWithTextureScaled(newBrush2, v5, v6, v3, mainTexture, bSclMainVert, bSclMainHor, max[0], min[2], min[0], max[2]); // flip max/min to reverse tex dir AddFaceWithTextureScaled(newBrush1, ve_3, ve_2, ve_1, trimTexture, bSclTrimVert, bSclTrimHor, min[1], min[2], max[1], max[2]); AddFaceWithTextureScaled(newBrush2, ve_1, ve_2, ve_3, trimTexture, bSclTrimVert, bSclTrimHor, max[1], min[2], min[1], max[2]); } else { AddFaceWithTextureScaled(newBrush1, v1, v3, v6, mainTexture, bSclMainVert, bSclMainHor, min[1], min[2], max[1], max[2]); AddFaceWithTextureScaled(newBrush1, v5, v2, v7, mainTexture, bSclMainVert, bSclMainHor, max[1], min[2], min[1], max[2]); AddFaceWithTextureScaled(newBrush2, v1, v3, v6, mainTexture, bSclMainVert, bSclMainHor, min[1], min[2], max[1], max[2]); AddFaceWithTextureScaled(newBrush2, v5, v2, v7, mainTexture, bSclMainVert, bSclMainHor, max[1], min[2], min[1], max[2]); // flip max/min to reverse tex dir AddFaceWithTextureScaled(newBrush1, ve_1, ve_2, ve_3, trimTexture, bSclTrimVert, bSclTrimHor, min[0], min[2], max[0], max[2]); AddFaceWithTextureScaled(newBrush2, ve_3, ve_2, ve_1, trimTexture, bSclTrimVert, bSclTrimHor, max[0], min[2], min[0], max[2]); } //---------------------------------- EntityClass* doorClass = GlobalEntityClassManager().findOrInsert("func_door", true); NodeSmartReference pEDoor1(GlobalEntityCreator().createEntity(doorClass)); NodeSmartReference pEDoor2(GlobalEntityCreator().createEntity(doorClass)); if(direction == 0) { Node_getEntity(pEDoor1)->setKeyValue("angle", "180"); Node_getEntity(pEDoor2)->setKeyValue("angle", "360"); } else { Node_getEntity(pEDoor1)->setKeyValue("angle", "270"); Node_getEntity(pEDoor2)->setKeyValue("angle", "90"); } srand((unsigned)time(NULL)); char teamname[256]; sprintf(teamname, "t%i", rand()); Node_getEntity(pEDoor1)->setKeyValue("team", teamname); Node_getEntity(pEDoor2)->setKeyValue("team", teamname); Node_getTraversable(pEDoor1)->insert(newBrush1); Node_getTraversable(pEDoor2)->insert(newBrush2); Node_getTraversable(GlobalSceneGraph().root())->insert(pEDoor1); Node_getTraversable(GlobalSceneGraph().root())->insert(pEDoor2); // ResetCurrentTexture(); }
void Entity_constructPreferences( PreferencesPage& page ){ page.appendCheckBox( "Show", "Light Radii", make_property<LightRadii>(GlobalEntityCreator()) ); }
void Entity_createFromSelection( const char* name, const Vector3& origin ){ #if 0 if ( string_equal_nocase( name, "worldspawn" ) ) { ui::alert( MainFrame_getWindow( ), "Can't create an entity with worldspawn.", "info" ); return; } #endif EntityClass* entityClass = GlobalEntityClassManager().findOrInsert( name, true ); bool isModel = ( string_compare_nocase_n( name, "misc_", 5 ) == 0 && string_equal_nocase( name + string_length( name ) - 5, "model" ) ) // misc_*model (also misc_model) || string_equal_nocase( name, "model_static" ) || ( GlobalSelectionSystem().countSelected() == 0 && string_equal_nocase( name, "func_static" ) ); bool brushesSelected = Scene_countSelectedBrushes( GlobalSceneGraph() ) != 0; if ( !( entityClass->fixedsize || isModel ) && !brushesSelected ) { globalErrorStream() << "failed to create a group entity - no brushes are selected\n"; return; } AABB workzone( aabb_for_minmax( Select_getWorkZone().d_work_min, Select_getWorkZone().d_work_max ) ); NodeSmartReference node( GlobalEntityCreator().createEntity( entityClass ) ); Node_getTraversable( GlobalSceneGraph().root() )->insert( node ); scene::Path entitypath( makeReference( GlobalSceneGraph().root() ) ); entitypath.push( makeReference( node.get() ) ); scene::Instance& instance = findInstance( entitypath ); if ( entityClass->fixedsize || ( isModel && !brushesSelected ) ) { Select_Delete(); Transformable* transform = Instance_getTransformable( instance ); if ( transform != 0 ) { transform->setType( TRANSFORM_PRIMITIVE ); transform->setTranslation( origin ); transform->freezeTransform(); } GlobalSelectionSystem().setSelectedAll( false ); Instance_setSelected( instance, true ); } else { if ( g_pGameDescription->mGameType == "doom3" ) { Node_getEntity( node )->setKeyValue( "model", Node_getEntity( node )->getKeyValue( "name" ) ); } Scene_parentSelectedBrushesToEntity( GlobalSceneGraph(), node ); Scene_forEachChildSelectable( SelectableSetSelected( true ), instance.path() ); } // tweaking: when right clic dropping a light entity, ask for light value in a custom dialog box // see SF bug 105383 if ( g_pGameDescription->mGameType == "hl" ) { // FIXME - Hydra: really we need a combined light AND color dialog for halflife. if ( string_equal_nocase( name, "light" ) || string_equal_nocase( name, "light_environment" ) || string_equal_nocase( name, "light_spot" ) ) { int intensity = g_iLastLightIntensity; if ( DoLightIntensityDlg( &intensity ) == eIDOK ) { g_iLastLightIntensity = intensity; char buf[30]; sprintf( buf, "255 255 255 %d", intensity ); Node_getEntity( node )->setKeyValue( "_light", buf ); } } } else if ( string_equal_nocase( name, "light" ) ) { if ( g_pGameDescription->mGameType != "doom3" ) { int intensity = g_iLastLightIntensity; if ( DoLightIntensityDlg( &intensity ) == eIDOK ) { g_iLastLightIntensity = intensity; char buf[10]; sprintf( buf, "%d", intensity ); Node_getEntity( node )->setKeyValue( "light", buf ); } } else if ( brushesSelected ) { // use workzone to set light position/size for doom3 lights, if there are brushes selected AABB bounds( Doom3Light_getBounds( workzone ) ); StringOutputStream key( 64 ); key << bounds.origin[0] << " " << bounds.origin[1] << " " << bounds.origin[2]; Node_getEntity( node )->setKeyValue( "origin", key.c_str() ); key.clear(); key << bounds.extents[0] << " " << bounds.extents[1] << " " << bounds.extents[2]; Node_getEntity( node )->setKeyValue( "light_radius", key.c_str() ); } } if ( isModel ) { const char* model = misc_model_dialog(MainFrame_getWindow()); if ( model != 0 ) { Node_getEntity( node )->setKeyValue( "model", model ); } } }