< Return to Video

TANKS! Unity Tutorial - Phase 4 of 8 - Tank Health

  • 0:03 - 0:04
    Phase 4.
  • 0:05 - 0:07
    So what we're going to do is use a
  • 0:07 - 0:09
    slider component, and it looks like this.
  • 0:09 - 0:11
    The slider component is going to have
  • 0:11 - 0:13
    a totally different appearance to what you
  • 0:13 - 0:15
    normally expect from a slider.
  • 0:15 - 0:17
    We're basically repurposing that
  • 0:17 - 0:19
    to create the same interaction.
  • 0:19 - 0:21
    And we're going to use the background
  • 0:21 - 0:23
    and the foreground elements, which are called fills
  • 0:23 - 0:25
    to create the same effect.
  • 0:25 - 0:27
    What you don't see in this footage is that we're
  • 0:27 - 0:29
    also going to use a script to change the
  • 0:29 - 0:32
    color of that radial health wheel over time.
  • 0:32 - 0:34
    So it's going to change from nice green healthy
  • 0:34 - 0:37
    to orange, to red as you loose health.
  • 0:37 - 0:39
    And you'll see that as we go through.
  • 0:41 - 0:43
    Okay, so first a couple of things.
  • 0:43 - 0:46
    We're going to setup Unity to work how we want.
  • 0:47 - 0:49
    Just make sure up at the top
  • 0:50 - 0:52
    that we're set to Pivot,
  • 0:52 - 0:54
    in our axis handles.
  • 0:54 - 0:56
    What you'll see if you don't do that is
  • 0:56 - 1:00
    the handles just won't appear exactly as we're doing them.
  • 1:00 - 1:02
    So pivot and local is what you should see
  • 1:02 - 1:04
    up at the top of the interface.
  • 1:04 - 1:06
    We're going to start creating this now
  • 1:07 - 1:09
    so I'm going to create a new slider.
  • 1:09 - 1:11
    So a slider
  • 1:11 - 1:13
    currently looks totally different to what
  • 1:13 - 1:15
    we're trying to create.
  • 1:15 - 1:17
    So go to Create button on the hierarchy,
  • 1:17 - 1:19
    then UI section and choose Slider.
  • 1:22 - 1:24
    Then because this new UI system
  • 1:24 - 1:26
    has a whole bunch of different stuff to it I'm just going to
  • 1:26 - 1:28
    cover some basics to begin with.
  • 1:28 - 1:30
    So whenever you have a new UI
  • 1:30 - 1:32
    element it has to be a member
  • 1:32 - 1:34
    of a particular canvas.
  • 1:35 - 1:37
    So a canvas could be something that's filling the whole
  • 1:37 - 1:39
    screen, what we call a screen space canvas.
  • 1:39 - 1:41
    Or it could be something that's an element within
  • 1:41 - 1:44
    the 3D world or 2D world which we call
  • 1:44 - 1:46
    a world space canvas.
  • 1:46 - 1:49
    So the default is screen space,
  • 1:49 - 1:51
    so what you notice is that when you've added
  • 1:51 - 1:53
    this brand new canvas you've
  • 1:53 - 1:55
    got this giant looking rectangle,
  • 1:55 - 1:56
    so what is that?
  • 1:56 - 1:58
    That is a screen space canvas,
  • 1:58 - 2:00
    that's the default for
  • 2:00 - 2:02
    any brand new UI canvas.
  • 2:02 - 2:04
    Because it assumes that if you're making
  • 2:04 - 2:06
    a UI you probably want to put in stuff that's
  • 2:06 - 2:08
    made in screen space like a score or
  • 2:08 - 2:10
    maybe health at the bottom,
  • 2:10 - 2:12
    maybe some kind of status text
  • 2:12 - 2:14
    that's rendered over the entire screen.
  • 2:14 - 2:16
    We don't want to do that in this instance,
  • 2:16 - 2:18
    we're going to do one of those later on.
  • 2:18 - 2:21
    But for this we just want to make it world space.
  • 2:21 - 2:24
    Now the reason it looks huge compared to this
  • 2:24 - 2:26
    is that actually the amount of pixels
  • 2:26 - 2:28
    compared to the amount of units
  • 2:28 - 2:30
    is far far greater,
  • 2:30 - 2:32
    so those numbers just match up
  • 2:32 - 2:34
    so it looks a lot bigger than the actual
  • 2:34 - 2:36
    elements on the ground.
  • 2:36 - 2:38
    We're going to turn that in to a world space canvas
  • 2:38 - 2:40
    and then effectively redesign it.
  • 2:40 - 2:42
    And then the thing that we've actually added
  • 2:43 - 2:45
    is the health slider
  • 2:45 - 2:46
    and it looks like this by default.
  • 2:46 - 2:48
    So it doesn't make any sense to use something like
  • 2:48 - 2:50
    this to represent health.
  • 2:50 - 2:52
    You could have just a health bar and it just gets smaller,
  • 2:52 - 2:54
    we certainly don't need the handle because nobody's going
  • 2:54 - 2:56
    to be dragging the health.
  • 2:56 - 2:58
    We don't want the player to give them self more
  • 2:58 - 2:59
    health during the game.
  • 2:59 - 3:01
    It would be cool but it's not very fair.
  • 3:03 - 3:06
    We're going to totally change how this behaves.
  • 3:06 - 3:08
    And the first thing that we're going to do to achieve that
  • 3:08 - 3:10
    is to tweak the event system.
  • 3:12 - 3:15
    Any new UI setup is made up of a canvas,
  • 3:15 - 3:16
    which is where something is rendered,
  • 3:16 - 3:18
    and then the event system handles any
  • 3:18 - 3:21
    input in to that, that you might need.
  • 3:21 - 3:23
    Now we want this game to be extendable
  • 3:23 - 3:25
    so that if you're working on
  • 3:25 - 3:27
    it and you want to add certain features then
  • 3:27 - 3:29
    you might want to have something that's clickable on the screen.
  • 3:29 - 3:31
    So we're going to leave the event system in there
  • 3:31 - 3:34
    so we're not going to have intractable UI element
  • 3:34 - 3:36
    but we do want the event system to stay in the game.
  • 3:36 - 3:39
    But what the event system does is it handles input
  • 3:39 - 3:41
    for you clicking on or using
  • 3:41 - 3:43
    a joypad to select stuff.
  • 3:44 - 3:46
    And what it does is it gives you
  • 3:46 - 3:48
    horizontal and vertical axis.
  • 3:48 - 3:50
    and they're the same as inputs in the input manager.
  • 3:50 - 3:52
    But we don't want to use those because we don't
  • 3:52 - 3:55
    want them to conflict with our actual controls of the game.
  • 3:55 - 3:57
    But all I'm going to get you guys to do is type
  • 3:57 - 4:01
    in to these UI on the end.
  • 4:01 - 4:03
    So that if you ever want to extend the game
  • 4:03 - 4:05
    in standalone input you will have
  • 4:05 - 4:08
    horizontal UI, vertical UI inputs
  • 4:08 - 4:10
    to map to controls.
  • 4:11 - 4:13
    Not important for the kind of behaviour
  • 4:13 - 4:14
    that we're going to create,
  • 4:14 - 4:16
    but that's all we need to do just to set that up.
  • 4:17 - 4:21
    So horizontal axis just put UI on the end of both of those.
  • 4:21 - 4:23
    Same for vertical.
  • 4:24 - 4:28
    Then the last thing to setup how the canvas behaves
  • 4:28 - 4:30
    is to set the scaling
  • 4:30 - 4:32
    and to set the actual rendering modes.
  • 4:33 - 4:35
    The first thing to look at is this
  • 4:35 - 4:37
    component called Canvas Scaler.
  • 4:37 - 4:39
    So a canvas scaler is there to help you
  • 4:39 - 4:41
    develop for multiple resolutions.
  • 4:42 - 4:45
    So you have a reference size, so UI Scale Mode,
  • 4:45 - 4:48
    and you can use a whole bunch of different scales there.
  • 4:48 - 4:50
    And then you have Reference Pixels Per Unit.
  • 4:52 - 4:54
    So we're going to scale this down from
  • 4:54 - 4:56
    something that's screen space, so absolutely massive
  • 4:56 - 4:57
    compared to the actual world,
  • 4:57 - 4:59
    way, way, way smaller.
  • 4:59 - 5:01
    So we have to turn this Reference Pixels Per Unit
  • 5:01 - 5:03
    down to 1 instead of 100.
  • 5:03 - 5:05
    That will allow us to have
  • 5:05 - 5:08
    sizes that are sensible, instead of typing
  • 5:08 - 5:11
    0.001 scales.
  • 5:11 - 5:14
    So we set those reference pixels all the way down to 1.
  • 5:15 - 5:17
    And then finally to make it exist in
  • 5:17 - 5:19
    the world instead of on the screen
  • 5:19 - 5:21
    in the canvas component itself we set the
  • 5:21 - 5:24
    render mode to World Space.
  • 5:24 - 5:26
    So not Screen Space Overlay or Camera
  • 5:26 - 5:28
    World Space.
  • 5:28 - 5:30
    And what you'll see then is the rect transforms,
  • 5:30 - 5:32
    so all the positions and the scales
  • 5:32 - 5:34
    and where it's rendered,
  • 5:34 - 5:36
    they stop being greyed out, you can edit those.
  • 5:36 - 5:38
    fields and that's exactly what we want.
  • 5:38 - 5:41
    So I'm just going to recap a couple of steps there.
  • 5:42 - 5:44
    So with our event system
  • 5:44 - 5:46
    we've had to rename a couple of axis
  • 5:46 - 5:49
    so they don't conflict with out input manager.
  • 5:49 - 5:51
    We've set horizontal and vertical
  • 5:51 - 5:53
    to HorizontalUI and VerticalUI
  • 5:54 - 5:55
    on the Canvas Scaler.
  • 5:55 - 5:58
    We've set reference pixels per unit to 1
  • 5:58 - 6:00
    so that the values will make sense once we've
  • 6:00 - 6:03
    scaled it all the way down to the size of the tank.
  • 6:04 - 6:06
    And then on the canvas component of the canvas game object
  • 6:06 - 6:08
    we've set that render mode to World Space so that
  • 6:08 - 6:12
    it can be just a small plane in the world that
  • 6:12 - 6:13
    we can mess around with.
  • 6:13 - 6:16
    Now that we've changed that stuff nothing looks different.
  • 6:16 - 6:18
    Okay, so that's fine, that makes sense.
  • 6:18 - 6:20
    We haven't actually changed the size
  • 6:20 - 6:22
    and the positions and the width and height.
  • 6:22 - 6:24
    What you'll notice now is the width and height
  • 6:24 - 6:26
    can be changed and I can scale those
  • 6:26 - 6:29
    and make them different, but we're not going to do that.
  • 6:29 - 6:31
    For those of you that are unfamiliar,
  • 6:31 - 6:33
    this is a rect transform component that
  • 6:33 - 6:35
    replaces the transform component on
  • 6:35 - 6:37
    all UI element and all it's
  • 6:37 - 6:39
    doing is just giving you a few extra properties
  • 6:39 - 6:41
    that you'l use to manipulate your
  • 6:41 - 6:44
    UI elements, for example, having a pivot position
  • 6:44 - 6:45
    which can be useful.
  • 6:45 - 6:49
    And the anchors, and we'll come on to the anchors in a bit.
  • 6:49 - 6:51
    So whenever you see UI elements they'll just
  • 6:51 - 6:53
    have a rect transform, a rectangular transform
  • 6:53 - 6:55
    instead of a normal transform.
  • 6:55 - 6:57
    Like James says, they basically inherit
  • 6:57 - 6:59
    from that behind the scenes so they've got a lot
  • 6:59 - 7:01
    of the same properties.
  • 7:01 - 7:03
    So we want this to be the health wheel,
  • 7:03 - 7:05
    sat underneath the tank as you saw in the video at the
  • 7:05 - 7:07
    start of this phase.
  • 7:07 - 7:09
    So we're literally going to drag this
  • 7:09 - 7:11
    canvas and make it a child of
  • 7:11 - 7:13
    the tank so in the hierarchy just
  • 7:13 - 7:16
    grab Canvas, drop it on to the tank.
  • 7:17 - 7:19
    We want that canvas to drive around with the tank.
  • 7:19 - 7:21
    So currently it's a giant huge rectangle
  • 7:21 - 7:23
    in the sky that if we move the
  • 7:23 - 7:25
    tank around it's going to move around with it.
  • 7:26 - 7:28
    So it's kind of strange, we don't want that.
  • 7:28 - 7:30
    So I'm going to change the position
  • 7:31 - 7:35
    to (0, 0.1, 0).
  • 7:35 - 7:37
    So that's basically centred that, so if I
  • 7:37 - 7:39
    scroll around the world now you can see the centre of that
  • 7:39 - 7:43
    UI is now right in the middle of where the tank is.
  • 7:44 - 7:46
    This would be an easier way to see it.
  • 7:46 - 7:49
    That's it's axis handle, right at 0.
  • 7:49 - 7:51
    And then we want the width and hight, instead of this giant
  • 7:51 - 7:54
    900 by 400something we want it to be much smaller
  • 7:54 - 7:58
    so we just change the width and hight to be 3.5.
  • 8:00 - 8:02
    Scaled it all the way down.
  • 8:04 - 8:06
    So all I've done there is just select the canvas
  • 8:06 - 8:08
    I've hovered of the scene view, I've pressed F
  • 8:08 - 8:10
    to frame select it, so I was all the way out
  • 8:10 - 8:11
    because it was showing me it.
  • 8:11 - 8:13
    Now it's smaller I can hover,
  • 8:13 - 8:15
    press F to zoom in.
  • 8:15 - 8:19
    So we're nearly there, it's currently rotated the wrong way though
  • 8:19 - 8:21
    so we don't really want that.
  • 8:21 - 8:23
    So we're going to change the rotation,
  • 8:23 - 8:26
    so rotation is the second to last property there,
  • 8:26 - 8:29
    to (90, 0, 0)
  • 8:29 - 8:31
    90 in the X axis only.
  • 8:34 - 8:35
    And then once you've done that it should be
  • 8:35 - 8:37
    flat on the floor.
  • 8:37 - 8:39
    Now for those of you who haven't used the UI system before
  • 8:40 - 8:42
    there are a bunch of tools up at the
  • 8:42 - 8:43
    top left of Unity.
  • 8:43 - 8:46
    The fifth one, T on the keyboard is the shortcut,
  • 8:46 - 8:48
    is the UI tool.
  • 8:49 - 8:51
    That will give you these sort of desktop publishing
  • 8:51 - 8:53
    style dots around the
  • 8:53 - 8:55
    corners of that rectangle.
  • 8:57 - 8:59
    Okay, so just a recap of those values.
  • 9:00 - 9:02
    We've dragged the canvas on to the tank
  • 9:02 - 9:05
    so it's going to move around with the tank, follow it around,
  • 9:05 - 9:06
    by being a child.
  • 9:06 - 9:08
    We've selected the canvas
  • 9:08 - 9:13
    and then we set the position to (0, 0.1, 0)
  • 9:13 - 9:16
    and the rotation to (90, 0, 0).
  • 9:16 - 9:18
    So this little square is going to move around
  • 9:18 - 9:20
    with it so I'm just going to show you that.
  • 9:20 - 9:22
    Now as we move this around you can see that
  • 9:22 - 9:25
    is a child object and is going to move around with our tank.
  • 9:29 - 9:31
    This tool is something that I'm using just to
  • 9:31 - 9:35
    show you more easily where these bounds are.
  • 9:35 - 9:37
    You can use it for scanning, we'll do that in a bit
  • 9:37 - 9:41
    when we make the aiming slider later in the day.
  • 9:41 - 9:43
    For now we've just setup our canvas
  • 9:43 - 9:45
    and we've setup our slider and we're just going to
  • 9:45 - 9:47
    save our scene to update it.
  • 9:47 - 9:49
    So the next thing that we're going to do is
  • 9:49 - 9:51
    to expand all of these objects and setup our
  • 9:51 - 9:53
    slider like we want because currently
  • 9:53 - 9:55
    the slider is not where we want it to be.
  • 9:56 - 9:58
    It's off somewhere else still
  • 9:59 - 10:00
    looking like that.
  • 10:00 - 10:02
    So that's great, and you know,
  • 10:02 - 10:04
    you can drive around and move it around,
  • 10:06 - 10:10
    but it's a bit weird, so we don't want that.
  • 10:10 - 10:12
    So instead we're just going to bring this in
  • 10:12 - 10:13
    to the same position.
  • 10:13 - 10:16
    You can see the slider itself is miles away from it's parent
  • 10:16 - 10:19
    it's (-122, -237, 0).
  • 10:19 - 10:21
    We don't want any of that so we're just going to
  • 10:21 - 10:25
    expand the canvas, the slider and everything.
  • 10:25 - 10:27
    There's a short way to do that, so if you
  • 10:27 - 10:29
    hold down alt on the keyboard
  • 10:29 - 10:32
    and you click on the arrow next to the canvas
  • 10:32 - 10:34
    you can show and hide
  • 10:34 - 10:36
    all of the child objects at once,
  • 10:36 - 10:38
    so alt - click that to expand all
  • 10:38 - 10:40
    and then once you've expanded all of it
  • 10:40 - 10:42
    we need to do some housekeeping.
  • 10:42 - 10:44
    So the first thing to do
  • 10:44 - 10:47
    is to get rid of the intractability that we've got
  • 10:47 - 10:49
    with this slider, we don't want people to be able to drag
  • 10:49 - 10:51
    as I said, that would be totally unfair.
  • 10:51 - 10:54
    So we're going to get rid of the Handle Slide Area.
  • 10:55 - 10:57
    So I'm going to select Handle Slide Area and
  • 10:57 - 10:59
    command backspace to delete it.
  • 11:00 - 11:02
    Or delete on PC.
  • 11:02 - 11:04
    A quick note, Handle Slide Area doesn't actually
  • 11:04 - 11:06
    make it intractable.
  • 11:06 - 11:08
    It's just the bit that you would grab
  • 11:08 - 11:10
    if it were intractable.
  • 11:10 - 11:13
    To make it non-intractable we'll have to deal with something else in a bit.
  • 11:14 - 11:16
    So with that deleted we're then
  • 11:16 - 11:19
    going to multi-select the Slider
  • 11:20 - 11:23
    the Background, Fill Area and the Fill.
  • 11:23 - 11:25
    So you can select the Slider,
  • 11:25 - 11:27
    hold down shift, click on the Fill
  • 11:27 - 11:29
    to select all of those game objects.
  • 11:29 - 11:32
    This bit is crucial, make sure you've got all of those
  • 11:32 - 11:33
    four selected.
  • 11:33 - 11:36
    So the the first one, shift, click on the last one.
  • 11:36 - 11:38
    The reason that we're selecting all of these at once is
  • 11:38 - 11:40
    we want to give them a certain anchoring,
  • 11:40 - 11:42
    a certain position that's all the same.
  • 11:42 - 11:44
    We basically want to lock them in to
  • 11:44 - 11:46
    where the canvas is.
  • 11:46 - 11:48
    So we know that canvas is nicely scaled at
  • 11:48 - 11:51
    3.5 square and it's following the tank around.
  • 11:51 - 11:53
    So we're going to tell these to do the same thing.
  • 11:53 - 11:55
    So in the Rect Transform we have this thing
  • 11:55 - 11:57
    called Anchor Presets.
  • 11:58 - 12:00
    And it's this little button here that you might not realise is
  • 12:00 - 12:02
    the button the first time, but if you click on it
  • 12:02 - 12:05
    you'll see this expanded panel of different
  • 12:05 - 12:07
    options for how you can layout your UI.
  • 12:08 - 12:10
    And what you also need to remember is that
  • 12:10 - 12:12
    any Rect Transform, the same as any canvas,
  • 12:12 - 12:14
    inherits a position and anchors
  • 12:14 - 12:16
    based on it's parent.
  • 12:16 - 12:18
    So if I tell all of these 4
  • 12:18 - 12:21
    items to stretch over their parent
  • 12:21 - 12:24
    they will be stretched over that 3.5 unit canvas.
  • 12:24 - 12:26
    So that's exactly what I'm going to do.
  • 12:26 - 12:28
    Another thing you'll notice here is it says
  • 12:28 - 12:30
    Shift: Also sets pivot.
  • 12:30 - 12:32
    Alt: Also sets position.
  • 12:32 - 12:34
    So that's exactly what we want, the latter there.
  • 12:34 - 12:36
    Alt setting position.
  • 12:36 - 12:38
    We want to stretch and also reset
  • 12:38 - 12:40
    the position at the same time for these things.
  • 12:41 - 12:43
    So I'm going to hold down alt and you'll notice
  • 12:43 - 12:46
    that when I tap alt now all of these options are changing.
  • 12:46 - 12:48
    So with alt held down the lower
  • 12:48 - 12:50
    right option is the one you want.
  • 12:51 - 12:53
    Stretch in both directions.
  • 12:54 - 12:56
    So if you click on that.
  • 12:57 - 12:59
    And then go back.
  • 13:00 - 13:03
    You should see that you now have a grey square.
  • 13:03 - 13:05
    So that grey is just the default image that
  • 13:05 - 13:07
    gets put on to a slider but now it's been
  • 13:07 - 13:10
    stretched out of proportion from what it expects to be.
  • 13:10 - 13:12
    We don't need to worry about that because we're just going to
  • 13:12 - 13:15
    go ahead and put on our health wheel graphic that
  • 13:15 - 13:17
    we made earlier.
  • 13:17 - 13:19
    A quick recap.
  • 13:19 - 13:21
    We expanded the canvas with alt.
  • 13:21 - 13:23
    Left clicking it's arrow expands all child objects.
  • 13:23 - 13:25
    And then with the Handle Slide Area
  • 13:25 - 13:26
    we've gotten rid of that because we don't want
  • 13:26 - 13:28
    to be dragging anything.
  • 13:28 - 13:30
    And then we've multi-selected all of the
  • 13:30 - 13:32
    parts except for the canvas
  • 13:32 - 13:34
    and we alt - clicked on the lower right
  • 13:35 - 13:36
    to get that view.
  • 13:36 - 13:38
    Cool, so like James said, this doesn't
  • 13:38 - 13:41
    make the slider not intractable, we need to
  • 13:41 - 13:43
    do that on the actual slider component.
  • 13:44 - 13:46
    And if you select the slider you'll see that slider
  • 13:46 - 13:48
    component has got this little
  • 13:48 - 13:52
    slider icon and we can get rid of that by just
  • 13:52 - 13:55
    unchecking Intractable.
  • 13:55 - 13:57
    Because basically what will happen is that
  • 13:57 - 13:59
    even though you get rid of the handle
  • 13:59 - 14:01
    that's just a focal point, you can get rid of
  • 14:01 - 14:03
    a handle on a slider and you can still have the
  • 14:03 - 14:05
    mouse drag it, so if you don't want a visual handle
  • 14:05 - 14:07
    you can still have it, but if you don't want it to be intractable
  • 14:07 - 14:09
    at all, uncheck that box.
  • 14:10 - 14:12
    Then because the transition
  • 14:12 - 14:14
    is a property is going to handle what happens
  • 14:14 - 14:16
    as you drag it we don't want that either.
  • 14:16 - 14:19
    So we're going to set that to None instead of Tint.
  • 14:19 - 14:21
    And that will get rid of a whole bunch of other options
  • 14:21 - 14:22
    we don't need, it's going to hide them.
  • 14:22 - 14:25
    And then this is going to be to demonstrate our health.
  • 14:25 - 14:27
    Now in code and in general terms
  • 14:27 - 14:29
    we think of our health of going from 100
  • 14:29 - 14:31
    down to 0, right?
  • 14:31 - 14:33
    So we're going to set our minimum value to 0
  • 14:33 - 14:35
    and our max value to 100.
  • 14:36 - 14:38
    And then the default value that we want,
  • 14:38 - 14:40
    so this slider at the bottom here,
  • 14:40 - 14:42
    we're going to drag that up to 100.
  • 14:43 - 14:45
    We want it to start with 100 health.
  • 14:45 - 14:48
    So you'll see that currently it's doing this.
  • 14:51 - 14:53
    So as I drag it you can see the slider's still working.
  • 14:54 - 14:56
    And I've dragged that all the way to 100.
  • 14:57 - 14:59
    So a quick recap.
  • 14:59 - 15:01
    Selected the slider and in the slider component
  • 15:01 - 15:03
    we don't want it to be intractable,
  • 15:03 - 15:05
    we don't want any animation during interaction
  • 15:05 - 15:08
    because there is none, so we set Transition to None.
  • 15:08 - 15:10
    And the Max Value and the Value slider
  • 15:10 - 15:12
    are both set to 100.
  • 15:18 - 15:20
    So this slider is going to be one of
  • 15:20 - 15:22
    2 sliders that are attached to the tank
  • 15:22 - 15:24
    so the first one is for the health wheel and then the other
  • 15:24 - 15:26
    one is going to be this arrow that fires out
  • 15:26 - 15:28
    when you hold down the fire button.
  • 15:28 - 15:30
    They're both using the slider component.
  • 15:30 - 15:32
    So we want to know what we're working with here,
  • 15:32 - 15:34
    we want to make sure things are nice and neat.
  • 15:34 - 15:38
    I'm going to select my slider, hit return on mac, F2 on pc,
  • 15:38 - 15:40
    and rename it HealthSlider.
  • 15:45 - 15:47
    As I said before, we don't want these default grey
  • 15:47 - 15:49
    graphics that are getting stretched over
  • 15:49 - 15:51
    our slider, that doesn't look good at all.
  • 15:51 - 15:53
    Instead what we're going to do is to change
  • 15:53 - 15:55
    the image component.
  • 15:55 - 15:57
    So the slider is made up of
  • 15:57 - 15:59
    that slider component itself, which handles the values.
  • 16:00 - 16:02
    And then the image components on a couple of child objects
  • 16:02 - 16:05
    which handle a background and a foreground.
  • 16:05 - 16:07
    So usually that's a background kind of
  • 16:07 - 16:10
    tube that's being filled up as you drag your slider around.
  • 16:10 - 16:12
    But in this instance it's just going to be a background
  • 16:12 - 16:14
    grey radial and then
  • 16:14 - 16:16
    a coloured radial sat on top of that
  • 16:16 - 16:18
    so that you've got some context of
  • 16:18 - 16:20
    where it's filling in.
  • 16:21 - 16:23
    If you select the Background game object you will
  • 16:23 - 16:25
    see one of those image components
  • 16:25 - 16:29
    and currently it's got this default background source image.
  • 16:29 - 16:31
    We're just going to click the circle select there
  • 16:31 - 16:33
    and instead, in the assets you'll
  • 16:33 - 16:35
    see there's something called HealthWheel.
  • 16:35 - 16:37
    That's a sprite that we've made earlier in Photoshop
  • 16:37 - 16:41
    but it's just a circle with a gap in the middle of it.
  • 16:45 - 16:48
    Once you've assigned that you won't see it
  • 16:48 - 16:50
    in the scene just yet, because remember the
  • 16:50 - 16:54
    foreground is on top of it, so it's obscuring it.
  • 16:54 - 16:56
    But we will see it in the preview at the
  • 16:56 - 16:58
    bottom of the inspector.
  • 16:58 - 17:00
    So you can be sure you've done it if it says HealthWheel
  • 17:00 - 17:02
    here in Source Image and it's at the bottom.
  • 17:02 - 17:04
    Then the last things that we need to do is to
  • 17:04 - 17:06
    change the alpha down a little bit.
  • 17:06 - 17:10
    So the colour defines, in addition to the
  • 17:10 - 17:12
    actual colour of the graphic that you put on
  • 17:12 - 17:14
    a kind of tint for this thing.
  • 17:14 - 17:16
    But it also defines what we call the alpha,
  • 17:16 - 17:18
    how transparent something is,
  • 17:18 - 17:20
    or how opaque it is.
  • 17:20 - 17:22
    What we want to do is to be able to see through
  • 17:22 - 17:24
    the background part of the health wheel
  • 17:24 - 17:26
    and see the desert, the sand underneath it,
  • 17:26 - 17:29
    you know, just a nice additional effect.
  • 17:29 - 17:32
    So I'm going to drag the alpha slider down.
  • 17:32 - 17:34
    So this line underneath the colour,
  • 17:34 - 17:36
    so the colour could be whatever you want it to be
  • 17:36 - 17:38
    it should be white, but generally speaking the line underneath
  • 17:38 - 17:41
    it defines whether it's semi transparent.
  • 17:41 - 17:44
    So if you set the alpha to a value of 80, 80.
  • 17:46 - 17:48
    You'll be able to see through that really nicely.
  • 17:49 - 17:52
    A quick recap, we've renamed it HealthSlider,
  • 17:52 - 17:55
    we've made the background image, the health wheel,
  • 17:55 - 17:57
    and we've made sure it's semi-transparent.
  • 17:58 - 18:00
    Hopefully straightforward?
  • 18:01 - 18:03
    Okay, so then we need to do a similar thing for the fills.
  • 18:03 - 18:05
    So the fill is your foreground.
  • 18:05 - 18:07
    An important point to note here is with the
  • 18:07 - 18:10
    canvas or with any part of the UI system
  • 18:10 - 18:12
    the order in which things are rendered
  • 18:12 - 18:15
    is from top to bottom.
  • 18:15 - 18:17
    From back to front.
  • 18:17 - 18:19
    So if you're used to Photoshop it's
  • 18:19 - 18:21
    basically the reverse of Photoshop.
  • 18:21 - 18:23
    So in Photoshop you have a layers panel.
  • 18:23 - 18:25
    Anything that's at the bottom of the list of layers is rendered
  • 18:25 - 18:29
    at the back and the top of the list of layers is on top.
  • 18:29 - 18:31
    Unity is the opposite of that
  • 18:31 - 18:33
    because it's using this nesting system
  • 18:33 - 18:36
    where child objects are rendered in front .
  • 18:36 - 18:38
    So our fill and our fill area are going to be
  • 18:38 - 18:40
    rendered on top, visually,
  • 18:40 - 18:41
    in front of the background.
  • 18:41 - 18:43
    So the fill is where you'll find the
  • 18:43 - 18:45
    next image component
  • 18:45 - 18:47
    and again we want to choose the Health Wheel.
  • 18:50 - 18:52
    So again I click next to Source Image
  • 18:52 - 18:54
    change it from Fill to Health Wheel,
  • 18:54 - 18:56
    which is one of our assets.
  • 18:57 - 18:58
    Choose that.
  • 18:58 - 19:00
    And then you'll see that we've got
  • 19:01 - 19:04
    a grey wheel, technically on top of another grey wheel,
  • 19:04 - 19:07
    right now because we don't have a script setting that up.
  • 19:08 - 19:10
    That's our two graphics setup,
  • 19:10 - 19:12
    we're not going to colour them here, the script is
  • 19:12 - 19:14
    going to handle the colouring, as I mentioned.
  • 19:14 - 19:16
    But we do need to control how
  • 19:16 - 19:18
    that image actually fills up
  • 19:18 - 19:20
    because what we want this to do is work kind of like
  • 19:20 - 19:22
    clockwise fill up radially around the side.
  • 19:22 - 19:24
    We don't want it to kind of wipe across the circle,
  • 19:24 - 19:26
    we want it to fill around, okay?
  • 19:26 - 19:28
    So instead of an image type which
  • 19:28 - 19:30
    is what we call Simple.
  • 19:31 - 19:33
    We're going to set this to Filled.
  • 19:33 - 19:35
    So on the image component on Fill
  • 19:35 - 19:37
    set it to Filled and it should
  • 19:37 - 19:40
    default to radial 360.
  • 19:42 - 19:46
    And then we need to change the Fill Origin to Left.
  • 19:47 - 19:49
    So Fill Origin will be just one point
  • 19:49 - 19:52
    around 90 degrees from which it starts emerging.
  • 19:52 - 19:54
    We chose left because it's visually
  • 19:54 - 19:56
    the bottom of the tank and it looked quite nice.
  • 19:57 - 20:00
    Again, it's not going to make a huge difference to the gameplay.
  • 20:00 - 20:02
    Finally we uncheck Clockwise.
  • 20:02 - 20:04
    We play tested it a few times and we felt
  • 20:04 - 20:07
    like anticlockwise made sense for when you're losing health.
  • 20:09 - 20:12
    But, you know, feel free to change that to taste.
  • 20:13 - 20:15
    Okay, the final thing that I've forgotten to do is
  • 20:15 - 20:17
    just to change the alpha on the Health Wheel.
  • 20:17 - 20:19
    We want to be able to see through this slightly
  • 20:19 - 20:22
    so I'm going to click on the colour block
  • 20:23 - 20:25
    on that image component and set
  • 20:25 - 20:27
    the alpha to 150.
  • 20:27 - 20:29
    Because if I leave this all the way full we won't see
  • 20:29 - 20:32
    a little bit of the desert through all of that, so,
  • 20:32 - 20:34
    both of these semi-transparent,
  • 20:34 - 20:36
    this one 150, the other one was,
  • 20:36 - 20:38
    a slightly lower value.
  • 20:40 - 20:42
    And as I said the script is going to handle the
  • 20:42 - 20:44
    colouring so it's going to go from green to red for us.
  • 20:45 - 20:47
    So a quick recap of those steps.
  • 20:48 - 20:50
    On the Fill game object we set the source image
  • 20:50 - 20:53
    to the Health Wheel, I tuned the alpha down a little bit
  • 20:53 - 20:55
    so you'll be able to see through it.
  • 20:55 - 20:57
    The image type is Filled so that you'll be able to
  • 20:57 - 20:59
    fill up radially, going round,
  • 20:59 - 21:01
    and we've made sure it starts at left,
  • 21:01 - 21:04
    which is just a particular position on that clock.
  • 21:04 - 21:07
    And then we unchecked Clockwise, so it's going to go
  • 21:07 - 21:09
    around backwards as you lose health.
  • 21:14 - 21:16
    Okay, so one final thing to make
  • 21:16 - 21:18
    sure that this behaves as we'd expect
  • 21:18 - 21:21
    it to as we're driving the tank around
  • 21:21 - 21:25
    is a brief script called UIDirectionControl.
  • 21:25 - 21:27
    So if you look in the Scripts
  • 21:27 - 21:29
    UI folder there's just one script
  • 21:29 - 21:31
    there called UIDirectionControl.
  • 21:32 - 21:34
    And we're going to grab this and
  • 21:34 - 21:38
    we're going to drag and drop this on to the HealthSlider.
  • 21:40 - 21:42
    So UIDirectionControl, grab the script,
  • 21:42 - 21:44
    drop it on to HealthSlider.
  • 21:45 - 21:48
    And when you reselect HealthSlider you should see
  • 21:49 - 21:51
    it's a component underneath the slider component.
  • 21:52 - 21:54
    And we're just going to show you that super quickly
  • 21:54 - 21:56
    what it looks like, it's just a couple of lines of code.
  • 21:56 - 21:58
    Don't worry about opening this one yourselves,
  • 21:58 - 22:00
    it's super quick.
  • 22:00 - 22:02
    In summary all this is doing is making sure
  • 22:02 - 22:04
    that the UI stays in
  • 22:04 - 22:06
    the same rotation that it was at the start.
  • 22:07 - 22:09
    So what it's doing is it finds the
  • 22:09 - 22:11
    rotation of the canvas,
  • 22:11 - 22:15
    so that's the transform.parent.localRotation
  • 22:16 - 22:18
    So finding the local rotation of the canvas.
  • 22:19 - 22:21
    And then using that every
  • 22:21 - 22:23
    update it's setting it's current rotation
  • 22:23 - 22:25
    to that local rotation.
  • 22:25 - 22:27
    So instead of moving around like
  • 22:27 - 22:29
    a normal child would and rotating,
  • 22:29 - 22:31
    it's just keeping the one that it
  • 22:31 - 22:32
    got at the start.
  • 22:33 - 22:37
    Yeah, we didn't notice this the first time we did it,
  • 22:37 - 22:39
    but basically that would look strange because
  • 22:39 - 22:42
    if you weren't losing health but you turned
  • 22:42 - 22:44
    around to where the tank is obscuring part of
  • 22:44 - 22:46
    the radial wheel it might look like
  • 22:46 - 22:48
    you were gaining health as you were driving
  • 22:48 - 22:50
    around and turning to see more of
  • 22:50 - 22:52
    the wheel so we realised that it would make total sense
  • 22:52 - 22:54
    to keep that rotation static
  • 22:54 - 22:56
    so this is just setting it every frame.
  • 22:56 - 22:58
    It's literally all that script does.
  • 23:00 - 23:02
    So make sure you've saved your scene, as always.
  • 23:03 - 23:05
    And because we've been working on our tank
  • 23:06 - 23:08
    what I want to point out to you is that
  • 23:08 - 23:10
    the tank and all of the parts that were with
  • 23:10 - 23:13
    it when we last updated the prefab are in blue.
  • 23:13 - 23:16
    These new child objects have their names in grey.
  • 23:17 - 23:22
    That again is reminding us, along with these emboldened parts
  • 23:22 - 23:25
    of the components that things aren't the same as the prefab.
  • 23:25 - 23:27
    So if I select my tank I'm going to hit
  • 23:27 - 23:29
    Apply at the top of the inspector
  • 23:29 - 23:31
    and now you'll see everything
  • 23:31 - 23:35
    is in blue and we've got no more bold parts
  • 23:35 - 23:37
    of any of our different components
  • 23:37 - 23:39
    in any of the game objects.
  • 23:39 - 23:41
    So our tank is now up to date.
  • 23:41 - 23:43
    We're getting close to a point where we can
  • 23:43 - 23:45
    use that tank as a prefab by
  • 23:45 - 23:47
    the game manager spawning more than one of them.
  • 23:47 - 23:49
    But we need to do some more things.
  • 23:49 - 23:51
    So we need our tank
  • 23:51 - 23:55
    to run out of health, we need to manage the health with a script
  • 23:55 - 23:57
    and we need the tank to explode and
  • 23:57 - 23:59
    make a sound when it's destroyed, right?
  • 23:59 - 24:01
    So we have a prefab
  • 24:01 - 24:04
    for the explosion part itself.
  • 24:04 - 24:08
    And then we're going to handle the actual behaviour manually.
  • 24:08 - 24:10
    In the Prefabs folder you'll find something
  • 24:10 - 24:12
    called TankExplosion.
  • 24:13 - 24:15
    We're just going to drag this in and
  • 24:15 - 24:17
    work with it very briefly.
  • 24:17 - 24:19
    So TankExplosion, if you drag and drop it in
  • 24:19 - 24:22
    to the hierarchy, you'll see is a particle effect.
  • 24:23 - 24:25
    And you'll notice that it plays back as soon as you
  • 24:25 - 24:27
    drop it in, it should look something like that.
  • 24:28 - 24:31
    And when we want to destroy the tank
  • 24:31 - 24:34
    we want to bring in this particle explosion,
  • 24:34 - 24:36
    move it to wherever the tank got destroyed,
  • 24:36 - 24:38
    play it back and play a sound.
  • 24:38 - 24:41
    So currently this particle system game object
  • 24:41 - 24:42
    doesn't have an audio source on it,
  • 24:42 - 24:44
    so that's what we're going to add first.
  • 24:44 - 24:47
    So once you've got your TankExplosion in your scene
  • 24:47 - 24:49
    click the Add Component button, and remember
  • 24:49 - 24:52
    'Sou' is a quick way to get to audio source.
  • 24:52 - 24:54
    Hit return and add the audio source
  • 24:54 - 24:55
    to the game object.
  • 24:55 - 24:57
    Then we need to tell it which clip to play,
  • 24:57 - 24:59
    so next to Audio Clip
  • 24:59 - 25:01
    click on the asset selection
  • 25:01 - 25:03
    so the circle select button there.
  • 25:04 - 25:06
    And we're going to choose TankExplosion.
  • 25:09 - 25:11
    Finally we don't want this to play
  • 25:11 - 25:13
    as soon as this gets put in the game because
  • 25:13 - 25:15
    basically what we do is to put
  • 25:15 - 25:17
    this asset in to the game and then
  • 25:17 - 25:20
    whenever a tank gets blown up just move it and play it.
  • 25:20 - 25:22
    But we don't want this to hear the
  • 25:22 - 25:24
    explosion sound as soon as the game starts
  • 25:24 - 25:26
    playing so we uncheck Play On Awake.
  • 25:28 - 25:30
    One more time, we've put the prefab in
  • 25:30 - 25:31
    for the explosion,
  • 25:31 - 25:33
    added an audio source and we've made sure
  • 25:33 - 25:35
    it doesn't play on awake.
  • 25:37 - 25:39
    Okay, so we just need to update that
  • 25:39 - 25:41
    prefab so I'm going to hit Apply at the top
  • 25:41 - 25:43
    of the inspector, you'll notice our text there
  • 25:43 - 25:46
    went from bold to unbold,
  • 25:46 - 25:48
    to regular I should say.
  • 25:48 - 25:50
    And that's all we need to do with that TankExplosion.
  • 25:50 - 25:52
    We just wanted to make you aware of what it was,
  • 25:52 - 25:55
    what it does and also add some functionality to it.
  • 25:55 - 25:57
    So now that we've updated the prefab,
  • 25:57 - 25:59
    so you can hit Apply as many times as you need to
  • 26:00 - 26:02
    we can then delete it out of the scene.
  • 26:05 - 26:07
    And then what we're going to do is handle the
  • 26:07 - 26:09
    health and we're going to reference this explosion
  • 26:09 - 26:11
    at that time as well, so,
  • 26:11 - 26:13
    in the Scripts Tank folder
  • 26:13 - 26:15
    you will find TankHealth.
  • 26:16 - 26:19
    And we're going to drag and drop TankHealth
  • 26:19 - 26:21
    on to our Tank game object.
  • 26:22 - 26:24
    And when you look at it in the inspector,
  • 26:24 - 26:26
  • 26:26 - 26:28
    I'll just show you it more easily,
  • 26:28 - 26:31
    The last component I've got there now is TankHealth.
  • 26:31 - 26:34
    So TankMovement is above it, it's the last one we worked on.
  • 26:34 - 26:36
    And now we've got TankHealth.
  • 26:38 - 26:40
    I'm going to double click the title of the script
  • 26:40 - 26:42
    to open it up in my script editor
  • 26:42 - 26:44
    and we're going to talk about how this works
  • 26:44 - 26:46
    and add some functionality.
  • 26:47 - 26:49
    Okay, so first thing you'll notice
  • 26:49 - 26:52
    is like before, we've got some portion of the script commented out.
  • 26:53 - 26:56
    So on lines 13 and 36
  • 26:56 - 26:59
    there are these /* */
  • 27:00 - 27:04
    Get rid of those bits because we want to use that bit of code.
  • 27:04 - 27:06
    So we're going to enable those by deleting
  • 27:06 - 27:08
    lines 13 and 36.
  • 27:08 - 27:12
    So it should show up in syntax highlight colours.
  • 27:13 - 27:17
    Okay, let's have a quick look at the public variables.
  • 27:18 - 27:20
    The first one is the starting health.
  • 27:21 - 27:24
    I'm going to start with 100, it makes perfect sense.
  • 27:24 - 27:26
    Next we've got a reference to that
  • 27:26 - 27:28
    slider because we want to change the slider's
  • 27:28 - 27:31
    value so that it's less or more.
  • 27:31 - 27:33
    So remember the slider is controlling
  • 27:33 - 27:35
    the fill image and how much
  • 27:35 - 27:37
    that radially fills up.
  • 27:37 - 27:39
    So it's just handling the values.
  • 27:39 - 27:41
    The image itself handles the rendering side,
  • 27:41 - 27:43
    the slider handles the values.
  • 27:44 - 27:46
    Okay, and like we said, we wanted to change
  • 27:46 - 27:48
    the colour based on the health, so we need
  • 27:48 - 27:50
    to access that image, so again we've got
  • 27:50 - 27:52
    a public variable so we can drag on
  • 27:52 - 27:55
    the image component of the Fill game object.
  • 27:56 - 27:59
    Next we've got a couple of colours,
  • 27:59 - 28:01
    you can change these in the inspector
  • 28:01 - 28:03
    if you want, but we thought that green
  • 28:03 - 28:05
    for full health and red for 0 health made sense.
  • 28:06 - 28:08
    If you like purple and orange
  • 28:08 - 28:10
    go for those colours.
  • 28:10 - 28:12
    And the last one is a reference
  • 28:12 - 28:14
    to the prefab, so,
  • 28:14 - 28:16
    what we're going to do is we're going to drag on
  • 28:16 - 28:18
    the explosion prefab that we just edited
  • 28:18 - 28:20
    so that we can instantiate it at
  • 28:20 - 28:22
    runtime and use it then.
  • 28:23 - 28:25
    Next we've got our private variables and
  • 28:25 - 28:27
    we've got a reference to the audio source
  • 28:27 - 28:29
    that's on the explosion prefab.
  • 28:30 - 28:32
    So when we instantiate it
  • 28:32 - 28:34
    we'll have a reference to
  • 28:34 - 28:36
    that instance.
  • 28:37 - 28:39
    Then from that we can find a reference to
  • 28:39 - 28:41
    the audio and just below it
  • 28:41 - 28:42
    the particle system as well.
  • 28:43 - 28:45
    So the explosion audio and particle systems will just be
  • 28:45 - 28:47
    references to components on that
  • 28:47 - 28:49
    instantiated game object
  • 28:49 - 28:51
    that we can use when we need to.
  • 28:51 - 28:54
    So notice James is using the word Instantiate.
  • 28:54 - 28:56
    We haven't really mentioned that just yet,
  • 28:56 - 28:59
    it just means to spawn a game object in the world,
  • 28:59 - 29:01
    and you'll see that very shortly in the Awake function.
  • 29:03 - 29:05
    Okay, so next we've got a
  • 29:05 - 29:06
    float value for the current health,
  • 29:06 - 29:08
    obviously we need to keep track of how much health
  • 29:08 - 29:10
    we've currently got, so we have that.
  • 29:11 - 29:13
    And lastly we've got a
  • 29:13 - 29:16
    boolean variable for whether you are dead or not.
  • 29:18 - 29:20
    Okay, next we've got the
  • 29:20 - 29:22
    Awake function, and if you remember Awake is called
  • 29:22 - 29:24
    at the start of the game
  • 29:24 - 29:27
    so we want to do these things to setup
  • 29:27 - 29:29
    what's going on for the rest of the game.
  • 29:31 - 29:33
    This first line is a little bit tricky so I'll
  • 29:33 - 29:35
    go over it a couple of times to make sure.
  • 29:36 - 29:39
    What we're doing is we've got our explosion particles.
  • 29:40 - 29:43
    And we're setting that to the
  • 29:43 - 29:46
    particle system component of an instantiated prefab.
  • 29:46 - 29:48
    So we're instantiating the prefab,
  • 29:48 - 29:50
    so that's Instantiate(m_ExplosionPrefab)
  • 29:50 - 29:53
    and then from that we're using GetComponent
  • 29:53 - 29:56
    to get that particle system reference that we need.
  • 29:56 - 29:59
    So basically we have a particle system variable.
  • 29:59 - 30:01
    We create an instance of the prefab that we know
  • 30:01 - 30:03
    has got that component on it and then
  • 30:03 - 30:05
    we assign that component, so we're doing
  • 30:05 - 30:07
    a couple of things all in one line basically.
  • 30:09 - 30:11
    And then it's very similar for the audio source
  • 30:11 - 30:13
    that's also on that game object.
  • 30:13 - 30:15
    But since we've already instantiated
  • 30:15 - 30:17
    we don't want 2 explosions
  • 30:17 - 30:19
    we're just going to use the reference to the particle system
  • 30:19 - 30:21
    to get the audio source component.
  • 30:21 - 30:23
    And lastly, since we don't want the tank to
  • 30:23 - 30:25
    explode at the start we're just
  • 30:25 - 30:27
    turning that game object off,
  • 30:27 - 30:30
    so m_ExplosionParticles.gameObject.SetActive(false);
  • 30:31 - 30:33
    So that's going to make it inactive in the hierarchy.
  • 30:33 - 30:35
    Yeah, so just to reiterate, whenever you're using
  • 30:35 - 30:37
    particle systems in Unity it's kind of more
  • 30:37 - 30:39
    efficient to put them in
  • 30:39 - 30:42
    the game than play them whenever you need them.
  • 30:42 - 30:44
    Stop them, play them, stop them, play them.
  • 30:44 - 30:46
    What a lot of people do, which is a beginner thing,
  • 30:46 - 30:49
    is to instantiate, so spawn a new particle system
  • 30:49 - 30:51
    and then use what's called Destroy to
  • 30:51 - 30:53
    move that game object from the hierarchy.
  • 30:53 - 30:55
    The problem with that is it can invoke
  • 30:55 - 30:57
    the garbage collector, which is a thing that is
  • 30:57 - 30:59
    basically registering what's going on in the scene
  • 30:59 - 31:01
    and removing references.
  • 31:01 - 31:03
    You don't want that because that will create spikes in performance
  • 31:03 - 31:07
    and make your game less performant basically.
  • 31:07 - 31:09
    So to avoid that always keep your particle
  • 31:09 - 31:11
    systems in memory, keep them in the scene,
  • 31:11 - 31:13
    play them when you need to, stop them when you need to,
  • 31:13 - 31:16
    and that's exactly what we're doing with the explosion.
  • 31:16 - 31:18
    We put it straight in to the game as soon as it starts
  • 31:18 - 31:20
    we switch it off straight away so you never
  • 31:20 - 31:22
    see it and then we assign our references
  • 31:22 - 31:24
    for when we need them.
  • 31:25 - 31:28
    That is definitely the most efficient way,
  • 31:28 - 31:30
    it's not always the simplest because
  • 31:30 - 31:32
    for example with the shells later on
  • 31:33 - 31:35
    we don't know how many we need, we're going to have to spawn
  • 31:35 - 31:37
    them as the player uses them.
  • 31:37 - 31:40
    There's a way round that using something called Object Pooling
  • 31:40 - 31:42
    which we've not included today, if you want to
  • 31:42 - 31:44
    understand object pooling come and see me at lunch or
  • 31:44 - 31:46
    after today and I'll explain it to you.
  • 31:46 - 31:48
    We do have some tutorials that cover
  • 31:48 - 31:51
    object pooling, I think Mike and Matt have done
  • 31:51 - 31:53
    those at various points, so there's live trainings
  • 31:53 - 31:55
    on object pooling as well, which you can find
  • 31:55 - 31:58
    on Unity3D.com/learn.
  • 31:58 - 32:00
    But that would be another way to keep
  • 32:00 - 32:02
    a whole bunch of objects and it's a more performant way to
  • 32:02 - 32:04
    keep them in and then spawn them whenever you need them.
  • 32:05 - 32:06
    We digress.
  • 32:06 - 32:08
    Okay, so you remember we're turning
  • 32:08 - 32:10
    tanks on and off when
  • 32:10 - 32:12
    we kill them and bring them back to life again?
  • 32:12 - 32:14
    So again we're going to be using
  • 32:14 - 32:16
    OnEnable to do stuff when the tank
  • 32:16 - 32:18
    first gets turned back on again.
  • 32:18 - 32:20
    So when the tank gets turned back on
  • 32:20 - 32:23
    we want to reset it's health to the StartingHealth.
  • 32:23 - 32:26
    We know that it's not dead so we set the
  • 32:26 - 32:28
    Dead boolean to false.
  • 32:28 - 32:30
    And we need to update it's UI
  • 32:30 - 32:32
    to make sure that it looks healthy as well.
  • 32:32 - 32:34
    So SetHealthUI is basically just
  • 32:34 - 32:36
    going to the component and setting it to whatever value
  • 32:36 - 32:38
    we tell it to, it's basically just a kind of
  • 32:38 - 32:41
    refresh that we do on the OnEnable.
  • 32:41 - 32:44
    We'll be setting up that function shortly
  • 32:44 - 32:46
    but first off let's go through the
  • 32:46 - 32:47
    TakeDamage function.
  • 32:47 - 32:49
    Note that that's a public function so that it can be
  • 32:49 - 32:51
    called from outside this script because
  • 32:51 - 32:53
    we want the shells to do the damage.
  • 32:54 - 32:56
    And it's also parsed in an amount
  • 32:56 - 32:59
    so that's the amount of damage that it is going to take.
  • 33:00 - 33:02
    So the first thing that we want to do with
  • 33:02 - 33:06
    TakeDamage is to reduce the current health
  • 33:06 - 33:07
    by the amount.
  • 33:07 - 33:15
    So m_CurrentHealth -= so that's setting CurrentHealth
  • 33:15 - 33:17
    by reducing it by amount.
  • 33:18 - 33:22
    So just a quick note for those of you not confident coders.
  • 33:22 - 33:24
    The argument that we're placing in is
  • 33:24 - 33:26
    what we're referring to here,
  • 33:26 - 33:28
    so TakeDamage in the parenthesis here,
  • 33:28 - 33:31
    float amount means that you can call this function
  • 33:31 - 33:34
    and then parse in whatever number you want there.
  • 33:34 - 33:36
    So the reason we've got that is TakeDamage
  • 33:36 - 33:39
    can be a number of different things.
  • 33:39 - 33:41
    Depending on where the shell hits near to the tank
  • 33:42 - 33:45
    will define how much we want to subtract.
  • 33:45 - 33:48
    If it's super close it's going to create a lot of blast damage.
  • 33:48 - 33:50
    If it's just on the cusp of how big that
  • 33:50 - 33:52
    blast radius is then quite a small amount.
  • 33:53 - 33:56
    So it's going to be a varying amount of damage we're taking away.
  • 33:56 - 33:58
    So we can parse in an argument called Amount
  • 33:58 - 34:01
    and then we subtract that from the CurrentHealth.
  • 34:02 - 34:04
    Okay so again we've just changed
  • 34:04 - 34:06
    how much health we currently have
  • 34:06 - 34:08
    so it would be good to update the UI
  • 34:08 - 34:10
    to reflect that, so again we'll call that
  • 34:10 - 34:12
    SetHealthUI function that we'll setup.
  • 34:14 - 34:18
    So remember that this is reducing our CurrentHealth,
  • 34:18 - 34:20
    but unless we tell the user by updating
  • 34:20 - 34:22
    or refreshing the UI
  • 34:22 - 34:23
    they're not going to know.
  • 34:24 - 34:26
    And the last thing that we need to do
  • 34:26 - 34:29
    in TakeDamage is check whether or not we're dead.
  • 34:31 - 34:34
    So if m_CurrentHealth
  • 34:34 - 34:39
    is less than or equal to 0f, because remember,
  • 34:39 - 34:41
    float, it's what we're checking it against,
  • 34:41 - 34:45
    and we're not already dead, so not Dead.
  • 34:46 - 34:50
    Then we can call the function OnDeath.
  • 34:53 - 34:54
    So just to remind you.
  • 34:54 - 34:56
    Less than or equal to 0
  • 34:56 - 34:58
    so we're run out of health.
  • 34:58 - 35:02
    & means add a second condition for the if statement.
  • 35:02 - 35:06
    And the ! there is just means not.
  • 35:06 - 35:09
    So if this thing isn't true and we're not already
  • 35:09 - 35:11
    then we'll call OnDeath.
  • 35:14 - 35:16
    Okay so the next function is the
  • 35:16 - 35:18
    SetHealthUI that we've talked about.
  • 35:19 - 35:21
    The two things that we want to do in this
  • 35:21 - 35:23
    was we want to set the value of the slider
  • 35:23 - 35:25
    and we want to set the colour of the slider.
  • 35:25 - 35:27
    To set the value of the slider
  • 35:27 - 35:34
    we say m_sSlider.value = m_CurrentHealth
  • 35:35 - 35:39
    So remember our slider goes from 0 to 100
  • 35:39 - 35:41
    as does our health.
  • 35:41 - 35:43
    So all we're doing is we're setting the value
  • 35:43 - 35:45
    of the slider based on the current health.
  • 35:45 - 35:47
    And the next thing, if you remember,
  • 35:47 - 35:49
    a slider is rendered by those image components
  • 35:49 - 35:52
    so that's what we need to address
  • 35:52 - 35:54
    in order to change it's colour.
  • 35:54 - 35:59
    So we say m_FillImage.color =
  • 36:00 - 36:04
    and what we're doing to do here is use a Lerp function.
  • 36:04 - 36:07
    So Lerp stands for Linear Interpolation, so we give it
  • 36:07 - 36:10
    2 values that we're interpolating between,
  • 36:10 - 36:12
    that we're making a blend of,
  • 36:12 - 36:14
    and we'll give it a third value that determines
  • 36:14 - 36:16
    how much of each colour we're using.
  • 36:16 - 36:18
    The function is Color.Lerp
  • 36:19 - 36:22
    and we open parenthesis and we give it the value
  • 36:22 - 36:24
    of a color that we want to
  • 36:24 - 36:26
    show when we are at 0.
  • 36:26 - 36:28
    So remember that we have that public variable
  • 36:28 - 36:30
    called ZeroHealthColor that's red.
  • 36:31 - 36:36
    The next is the color that we want to use
  • 36:36 - 36:38
    when our third variable is 1.
  • 36:38 - 36:40
    So 1 not 100.
  • 36:40 - 36:42
    So we need a value that is between
  • 36:42 - 36:44
    0 and 1 that reflects
  • 36:44 - 36:46
    what percentage of health we have.
  • 36:47 - 36:49
    So to do that, all we'll do is
  • 36:49 - 36:51
    we divide the current health by the starting health.
  • 36:52 - 36:55
    So if you've got full health, 100.
  • 36:55 - 36:57
    Then your starting health is 100.
  • 36:57 - 36:59
    100 divided by 100 is going to be 1.
  • 36:59 - 37:03
    If you've got 0 health, 0 divided by 100 is 0
  • 37:03 - 37:06
    so you're going to use the ZeroHealthColor.
  • 37:06 - 37:08
    Likewise, if you've got 50 health,
  • 37:08 - 37:10
    50 divided by 100, you've got half,
  • 37:10 - 37:12
    so it's going to be halfway between those two colors.
  • 37:13 - 37:15
    So that's basically what we're doing every time we
  • 37:15 - 37:18
    refresh the UI, we reset the slider and
  • 37:18 - 37:20
    the slider resets the image for us
  • 37:20 - 37:22
    and then we reset the color to make sure it looks appropriate.
  • 37:23 - 37:25
    Okay, so the last function that we're going to do
  • 37:25 - 37:27
    is OnDeath, so this is called
  • 37:27 - 37:29
    when the tank first dies
  • 37:30 - 37:32
    and since we have that Dead boolean
  • 37:33 - 37:35
    we're not going to call it more than once.
  • 37:35 - 37:37
    So the first thing to do here is make sure
  • 37:37 - 37:40
    that we're only going to call it once by setting Dead to true.
  • 37:41 - 37:43
    As soon as we call the function.
  • 37:46 - 37:48
    The next thing we want to do
  • 37:48 - 37:50
    is play all the effects
  • 37:50 - 37:52
    for the explosion.
  • 37:53 - 37:56
    So first off, the explosion particles need to be in
  • 37:56 - 38:00
    the correct place, so m_ExplosionParticles.transform.position
  • 38:02 - 38:04
    The position of the particles will set to
  • 38:04 - 38:06
    transform.position, that's the tank's position.
  • 38:08 - 38:10
    So wherever you were when you died,
  • 38:10 - 38:12
    grab the particles that we put in at the start of the game,
  • 38:12 - 38:14
    move them there and then.
  • 38:14 - 38:16
    And then once they've been moved to the correct
  • 38:16 - 38:18
    position we need to turn them back on,
  • 38:18 - 38:20
    because remember we turned them off at the start of the game.
  • 38:20 - 38:24
    So m_ExplosionParticles.gameObject.SetActive
  • 38:25 - 38:27
    true in parenthesis.
  • 38:27 - 38:29
    So that's turning the game object back on.
  • 38:31 - 38:33
    Once we've turned it back on then we can
  • 38:33 - 38:36
    actually play these variables,
  • 38:36 - 38:38
    so m_ExplosionParticles.Play
  • 38:39 - 38:43
    and m_ExplosionAudio
  • 38:43 - 38:45
    So that's playing the particles,
  • 38:45 - 38:47
    and playing the audio.
  • 38:48 - 38:50
    And the final thing that we want to do in this
  • 38:50 - 38:52
    is actually turn the tank off
  • 38:52 - 38:56
    so gameObject.SetActive (false)
  • 39:00 - 39:02
    So all that's doing is, we're saying
  • 39:02 - 39:04
    that we only want to call it once,
  • 39:04 - 39:06
    so Dead gets set to true.
  • 39:06 - 39:08
    We take the particle system and we move it to
  • 39:08 - 39:10
    the correct position and turn it on.
  • 39:11 - 39:13
    Then we play the particles,
  • 39:13 - 39:15
    we play the audio and we turn the tank off.
  • 39:17 - 39:20
    And that's all there is to it, so save your script
  • 39:20 - 39:22
    and return to the editor.
  • 39:22 - 39:24
    So just a quick reminder of what we've just done there.
  • 39:24 - 39:26
    We've setup our tank damage.
  • 39:27 - 39:29
    Whenever we get damage we have to update
  • 39:29 - 39:31
    the UI based on the current health
  • 39:32 - 39:34
    and we also have to deactivate,
  • 39:34 - 39:38
    when the tank dies and bring in the effects as well.
  • 39:39 - 39:41
    So once you've saved your script, go back to Unity
  • 39:41 - 39:43
    and also save your scene.
  • 39:43 - 39:45
    Just a quick reminder, if you've got errors
  • 39:45 - 39:47
    with the script they will be at the bottom of
  • 39:47 - 39:49
    the Unity interface where you've got a grey bar down
  • 39:49 - 39:51
    at the bottom here, they will also
  • 39:51 - 39:54
    be in Window - Console.
  • 39:58 - 40:00
    So we've finished our script, we've saved our script
  • 40:00 - 40:02
    and we're back inn Unity and that
  • 40:02 - 40:04
    script as a component
  • 40:04 - 40:06
    is TankHealth
  • 40:06 - 40:09
    and as you see we need to assign some references.
  • 40:09 - 40:11
    So I'm going to just alt-click on the arrow
  • 40:11 - 40:13
    next to my tank in the hierarchy to expand
  • 40:13 - 40:15
    all of it so I can definitely see all the things
  • 40:15 - 40:17
    that I might need to click on
  • 40:17 - 40:19
    and then I'm going to assign the Slider
  • 40:19 - 40:22
    called HealthSlider
  • 40:23 - 40:25
    to the Slider variable.
  • 40:25 - 40:27
    One more time, I'm grabbing
  • 40:27 - 40:29
    HealthSlider, it's underneath Canvas,
  • 40:29 - 40:32
    dropping it on to the slider variable
  • 40:32 - 40:34
    so that's that reference assigned,
  • 40:34 - 40:36
    and then Fill, the one at the very
  • 40:36 - 40:38
    bottom of all the list of game objects,
  • 40:39 - 40:41
    dropping that on to Fill Image.
  • 40:41 - 40:43
    So with the reference to Health Slider it's going to set the
  • 40:43 - 40:45
    value and show the health and update properly
  • 40:45 - 40:47
    and with the reference to Fill Image we're going to
  • 40:47 - 40:49
    use these two color blocks here
  • 40:49 - 40:51
    to define, you know,
  • 40:51 - 40:54
    what it looks like at 0 and 100% and
  • 40:54 - 40:56
    everything in between color-wise.
  • 40:56 - 40:59
    Finally, the Explosion prefab
  • 40:59 - 41:01
    is in the Prefabs folder.
  • 41:01 - 41:02
    We edited it earlier.
  • 41:02 - 41:04
    All we need to do is find TankExplosion
  • 41:04 - 41:07
    and drag it on as the explosion prefab
  • 41:08 - 41:10
    using this variable here.
  • 41:11 - 41:13
    One more time, drag TankExplosion
  • 41:13 - 41:15
    drop it on to the Explosion prefab.
  • 41:15 - 41:17
    If you then save your scene.
  • 41:19 - 41:21
    The last thing we need to do is just make sure
  • 41:21 - 41:23
    this tank is up to date prefab-wise.
  • 41:24 - 41:25
    You know it, we've done it before,
  • 41:26 - 41:29
    hit the Apply button at the top of the inspector.
  • 41:29 - 41:31
    Hit it as many times as you like just to be sure.
  • 41:33 - 41:35
    And then you can play your game.
  • 41:37 - 41:39
    Now you won't see anything changing
  • 41:39 - 41:41
    until we've got some shells that damage
  • 41:41 - 41:43
    the tank and we'll do that right after lunch.
  • 41:43 - 41:45
    But for now what you should be seeing is
  • 41:45 - 41:48
    that the tank is driving around and we've got our health wheel there.
  • 41:49 - 41:51
    Cool, so you should see your tank driving around
  • 41:51 - 41:53
    it should have the health wheel attached to it,
  • 41:53 - 41:56
    this will all make a lot more sense once you've got the shells coming in
  • 41:56 - 41:58
    which is in the next phase, so just to
  • 41:58 - 42:00
    recap that last part.
  • 42:00 - 42:02
    We've assigned the HealthSlider to the
  • 42:02 - 42:04
    HealthSlider variable.
  • 42:04 - 42:06
    We've got the Fill game object
  • 42:06 - 42:08
    and assigned it to the FillImage and then
  • 42:08 - 42:10
    we've got the TankExplosion variable from the Prefabs
  • 42:10 - 42:13
    in the project and put that on to that variable.
  • 42:15 - 42:17
    And then we've applied, we need to update our tank.
  • 42:17 - 42:19
    As we work on the tank we need to keep updating
  • 42:19 - 42:21
    it until it's finished and then we'll
  • 42:21 - 42:23
    get rid of it entirely and it will be stored in our project
  • 42:23 - 42:25
    to spawn at the start of the game.
  • 42:25 - 42:27
    So if you've done all of that save your scene,
  • 42:28 - 42:31
    pat yourself on the back, it's the end of phase 4.
Title:
TANKS! Unity Tutorial - Phase 4 of 8 - Tank Health
Description:

more » « less
Duration:
42:35

English subtitles

Revisions