Lesson 2.11: The Wrap

We have created our initial game engine which supports a player, location, game world, and moving around within it. Then we created the UI elements/components to display those in our game screen. We now have a game that we can move around in and investigate the images and descriptions of each location in our limited world. That’s some great progress.

While building these game features, we covered a lot of advanced development topics and design patterns:

  • Model-View-ViewModel (MVVM) design pattern
  • Dependency Injection pattern
  • Factory method design pattern
  • C# Language features:
    • Extension methods
    • Ternary operator
    • is null operator
    • Linq extensions
    • Lambda expressions
    • Null coalescing operator
    • Verbatim strings
  • Blazor concepts for Components, Parameters, and EventCallbacks
  • Mocking frameworks for isolating test behavior

Hopefully learning all of that in the context of developing a game engine and UI has made it more enjoyable.

At the end of this chapter, we are going to create another Pull Request to merge our “chapter-2” branch changes into the main branch. For a refresher on how to create and complete a Git Pull Request, please jump back to Lesson 1.11 (if you need that).

Finding Chapter Commits

As I commit changes and merge them to the main branch, the code changes and it becomes hard to see just the code for a particular lesson in the latest main branch source. To help with that, I am keeping the chapter branches alive and not deleting them after pull requests. To see the code for each lesson, we can go to the Azure DevOps web site and look at each individual commit.

  1. Launch the Azure DevOps site to the commit list: https://dev.azure.com/d20Tek/SimpleRPG/_git/simple-rpg-game/commits
Fig 1 – Git commit list
  1. Select the “chapter-2” branch in the header dropdown… it may start out in the main branch.
  2. It shows a list of all commits made to the “chapter-2” branch.
  3. I try to name the commit with the lesson number (like 2.6 for the Lesson 2.6 article), so that it is easier to follow along with the changes as you read a lesson.
  4. There are some clean up changes or bug fixes that won’t have the lesson tag, but hopefully you can follow along with those too.
  5. Click on a particular commit – 2.6: Refactoring page into PlayerComponent.
Fig 2 – Commit side-by-side diff view
  1. This presents the diff view of the changes for each file in the commit. You can see what changed from the previous commit.
  2. Change the code view by clicking on the “Side-by-side” dropdown and select the Modified Content item.
Fig 3 – Commit modified content view
  1. This shows the file’s latest changes and should correspond to the code presented in the lesson.

Now that we have a simple game engine as our starting point, we can move on to additional RPG game features. In the next chapter, we will start looking at game items, traders, monsters and a simple combat engine.

6 thoughts on “Lesson 2.11: The Wrap

  1. Hi Pedro. I have a question about UI update. Up to now, the UI update originated from the user’s action(button click), and in this case UI change is applied immediately after the action. However, if the property of an object is changed systematically, it is not immediately reflected in the UI. For instance, if I tried to increase user’s experience points by 100 points every 10 seconds for 1 minute using system.timer.timer, it is not reflected in the UI immediately. in this case, how can i force UI update based on timer.

    Like

    1. Hi Pedro. I managed to implement it using StateHasChanged method.
      I wonder if there are better ways to achieve this. Thanks.

      private System.Timers.Timer timer;

      protected override void OnInitialized()
      {
      timer = new System.Timers.Timer(1000);
      timer.Elapsed += new System.Timers.ElapsedEventHandler(timer_Elapsed);
      timer.Start();
      base.OnInitialized();
      }

      void timer_Elapsed(object sender, System.Timers.ElapsedEventArgs e) {
      //some property changes
      StateHasChanged();
      }

      Like

    2. Hi Arnold, the StateHasChanged call is what causes a re-calculation and re-render of the page/component. That is a good way to make it happen.

      The other option is to provide an EventCallback, like I showed in the MovementComponent, which you invoke in the timer handler. The EventCallback can also force a recalculation of the component/page rendering. But when you cannot get a change any other way, StateHasChanged is the right method to call.

      Like

Leave a comment