Exemple #1
0
        private void GetIslandBalls(List <Island> islands, BallPrefabController ball)
        {
            Island island = islands.FirstOrDefault(i => i.balls.Contains(ball));

            if (island == null)
            {
                island = new Island();
                island.balls.Add(ball);
                islands.Add(island);

                if (ball.position.x == 0)
                {
                    island.aloneIsland = false;
                }
            }

            List <BallPrefabController> neighbors = GetExistingNeighbors(ball);

            foreach (BallPrefabController neighbor in neighbors)
            {
                if (island.balls.Contains(neighbor))
                {
                    continue;
                }
                island.balls.Add(neighbor);
                if (neighbor.position.x == 0)
                {
                    island.aloneIsland = false;
                }
                GetIslandBalls(islands, neighbor);
            }
        }
Exemple #2
0
 /// <summary>
 /// Usuwa piłkę z logiki
 /// </summary>
 /// <param name="ball"></param>
 private void RemoveBall(BallPrefabController ball)
 {
     balls[ball.position.x, ball.position.y] = null;
     ballConfigurations[ball.ballConfiguration]--;
     if (ballConfigurations[ball.ballConfiguration] < 1)
     {
         ballConfigurations.Remove(ball.ballConfiguration);
     }
 }
Exemple #3
0
 /// <summary>
 /// Próbuje przypisać pozycje dla piłki, zwraca true jeżeli się powiedzie
 /// </summary>
 /// <param name="ball"></param>
 /// <param name="row"></param>
 /// <param name="column"></param>
 /// <returns></returns>
 private bool TrySetBallPosition(BallPrefabController ball, Vector2Int position)
 {
     if (IsPositionExistAndEmpty(position))
     {
         balls[position.x, position.y] = ball;
         ball.Set(position, GetBallPosition(position.x, position.y));
         return(true);
     }
     return(false);
 }
Exemple #4
0
 public void ReUse(BallPrefabController ball)
 {
     if (ball.GetType() == typeof(PlayerBallPrefabController))
     {
         usedPlayerBalls.Add(ball as PlayerBallPrefabController);
     }
     else
     {
         usedBalls.Add(ball);
     }
 }
Exemple #5
0
        /// <summary>
        /// Dodaje do przekaznej listy sąsiadów od ball którzy mają ten sam BallConfiguration co ball
        /// </summary>
        /// <param name="sameBalls"></param>
        /// <param name="neighbors"></param>
        /// <param name="ball"></param>

        private void AddSameBalls(List <BallPrefabController> sameBalls,
                                  List <BallPrefabController> neighbors, BallPrefabController ball)
        {
            List <Vector2Int> positions = new List <Vector2Int>(6);

            GetNeighborsPositions(positions, ball);

            List <BallPrefabController> newBalls = new List <BallPrefabController>(6);

            foreach (Vector2Int p in positions)
            {
                if (p.x < 0 || p.x > ballsRows - 1 ||
                    p.y < 0 || p.y > columns - 1)
                {
                    continue;
                }

                BallPrefabController b = balls[p.x, p.y];
                if (b == null)
                {
                    continue;
                }

                if (b.ballConfiguration.Equals(ball.ballConfiguration))
                {
                    if (!sameBalls.Contains(b))
                    {
                        newBalls.Add(b);
                    }
                }
                else
                {
                    if (!neighbors.Contains(b))
                    {
                        neighbors.Add(b);
                    }
                }

//                if (b != null &&
//                    b.ballConfiguration.Equals(ball.ballConfiguration) &&
//                    !sameBalls.Contains(b))
//                    newBalls.Add(b);
            }

            sameBalls.AddRange(newBalls);

            foreach (BallPrefabController newBall in newBalls)
            {
                AddSameBalls(sameBalls, neighbors, newBall);
            }
        }
Exemple #6
0
        private List <BallPrefabController> GetExistingNeighbors(BallPrefabController ball)
        {
            List <Vector2Int> positions = new List <Vector2Int>(6);

            GetNeighborsPositions(positions, ball);
            positions = positions.FindAll(IsPositionExistAndFull);
            List <BallPrefabController> result = new List <BallPrefabController>(positions.Count);

            foreach (Vector2Int p in positions)
            {
                result.Add(balls[p.x, p.y]);
            }
            return(result);
        }
Exemple #7
0
        /// <summary>
        /// Sprawdza czy dla przypisanej do player ball pozycji następuje zbicie.
        /// Jeżeli tak to zbija i punktuje.
        /// </summary>
        /// <param name="ball"></param>
        /// <returns></returns>
        private void Score(BallPrefabController ball)
        {
            List <BallPrefabController> scoredBalls = new List <BallPrefabController>
            {
                ball
            };
            List <BallPrefabController> neighbors = new List <BallPrefabController>();

            //sprawdz takie same piłki
            AddSameBalls(scoredBalls, neighbors, ball);

            //jeżeli są conajmniej 3
            if (scoredBalls.Count < 3)
            {
                EmitRow();
                if (CheckLose())
                {
                    gameController.Loose();
                }
                else
                {
                    comboCount = 0;
                    emitedPlayerBallsCount++;
                    playerBallEmiter.NextBall();
                }
                return;
            }

            comboCount++;
            //usuń referencje
            foreach (BallPrefabController b in scoredBalls)
            {
                RemoveBall(b);
            }

            //samotne wyspy piłek
            List <Island> aloneIslands = new List <Island>();

            GetIslandBalls(neighbors, aloneIslands);
            //usun referencje
            foreach (Island island in aloneIslands)
            {
                foreach (BallPrefabController b in island.balls)
                {
                    RemoveBall(b);
                }
            }
            //zniszcz
            StartCoroutine(DestroyBalls(scoredBalls, aloneIslands));
        }
Exemple #8
0
        /// <summary>
        /// Rozpoczyna emitowanie kólek
        /// </summary>
        /// <returns></returns>
        public IEnumerator StartEmit()
        {
            if (Screen.orientation == ScreenOrientation.Portrait ||
                Screen.orientation == ScreenOrientation.PortraitUpsideDown)
            {
                columns = PORTRAIT_COLUMNS;
            }
            else
            {
                columns = LANDSCAPE_COLUMNS;
            }

            rows = BALLS_TO_EMIT / columns;
            //TODO hardcoding
            ballsRows = rows * ALL_ROWS_MULTIPLIER + 1;

            balls           = new BallPrefabController[ballsRows, columns];
            usedBalls       = new List <BallPrefabController>(ballsRows * columns);
            usedPlayerBalls = new List <PlayerBallPrefabController>(10);

            ballConfigurations =
                new Dictionary <BallConfiguration, int>(configurations.Count);
            foreach (BallConfiguration ballConfiguration in configurations)
            {
                ballConfigurations.Add(ballConfiguration, 0);
            }

            for (int row = 0; row < rows; row++)
            {
                for (int column = 0; column < columns; column++)
                {
                    BallPrefabController newBall = Instantiate(ballPrefab);
                    newBall.transform.SetParent(transform, false);
                    balls[row, column] = newBall;
                    newBall.Set(new Vector2Int(row, column), GetBallPosition(row, column),
                                GetRandomBallConfiguration());
                    yield return(null);
                }
            }
            nextBallEmit = Random.Range(ADD_BALL_MIN, ADD_BALL_MAX);

            playerBallEmiter.StartEmit();
        }
        protected void OnCollisionEnter2D(Collision2D coll)
        {
            if (emiter == null)
            {
                return;
            }

            BallPrefabController ball = coll.gameObject.GetComponent <BallPrefabController>();

            if (ball == null && !coll.gameObject.name.Equals(TOP_ZONE_COLLIDER))
            {
                return;
            }


            rigidbody2d.constraints = RigidbodyConstraints2D.FreezePositionY
                                      | RigidbodyConstraints2D.FreezePositionX;
            emiter.OnPlayerBallStay(ball);
            emiter = null;
        }
Exemple #10
0
        private void GetNeighborsPositions(List <Vector2Int> positions, BallPrefabController ball)
        {
            positions.Add(new Vector2Int(ball.position.x, ball.position.y - 1));
            positions.Add(new Vector2Int(ball.position.x, ball.position.y + 1));
            positions.Add(new Vector2Int(ball.position.x + 1, ball.position.y));
            positions.Add(new Vector2Int(ball.position.x - 1, ball.position.y));

            if ((firstBallPaddingLeft && ball.position.x % 2 == 0) ||
                (!firstBallPaddingLeft && ball.position.x % 2 == 1)) //zmiana

            {
                positions.Add(new Vector2Int(ball.position.x + 1, ball.position.y - 1));
                positions.Add(new Vector2Int(ball.position.x - 1, ball.position.y - 1));
            }
            else
            {
                positions.Add(new Vector2Int(ball.position.x + 1, ball.position.y + 1));
                positions.Add(new Vector2Int(ball.position.x - 1, ball.position.y + 1));
            }
        }
Exemple #11
0
        public void EmitRow()
        {
            if (emitedPlayerBallsCount - lastBallEmit != nextBallEmit)
            {
                return;
            }

            firstBallPaddingLeft = !firstBallPaddingLeft;
            MoveAllBallsDown();

            lastBallEmit = emitedPlayerBallsCount + nextBallEmit;
            nextBallEmit = Random.Range(ADD_BALL_MIN, ADD_BALL_MAX);
            List <BallPrefabController> ballsToEmit = new List <BallPrefabController>(columns);

            int count = usedBalls.Count;

            for (int i = count - 1; i >= 0 && count - i <= columns; i--)
            {
                usedBalls[i].ReUse();
                ballsToEmit.Add(usedBalls[i]);
                usedBalls.RemoveAt(i);
            }

            count = ballsToEmit.Count;
            for (int i = count; i < columns; i++)
            {
                BallPrefabController newBall = Instantiate(ballPrefab);
                newBall.transform.SetParent(transform, false);
                ballsToEmit.Add(newBall);
            }

            for (int column = 0; column < columns; column++)
            {
                balls[0, column] = ballsToEmit[column];
                ballsToEmit[column].Set(new Vector2Int(0, column), GetBallPosition(0, column),
                                        GetNextBallConfiguration());
                ballConfigurations[ballsToEmit[column].ballConfiguration]++;
            }
        }
 /// <summary>
 /// Wywołuje player ball gdy doleci do kólek
 /// </summary>
 public void OnPlayerBallStay(BallPrefabController collisionBall)
 {
     //przekazanie do obliczenia pozycji w emiterze kólek
     ballsEmiter.OnPlayerBallStay(playerBall, collisionBall);
 }
Exemple #13
0
        /// <summary>
        /// Metoda którą wywołuje pierwotnie player ball gdy doleci do kólek i zatrzyma swoją pozycję.
        /// Zwraca true jeżeli koniec gry.
        /// </summary>
        /// <param name="ball"></param>
        public void OnPlayerBallStay(BallPrefabController ball, BallPrefabController collisionBall)
        {
            ballConfigurations[ball.ballConfiguration]++;
            //dobieranie pozycji dla piłki
            float row    = -((ball.rectTransform.anchoredPosition.y - sizeAdjuster.ballRadius) / sizeAdjuster.rowHeight);
            int   rowInt = (int)(row - 0.5f);

            //kolizja z sufitem
            if (collisionBall == null)
            {
                rowInt = 0;
            }
            Vector2Int position = null;



            float column;

            if ((firstBallPaddingLeft && rowInt % 2 == 0) || (!firstBallPaddingLeft && rowInt % 2 == 1))//zmiana

            {
                column = (ball.rectTransform.anchoredPosition.x - sizeAdjuster.ballRadius) /
                         sizeAdjuster.ballDiameter;
            }
            else
            {
                column = (ball.rectTransform.anchoredPosition.x - sizeAdjuster.ballDiameter) /
                         sizeAdjuster.ballDiameter;
            }
            int columnInt = (int)(column + 0.5f);

            if (columnInt < 0)
            {
                columnInt = 0;
            }
            else if (columnInt >= columns)
            {
                columnInt = columns - 1;
            }

            position = new Vector2Int(rowInt, columnInt);
            if (!IsPositionExistAndEmpty(position))
            {
                if (collisionBall != null)
                {
                    float             diff = int.MaxValue;
                    List <Vector2Int> possiblePositions = new List <Vector2Int>(6);
                    GetNeighborsPositions(possiblePositions, collisionBall);
                    possiblePositions = possiblePositions.FindAll(IsPositionExistAndEmpty);
                    foreach (Vector2Int p in possiblePositions)
                    {
                        float rowDiff = Math.Abs(p.x - row);
                        if (rowDiff < diff)
                        {
                            position = p;
                            diff     = rowDiff;
                        }
                    }

                    if ((firstBallPaddingLeft && position.x % 2 == 0) ||
                        (!firstBallPaddingLeft && position.x % 2 == 1)) //zmiana

                    {
                        column = (ball.rectTransform.anchoredPosition.x - sizeAdjuster.ballRadius) /
                                 sizeAdjuster.ballDiameter;
                    }
                    else
                    {
                        column = (ball.rectTransform.anchoredPosition.x - sizeAdjuster.ballDiameter) /
                                 sizeAdjuster.ballDiameter;
                    }

                    foreach (Vector2Int p in possiblePositions)
                    {
                        float sumdiff = Math.Abs(p.x - row + p.y - column);
                        if (sumdiff < diff)
                        {
                            position = p;
                            diff     = sumdiff;
                        }
                    }
                }
                else
                {
                    //TODO dla kolizji z sufitem, ale chyba wszystko zawsze działa
                }
            }

            //spróbuj ustawić pozycje
            if (TrySetBallPosition(ball, position))
            {
                //punktuj!
                Score(ball);
            }
            else
            {
                //co prawda nie wchodzi tu raczej ale jakby co to:
                ball.DestroyBall(this, 0);
                playerBallEmiter.NextBall();
                Debug.LogError("Could not change ball position for row = " + row + "(" + rowInt +
                               ") and column = " + column + "(" + columnInt + ")");
            }
        }