TOOL.Category = "Conna's Tools" TOOL.Name = "#Position Switcher Tool" TOOL.Command = nil TOOL.ConfigName = "" // Settings TOOL.Sel = {} TOOL.Sel[1] = nil TOOL.Sel[2] = nil // ConVars TOOL.ClientConVar["Key"] = "5" TOOL.ClientConVar["Ghost"] = "1" // Client if (CLIENT) then language.Add("Tool_positionswitcher_name", "Position Switcher Tool") language.Add("Tool_positionswitcher_desc", "Switch an entity between two positions") language.Add("Tool_positionswitcher_0", "Create two entities the same model and select them both with this tool") language.Add("Undone_positionswitcher", "Undone Position Switcher") end // Message function TOOL:Message(Text) if SERVER then self:GetOwner():SendLua("GAMEMODE:AddNotify('"..Text.."', NOTIFY_GENERIC, 10)") self:GetOwner():SendLua("surface.PlaySound('ambient/water/drip"..math.random(1, 4)..".wav')") end end // Left click function TOOL:LeftClick(Trace) if Trace.Entity then if !Trace.Entity:IsValid() or Trace.Entity:IsPlayer() or Trace.HitWorld or Trace.Entity:IsNPC() then return false end end if(CLIENT) then return true end if(!SERVER) then return false end if (Trace.Entity.PositionSwitcher) then self:Message("This entity is already part of a Position Switcher!") return false end if not self.Sel[1] then self.Sel[1] = Trace.Entity self:Message("First entity has been selected!") return true end if not (self.Sel[2]) then if (self.Sel[1]:IsValid()) then self.Sel[2] = Trace.Entity local Key = self:GetClientNumber("Key") Trace.Entity.PositionSwitcher = {} Trace.Entity.PositionSwitcher.Current = 2 Trace.Entity.PositionSwitcher.FirstPosition = self.Sel[1]:GetPos() Trace.Entity.PositionSwitcher.SecondPosition = self.Sel[2]:GetPos() Trace.Entity.PositionSwitcher.FirstAngle = self.Sel[1]:GetAngles() Trace.Entity.PositionSwitcher.SecondAngle = self.Sel[2]:GetAngles() if (Wire_CreateOutputs) then Trace.Entity.Outputs = Wire_CreateOutputs(Trace.Entity, {"Position"}) end if (Wire_TriggerOutput) then Wire_TriggerOutput(Trace.Entity, "Position", 2) end local Ghost = self:GetClientNumber("Ghost") local Table = {} if Ghost == 1 then for I = 1, 2 do Table[I] = ents.Create(self.Sel[I]:GetClass()) Table[I]:SetPos(self.Sel[I]:GetPos()) Table[I]:SetAngles(self.Sel[I]:GetAngles()) Table[I]:SetModel(self.Sel[I]:GetModel()) Table[I]:SetMoveType(MOVETYPE_NONE) Table[I]:SetNotSolid(true) Table[I]:PhysicsInit(SOLID_VPHYSICS) Table[I]:SetCollisionGroup(COLLISION_GROUP_DEBRIS) Table[I]:DrawShadow(false) Table[I]:SetRenderMode(3) Table[I]:SetColor(255, 255, 255, 100) Table[I]:Spawn() local Phys = Table[I]:GetPhysicsObject() if Phys then Phys:EnableMotion(false) end Table[I].PositionSwitcher = {} end local Phys = Trace.Entity:GetPhysicsObject() if Phys then Phys:EnableMotion(false) end Trace.Entity.PositionSwitcher.FirstGhost = Table[1] Trace.Entity.PositionSwitcher.SecondGhost = Table[2] Trace.Entity:DeleteOnRemove(Table[1]) Trace.Entity:DeleteOnRemove(Table[2]) end self.Sel[1]:Remove() Trace.Entity.PositionSwitcher.ID = numpad.OnUp(self:GetOwner(), Key, "Position.Toggle", Trace.Entity, false) self:Message("Second entity has been selected, now press "..Key.." to switch between positions!") local function Function(Undo, Entity) if (Entity:IsValid()) then numpad.Remove(Entity.PositionSwitcher.ID) Entity:SetPos(Entity.PositionSwitcher.SecondPosition) Entity:SetAngles(Entity.PositionSwitcher.SecondAngle) Entity.PositionSwitcher = nil end end undo.Create("positionswitcher") undo.AddEntity(self.Sel[1]) undo.AddEntity(self.Sel[2]) if (Table[1] and Table[2]) then undo.AddEntity(Table[1]) undo.AddEntity(Table[2]) end undo.AddFunction(Function, Trace.Entity) undo.SetPlayer(self:GetOwner()) undo.Finish() self.Sel[1] = nil self.Sel[2] = nil else self:Message("The first entity is no longer valid!") self.Sel[1] = nil end end return true end // Server if SERVER then // Pressed key function TOOL.Pressed(Player, Entity, Key, IDX) if !Entity:IsValid() then return end if not Key then local Pos = {} Pos[1] = Entity.PositionSwitcher.FirstPosition Pos[2] = Entity.PositionSwitcher.SecondPosition local Ang = {} Ang[1] = Entity.PositionSwitcher.FirstAngle Ang[2] = Entity.PositionSwitcher.SecondAngle if (Entity.PositionSwitcher.FirstGhost) then Pos[1] = Entity.PositionSwitcher.FirstGhost:GetPos() Ang[1] = Entity.PositionSwitcher.FirstGhost:GetAngles() end if (Entity.PositionSwitcher.SecondGhost) then Pos[2] = Entity.PositionSwitcher.SecondGhost:GetPos() Ang[2] = Entity.PositionSwitcher.SecondGhost:GetAngles() end if (Entity.PositionSwitcher.Current == 1) then Entity:SetPos(Pos[2]) Entity:SetAngles(Ang[2]) Entity.PositionSwitcher.Current = 2 else Entity:SetPos(Pos[1]) Entity:SetAngles(Ang[1]) Entity.PositionSwitcher.Current = 1 end if (Wire_TriggerOutput) then Wire_TriggerOutput(Entity, "Position", Entity.PositionSwitcher.Current) end local Phys = Entity:GetPhysicsObject() if Phys then Phys:EnableMotion(false) end end end numpad.Register("Position.Toggle", TOOL.Pressed) end // Build CPanel function TOOL.BuildCPanel(Panel) Panel:AddControl("Header", {Text = "#Tool_positionswitcher_name", Description = "#Tool_positionswitcher_desc"}) Panel:AddControl("Numpad", {Label = "Button", ButtonSize = "22", Command = "positionswitcher_Key"}) Panel:AddControl("Checkbox", {Label = "#Show a ghost of the two positions", Command = "positionswitcher_Ghost"}) end