NebulaGames

C++ To Blueprints Random Loot Drop

Mar 17th, 2019
2,445
0
Never
Not a member of Pastebin yet? Sign Up, it unlocks many cool features!
C++ 2.87 KB | None | 0 0
  1. #pragma once
  2.  
  3. #include "CoreMinimal.h"
  4. #include "Kismet/BlueprintFunctionLibrary.h"
  5. #include "Runtime/Engine/Classes/GameFramework/Actor.h"
  6. #include "Kismet/KismetMathLibrary.h"
  7. #include "LootBox.generated.h"
  8.  
  9.  
  10. // Custom struct that ties an object class to an integer to determine drop rate
  11.  
  12. USTRUCT(BlueprintType)
  13. struct FLoot_Box
  14. {
  15.     GENERATED_USTRUCT_BODY()
  16.  
  17. public:
  18.  
  19.     UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Nebula Structs")
  20.         TSubclassOf <AActor> Item_Class;
  21.     UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "Nebula Structs", meta = (ClampMin = "0", ClampMax = "100", UIMin = "0", UIMax = "100"))
  22.         int32 Drop_Rate;
  23.  
  24. };
  25.  
  26. UCLASS()
  27. class CODE_TEST_API ULootBox : public UBlueprintFunctionLibrary
  28. {
  29.     GENERATED_BODY()
  30.  
  31. public:
  32.  
  33.     /* Input "Loot Box" struct array and their respective "drop rate" ( 50 = 50% chance of being selected),
  34.     output will be the randomly selected class. The boolean output is for error handling to ensure the total "drop rate" = 100
  35.     Node will not function unless the total is exactly 100, negative values will be treated as their positive counterparts */
  36.  
  37.     UFUNCTION(BlueprintCallable, meta = (Category = "Nebula Nodes", Keywords = "Loot, Drop, Random, Loot Box, Chance"))
  38.         static void Random_Drop_Rate(TArray <FLoot_Box> Loot_Classes, TSubclassOf <AActor> &Drop_Item, bool &Drop_Rate_Equal_100);
  39.  
  40. };
  41.  
  42.  
  43. ------------------------------------------------------------------------------------------------------------------------------
  44.  
  45.  
  46. // Fill out your copyright notice in the Description page of Project Settings.
  47.  
  48. #include "LootBox.h"
  49.  
  50. void ULootBox::Random_Drop_Rate(TArray <FLoot_Box> Loot_Classes, TSubclassOf <AActor> &Drop_Item, bool &Drop_Rate_Equal_100)
  51. {
  52.     // Declare temporary integer array for storing all "Drop Rates"
  53.  
  54.     TArray <int32> DropRateArray;
  55.     int32 EqualTo100 = 0;
  56.  
  57.     // Add input array drop rates to temporary array while summing the values to create a range "max" for each Loot Item
  58.  
  59.     for (int x = 0; x < Loot_Classes.Num(); ++x)
  60.     {
  61.         if (x == 0)
  62.         {
  63.             DropRateArray.Add(FMath::Abs(Loot_Classes[x].Drop_Rate));
  64.         }
  65.         else
  66.         {
  67.             DropRateArray.Add(FMath::Abs(Loot_Classes[x].Drop_Rate) + (DropRateArray[x-1]));
  68.         }
  69.     }
  70.  
  71.     // Ensure all "Drop Rates" sum to EXACTLY 100
  72.  
  73.     if (DropRateArray.Last() == 100)
  74.     {  
  75.         // Generate a random number
  76.  
  77.         int32 DropIndex = UKismetMathLibrary::RandomIntegerInRange(1, 100);      
  78.  
  79.         // Start with the lowest range "max value" and keep moving up until random int <= max of range
  80.  
  81.         for (int x = 0; x < DropRateArray.Num(); ++x)
  82.         {
  83.             if (DropIndex <= DropRateArray[x])
  84.             {
  85.                 Drop_Item = Loot_Classes[x].Item_Class;
  86.                 break;
  87.             }
  88.             else
  89.                 ;
  90.         }
  91.         Drop_Rate_Equal_100 = true;
  92.     }
  93.  
  94.     // If drop rates do NOT sum to exactly 100 return a false boolean and a null drop item
  95.  
  96.     else
  97.     {
  98.         Drop_Item = nullptr;
  99.         Drop_Rate_Equal_100 = false;
  100.     }
  101. }
Advertisement
Add Comment
Please, Sign In to add comment