/// <summary> /// Compute a weight on the move /// </summary> public virtual WeightData WeightMove(AIMove m, int width, int height, int depth) { var w = new WeightData(); blocksInComboIndex = 0; currentComboBlocksIndex = 0; if (m.gridAfterMove == null) { Log.Error("AI - Missing grid for move!"); return(w); } int weight = WeightGeneral(m, depth); // Compute combos sbyte currentBlock = 0; int currentCombo = 0; void CommitCommbo() { weight += WeightCombo(currentCombo, currentBlock, m.gridAfterMove, width, height); w.combosCount++; // Transfer current list to general list for (int i = 0; i < currentComboBlocksIndex; i++) { if (blocksInComboIndex < blocksInCombo.Length) { blocksInCombo[blocksInComboIndex] = currentComboBlocks[i]; blocksInComboIndex++; } } } var highestBlock = Vector2.one * -1; // Vertical for (int x = 0; x < width; x++) { for (int y = 0; y < height; y++) { sbyte block = m.gridAfterMove[x, y]; if (block == 99) { continue; } // Not in a combo if (currentBlock == 0) { if (block > 0) { currentBlock = block; currentCombo = 1; // Same than a list.Add(new Vector) but better when 10 000 elements! currentComboBlocks[currentComboBlocksIndex].x = x; currentComboBlocks[currentComboBlocksIndex].y = y; currentComboBlocksIndex++; } else { currentBlock = 0; currentCombo = 0; currentComboBlocksIndex = 0; } } else { // Blocks are falling if (block == 0) { // Skip continue; } // Check for an identical block if (currentBlock == block) { currentCombo++; currentComboBlocks[currentComboBlocksIndex].x = x; currentComboBlocks[currentComboBlocksIndex].y = y; currentComboBlocksIndex++; } // Combo breaker else { if (currentCombo >= 3) { CommitCommbo(); } // Reset currentCombo = 1; currentBlock = block; currentComboBlocks[currentComboBlocksIndex].x = x; currentComboBlocks[currentComboBlocksIndex].y = y; currentComboBlocksIndex++; } } if (block > 0) { if (y > highestBlock.y) { highestBlock.x = x; highestBlock.y = y; } } } // y if (currentCombo >= 3) { CommitCommbo(); } // Reset currentBlock = 0; currentCombo = 0; currentComboBlocksIndex = 0; // list.Clear } // x // Horizontal for (int y = 0; y < height; y++) { for (int x = 0; x < width; x++) { sbyte block = m.gridAfterMove[x, y]; if (block == 99) { continue; } // Not in a combo if (currentBlock == 0) { if (block > 0) { currentBlock = block; currentCombo = 1; currentComboBlocks[currentComboBlocksIndex].x = x; currentComboBlocks[currentComboBlocksIndex].y = y; currentComboBlocksIndex++; } else { currentBlock = 0; currentCombo = 0; currentComboBlocksIndex = 0; } } else { // Check for an identical block if (currentBlock == block) { currentCombo++; currentComboBlocks[currentComboBlocksIndex].x = x; currentComboBlocks[currentComboBlocksIndex].y = y; currentComboBlocksIndex++; } // Combo breaker else { if (currentCombo >= 3) { CommitCommbo(); } // Reset currentCombo = 1; currentBlock = block; currentComboBlocks[currentComboBlocksIndex].x = x; currentComboBlocks[currentComboBlocksIndex].y = y; currentComboBlocksIndex++; } } } // x if (currentCombo >= 3) { CommitCommbo(); } // Reset currentBlock = 0; currentCombo = 0; currentComboBlocksIndex = 0; } // y // Check if the game over is near weight += WeightDanger(m, highestBlock, w); w.total = weight; w.blocksInCombo = blocksInCombo.Take(blocksInComboIndex).ToArray(); return(w); }