// Update is called once per frame void FixedUpdate() { // canvas.SetActive(false); // Check if to generate new random event if (timeCounter - lastPrint > 1) { lastPrint = timeCounter; } if (eventTimer > EVENT_INTERVAL) { eventTimer = 0; if (waitingEventsId.Count + ongoingEventsId.Count < shelves.Length - 1) { int newIdx = GenRandEvent(); Event newWaitingEvent = eventsDict[newIdx]; newWaitingEvent.markEvent(eventWaitingMat); waitingEventsId.Add(newIdx); totalEventCounter++; } } /* * if (cleanCounter >= CLEAN_INTERVAL && GameObject.FindGameObjectsWithTag("shatter") != null) * { * foreach (GameObject shatterObject in GameObject.FindGameObjectsWithTag("shatter")) * { * // Debug.Log("cleaning + " + shatterObject); * Destroy(shatterObject); * } * cleanCounter = 0; * }*/ // while available drones, pop event // assign drone dst, to-do event, remove from avail, add to working drones // direction if (availableDronesId.Count > 0 && waitingEventsId.Count > 0) { int e = waitingEventsId.Next(); int d = Utility.IS_RND_TAKEOFF ? availableDronesId.NextRnd() : availableDronesId.Next(); Drone availableDrone = dronesDict[d]; availableDrone.AddEvent(eventsDict[e]); availableDronesId.Remove(d); workingDronesId.Add(d); waitingEventsId.Remove(e); ongoingEventsId.Add(e); } // apply force meanwhile check collision foreach (int i in workingDronesId) { Vector3 force = new Vector3(); bool replan = false; bool isWarning = false; foreach (int j in workingDronesId) { if (i == j) { continue; } Vector3 delta = dronesDict[i].gameObjectPointer.transform.Find("pCube2").gameObject.transform.position - dronesDict[j].gameObjectPointer.transform.Find("pCube2").gameObject.transform.position; float dis = delta.magnitude; //Vector3 delta = dronesDict[i].curPos - dronesDict[j].curPos; //if (i != j && Utility.IsMoreThan(delta, CUTOFF_INTERACT)) //{ // isWarning = false; //} if (dronesDict[i].gameObjectPointer.activeSelf == false || dronesDict[j].gameObjectPointer.activeSelf == false) { continue; } if (dis < Utility.INTERACT_DIM) { //Debug.Log("The Drone: " + i + "and " + j + "will warning"); // collide isWarning = true; if (dis < Utility.BOUND_DIM) { if (!(EnableSafeZoneTravel && dronesDict[i].safetyStatus == Drone.SafetyStatus.TO_SAFE_ZONE && dronesDict[j].safetyStatus == Drone.SafetyStatus.TO_SAFE_ZONE && dronesDict[i].safetyStatus == Drone.SafetyStatus.TO_NONSAFE_ZONE && dronesDict[j].safetyStatus == Drone.SafetyStatus.TO_NONSAFE_ZONE)) { isWarning = false; //Debug.Log("drone: " + i + ", " + j + " collide dealing event: " + dronesDict[i].eventId + ", " + dronesDict[j].eventId); dronesDict[i].status = Drone.DroneStatus.COLLIDE; dronesDict[j].status = Drone.DroneStatus.COLLIDE; //dronesDict[i].gameObjectPointer.GetComponent<DroneProperties>().classPointer.CollideEffect(); //dronesDict[j].gameObjectPointer.GetComponent<DroneProperties>().classPointer.CollideEffect(); } if (!dronesDict[i].isCollided && !dronesDict[j].isCollided) { userError++; Debug.LogFormat("===== Drone {0}, Drone {1} | COLLISION =====", i, j); } dronesDict[j].isCollided = true; dronesDict[i].isCollided = true; } else { //Debug.Log("drone " + i + ", " + j + " system plan error"); systemError++; } } else if (Utility.IsLessThan(delta, Utility.CUTOFF_REPLAN)) { //dronesDict[i].WarningEffect(false); //dronesDict[j].WarningEffect(false); // replan with certain failure rate if (rnd.NextDouble() < 1 - REPLAN_FAIL_RATE) { Debug.Log("replan for " + i); force += delta; replan = true; } } } // update direction dronesDict[i].isWarning = (isWarning && EnableWarning); dronesDict[i].direction = replan ? Vector3.Normalize(force) : Vector3.Normalize(dronesDict[i].dstPos - dronesDict[i].curPos); } // check status // move every working drone for (int i = 0; i < numDrones; i++) { Drone currDrone = dronesDict[i]; Drone.DroneStatus status = currDrone.status; if (status == Drone.DroneStatus.PARKED) { dronesDict[i].WarningRender(false); continue; } else if (status == Drone.DroneStatus.COLLIDE) { /* * dronesDict[i].isPaused = false; * dronesDict[i].WarningRender(false); * dronesDict[i].curPos = dronesDict[i].parkingPos; * // check the event can be added back * int eid = dronesDict[i].eventId; * // if (!waitingEventsId.Contains(eid) && !ongoingEventsId.Contains(eid)) * waitingEventsId.Add(eid); * * Event curEvent = eventsDict[dronesDict[i].eventId]; * curEvent.markEvent(eventWaitingMat); * * dronesDict[i].status = Drone.DroneStatus.PARKED; */ // new currDrone.gameObjectPointer.SetActive(false); } //else if (status == Drone.DroneStatus.TO_SHELF || status == 3) else if (status == Drone.DroneStatus.TO_SHELF) { if (dronesDict[i].isWarning == true) { dronesDict[i].WarningRender(true); //canvas.SetActive(true); } else { dronesDict[i].WarningRender(false); } } Drone.MoveStatus moveStatus = dronesDict[i].Move(); if (moveStatus == Drone.MoveStatus.END_TO_SHELF) // drone status 2 --> 3 { Event curEvent = eventsDict[dronesDict[i].eventId]; curEvent.markEvent(eventIdleMat); ongoingEventsId.Remove(dronesDict[i].eventId); } if (dronesDict[i].status == Drone.DroneStatus.PARKED) { //dronesDict[i].HideArrow(); workingDronesId.Remove(i); availableDronesId.Add(i); ongoingEventsId.Remove(dronesDict[i].eventId); } } // update counter timeCounter += Time.fixedDeltaTime; eventTimer += Time.fixedDeltaTime; cleanCounter += Time.fixedDeltaTime; #if IS_USER_STUDY if (timeCounter >= EXIT_TIME) { QuitGame(); } #endif }
// Update is called once per frame void Update() { // canvas.SetActive(false); // Check if to generate new random event if (timeCounter % EVENT_INTERVAL == 0) { if (waitingEventsId.Count + ongoingEventsId.Count < shelves.Length - 1) { int newIdx = GenRandEvent(); Event newWaitingEvent = eventsDict[newIdx]; newWaitingEvent.markEvent(eventWaitingMat); waitingEventsId.Add(newIdx); totalEventCounter++; } } if (cleanCounter == CLEAN_INTERVAL && GameObject.FindGameObjectsWithTag("shatter") != null) { foreach (GameObject shatterObject in GameObject.FindGameObjectsWithTag("shatter")) { // Debug.Log("cleaning + " + shatterObject); Destroy(shatterObject); } cleanCounter = -1; } // while available drones, pop event // assign drone dst, to-do event, remove from avail, add to working drones // direction if (availableDronesId.Count > 0 && waitingEventsId.Count > 0) { int e = waitingEventsId.Next(); int d = Utility.IS_RND_TAKEOFF ? availableDronesId.NextRnd() : availableDronesId.Next(); //if (numDrones == 4) //{ // e = Utility.EventIt.Current; d = Utility.DroneIt.Current; // Utility.EventIt.MoveNext(); Utility.DroneIt.MoveNext(); // Debug.Log("e: " + e + " d: " + d); //} //else //{ // e = waitingEventsId.Next(); // d = Utility.IS_RND_TAKEOFF ? availableDronesId.NextRnd() : availableDronesId.Next(); //} dronesDict[d].AddEvent(eventsDict[e]); // Debug.Log("assign event " + e + " to drone " + d + " with direction: " + dronesDict[d].direction); availableDronesId.Remove(d); workingDronesId.Add(d); waitingEventsId.Remove(e); ongoingEventsId.Add(e); } // apply force meanwhile check collision foreach (int i in workingDronesId) { Vector3 force = new Vector3(); bool replan = false; bool isWarning = false; foreach (int j in workingDronesId) { Vector3 delta = dronesDict[i].gameObjectPointer.transform.Find("pCube2").gameObject.transform.position - dronesDict[j].gameObjectPointer.transform.Find("pCube2").gameObject.transform.position; float dis = delta.magnitude; //Vector3 delta = dronesDict[i].curPos - dronesDict[j].curPos; //if (i != j && Utility.IsMoreThan(delta, CUTOFF_INTERACT)) //{ // isWarning = false; //} if (i != j && Utility.IsLessThan(delta, Utility.CUTOFF_INTERACT)) { //Debug.Log("The Drone: " + i + "and " + j + "will warning"); // collide isWarning = true; if (Utility.IsLessThan(delta, Utility.COLLISION_BOUND)) { isWarning = false; //Debug.Log("drone: " + i + ", " + j + " collide dealing event: " + dronesDict[i].eventId + ", " + dronesDict[j].eventId); userError++; dronesDict[i].status = 5; dronesDict[j].status = 5; dronesDict[i].gameObjectPointer.GetComponent <DroneProperties>().classPointer.CollideEffect(); dronesDict[j].gameObjectPointer.GetComponent <DroneProperties>().classPointer.CollideEffect(); } else { //Debug.Log("drone " + i + ", " + j + " system plan error"); systemError++; } } else if (i != j && Utility.IsLessThan(delta, Utility.CUTOFF_REPLAN)) { //dronesDict[i].WarningEffect(false); //dronesDict[j].WarningEffect(false); // replan with certain failure rate if (rnd.NextDouble() < 1 - REPLAN_FAIL_RATE) { // Debug.Log("replan for " + i); force += delta; replan = true; } } } // update direction dronesDict[i].isWarning = isWarning; dronesDict[i].direction = replan ? Vector3.Normalize(force) : Vector3.Normalize(dronesDict[i].dstPos - dronesDict[i].curPos); } // check status // move every working drone for (int i = 0; i < numDrones; i++) { int status = dronesDict[i].status; if (status == 0) { dronesDict[i].WarningRender(false); continue; } else if (status == 5) { dronesDict[i].isPaused = false; dronesDict[i].WarningRender(false); dronesDict[i].curPos = dronesDict[i].parkingPos; // check the event can be added back int eid = dronesDict[i].eventId; // if (!waitingEventsId.Contains(eid) && !ongoingEventsId.Contains(eid)) waitingEventsId.Add(eid); Event curEvent = eventsDict[dronesDict[i].eventId]; curEvent.markEvent(eventWaitingMat); dronesDict[i].status = 0; } else if (status == 2 || status == 3) { if (dronesDict[i].isWarning == true) { dronesDict[i].WarningRender(true); //canvas.SetActive(true); } else { dronesDict[i].WarningRender(false); } } int moveStatus = dronesDict[i].Move(); if (moveStatus == 1) // drone status 2 --> 3 { Event curEvent = eventsDict[dronesDict[i].eventId]; curEvent.markEvent(eventIdleMat); ongoingEventsId.Remove(dronesDict[i].eventId); } else if (moveStatus == 2) // end of whole trip { successEventCounter++; } if (dronesDict[i].status == 0) { //dronesDict[i].HideArrow(); workingDronesId.Remove(i); availableDronesId.Add(i); ongoingEventsId.Remove(dronesDict[i].eventId); } } // update counter timeCounter++; cleanCounter++; #if IS_USER_STUDY if (timeCounter >= EXIT_TIME) { QuitGame(); } #endif }
// Update is called once per frame void FixedUpdate() { if (timeCounter - lastPrint > 1) { lastPrint = timeCounter; } //Debug.LogFormat("{0} {1}", eventTimer, EVENT_INTERVAL); // Check if to generate new random event if (eventTimer > EVENT_INTERVAL) { eventTimer = 0; //Debug.Log("New Event Attempt"); if (waitingEventsId.Count + ongoingEventsId.Count < shelves.Length - 1) { // Debug.Log("New Event Created"); int newIdx = GenRandEvent(); waitingEventsId.Add(newIdx); totalEventCounter++; } } // try to gaurentee there are 6 crashes per minute if (sixtysecsCounter < 60) { sixtysecsCounter += Time.fixedDeltaTime; } else { currMinuteCrashCounter = 0; sixtysecsCounter = 0; } if (availableDronesId.Count > 0 && waitingEventsId.Count > 0) { if (currMinuteCrashCounter >= 6) { Debug.Log("???????????????????????"); PairPermutation formPermute = new PairPermutation(); int[] droneIDArray = availableDronesId.getList().ToArray(); int[] eventIDArray = waitingEventsId.getList().ToArray(); Debug.Log(string.Join(" ", droneIDArray)); List <int[]> dronePermutations = PairPermutation.GetPermutation(droneIDArray); int counter = 0; bool hasSolution = false; foreach (int[] permute in dronePermutations) { int numOptions = permute.Length; int size = numOptions * numOptions; List <bool> pairIntersection = new List <bool>(); bool collision = false; for (int i = 0; i < numOptions - 1; i++) { for (int j = 0; j < numOptions - 1; j++) { Vector3 p1, p2, p3, p4; p1 = eventsDict[eventIDArray[i]].pos; p2 = dronesDict[droneIDArray[i]].hoverPos; p3 = eventsDict[eventIDArray[j]].pos; p4 = dronesDict[droneIDArray[j]].hoverPos; collision = IsWithinCollisionBound(p1, p2, p3, p4); Debug.LogFormat("Drone {0} Event {1} | Drone {2} Event{3} could crash!!!!!!!", droneIDArray[i], eventIDArray[i], droneIDArray[j], eventIDArray[j]); if (collision) { break; } } if (collision) { break; } } if (!collision) { hasSolution = true; break; } else { collision = false; counter++; } } if (hasSolution) { int[] solution = dronePermutations[counter]; Utility.IS_RND_TAKEOFF = false; OrderedSet <int> newAvailableDronesID = new OrderedSet <int>(); foreach (int item in solution) { newAvailableDronesID.Add(item); } availableDronesId = newAvailableDronesID; } } else { Utility.IS_RND_TAKEOFF = true; } int e = waitingEventsId.Next(); int d = Utility.IS_RND_TAKEOFF ? availableDronesId.NextRnd() : availableDronesId.Next(); Drone nextDrone = dronesDict[d]; Event nextEvent = eventsDict[e]; nextDrone.AddEvent(nextEvent); availableDronesId.Remove(d); workingDronesId.Add(d); waitingEventsId.Remove(e); ongoingEventsId.Add(e); } //if (availableDronesId.Count > 0 && waitingEventsId.Count > 0) //{ // //Debug.Log("Assigning event to drone"); // int e = waitingEventsId.NextRnd(); // //int e = waitingEventsId.Next(); // int d = Utility.IS_RND_TAKEOFF ? availableDronesId.NextRnd() : availableDronesId.Next(); // Drone avalibleDrone = dronesDict[d]; // avalibleDrone.AddEvent(eventsDict[e]); // availableDronesId.Remove(d); // workingDronesId.Add(d); // waitingEventsId.Remove(e); // ongoingEventsId.Add(e); //} // apply force meanwhile check collision foreach (int i in workingDronesId) { //Debug.Log("Drone Collision Loop 1"); foreach (int j in workingDronesId) { if (i == j) { continue; } //Debug.Log("Drone Collision Loop 2"); Vector3 delta = dronesDict[i].gameObjectPointer.transform.Find("pCube2").gameObject.transform.position - dronesDict[j].gameObjectPointer.transform.Find("pCube2").gameObject.transform.position; float dis = delta.magnitude; //if (Utility.IsLessThan(delta, Utility.CUTOFF_INTERACT)) if (dis < Utility.INTERACT_DIM) { //if (Utility.IsLessThan(delta, Utility.COLLISION_BOUND)) if (dis < Utility.BOUND_DIM) { //Debug.Log("2. DroneID " + dronesDict[i].droneId + " Drone Collision"); if (!dronesDict[i].isCollided && !dronesDict[j].isCollided) { userError++; currMinuteCrashCounter++; Debug.LogFormat("===== Drone {0}, Drone {1} | COLLISION =====", i, j); } dronesDict[i].isCollided = true; dronesDict[j].isCollided = true; } else { systemError++; } } } dronesDict[i].direction = Vector3.Normalize(dronesDict[i].dstPos - dronesDict[i].curPos); } // check status // move every working drone for (int i = 0; i < numDrones; i++) { Drone currDrone = dronesDict[i]; Drone.DroneStatus status = currDrone.status; if (status == Drone.DroneStatus.PARKED) { continue; } Drone.MoveStatus moveStatus = currDrone.Move(); if (moveStatus == Drone.MoveStatus.END_TO_SHELF) // drone status 2 --> 3 { ongoingEventsId.Remove(currDrone.eventId); if (!currDrone.isCollided) { successEventCounter++; Debug.LogFormat("Drone {0} | event {1} | COMPLETE", i, currDrone.eventId); } else { Debug.LogFormat("Drone {0} event {1} | CRASH", i, currDrone.eventId); } } if (currDrone.status == Drone.DroneStatus.PARKED) { currDrone.isCollided = false; workingDronesId.Remove(i); availableDronesId.Add(i); ongoingEventsId.Remove(currDrone.eventId); } } // update counter timeCounter += Time.fixedDeltaTime; eventTimer += Time.fixedDeltaTime; cleanCounter++; #if IS_USER_STUDY if (SEED <= MAX_SEED) { if (timeCounter >= EXIT_TIME) { Debug.Log("====================End of a 3 minute user study============================="); //Debug.Log(SEED); ResetSim(); ReloadScene(); //QuitGame(); } } else { Debug.Log("???????????????????????????"); QuitGame(); } #endif }