Optimizing Fruit Spawning
Code by Ireneusz A.user_6919294
pascal
a year ago
3.1 kB
9
Indexable
// Hej Daria, ja bym zrobił tak ^_-
type
// Struktura przechowująca typ owocu i jego prawdopodobieństwo wystąpienia
TFruitProbability = record
FruitType: TFruitType;
Probability: Integer; // Wartość w promilach (na 1000)
end;
const
// Tablica definiująca prawdopodobieństwa wystąpienia każdego typu owocu
// Wartości sumują się do 1000 (100%)
FRUIT_PROBABILITIES: array[0..6] of TFruitProbability = (
(FruitType: ftApple; Probability: 300), // 30%
(FruitType: ftBanana; Probability: 200), // 20%
(FruitType: ftStrawberry; Probability: 150), // 15%
(FruitType: ftOrange; Probability: 150), // 15%
(FruitType: ftGrape; Probability: 100), // 10%
(FruitType: ftWatermelon; Probability: 90), // 9%
(FruitType: ftDragonFruit; Probability: 10) // 1%
);
{*
Funkcja losuje typ owocu na podstawie zdefiniowanych prawdopodobieństw
@return Wylosowany typ owocu
*}
function GetRandomFruitType: TFruitType;
var
RandomValue, AccumulatedProb: Integer;
I: Integer;
begin
// Losujemy liczbę z zakresu 0-999
RandomValue := Random(1000);
AccumulatedProb := 0;
// Przechodzimy przez tablicę prawdopodobieństw, sumując je
// aż znajdziemy przedział, w którym mieści się wylosowana liczba
for I := Low(FRUIT_PROBABILITIES) to High(FRUIT_PROBABILITIES) do
begin
Inc(AccumulatedProb, FRUIT_PROBABILITIES[I].Probability);
if RandomValue < AccumulatedProb then
Exit(FRUIT_PROBABILITIES[I].FruitType);
end;
// Zabezpieczenie - gdyby coś poszło nie tak, zwracamy ostatni typ owocu
Result := FRUIT_PROBABILITIES[High(FRUIT_PROBABILITIES)].FruitType;
end;
{*
Procedura tworzy nowy owoc lub przenosi istniejący w nowe miejsce
Odpowiada za:
- Wylosowanie typu owocu zgodnie z zadanymi prawdopodobieństwami
- Utworzenie lub aktualizację instancji owocu
- Umieszczenie owocu w losowej pozycji na planszy
*}
procedure TMainForm.SpawnFood;
var
NewFruitType: TFruitType;
NewPosition: TPointF;
begin
// Losujemy nowy typ owocu według zdefiniowanych prawdopodobieństw
NewFruitType := GetRandomFruitType;
// Jeśli nie mamy owocu lub typ się zmienił, tworzymy nową instancję
if (not Assigned(FCurrentFruit)) or (FCurrentFruit.FruitType <> NewFruitType) then
begin
// Bezpiecznie zwalniamy poprzedni owoc (jeśli istniał)
FreeAndNil(FCurrentFruit);
// Tworzymy nowy owoc i ustawiamy jego rodzica
FCurrentFruit := TFruit.Create(Self, NewFruitType);
FCurrentFruit.Parent := GameRec;
end;
// Obliczamy nową pozycję, upewniając się, że owoc nie wyjdzie poza granice
// Max(0, ...) zapewnia, że pozycja nie będzie ujemna
NewPosition.X := Max(0, Random(Round(GameRec.Width - FCurrentFruit.Width)));
NewPosition.Y := Max(0, Random(Round(GameRec.Height - FCurrentFruit.Height)));
// Ustawiamy obliczoną pozycję
FCurrentFruit.Position := NewPosition;
end;
// Nie ma za co, pozdrawiam Irek. Editor is loading...
Leave a Comment