//---------------------------------------------------------СЕРДЦЕБИЕНИЕ-------------------------------------------------- void Update() { //Проработка состояний: switch (state) { case aStarState.pause: if (clientList.Count > 0) { activeClient = clientList [0]; state = aStarState.find; } break; //команда расчитать путь: case aStarState.find: //Для каждого клиента в списке клиентов: //Выполняем поиск пути между ближайшими поинтами: StartCoroutine(findPath(activeClient)); break; //сбрасываем текущее соcтояние case aStarState.founded: clientList.Remove(activeClient); activeClient = null; state = aStarState.pause; break; } }
private void HandlePatchFinish(ClientPatch Patch, bool Cancel) { UpdateProgressbar(100); if (ApplyPatch(Patch) == true) { RegHelper.SavePatch(Patch.PatchID); mPatchedFiles.Add(Patch.PatchID); } mPatchProgress++; ProgressPatches(); }
private void HandlePatchFinish(ClientPatch Patch, bool Cancel) { UpdateProgressbar(100); if (TaskbarManager.IsPlatformSupported) { mWin7Taskbar.SetProgressState(TaskbarProgressBarState.NoProgress); } if (ApplyPatch(Patch) == true) { mRegistry.SavePatch(Patch.ID); mPatchedFiles.Add(Patch.ID); } mPatchProgress++; ProgressPatches(); }
//---------------------------------------------------------СЕРДЦЕБИЕНИЕ-------------------------------------------------- void Update() { //В любой момент можно запустить инициализацию: if (autoInit) { initialize(); } //Проработка состояний: switch (state) { case aStarState.pause: if (clientList.Count > 0) { activeClient = clientList [0]; findFilter.Clear(); findFilter.Add(activeClient.my_patch_Filter); state = aStarState.find; } break; //команда расчитать путь: case aStarState.find: //Для каждого клиента в списке клиентов: //Выполняем поиск пути между ближайшими поинтами: StartCoroutine(findPath(activeClient)); break; //сбрасываем текущее соcтояние case aStarState.founded: clientList.Remove(activeClient); activeClient = null; state = aStarState.pause; break; } }
//---------------------------------------------------PatchFORPoint----------------------------------------------------- //Для многопоточности требуется изменить метод под static(а так-же перенести переменные в clientPatch) public IEnumerator findPath(ClientPatch client) { if (mapPointList.Count > 0) { //Получаем поинты старта и финиша: Point start = mapPointDictionary[Vector3toVector3i(client.lostPoint)]; Point finish = mapPointDictionary[Vector3toVector3i(client.targetPosition.position)]; found = false; noroute = false; openList = new List <Point>(); //8 доступных ячеек для каждой(это в 2д пространстве), пополняется при выборе следующей точки с минимальной стоимостью окружающими ее closedList = new List <Point>(); tmpList = new List <Point>(); //1) Добавляем стартовую клетку в открытый список. openList.Add(start); min = start; //2) Повторяем следующее: while (!found & !noroute) { //пока путь еще не найден и не известно что пути не существует //a) Ищем в открытом списке клетку с наименьшей стоимостью F. Делаем ее текущей клеткой. min = openList[0]; int m = openList.Count; for (int k = 0; k < m; k++) { Point point = openList[k]; // тут я специально тестировал, при < или <= выбираются разные пути, // но суммарная стоимость G у них совершенно одинакова. Забавно, но так и должно быть. if (point.F <= min.F) { min = point; } } //b) Помещаем ее в закрытый список. (И удаляем с открытого) closedList.Add(min); openList.Remove(min); //c) Для каждой из соседних(min) 8-ми клеток(в нашем случае их может и не быть 8) ... tmpList.Clear(); int otherx = 0; int othery = 0; int otherz = 0; int iteration = iterations; int i = 0; Vector3i vector = Vector3i.zero; Point otherPoint; //идем от старта: //--------------------------------------------------FORWARD otherz = min.pointPosition.z + stepForward; //формируем позицию запроса vector.x = min.pointPosition.x; vector.y = min.pointPosition.y; vector.z = otherz; //Проверяем содержит ли коллекция поинт с такой позицией(если да то определяем его как поинт впереди) if (mapPointDictionary.ContainsKey(vector)) { otherPoint = mapPointDictionary[vector]; if (!closedList.Contains(otherPoint)) { tmpList.Add(otherPoint); } } //---------------------------------------------------BACK otherz = min.pointPosition.z - stepForward; //формируем позицию запроса vector.x = min.pointPosition.x; vector.y = min.pointPosition.y; vector.z = otherz; //Проверяем содержит ли коллекция поинт с такой позицией(если да то определяем его как поинт впереди) if (mapPointDictionary.ContainsKey(vector)) { otherPoint = mapPointDictionary[vector]; if (!closedList.Contains(otherPoint)) { tmpList.Add(otherPoint); } } //----------------------------------------------------RIGHT otherx = min.pointPosition.x + stepRight; //формируем позицию запроса vector.x = otherx; vector.y = min.pointPosition.y; vector.z = min.pointPosition.z; //Проверяем содержит ли коллекция поинт с такой позицией(если да то определяем его как поинт впереди) if (mapPointDictionary.ContainsKey(vector)) { otherPoint = mapPointDictionary[vector]; if (!closedList.Contains(otherPoint)) { tmpList.Add(otherPoint); } } //-----------------------------------------------------LEFT otherx = min.pointPosition.x - stepRight; //формируем позицию запроса vector.x = otherx; vector.y = min.pointPosition.y; vector.z = min.pointPosition.z; //Проверяем содержит ли коллекция поинт с такой позицией(если да то определяем его как поинт впереди) if (mapPointDictionary.ContainsKey(vector)) { otherPoint = mapPointDictionary[vector]; if (!closedList.Contains(otherPoint)) { tmpList.Add(otherPoint); } } if (find != typeFind.xz) { //-----------------------------------------------------Up othery = min.pointPosition.y + stepUp; //формируем позицию запроса vector.x = min.pointPosition.x; vector.y = othery; vector.z = min.pointPosition.z; //Проверяем содержит ли коллекция поинт с такой позицией(если да то определяем его как поинт впереди) if (mapPointDictionary.ContainsKey(vector)) { otherPoint = mapPointDictionary[vector]; if (!closedList.Contains(otherPoint)) { tmpList.Add(otherPoint); } } //-----------------------------------------------------Down othery = min.pointPosition.y - stepUp; //формируем позицию запроса vector.x = min.pointPosition.x; vector.y = othery; vector.z = min.pointPosition.z; //Проверяем содержит ли коллекция поинт с такой позицией(если да то определяем его как поинт впереди) if (mapPointDictionary.ContainsKey(vector)) { otherPoint = mapPointDictionary[vector]; if (!closedList.Contains(otherPoint)) { tmpList.Add(otherPoint); } } } //-------------------------------------------------------------------Движение по диагоналям------------------------------------------ /* * //-----------------------------------------------------LEFT-FORWARD * otherx = min.pointTransform.position.x - stepRight; * otherz = min.pointTransform.position.z + stepForward; * //формируем позицию запроса * vector.x = otherx; * vector.y = min.pointTransform.position.y; * vector.z = otherz; * //Проверяем содержит ли коллекция поинт с такой позицией(если да то определяем его как поинт впереди) * if (mapPointDictionary.ContainsKey(vector)) * { * otherPoint = mapPointDictionary[vector]; * if (!closedList.Contains(otherPoint)) * { * tmpList.Add(otherPoint); * } * } * * //-----------------------------------------------------RIGHT-FORWARD * //if point step right-forward(+x, +z) * * otherx = min.pointTransform.position.x + stepRight; * otherz = min.pointTransform.position.z + stepForward; * //формируем позицию запроса * vector.x = otherx; * vector.y = min.pointTransform.position.y; * vector.z = otherz; * //Проверяем содержит ли коллекция поинт с такой позицией(если да то определяем его как поинт впереди) * if (mapPointDictionary.ContainsKey(vector)) * { * otherPoint = mapPointDictionary[vector]; * if (!closedList.Contains(otherPoint)) * { * tmpList.Add(otherPoint); * } * } * * //------------------------------------------------------LEFT-BACK * //if point step left-back(-x, -z) * otherx = min.pointTransform.position.x - stepRight; * otherz = min.pointTransform.position.z - stepForward; * //формируем позицию запроса * vector.x = otherx; * vector.y = min.pointTransform.position.y; * vector.z = otherz; * //Проверяем содержит ли коллекция поинт с такой позицией(если да то определяем его как поинт впереди) * if (mapPointDictionary.ContainsKey(vector)) * { * otherPoint = mapPointDictionary[vector]; * if (!closedList.Contains(otherPoint)) * { * tmpList.Add(otherPoint); * } * } * * //-------------------------------------------------------RIGHT-BACK * //if point step right-back(-x) * otherx = min.pointTransform.position.x + stepRight; * otherz = min.pointTransform.position.z - stepForward; * //формируем позицию запроса * vector.x = otherx; * vector.y = min.pointTransform.position.y; * vector.z = otherz; * //Проверяем содержит ли коллекция поинт с такой позицией(если да то определяем его как поинт впереди) * if (mapPointDictionary.ContainsKey(vector)) * { * otherPoint = mapPointDictionary[vector]; * if (!closedList.Contains(otherPoint)) * { * tmpList.Add(otherPoint); * } * } */ /* * if (i == iteration) * { * iteration += iterations; * yield return null; * } */ // } iteration = iterations; //После того как мы добавили в список tmpList окружающие min поинт поинты, выполняем следующее: for (i = 0; i < tmpList.Count; i += 1) { Point neightbour = tmpList[i]; /* * //foreach (Point neightbour in tmpList.ToArray()) { * //Если клетка непроходимая или она находится в закрытом списке, игнорируем ее. В противном случае делаем следующее(похоже строчка не нужна). * if (neightbour.type == Point.typePoint.blocked) * { * continue; * } */ //Если Point дверь, то нужно предпринять следующие действия: if (neightbour.type == Point.typePoint.door) { continue; } //Если клетка еще не в открытом списке, то добавляем ее туда. Делаем текущую клетку родительской для это клетки. Расчитываем стоимости F, G и H клетки. if (!openList.Contains(neightbour)) { openList.Add(neightbour); neightbour.parent = min; neightbour.H = (int)neightbour.mandist(finish); //стоимость до итоговой точки neightbour.G = start.price(min); //стоимость относительно прямой или диагонали neightbour.F = neightbour.H + neightbour.G; //суммарная стоимость continue; } //Debug.Log ("this"); // Если клетка уже в открытом списке, то проверяем, не дешевле ли будет путь через эту клетку. Для сравнения используем стоимость G. if (neightbour.G + neightbour.price(min) < min.G) { // Более низкая стоимость G указывает на то, что путь будет дешевле. Эсли это так, то меняем родителя клетки на текущую клетку и пересчитываем для нее стоимости G и F. neightbour.parent = min; // вот тут я честно хз, надо ли min.parent или нет neightbour.H = (int)neightbour.mandist(finish); neightbour.G = start.price(min); neightbour.F = neightbour.H + neightbour.G; } if (i == iteration) { iteration += iterations; yield return(null); } // Если вы сортируете открытый список по стоимости F, то вам надо отсортировать весь список в соответствии с изменениями. //state = aStarState.founded; } //d) Останавливаемся если: //Добавили целевую клетку в открытый список, в этом случае путь найден. //Или открытый список пуст и мы не дошли до целевой клетки. В этом случае путь отсутствует. if (openList.Contains(finish)) { found = true; } if (openList.Count == 0) { noroute = true; } } List <Point> completePatch = new List <Point>(); //3) Сохраняем путь. Двигаясь назад от целевой точки, проходя от каждой точки к ее родителю до тех пор, пока не дойдем до стартовой точки. Это и будет наш путь. if (!noroute) { //формируем список возвращаемый клиенту(внимание список будет получен с конца(start в конце)а так-же необходимо отменить применение настроек): completePatch.Add(finish); Point rd = finish.parent; while (!rd.equals(start)) { completePatch.Add(rd); rd = rd.parent; if (rd == null) { break; } } if (!completePatch.Contains(start)) { completePatch.Add(start); } client.patch = completePatch; //Указываем клиенту список point которые следует пройти для начала /* * //Очищаем зависимости в поинтах: * foreach(Point p in client.mapPointList.ToArray()){ * p.parent = null; * p.F = 0; * p.G = 0; * p.H = 0; * p.myPrice = 0; * } */ //Debug.Log("Список поинтов установлен клиенту"); min = null; tmpList = new List <Point>(); openList = new List <Point>(); closedList = new List <Point>(); blockedPointList = new List <Point>(); } else { client.patch = new List <Point>(); min = null; tmpList = new List <Point>(); openList = new List <Point>(); closedList = new List <Point>(); blockedPointList = new List <Point>(); //Очищаем зависимости в поинтах: /* * foreach(Point p in client.mapPointList.ToArray()){ * p.parent = null; * p.F = 0; * p.G = 0; * p.H = 0; * p.myPrice = 0; * } */ /* * //обнуляем текущий приказ, мы дошли до места назначения * if (client.unit.firstOrder != null) * { * client.unit.firstOrder.complete = true; * } * //Debug.Log("Пути нет"); */ } state = aStarState.founded; } else { Debug.Log("Список поинтов клиента пуст"); } }
//---------------------------------------------------PatchFORPoint----------------------------------------------------- //Для многопоточности требуется изменить метод под static(а так-же перенести переменные в clientPatch) public IEnumerator findPath(ClientPatch client) { if (mapPointList.Count > 0) { if (mapPointDictionary.ContainsKey(Vector3toVector3i(client.lostPointVector3D)) && mapPointDictionary.ContainsKey(Vector3toVector3i(client.targetPosition.position))) { //Получаем поинты старта и финиша: Point start = mapPointDictionary[Vector3toVector3i(client.lostPointVector3D)]; Point finish = mapPointDictionary[Vector3toVector3i(client.targetPosition.position)]; found = false; noroute = false; openList = new List <Point>(); //8 доступных ячеек для каждой(это в 2д пространстве), пополняется при выборе следующей точки с минимальной стоимостью окружающими ее closedList = new List <Point>(); tmpList = new List <Point>(); //1) Добавляем стартовую клетку в открытый список. openList.Add(start); min = start; //2) Повторяем следующее: while (!found & !noroute) { //пока путь еще не найден и не известно что пути не существует //a) Ищем в открытом списке клетку с наименьшей стоимостью F. Делаем ее текущей клеткой. findFilter[0].min_searcher(this); //b) Помещаем ее в закрытый список. (И удаляем с открытого) closedList.Add(min); openList.Remove(min); //c) Для каждой из соседних(min) 8-ми клеток(в нашем случае их может и не быть 8) ... tmpList.Clear(); int iteration = iterations; int i = 0; //тут пробегаем по фильтрам: for (int n = 0; n < findFilter.Count; n++) { PatchFilter nextFilter = findFilter[n]; nextFilter.filter(min, this); } iteration = iterations; //После того как мы добавили в список tmpList окружающие min поинт поинты, выполняем следующее: for (i = 0; i < tmpList.Count; i += 1) { Point neightbour = tmpList[i]; ///* //Если клетка непроходимая или она находится в закрытом списке, игнорируем ее. В противном случае делаем следующее(похоже строчка не нужна). if (neightbour.point_type == Point.typePoint.blocked && !activeClient.ignore_blocked) { continue; } //*/ //Если клетка еще не в открытом списке, то добавляем ее туда. Делаем текущую клетку родительской для это клетки. Расчитываем стоимости F, G и H клетки. if (!openList.Contains(neightbour)) { openList.Add(neightbour); neightbour.parent = min; neightbour.H = (int)neightbour.mandist(finish); //стоимость до итоговой точки neightbour.G = start.price(min); //стоимость относительно прямой или диагонали neightbour.F = neightbour.H + neightbour.G; //суммарная стоимость continue; } // Если клетка уже в открытом списке, то проверяем, не дешевле ли будет путь через эту клетку. Для сравнения используем стоимость G. if (neightbour.G + neightbour.price(min) < min.G) { // Более низкая стоимость G указывает на то, что путь будет дешевле. Эсли это так, то меняем родителя клетки на текущую клетку и пересчитываем для нее стоимости G и F. neightbour.parent = min; // вот тут я честно хз, надо ли min.parent или нет neightbour.H = (int)neightbour.mandist(finish); neightbour.G = start.price(min); neightbour.F = neightbour.H + neightbour.G; } if (i == iteration) { iteration += iterations; yield return(null); } // Если вы сортируете открытый список по стоимости F, то вам надо отсортировать весь список в соответствии с изменениями. } //d) Останавливаемся если: //Добавили целевую клетку в открытый список, в этом случае путь найден. //Или открытый список пуст и мы не дошли до целевой клетки. В этом случае путь отсутствует. if (openList.Contains(finish)) { found = true; } if (openList.Count == 0) { noroute = true; } } List <Point> completePatch = new List <Point>(); //3) Сохраняем путь. Двигаясь назад от целевой точки, проходя от каждой точки к ее родителю до тех пор, пока не дойдем до стартовой точки. Это и будет наш путь. if (!noroute) { //формируем список возвращаемый клиенту(внимание список будет получен с конца(start в конце)а так-же необходимо отменить применение настроек): completePatch.Add(finish); Point rd = finish.parent; while (!rd.equals(start)) { completePatch.Add(rd); rd = rd.parent; if (rd == null) { break; } } if (!completePatch.Contains(start)) { completePatch.Add(start); } client.patch = completePatch; //Указываем клиенту список point которые следует пройти для начала min = null; tmpList = new List <Point>(); openList = new List <Point>(); closedList = new List <Point>(); } else { activeClient.patch_not_realy = true; client.patch = new List <Point>(); min = null; tmpList = new List <Point>(); openList = new List <Point>(); closedList = new List <Point>(); } state = aStarState.founded; } else { //Debug.Log("Список поинтов клиента пуст"); } } else { activeClient.patch_not_realy = true; } }
private bool ApplyPatch(ClientPatch Patch) { string grfPath; bool retVal = true; switch (Patch.PatchAction) { case EPatchAction.PatcherUpdate: case EPatchAction.None: return(true); case EPatchAction.PatchReset: // reset reg RegHelper.PatchReset(Patch.PatchID); // fake count, so no patch proceed PatchlistHelper.Patches.Clear(); // info MessageBox.Show("Your patches has been reset.\nPlease restart the Patcher to patch again.\n\nThank you.", "Patcher notice", MessageBoxButtons.OK, MessageBoxIcon.Information); // close app Close(); // dont try to update on success return(false); case EPatchAction.GrfAdd: grfPath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, Patch.Target) + ".grf"; try { GrfHelper.GrfFromCache(Patch.Target, grfPath); // ensure GRF get loaded GrfHelper.MergeGrf(Patch.Target, Patch.FilePath); } catch (Exception e) { retVal = false; MessageBox.Show("Failed to apply Patch \"" + Patch.PatchName + "\".\nSkip.."); System.Diagnostics.Debug.WriteLine(e); } break; case EPatchAction.GrfDelete: grfPath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, Patch.Target) + ".grf"; try { GrfHelper.GrfFromCache(Patch.Target, grfPath); // ensure GRF get loaded GrfHelper.DeleteFromGrf(Patch.Target, Patch.PatchName); } catch (Exception e) { retVal = false; MessageBox.Show("Failed to apply Patch \"" + Patch.PatchName + "\".\nSkip.."); System.Diagnostics.Debug.WriteLine(e); } break; case EPatchAction.DataAdd: if (DataHelper.AddFiles(Patch.FilePath) == false) { retVal = false; MessageBox.Show("Failed to apply Patch \"" + Patch.PatchName + "\".\nSkip.."); } break; case EPatchAction.DataDelete: if (DataHelper.DeleteFile(Patch.PatchName) == false) { retVal = false; MessageBox.Show("Failed to apply Patch \"" + Patch.PatchName + "\".\nSkip.."); } break; } return(retVal); }
private void HandlePatchProgress(ClientPatch Patch, System.Net.DownloadProgressChangedEventArgs e) { UpdateProgressbar(e.ProgressPercentage); UpdateStatus("Work on: " + Patch.PatchDisplayname + " [ " + Tools.GetFileSize(e.BytesReceived) + " / " + Tools.GetFileSize(e.TotalBytesToReceive) + " ]"); }
private bool ApplyPatch(ClientPatch patch) { string grfPath; bool retVal = true; switch (patch.Action) { case EPatchAction.PatcherUpdate: case EPatchAction.None: return(true); case EPatchAction.PatchReset: // Reset registry mRegistry.PatchReset(patch.ID); // Fake patch count, so no patch will be downloaded after this mPatches.Clear(); // Output info MessageBox.Show("Your patches has been reset.\nPlease restart the Patcher to patch again.\n\nThank you.", "Patcher notice", MessageBoxButtons.OK, MessageBoxIcon.Information); // Close the patcher asap Close(); return(false); case EPatchAction.GrfAdd: grfPath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, patch.Target); if (grfPath.EndsWith(".grf") == false) { grfPath += ".grf"; } try { GrfHelper.GrfFromCache(patch.Target, grfPath); // Ensure the GRF got loaded GrfHelper.MergeGrf(patch.Target, patch.FilePath); } catch (Exception e) { retVal = false; MessageBox.Show("Failed to apply Patch \"" + patch.Name + "\".\nSkip.."); System.Diagnostics.Debug.WriteLine(e); } break; case EPatchAction.GrfDelete: grfPath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, patch.Target) + ".grf"; try { GrfHelper.GrfFromCache(patch.Target, grfPath); // Ensure the GRF got loaded GrfHelper.DeleteFromGrf(patch.Target, patch.Name); } catch (Exception e) { retVal = false; MessageBox.Show("Failed to apply Patch \"" + patch.Name + "\".\nSkip.."); System.Diagnostics.Debug.WriteLine(e); } break; case EPatchAction.DataAdd: if (DataHelper.AddFiles(patch) == false) { retVal = false; MessageBox.Show("Failed to apply Patch \"" + patch.Name + "\".\nSkip.."); } break; case EPatchAction.DataDelete: if (DataHelper.DeleteFile(patch.Name) == false) { retVal = false; MessageBox.Show("Failed to apply Patch \"" + patch.Name + "\".\nSkip.."); } break; } return(retVal); }
private bool ApplyPatch(ClientPatch Patch) { string grfPath; bool retVal = true; switch (Patch.PatchAction) { case EPatchAction.PatcherUpdate: case EPatchAction.None: return true; case EPatchAction.PatchReset: // reset reg RegHelper.PatchReset(Patch.PatchID); // fake count, so no patch proceed PatchlistHelper.Patches.Clear(); // info MessageBox.Show("Your patches has been reset.\nPlease restart the Patcher to patch again.\n\nThank you.", "Patcher notice", MessageBoxButtons.OK, MessageBoxIcon.Information); // close app Close(); // dont try to update on success return false; case EPatchAction.GrfAdd: grfPath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, Patch.Target) + ".grf"; try { GrfHelper.GrfFromCache(Patch.Target, grfPath); // ensure GRF get loaded GrfHelper.MergeGrf(Patch.Target, Patch.FilePath); } catch (Exception e) { retVal = false; MessageBox.Show("Failed to apply Patch \"" + Patch.PatchName + "\".\nSkip.."); System.Diagnostics.Debug.WriteLine(e); } break; case EPatchAction.GrfDelete: grfPath = Path.Combine(AppDomain.CurrentDomain.BaseDirectory, Patch.Target) + ".grf"; try { GrfHelper.GrfFromCache(Patch.Target, grfPath); // ensure GRF get loaded GrfHelper.DeleteFromGrf(Patch.Target, Patch.PatchName); } catch (Exception e) { retVal = false; MessageBox.Show("Failed to apply Patch \"" + Patch.PatchName + "\".\nSkip.."); System.Diagnostics.Debug.WriteLine(e); } break; case EPatchAction.DataAdd: if (DataHelper.AddFiles(Patch.FilePath) == false) { retVal = false; MessageBox.Show("Failed to apply Patch \"" + Patch.PatchName + "\".\nSkip.."); } break; case EPatchAction.DataDelete: if (DataHelper.DeleteFile(Patch.PatchName) == false) { retVal = false; MessageBox.Show("Failed to apply Patch \"" + Patch.PatchName + "\".\nSkip.."); } break; } return retVal; }
public static bool AddFiles(ClientPatch patch) { string abPath = Path.GetDirectoryName(System.Windows.Forms.Application.ExecutablePath); return(UnpackFile(patch.FilePath, abPath)); }