/// <summary> /// Destroys a specific gate in the gate list /// </summary> /// <param name="GateIndex">The index in the CurrentGates list</param> public static void DestroyGate(int GateIndex) { // Store a temporary copy GateBehaviour CurrentGate = CurrentGates[GateIndex]; // Remove the gate CurrentGates.RemoveAt(GateIndex); // Then run the delete method CurrentGate.Delete(); }
private void Start() { EndPanel.SetActive(false); UnityEngine.Random.InitState(RaceParameters.Seed); GateBehaviour previousGate = null; for (var i = 0; i < NumberOfGate; i++) { var angle = UnityEngine.Random.value * (RaceParameters.MaxAngle * 2) - RaceParameters.MaxAngle; var distance = UnityEngine.Random.value * (RaceParameters.MaxDistance - RaceParameters.MinDistance) + RaceParameters.MinDistance; CurrentGatePosition += new Vector3(distance * Mathf.Sin(Mathf.Deg2Rad * angle), distance * Mathf.Cos(Mathf.Deg2Rad * angle), 0); var nextGate = Instantiate(GatePrefab, GateParent.transform, false); nextGate.transform.localPosition = CurrentGatePosition; previousGate = nextGate.GetComponent <GateBehaviour>(); previousGate.GateId = i; m_GateBehaviourDictionary.Add(i, previousGate); Debug.Log("Gate num" + i + " is placed at " + CurrentGatePosition); } m_TextList = new List <Text>(RaceParameters.NumberOfLap); for (var i = 0; i < RaceParameters.NumberOfLap; i++) { var go = Instantiate(LapTimePrefab, LapTimeParent.transform); var text = go.GetComponent <Text>(); text.text = "--:--:--"; m_TextList.Add(text); } m_CurrentTargetGate = 0; Player.SetNextGateTransform(m_GateBehaviourDictionary[0].transform); IsCourseOngoing = true; }
/// <summary> /// Spawns a logic gate in the world /// </summary> /// <param name="Gate">The gate type to spawn</param> /// <param name="Location">The world position to spawn it</param> public static GateBehaviour SpawnGate(LogicGate Gate, Vector2 Position) { // Check that there are no other gates nearby for (int i = 0; i < CurrentGates.Count; i++) { // If the distance is below a certain threshold, do not allow a gate to be placed if (Mathf.Pow(Vector2.Distance(Position, CurrentGates[i].transform.position), 2f) < 0.001f) { return(null); } } // Setup the object GameObject GateObject = new GameObject(); GateObject.transform.position = Position; GateObject.transform.localScale = Vector3.one * 0.2f; GateObject.name = "Gate (" + Gate.GateName + ")"; // name is just "Gate (Type)", using gate list count is gonna be odd :) GateObject.transform.parent = GateParent.transform; // Setup gate behaviour GateBehaviour GateScript = GateObject.AddComponent <GateBehaviour>(); GateScript.LogicGate = Gate; GateScript.Working = true; // Setup sprite renderer SpriteRenderer GateSR = GateObject.AddComponent <SpriteRenderer>(); GateSR.sprite = Gate.GateSprite; GateSR.sortingOrder = 3; // Add the gate to the list, bearing in mind we need the GateBehaviour CurrentGates.Add(GateScript); // Return the gate behaviour return(GateScript); }
void Start() { Tracker = this.transform.parent.GetComponent<TrackingTransformBehaviour>() as TrackingTransformBehaviour; Gate = this.transform.parent.GetComponent<GateBehaviour>() as GateBehaviour; }
/// <summary> /// Handles the input terminals /// </summary> void HandleInputClicking(float ButtonX, float ButtonY, float ButtonWidth, int Id, int ConnectionID) { // Handle wire dragging if (GUI.Button(new Rect(ButtonX, ButtonY, ButtonWidth, ButtonWidth), "", InputButtonStyle) && CurrentTool == PlayerTool.CreateWire) { if (!IsDraggingWire) { // Play sound PickupSound.Play(); // If source connected already, sever that connection // If source-connected already, delete connection if (Gates.CurrentGates[Id].Sources[ConnectionID] != null && Gates.CurrentGates[Id].Sources[ConnectionID] != Gates.CurrentGates[Id].EndConnection) { Gates.CurrentGates[Id].Sources[ConnectionID].RemoveConnections(Gates.CurrentGates[Id].Sources[ConnectionID].GetGateID(Gates.CurrentGates[Id])); } // Fetch all the details we need and set the player to be dragging IsDraggingWire = true; DraggingOutput = false; GateDraggingFrom = Gates.CurrentGates[Id]; GateDraggingFromInputID = ConnectionID; DraggingOrigin = new Vector2(ButtonX, Screen.height - ButtonY); } else if (IsDraggingWire && DraggingOutput && Gates.CurrentGates[Id] != GateDraggingFrom && !DraggingSource && !DraggingEnd) { // Play sound DropSound.Play(); // First stop the player from dragging anymore IsDraggingWire = false; DraggingEnd = false; DraggingSource = false; // Make sure to disconnect other wires if (Gates.CurrentGates[Id].InputGates[ConnectionID] != null) { // Get rid of the output connection Gates.CurrentGates[Id].InputGates[ConnectionID].OutputGate = null; // Get rid of the wire Destroy(Gates.CurrentGates[Id].InputGates[ConnectionID].WireObject.gameObject); // Get rid of the input connection Gates.CurrentGates[Id].InputGates[ConnectionID] = null; } // Then connect this gate to the one we dragged from Gates.CurrentGates[Id].InputGates[ConnectionID] = GateDraggingFrom; // And connect the one we dragged from to this gate GateDraggingFrom.OutputGate = Gates.CurrentGates[Id]; GateDraggingFrom.OGCID = ConnectionID; // Create wire CreateWire(ButtonWidth, ButtonX, ButtonY, Id, ConnectionID); } else if (IsDraggingWire && DraggingSource) { // Play sound DropSound.Play(); // Stop dragging wire IsDraggingWire = false; DraggingEnd = false; DraggingSource = false; // Make sure to disconnect other wires if (Gates.CurrentGates[Id].InputGates[ConnectionID] != null) { // Get rid of the input connection Gates.CurrentGates[Id].OutputGate.InputGates[ConnectionID] = null; // Get rid of the output connection Gates.CurrentGates[Id].InputGates[ConnectionID] = null; // Get rid of the wire Destroy(Gates.CurrentGates[Id].InputGates[ConnectionID].WireObject); } // If source-connected already, delete connection if (Gates.CurrentGates[Id].Sources[ConnectionID] != null) { Gates.CurrentGates[Id].Sources[ConnectionID].RemoveConnections(Gates.CurrentGates[Id].Sources[ConnectionID].GetGateID(Gates.CurrentGates[Id])); } // Connect this gate to the source Gates.CurrentGates[Id].Sources[ConnectionID] = SourceDraggingFrom; // Connect end to the gate SourceDraggingFrom.Gates.Add(Gates.CurrentGates[Id]); SourceDraggingFrom.GateInputIDs.Add(ConnectionID); // Create a wire LineRenderer NewWire = CreateSourceEndWire(true, ButtonWidth, ButtonX, ButtonY); // Parent it to the gate NewWire.transform.parent = Gates.CurrentGates[Id].transform; // Assign it as an end wire Gates.CurrentGates[Id].SourceWires[ConnectionID] = NewWire; } } }
/// <summary> /// Handles output terminals /// </summary> void HandleOutputClicking(float ButtonX, float ButtonY, float ButtonWidth, int Id) { // If we aren't already dragging, then set it so we are dragging, // and that we're dragging an output wire if (!IsDraggingWire) { // Play sound PickupSound.Play(); // If connected already, delete current connection if (Gates.CurrentGates[Id].OutputGate != null) { // Delete current connection Gates.CurrentGates[Id].OutputGate.InputGates[Gates.CurrentGates[Id].OGCID] = null; // Remove output gate connection Gates.CurrentGates[Id].OutputGate = null; // Delete wire Destroy(Gates.CurrentGates[Id].WireObject.gameObject); } // If end-connected already, delete connection if (Gates.CurrentGates[Id].EndConnection != null) { Gates.CurrentGates[Id].EndConnection.RemoveConnections(Gates.CurrentGates[Id].EndConnection.GetGateID(Gates.CurrentGates[Id])); } // Pickup wire IsDraggingWire = true; DraggingOutput = true; DraggingSource = false; DraggingEnd = false; GateDraggingFrom = Gates.CurrentGates[Id]; GateDraggingFromInputID = 2; // 2 = outputs only, not really needed I suppose... DraggingOrigin = new Vector2(ButtonX, Screen.height - ButtonY); } else if (IsDraggingWire && !DraggingOutput && Gates.CurrentGates[Id] != GateDraggingFrom && !DraggingSource && !DraggingEnd) { // Play sound DropSound.Play(); // However if we are dragging a wire and it's not an output // wire, then connect them IsDraggingWire = false; // Make sure to disconnect other wires if (Gates.CurrentGates[Id].OutputGate != null) { // Get rid of the input connection Gates.CurrentGates[Id].OutputGate.InputGates[Gates.CurrentGates[Id].OGCID] = null; // Get rid of the output connection Gates.CurrentGates[Id].OutputGate = null; // Get rid of the wire Destroy(Gates.CurrentGates[Id].WireObject.gameObject); } // If end-connected already, delete connection if (Gates.CurrentGates[Id].EndConnection != null) { Gates.CurrentGates[Id].EndConnection.RemoveConnections(Gates.CurrentGates[Id].EndConnection.GetGateID(Gates.CurrentGates[Id])); } // Connect this gate to the one we dragged from Gates.CurrentGates[Id].OutputGate = GateDraggingFrom; Gates.CurrentGates[Id].OGCID = GateDraggingFromInputID; // Connect the one we dragged from to this gate GateDraggingFrom.InputGates[GateDraggingFromInputID] = Gates.CurrentGates[Id]; // Create wire CreateWire(ButtonWidth, ButtonX, ButtonY, Id, 2); } else if (IsDraggingWire && DraggingEnd) { // Play sound DropSound.Play(); // Stop dragging wire IsDraggingWire = false; DraggingEnd = false; DraggingSource = false; DraggingOutput = false; // Make sure to disconnect other wires if (Gates.CurrentGates[Id].OutputGate != null) { // Get rid of the input connection Gates.CurrentGates[Id].OutputGate.InputGates[Gates.CurrentGates[Id].OGCID] = null; // Get rid of the output connection Gates.CurrentGates[Id].OutputGate = null; // Get rid of the wire Destroy(Gates.CurrentGates[Id].WireObject.gameObject); } // If end-connected already, delete connection if (Gates.CurrentGates[Id].EndConnection != null) { Gates.CurrentGates[Id].EndConnection.RemoveConnections(Gates.CurrentGates[Id].EndConnection.GetGateID(Gates.CurrentGates[Id])); } // Connect this gate to the end Gates.CurrentGates[Id].EndConnection = SourceDraggingFrom; // Connect end to the gate SourceDraggingFrom.Gates.Add(Gates.CurrentGates[Id]); SourceDraggingFrom.GateInputIDs.Add(2); // Create a wire LineRenderer NewWire = CreateSourceEndWire(false, ButtonWidth, ButtonX, ButtonY); // Parent it to the gate NewWire.transform.parent = Gates.CurrentGates[Id].transform; // Assign it as an end wire Gates.CurrentGates[Id].EndWire = NewWire; } }
// Draw the player's UI void OnGUI() { // Get a UI scaling variable float UIScale = Screen.width / 2560f; // Draw the panel UI if need be if (_LevelManager.ViewingPanel) { // Draw a 'toolbox' at the top of the screen // First the tool box itself GUI.DrawTexture(new Rect(0, 0, 2560f * UIScale, 360f * UIScale), ToolboxImage); // Then the tools. Loop through the 'all logic gates' list float ToolImageWidth = 240f * UIScale; float ToolBaseX = 50f * UIScale; // AND Gate HandleToolClick(true, "AND", UIScale, ToolBaseX, 0, Gates.Gate_AND.GateSprite.texture); // OR Gate HandleToolClick(true, "OR", UIScale, ToolBaseX, 1, Gates.Gate_OR.GateSprite.texture); // XOR Gate HandleToolClick(true, "XOR", UIScale, ToolBaseX, 2, Gates.Gate_XOR.GateSprite.texture); // NAND Gate HandleToolClick(true, "NAND", UIScale, ToolBaseX, 3, Gates.Gate_NAND.GateSprite.texture); // NOR Gate HandleToolClick(true, "NOR", UIScale, ToolBaseX, 4, Gates.Gate_NOR.GateSprite.texture); // XNOR Gate HandleToolClick(true, "XNOR", UIScale, ToolBaseX, 5, Gates.Gate_XNOR.GateSprite.texture); // NOT Gate HandleToolClick(true, "NOT", UIScale, ToolBaseX, 6, Gates.Gate_NOT.GateSprite.texture); // Wire tool HandleToolClick(false, "Wire", UIScale, ToolBaseX, 7, WireToolIcon); // Return to ship HandleToolClick(false, "Ship", UIScale, ToolBaseX, 8, ShipIcon); // Render tooltips // AND Gate HandleTooltip("AND", UIScale, ToolBaseX, 0); // OR Gate HandleTooltip("OR", UIScale, ToolBaseX, 1); // XOR Gate HandleTooltip("XOR", UIScale, ToolBaseX, 2); // NAND Gate HandleTooltip("NAND", UIScale, ToolBaseX, 3); // NOR Gate HandleTooltip("NOR", UIScale, ToolBaseX, 4); // XNOR Gate HandleTooltip("XNOR", UIScale, ToolBaseX, 5); // NOT Gate HandleTooltip("NOT", UIScale, ToolBaseX, 6); // Wire tool HandleTooltip("Wire", UIScale, ToolBaseX, 7); // Return to ship HandleTooltip("Ship", UIScale, ToolBaseX, 8); // Render the inputs and outputs for (int i = 0; i < _Gates.InputCount; i++) { // Calculate positions float ButtonX = SourceBasePos.x; float ButtonY = SourceBasePos.y + 90f * i * UIScale; float ButtonWidth = 28 * UIScale; // Draw the button. Stay consistent in the colour and icons as the rest of the gates if (GUI.Button(new Rect(ButtonX, ButtonY, ButtonWidth, ButtonWidth), "", OutputButtonStyle) && CurrentTool == PlayerTool.CreateWire) { // If we aren't already dragging, make it so if (!IsDraggingWire) { // Play sound PickupSound.Play(); // Pickup wire IsDraggingWire = true; DraggingOutput = false; DraggingSource = true; DraggingEnd = false; GateDraggingFrom = null; SourceDraggingFrom = _Gates.InputConnections[i]; DraggingOrigin = new Vector2(ButtonX, Screen.height - ButtonY); } else if (IsDraggingWire && !DraggingOutput && !DraggingSource && !DraggingEnd) { // Play sound DropSound.Play(); // Stop dragging wire IsDraggingWire = false; // Connect the source _Gates.InputConnections[i].Gates.Add(GateDraggingFrom); _Gates.InputConnections[i].GateInputIDs.Add(GateDraggingFromInputID); // Connect the gate GateDraggingFrom.Sources[GateDraggingFromInputID] = _Gates.InputConnections[i]; // Create a wire LineRenderer NewWire = CreateSourceEndWire(true, ButtonWidth, ButtonX, ButtonY); // Parent it to the gate NewWire.transform.parent = GateDraggingFrom.transform; // Assign it to the gate if (DraggingOutput) { // Assign it as an end wire GateDraggingFrom.EndWire = NewWire; } else { // Assign it as a source wire GateDraggingFrom.SourceWires[GateDraggingFromInputID] = NewWire; } } } // Handle the tooltip HandleTooltip(_Gates.InputConnections[i].Label, UIScale, 0, i, _Gates.InputConnections[i].Description, true); } // Render outputs for (int i = 0; i < _Gates.OutputCount; i++) { // Calculate positions float ButtonX = OutBasePos.x; float ButtonY = OutBasePos.y + 90f * i * UIScale; float ButtonWidth = 28 * UIScale; // Draw the button. Stay consistent in the colour and icons as the rest of the gates if (GUI.Button(new Rect(ButtonX, ButtonY, ButtonWidth, ButtonWidth), "", InputButtonStyle) && CurrentTool == PlayerTool.CreateWire) { // If we aren't already dragging, make it so if (!IsDraggingWire) { // Play sound PickupSound.Play(); // Pickup wire IsDraggingWire = true; DraggingOutput = false; DraggingSource = false; DraggingEnd = true; GateDraggingFrom = null; SourceDraggingFrom = _Gates.OutputConnections[i]; DraggingOrigin = new Vector2(ButtonX, Screen.height - ButtonY); } else if (IsDraggingWire && DraggingOutput && !DraggingSource && !DraggingEnd) { // Sever connections first if the output is connected already if (_Gates.OutputConnections[i].Gates.Count > 0) { _Gates.OutputConnections[i].RemoveAllConnections(); } // Play sound DropSound.Play(); // Stop dragging wire IsDraggingWire = false; // Connect the source _Gates.OutputConnections[i].Gates.Add(GateDraggingFrom); _Gates.OutputConnections[i].GateInputIDs.Add(GateDraggingFromInputID); // Connect the gate GateDraggingFrom.EndConnection = _Gates.OutputConnections[i]; // Create a wire LineRenderer NewWire = CreateSourceEndWire(false, ButtonWidth, ButtonX, ButtonY); // Parent it to the gate NewWire.transform.parent = GateDraggingFrom.transform; // Assign it as an end wire GateDraggingFrom.EndWire = NewWire; } } // Handle the tooltip HandleTooltip(_Gates.OutputConnections[i].Label, UIScale, 0, i, _Gates.OutputConnections[i].Description, true, false); } // Fetch a local copy of the gates list List <GateBehaviour> GateList = Gates.CurrentGates; // Loop through each gate and draw 4 buttons; one for each input, // one for the output, and one to delete it for (int i = 0; i < GateList.Count; i++) { // Get the screen position of the logic gate Vector2 GatePosition = Camera.main.WorldToScreenPoint(GateList[i].transform.position); GatePosition.y = Screen.height - GatePosition.y; // Draw the output button float OutputX = GatePosition.x + 46f * UIScale; float OutputY = GatePosition.y + 16f * UIScale; float CrossY = GatePosition.y - 44f * UIScale; float OutputWidth = 28 * UIScale; // Toggle the player dragging status if clicked on if (GUI.Button(new Rect(OutputX, OutputY, OutputWidth, OutputWidth), "", OutputButtonStyle) && CurrentTool == PlayerTool.CreateWire) { HandleOutputClicking(OutputX, OutputY, OutputWidth, i); } // Now draw the input buttons if (!GateList[i].LogicGate.HasOneInput) { // Two inputs float InputX = GatePosition.x - 68f * UIScale; float InputY1 = GatePosition.y - 44f * UIScale; float InputY2 = GatePosition.y + 16f * UIScale; float InputWidth = 28 * UIScale; // Handle clicking (button 0) HandleInputClicking(InputX, InputY1, InputWidth, i, 0); // Handle clicking (button 1) HandleInputClicking(InputX, InputY2, InputWidth, i, 1); } else { // One input float InputX = GatePosition.x - 68f * UIScale; float InputY = GatePosition.y - 14f * UIScale; float InputWidth = 28 * UIScale; // Handle clicking HandleInputClicking(InputX, InputY, InputWidth, i, 0); } // Gate delete button if (GUI.Button(new Rect(OutputX, CrossY, OutputWidth, OutputWidth), "", CrossButtonStyle)) { // Play sound DropSound.Play(); // Destroy gate Gates.DestroyGate(Gates.GetGateID(Gates.CurrentGates[i])); } } } else { // Setup a GUI style ToolMiscStyle.normal.background = PanelIcon; ToolMiscStyle.hover.background = PanelIconHover; ToolMiscStyle.active.background = PanelIcon; // Create the button if (GUI.Button(new Rect(50f * UIScale, 50f * UIScale, 160f * UIScale, 160f * UIScale), "", ToolMiscStyle)) { // Play sound PickupSound.Play(); // View panel _LevelManager.ViewingPanel = true; _LevelManager.RecalculateUI(); } } }
// Update is called once per frame void Update() { // Preview line stuff if (IsDraggingWire) { // Set active PreviewLine.gameObject.SetActive(true); // Get some shorter-named variables float MouseX = Input.mousePosition.x; float MouseY = Screen.height - Input.mousePosition.y; float ImageWidth = 14 * (Screen.width / 2560f); // Set the points on the line renderer Vector2 LRPoint1 = Camera.main.ScreenToWorldPoint(new Vector2(DraggingOrigin.x + ImageWidth / 2f, DraggingOrigin.y - ImageWidth / 2f)); Vector2 LRPoint2 = Camera.main.ScreenToWorldPoint(new Vector2(MouseX + ImageWidth / 2f, Screen.height - MouseY - ImageWidth / 2f)); PreviewLine.SetPositions(new Vector3[] { new Vector3(LRPoint1.x, LRPoint1.y, -7), new Vector3(LRPoint2.x, LRPoint2.y, -7) }); PreviewLine.sortingOrder = 4; } else { PreviewLine.gameObject.SetActive(false); } // Handle viewing panel stuff if (_LevelManager.ViewingPanel) { // Check for player clicks. Record the position if so. if (Input.GetMouseButtonUp(0)) { // First we need to know if we hit the switch, if we're clicking to place // a logic gate or if we're dragging the view around (maybe not the last one?) if (MouseInBounds) { // Get the player's mouse position in world co-ordinates Vector2 MouseWorldCoords = Camera.main.ScreenToWorldPoint(Input.mousePosition); // Spawn a logic gate or create wiring depending on the tool if (CurrentTool == PlayerTool.PlaceGate) { // Play a sound DropSound.Play(); // Spawn the selected logic gate at mouse position switch (SelectedGate) { case GateSelection.AND: Gates.SpawnGate(Gates.Gate_AND, MouseWorldCoords); break; case GateSelection.NAND: Gates.SpawnGate(Gates.Gate_NAND, MouseWorldCoords); break; case GateSelection.OR: Gates.SpawnGate(Gates.Gate_OR, MouseWorldCoords); break; case GateSelection.NOR: Gates.SpawnGate(Gates.Gate_NOR, MouseWorldCoords); break; case GateSelection.XOR: Gates.SpawnGate(Gates.Gate_XOR, MouseWorldCoords); break; case GateSelection.XNOR: Gates.SpawnGate(Gates.Gate_XNOR, MouseWorldCoords); break; case GateSelection.NOT: Gates.SpawnGate(Gates.Gate_NOT, MouseWorldCoords); break; } } } } // Right-clicking stops dragging a wire if (Input.GetMouseButtonUp(1)) { IsDraggingWire = false; GateDraggingFrom = null; DropSound.Play(); } } }
/// <summary> /// Gets the ID of a speciifc gate in the connections /// </summary> public int GetGateID(GateBehaviour Gate) { return(Gates.FindIndex(0, Gates.Count, x => x == Gate)); }
/// <summary> /// Fetches the index in the CurrentGates list for a specific object with a gate behaviour /// </summary> /// <param name="Gate">The gate behaviour component of the game object</param> /// <returns></returns> public static int GetGateID(GateBehaviour Gate) { // Return the index of the gate in the list return(CurrentGates.FindIndex(0, CurrentGates.Count, x => x == Gate)); }