Announcement

Collapse
No announcement yet.

[SUPPORT] Advanced Turn Based Tile Toolkit

Collapse
X
 
  • Filter
  • Time
  • Show
Clear All
new posts

    Originally posted by Sreno1 View Post
    Wow, thank you so much. This is great, exactly what I was looking for!
    No, problem! I was planning to implement what you were asking for pretty soon anyway. You asking just sped me up a bit. I'll be using some of that code for the first game example I'm working on, showing how you can use 2D with the toolkit and adding touch contols. Here's a little WIP screenshot of the mobile game map, using my own shoddy pixel art:

    Click image for larger version

Name:	JNHKvto.png
Views:	1
Size:	311.6 KB
ID:	1075598
    The Advanced Turn Based Tile Toolkit (Marketplace page - Feedback thread)

    Comment


      I just bought this blueprint pack today, and just fiddling around with it, it's amazing what you've done so far! After watching the tutorial videos and reading this thread, I do have a couple questions I hope you can answer;
      I can't seem to find the option for diamond shaped vision. Maybe I'm just thick and glossed over it, I'm not sure. Can you help me?
      Secondly, I want to be able to set a minimum attack range, so a ranged unit can't attack the tiles immediately adjacent to it, for example. Would that be possible?
      Finally, I'd like to have a setup for counter-attacks, so an attacking melee unit also takes some damage from the attacked melee unit. I have a couple ideas on how to implement this, but I figured I'd consult the creator of the blueprint first before tinkering around blindly, or accidentally skipping over a readily available option.

      EDIT: I found the diamond shaped vision option! And the minimum range option (though I can't seem to figure out how to get that to apply on a per-unit basis, so melee units can still attack tiles immediately around them. Some help would be nice but I might figure it out yet) So disregard that, I'm still a noob at this.

      Also, something else I can't seem to figure out in the interim: When the game starts, one of the units is already selected. Would it be possible to have the game start in a "Neutral" state, with no units selected, just a free cursor, before selecting and issuing orders to a unit?
      Last edited by MonkeyPants; 05-04-2015, 01:36 AM.

      Comment


        Originally posted by MonkeyPants View Post
        I just bought this blueprint pack today, and just fiddling around with it, it's amazing what you've done so far! After watching the tutorial videos and reading this thread, I do have a couple questions I hope you can answer;
        I can't seem to find the option for diamond shaped vision. Maybe I'm just thick and glossed over it, I'm not sure. Can you help me?
        Secondly, I want to be able to set a minimum attack range, so a ranged unit can't attack the tiles immediately adjacent to it, for example. Would that be possible?
        Finally, I'd like to have a setup for counter-attacks, so an attacking melee unit also takes some damage from the attacked melee unit. I have a couple ideas on how to implement this, but I figured I'd consult the creator of the blueprint first before tinkering around blindly, or accidentally skipping over a readily available option.

        EDIT: I found the diamond shaped vision option! And the minimum range option (though I can't seem to figure out how to get that to apply on a per-unit basis, so melee units can still attack tiles immediately around them. Some help would be nice but I might figure it out yet) So disregard that, I'm still a noob at this.

        Also, something else I can't seem to figure out in the interim: When the game starts, one of the units is already selected. Would it be possible to have the game start in a "Neutral" state, with no units selected, just a free cursor, before selecting and issuing orders to a unit?
        Hi MonkeyPants, glad you figured out the diamond shape/minimum range stuff on your own. It is not set up at a per-unit basis at the moment, but it is very easy to set up. First you should create two new public variables in the Unit_Parent blueprint; one boolean and one integer. You could call the boolean “diamond shaped range” and the integer “min range”. Then in ATBTT_PlayerController go to the Activate Unit part of the blueprint and get those two public variables from current pawn, the same way I get current move, range etc. in that part of the graph. Connect diamond shaped range to the “Diamond Shape” poolean input in the Find Tiles In Range function and min range on the min range integer input and you’re good to go.

        It is worth noting one bug, though. If you enable diagonal movement on a pawn, but have diamond shaped vision and a range of 1 it will cause problems. The reason is that when the AI finds a path to a player it naïvely assumes that any tile that is 1 movement away from the player are also in range of the player. If the AI does have diagonal movement it may stop on one of the tiles diagonal to the player and then try to attack. If it has a diamond shaped range of 1 the player will not be in range. When looking for a target this will return 0 and the AI will teleport to index 0 on the grid. To avoid this do not use any units with both diagonal movement, diamond shaped vision and a range of 1. I think this is a corner case as all games I know of with diagonal movement do not have diamond shaped vision. I am nonetheless working on a solution, but it’s actually a somewhat tricky problem to solve.

        As for starting the game with no units selected, I solved this for another user a few posts up. Look at my post three posts before your own.

        There are a number of different ways to set up counter attacks, and it depends a bit what you’re going for. I would start by looking in the blueprint graph of Unit_Parent in the Receive Damage part of the graph. From there you should fire a new attack target event from the unit receiving damage. There’s a bit more to it than that, but that’s the general idea.
        The Advanced Turn Based Tile Toolkit (Marketplace page - Feedback thread)

        Comment


          So I've been tinkering with getting my ATB style system to work, where each unit has a stat with say 100pts, and each world tick they regenerate some number of those points, and when it reaches the max value they call their turn and act accordingly.

          Most "difficult" part is figuring out what blueprint nodes I can safely just delete XD in regards to turn structure and ordering!

          Beyond that it's been a joy working with this.

          Any suggestions for how to easily do grid highlighting for things like abilities and spells?(such as a fireball that hits X hexes).

          Comment


            Hi VFe, can't say I completely understand the first thing you are trying to accomplish. Are you assigning each unit a random initiative value each turn and activating them in that order? Or are they using points from a pool during their turn and how much points they use determine how long until they can act again?

            Turn structure and ordering is pretty much exclusively handled in ATBTT_Game_Mode, with the exception of switching between units by clicking on them, which is handled by ATBTT_PlayerController.

            If you want to highlight an area a spell hits I suggest you use the Find Tile In Range function and simply call it from the center of the explosion.
            The Advanced Turn Based Tile Toolkit (Marketplace page - Feedback thread)

            Comment


              Originally posted by VFe View Post
              So I've been tinkering with getting my ATB style system to work, where each unit has a stat with say 100pts, and each world tick they regenerate some number of those points, and when it reaches the max value they call their turn and act accordingly.
              Great idea, mind to share how you increase the points of all units and check if they are higher than 100 at the same time? Main problem I see should be to first get all results after a tick, then look which of them are higher than 100 and finally check which one of them is highest.
              Are you using a ForLoop with the initiative order array to compare the current points of each pawn to 100? I wouldn't even know how to compare a value of a group of pawns which is variable in size to get the pawn with the largest value..

              @ Monokkel
              Could you please briefly explain to me how ranged attacks work? I'm working on activated abilities and I'm struggeling with creating attacks with a different range than the characters 'Range' value. Everything works fine for attacks with the same range as the pawns and changing the characters 'Range' on activation of the ability works, too. Isn't there a function I can run to set the attack range to my custom spell range variable without touching the characters 'Range' value?

              Comment


                @Monokkel
                Ah yeah, you're right, it's weird how I missed that post. Thanks so much for your patience!
                And what you described for counter-attacks is almost exactly what I ended up doing. Works great!

                Comment


                  Originally posted by Hinato View Post
                  Could you please briefly explain to me how ranged attacks work? I'm working on activated abilities and I'm struggeling with creating attacks with a different range than the characters 'Range' value. Everything works fine for attacks with the same range as the pawns and changing the characters 'Range' on activation of the ability works, too. Isn't there a function I can run to set the attack range to my custom spell range variable without touching the characters 'Range' value?
                  There is indeed. Run the function Find Tiles in Range, which is stored in BP_GridManager. It is usually called in ATBTT_PlayerController in the Activate Unit part of the blueprint graph. Here the range value of current pawn is connected to the range input of Find Tiles In Range, which is why visibility works like it does out of the box.

                  Originally posted by MonkeyPants View Post
                  @Monokkel
                  Ah yeah, you're right, it's weird how I missed that post. Thanks so much for your patience!
                  And what you described for counter-attacks is almost exactly what I ended up doing. Works great!
                  Happy to hear it works!
                  The Advanced Turn Based Tile Toolkit (Marketplace page - Feedback thread)

                  Comment


                    Originally posted by Monokkel View Post
                    Hi VFe, can't say I completely understand the first thing you are trying to accomplish. Are you assigning each unit a random initiative value each turn and activating them in that order? Or are they using points from a pool during their turn and how much points they use determine how long until they can act again?
                    Second one, essentially, blurring the lines between turn based and real-time a bit. I was just commenting that because my system is so different the hardest part has been having to read your code in depth and figure out which parts I can safely delete without losing other functionality XD. Which is a good thing!

                    Great idea, mind to share how you increase the points of all units and check if they are higher than 100 at the same time? Main problem I see should be to first get all results after a tick, then look which of them are higher than 100 and finally check which one of them is highest.
                    Are you using a ForLoop with the initiative order array to compare the current points of each pawn to 100? I wouldn't even know how to compare a value of a group of pawns which is variable in size to get the pawn with the largest value..
                    Every unit has an Action Point and Action Point Regen attribute, so in unit parent every tick their AP pool is filled by an amount determined by their APR, and when that threshold hits 100, the unit either takes an action according to its AI, or if controlled by the player, an action going by its list of queued actions, pays the cost of the associated action(which varies) from their AP pool, and then can't act until it hits 100 again.

                    When a unit hits 100 they're added to an array and only take their action if they're the only member in the array, in the event that two units are in the array(they both hit 100 on the same event tick), they're sorted by their swiftness attribute and the higher acts first, in the event they have the same swiftness, a random die is rolled for each until the die rolls are not the same and the highest goes first. Basically in this "psuedo-realtime" setup gotta make sure that no two units are ever acting at exactly the same time or else you get weird results(like two units moving to the same valid hex at the same time and such).

                    Game I'm working on is somewhat a hybrid SRPG and RTS in terms of its system.
                    Last edited by VFe; 05-05-2015, 10:38 AM.

                    Comment


                      Originally posted by VFe View Post
                      When a unit hits 100 they're added to an array and only take their action if they're the only member in the array, in the event that two units are in the array(they both hit 100 on the same event tick), they're sorted by their swiftness attribute and the higher acts first, in the event they have the same swiftness, a random die is rolled for each until the die rolls are not the same and the highest goes first.
                      We thought about a system like that, too. But we are still not sure if we want to go with something like that. The other idea would be that every character acts when a counter (counting up from 0) is equal to his initiative value or a multiple of that. A random roll when initiative of multiple characters is the same would also be necessary here.
                      We just want to give characters with higher initiative the ability to act more often than characters with lower initiative.

                      Is there a way to easily sort an array of actors by one of their values? (Sort all actors with Action Points greater than 100 by their Swiftness)

                      Originally posted by Monokkel View Post
                      There is indeed. Run the function Find Tiles in Range, which is stored in BP_GridManager. It is usually called in ATBTT_PlayerController in the Activate Unit part of the blueprint graph. Here the range value of current pawn is connected to the range input of Find Tiles In Range, which is why visibility works like it does out of the box.
                      Thx! Going to look into that right now!

                      Edit: Everything worked out quite well! Only thing that seems to be a little more work is getting targeting meshes on enemy as well as player tiles (for abilities that could target either of them).

                      While I'm at it.. Is there an easy way to get all tiles within a non-tile radius?
                      Let's say I give an input in UE4 units, like for example 480 units. Now I want to get all tiles whose center is within a 480 units radius and finally get all pawns that are on those tiles.
                      Last edited by Hinato; 05-05-2015, 04:57 PM.

                      Comment


                        Originally posted by VFe View Post
                        Second one, essentially, blurring the lines between turn based and real-time a bit. I was just commenting that because my system is so different the hardest part has been having to read your code in depth and figure out which parts I can safely delete without losing other functionality XD. Which is a good thing!

                        Every unit has an Action Point and Action Point Regen attribute, so in unit parent every tick their AP pool is filled by an amount determined by their APR, and when that threshold hits 100, the unit either takes an action according to its AI, or if controlled by the player, an action going by its list of queued actions, pays the cost of the associated action(which varies) from their AP pool, and then can't act until it hits 100 again.

                        When a unit hits 100 they're added to an array and only take their action if they're the only member in the array, in the event that two units are in the array(they both hit 100 on the same event tick), they're sorted by their swiftness attribute and the higher acts first, in the event they have the same swiftness, a random die is rolled for each until the die rolls are not the same and the highest goes first. Basically in this "psuedo-realtime" setup gotta make sure that no two units are ever acting at exactly the same time or else you get weird results(like two units moving to the same valid hex at the same time and such).

                        Game I'm working on is somewhat a hybrid SRPG and RTS in terms of its system.
                        Ok, I think I understand. That’s a pretty interesting setup, though I would personally do it a bit differently. I would avoid increasing something per tick and instead go for something more predictable. One way could be to have an initiative counter that starts at 0. Units start with different initiative values with 0 being the best and higher values being worse. The game would check if any pawns have initiative 0; and if not would increase the counter by 1 and check again. When a unit takes an action it increases its initiative by a certain amount depending on the action. If a unit has an initiative value equal to the counter, but has not added any actions to its queue yet it would increase its initiative by 1.

                        So for example, you have two units, one fast with starting initiative 1 and one slow with starting initiative 3. The game initiative counter starts at 0 and checks all units for that value with a foreach-loop. Finding no pawns it increases to 1 and checks again. The unit with initiative 1 has queued an attack action and now gets to act, the attack costing 2 initiative, putting its initiative at 3. The counter increases to 2, finding no pawns. Then it increases to 3 finding two pawns, deciding between them by coin-toss or comparing speed attributes. The slow unit is activated, but has no queued action and gets its initiative increased to 4, and so on.

                        If I understood your solution correctly, I think this will achieve similar results, but will be more predictable and easier to balance compared to using a PerTick counter, which would be affected by things like the animation and move speeds of units.

                        Originally posted by Hinato View Post
                        Is there a way to easily sort an array of actors by one of their values? (Sort all actors with Action Points greater than 100 by their Swiftness)
                        Sorting is certainly possible, but a bit tricky to explain. See the function Sort Pawns In Initiative Order Depending On Attribute (Or something similar. Can’t check now) in ATBTT_GameMode for an example sorting algorithm.


                        Originally posted by Hinato View Post
                        Edit: Everything worked out quite well! Only thing that seems to be a little more work is getting targeting meshes on enemy as well as player tiles (for abilities that could target either of them).
                        Ok, great! As for getting targeting meshes on both players and enemies, there are a couple of ways to do this. One is to modify the function to find both kinds of units (this is done in the last two nested functions inside Find Tiles In Range). If you do this, be sure to make it an option to only look for one type of pawn. Another way to do it is to run a ForEach-loop on the tiles in range array and compare the index (inside the range struct) of each tile in range with the same indexes of the Pawn Array to see what pawns of what factions are on each tile. This can be done after the Find Tiles In Range function has been run.

                        Originally posted by Hinato View Post
                        While I'm at it.. Is there an easy way to get all tiles within a non-tile radius?
                        Let's say I give an input in UE4 units, like for example 480 units. Now I want to get all tiles whose center is within a 480 units radius and finally get all pawns that are on those tiles.
                        Not out of the box, no. Can I ask why you would want to do this? It might be achievable using a tile radius instead. If you are using a hex grid, the XY-distance to a tile will always have a predictable relationship to the number of tiles it is from the starting point. In this case you can just take the distance you are interested in and divide it by NodeGapX (the distance in unreal units between tiles) and use that as the range input for a Find Tiles In Range function. This wouldn’t work with square grids as distances between tiles vary.
                        The Advanced Turn Based Tile Toolkit (Marketplace page - Feedback thread)

                        Comment


                          Thought I could post a couple of PMs between me and Wisdom-HELLy about implementing cover systems, since it might be of interest to more users. I’ve got HELLy’s permission to post this:
                          Originally posted by Wisdom-HELLy View Post
                          We are trying to accomplish a double work for our project: convert actual movement/attack system with a free action points system (attack and movement on demand if you have enough action points to accomplish) and apply a basic coverage system when the unit stands in front of a short wall (long wall gives hide to the unit so we don't need to make two coverages like XCOM).

                          With the second target, we've created an array of indexes+tile_parent (as I wrote in the main topic) that we can use to get a tile_parent from index.
                          This is essential for our coverage system because I think that the unit itself should trigger the coverage when at the end of a movement cycle it stands in front of a wall.

                          So, basically we find northern, eastern, western and southern tile from the current pawn index and then if in one of these 4 tiles we find a small wall we apply coverage (bonus and animation).
                          My first concern is about the bonus: my idea was to create 4 integer property like north coverage bonus, south coverage bonus etc. but... how can I line trace the attacker and check the rotation of the victim to know if the attack will suffer the malus from victim coverage?
                          My idea was to raycast from the attacker and get an array of tiles, but I think that is expensive and tricky.

                          A second idea is to check the area hit by the attacker shot...but in this case we need to assume there is a fixed NORD in the map.
                          I explain better: all pawns rotation should be relative from a fixed NORD of the map, so I can understand if a shot is taken from south of the map, for example, and apply the southern bonus for the victim.

                          What do you think will be the best solution? Maybe I missed a solution better than these?

                          Thanks,
                          HELLy
                          Your cover system seems reasonable. An adjustment I would probably want to make if you want to be as close to XCOM as possible is to pregenerate all the cover instead of calculating it each time a unit enters a tile that might have cover. This way you can have the option of showing all tiles with cover to the player at any time (possibly when he/she presses a button). To do this, I would follow my example in the “Add Viewport Terrain To Arrays” function in BP_GridManager. In the last part of this function I assign edge costs to all indexes depending on the height difference between each tile and its neighbors. Something very similar could be done with a cover system. An integer storage like you suggest is one possibility here. A slightly less efficient, but more intuitive one is to use structs like I do with edge costs.

                          As for deciding whether or not a unit has cover depending on where the attacker is standing in relation to the target, there are many ways to do this. If what you want to achieve is simply to for instance give cover bonus to a unit with eastern cover against all units east of that unit, you could simply find the X location of one unit and subtract it from the other. Depending on whether it is negative or positive you know which side of the unit it is. Same for north and south cover, only with the Y location.

                          Also, you’re saying that you are working on an action point system. I’m unsure if you are asking for my help on this, but if you are, know that the toolkit has a half-way implemented action point system already. If you check “Unit Can Split Up Turns” on a unit, movement can be parceled into multiple moves. This is quite simple to convert to also work for attacks. Rename Current and Max move to current/max action points and check that you have enough before making an attack, subtracting the appropriate number from current action points if you do. Also, disable the part in Receive Damage in Unit_Parent that ends the turn after a unit takes damage.

                          Those are my suggestions in any case. Looking forward to seeing your game in action!

                          - Knut
                          The Advanced Turn Based Tile Toolkit (Marketplace page - Feedback thread)

                          Comment


                            Originally posted by Monokkel View Post
                            Not out of the box, no. Can I ask why you would want to do this? It might be achievable using a tile radius instead.
                            I thought about creating AoEs like XCom grenades. There you can specify the center of your AoE independent of tile position and enemies that are going to be hit are marked with red color. I wanted to do something similar but show a decal on the tiles that are going to be hit instead of giving the units a red texture (we're using square tiles by the way).
                            With this I want to give the player more freedom of how exactly AoEs are placed and introduce an attribute which affects AoE radius with every point instead of increasing the radius by 1 tile every X points.

                            Maybe I need to get all pawns in a specified radius arround the mouse cursor and then check on which tiles those pawns are? So instead of looking if the radius overlaps with the center of a tile I could check which pawn meshes are overlapping with the radius. This could maybe work by using a sphere trace, unfortunately I have 0 experience with that so now I'll just continue searching the web for useful information

                            Also thanks for sharing the cover discussion! Some interesting stuff there
                            Last edited by Hinato; 05-06-2015, 11:47 AM.

                            Comment


                              @Hinato: You might consider not bothering querying the tiles at all, then. Simply use a spherical collision volume, enable collision on the skeletal meshes on pawns and see what pawns are overlapping the sphere. When the grenade explodes, run the Recieve Damage event on all units with skeletal meshes overlapping the sphere.
                              The Advanced Turn Based Tile Toolkit (Marketplace page - Feedback thread)

                              Comment


                                A couple very quick, probably very stupid questions;
                                So I did what you suggested above, as far as starting the camera free, and it worked, except now when the game starts it hovers over an enemy, and I can't seem to figure out how to prevent it from doing that.
                                Also, I would like the camera to be zoomed out a little more than the default when the game starts, but I can't seem to find that value in the camera blueprint that allows me to do that. I tried simply moving the camera itself in the blueprint viewport, which works, except then I can't zoom back IN again. I'm wondering if there's a smoother way to manipulate that in the blueprint itself.

                                Comment

                                Working...
                                X