예제 #1
0
        bool CheckLineToPrint(SlotLine lineId, GenSymbolId symbolId, SymbolCombination symbolCombination, MatrixInWork matrix)
        {
            int maxMajorSymbols = symbolCombination.count;

            for (int i = 0; i < lineId.indexOnDrum.Length; i++)
            {
                int          indexInDrum  = lineId.indexOnDrum[i];
                SymbolInWork matrixSymbol = matrix.symbols[i][indexInDrum];

                if (i < maxMajorSymbols)
                {
                    if ((matrixSymbol.symbolMask & symbolId.symbolId) == 0)
                    {
                        return(false);
                    }
                }
                else
                {
                    if ((matrixSymbol.symbolMask & symbolId.symbolId) != 0 && matrixSymbol.fixedSymbol)
                    {
                        return(false);
                    }
                }
            }

            return(true);
        }
예제 #2
0
        bool RemoveLine(SlotLine lineId, GenSymbolId symbolId, MatrixInWork matrix)
        {
            int maxMajorDrums = symbolId.symbolConfig.combinations[0].count;

            for (int i = 1; i < maxMajorDrums; i++)
            {
                SymbolInWork workSymbol = matrix.symbols[i][lineId.indexOnDrum[i]];
                uint         symbolMask = workSymbol.symbolMask;
                if ((symbolMask & symbolId.symbolId) == 0)
                {
                    return(true);
                }
                else if (!workSymbol.fixedSymbol)
                {
                    workSymbol.symbolMask = workSymbol.symbolMask - symbolId.symbolId;
                    return(true);
                }
            }

            for (int i = maxMajorDrums; i < lineId.indexOnDrum.Length; i++)
            {
                SymbolInWork workSymbol = matrix.symbols[i][lineId.indexOnDrum[i]];
                if (!workSymbol.fixedSymbol)
                {
                    workSymbol.symbolMask = workSymbol.symbolMask - symbolId.symbolId;
                }
            }

            return(false);
        }
예제 #3
0
        public SymbolInWork Copy()
        {
            SymbolInWork newSymbol = new SymbolInWork();

            newSymbol.symbolMask  = symbolMask;
            newSymbol.fixedSymbol = fixedSymbol;
            return(newSymbol);
        }
예제 #4
0
 public MatrixInWork(int drumCount, int maxDrumHeight, bool createSymbols = true)
 {
     symbols = new SymbolInWork[drumCount][];
     for (int i = 0; i < symbols.Length; i++)
     {
         symbols[i] = new SymbolInWork[maxDrumHeight];
         if (createSymbols)
         {
             for (int j = 0; j < maxDrumHeight; j++)
             {
                 symbols[i][j] = new SymbolInWork();
             }
         }
     }
 }
예제 #5
0
 public void Set(SymbolInWork src)
 {
     symbolMask  = src.symbolMask;
     fixedSymbol = src.fixedSymbol;
 }
예제 #6
0
        void ProcessSymbols(int[] firstIndicies, MatrixInWork startMatrix)
        {
            List <MatrixStepBySymbol> steps = new List <MatrixStepBySymbol>();

            int   currentIndex       = 0;
            float symbolRewardFactor = 1.0f;
            float curReward          = 0.0f;

            float rewardChanceModifier = 1.0f;
            float maxRewardChanceValue = 16.0f;

            List <string> excludedLines   = new List <string>();
            int           countClearStart = 0;
            int           countIterations = 0;

            List <GenSymbolId> symbolsToGenerate = symbolIdToGenSymbol.Values.ToList();


            while (true)
            {
                countIterations++;

                if (currentIndex >= firstIndicies.Length)
                {
                    currentIndex = 0;
                }

                GenSymbolId  currentSymbol = symbolsToGenerate[Random.Range(0, symbolsToGenerate.Count)];
                MatrixInWork curMatrix;
                if (steps.Count == 0)
                {
                    curMatrix = startMatrix;
                    countClearStart++;
                }
                else
                {
                    curMatrix = steps.Last().matrix;
                }

                float needAllReward = (currentSpinInfo.finalRewardPercent - curReward);
                MatrixStepBySymbol   newStep;
                SymbolStepResultType result = FindMatrixForSymbol(firstIndicies[currentIndex], currentSymbol, curMatrix, needAllReward, rewardChanceModifier, excludedLines, out newStep);

                //если успешно добавили новую линию
                if (result == SymbolStepResultType.Success)
                {
                    float newFinalReward = curReward + newStep.currentReward;

                    //если достигли требуемой награды, прекращаем алгоритм
                    if (Mathf.Abs(newFinalReward - currentSpinInfo.finalRewardPercent) < currentSymbol.symbolConfig.GetMinimumReward() * 0.5f)
                    {
                        Debug.LogError("Reward reached!");
                        curReward += newStep.currentReward;
                        excludedLines.Add(newStep.lineCombination.tag);
                        steps.Add(newStep);
                        break;
                    }
                    else if (newFinalReward > (currentSpinInfo.finalRewardPercent +
                                               currentSymbol.symbolConfig.GetMinimumReward()))
                    {
                        //если не получилось за несколько раз, выдаем текущий результат (хоть он и не валидный)
                        if (rewardChanceModifier < (-maxRewardChanceValue + 0.001f))
                        {
                            Debug.LogError("Reward is very big! Finished");
                            curReward += newStep.currentReward;
                            excludedLines.Add(newStep.lineCombination.tag);
                            steps.Add(newStep);
                            break;
                        }
                        else
                        {
                            //уменьшаем вероятность больших наград и начинаем сначала
                            steps.Clear();
                            currentIndex = 0;
                            curReward    = 0.0f;
                            excludedLines.Clear();
                            rewardChanceModifier = Mathf.Min(rewardChanceModifier, -1.0f);
                            rewardChanceModifier = rewardChanceModifier * 2.0f;
                        }

                        continue;
                    }

                    curReward += newStep.currentReward;
                    currentIndex++;
                    steps.Add(newStep);
                    excludedLines.Add(newStep.lineCombination.tag);
                }
                else if (result == SymbolStepResultType.EstimateRewardIsSmall)
                {
                    //минимальная комбинация слишком большая для награды, которую осталось набрать, значит все ок, прерываем алгоритм.
                    break;
                }
                else if (result == SymbolStepResultType.NoAvaliableLines || result == SymbolStepResultType.LinesNotFound)
                {
                    //если не получилось за несколько раз, выдаем текущий результат (хоть он и не валидный)
                    if (rewardChanceModifier > (maxRewardChanceValue - 0.0001f))
                    {
                        Debug.LogError("Reward not reached, lines incorrect..");
                        break;
                    }
                    else
                    {
                        //уменьшаем вероятность больших наград и начинаем сначала
                        steps.Clear();
                        currentIndex = 0;
                        curReward    = 0.0f;
                        excludedLines.Clear();
                        rewardChanceModifier = Mathf.Max(rewardChanceModifier, 1.0f);
                        rewardChanceModifier = rewardChanceModifier * 2.0f;
                    }

                    continue;
                }
                else
                {
                    Debug.LogError("Something wrong! Unknown SymbolStepResultType");
                    steps.Clear();
                    excludedLines.Clear();
                    currentIndex         = 0;
                    curReward            = 0.0f;
                    rewardChanceModifier = 0.0f;
                }
            }

            Shuffle(symbolsToGenerate);

            //убираем линии которые еще могут сыграть, также генерим первые символы, если они еще не созданы, таким образом, что они не сыграют
            foreach (var curFirstindex in firstIndicies)
            {
                MatrixInWork lastMatrix   = steps.Last().matrix;
                SymbolInWork matrixSymbol = lastMatrix.symbols[0][curFirstindex];
                if (symbolIdToGenSymbol.ContainsKey(matrixSymbol.symbolMask))
                {
                    GenSymbolId foundSymbol;
                    if (symbolIdToGenSymbol.TryGetValue(matrixSymbol.symbolMask, out foundSymbol))
                    {
                        List <SlotLine> noRemoveLines;
                        bool            isRemoved = RemoveLinesForSymbol(curFirstindex, foundSymbol, lastMatrix, excludedLines, out noRemoveLines);
                        if (!isRemoved && noRemoveLines != null)
                        {
                            AddPlayingLinesToSteps(foundSymbol, lastMatrix, noRemoveLines, steps, excludedLines);
                        }
                    }
                }
                else
                {
                    GenSymbolId symbolFound = null;
                    for (int j = 0; j < symbolsToGenerate.Count; j++)
                    {
                        GenSymbolId curSymbol = symbolsToGenerate[j];
                        if ((curSymbol.symbolId & matrixSymbol.symbolMask) != 0 && !CheckSymbolByFirstUsed(firstIndicies, lastMatrix, curSymbol))
                        {
                            lastMatrix.symbols[0][curFirstindex].symbolMask = curSymbol.symbolId;
                            symbolFound = curSymbol;
                            break;
                        }
                    }

                    if (symbolFound == null)
                    {
                        symbolFound = symbolsToGenerate[0];
                    }

                    List <SlotLine> noRemoveLines;
                    bool            isRemoved = RemoveLinesForSymbol(curFirstindex, symbolFound, lastMatrix, excludedLines, out noRemoveLines);
                    if (!isRemoved && noRemoveLines != null)
                    {
                        AddPlayingLinesToSteps(symbolFound, lastMatrix, noRemoveLines, steps, excludedLines);
                    }
                }
            }

            //генерим оставшиеся символы, которые точно не сыграют
            MatrixInWork matrix = steps.Last().matrix;

            for (int i = 0; i < matrix.symbols.Length; i++)
            {
                for (int j = 0; j < matrix.symbols[i].Length; j++)
                {
                    SymbolInWork symbol = matrix.symbols[i][j];
                    if (!symbol.fixedSymbol)
                    {
                        Shuffle(symbolsToGenerate);
                        foreach (var curSymbolId in symbolsToGenerate)
                        {
                            if ((symbol.symbolMask & curSymbolId.symbolId) != 0)
                            {
                                symbol.symbolMask  = curSymbolId.symbolId;
                                symbol.fixedSymbol = true;
                            }
                        }
                    }
                }
            }

            Debug.Log("Finish generate! Need reward=" + currentSpinInfo.finalRewardPercent + "; real reward=" + curReward + "; steps=" + steps.Count + "; clearStart=" + countClearStart + "; allIterations=" + countIterations);

            int k1 = 0;

            foreach (var curStep in steps)
            {
                Debug.Log("Step" + (k1++) + ": Symbol=" + curStep.symbolId.symbolConfig.tag + "; Line=" + curStep.lineCombination.ToString() + "; reward=" + curStep.combination.reward);
            }

            matrix = steps.Last().matrix;
            for (int i = 0; i < matrix.symbols.Length; i++)
            {
                string curLine = i + ": ";
                for (int j = 0; j < matrix.symbols[i].Length; j++)
                {
                    string curSymbolStr = "[";
                    foreach (var s in symbolsToGenerate)
                    {
                        if ((matrix.symbols[i][j].symbolMask & s.symbolId) == 0)
                        {
                            curSymbolStr += "<_" + s.symbolConfig.tag + "_>";
                        }
                        else
                        {
                            curSymbolStr += "<" + s.symbolConfig.tag + ">";
                        }
                    }

                    curSymbolStr = curSymbolStr.Trim(new char[] { ',' }) + "]";
                    curLine     += curSymbolStr + ",";
                }
                curLine = curLine.Trim(new char[] { ',' }) + "]";

                Debug.Log("Matrix line " + curLine);
            }
        }