Skip to content

How Surface Works

Mick A edited this page Apr 29, 2019 · 1 revision

Next Chapter >> Creating the Application

Previous Chapter << Introduction to Surface

The Surface Engine, in it's current form, is an API for constructing interactive applications. Basically, it handles all the boring stuff and exposes functions that let you build games. There are a few core concepts that power Surface, so let's get some basic definitions out of the way before continuing.

Core Aspects

  • Application: The literal application that runs, responsible for handling user inputs and rendering Views.

  • View: Contains Layers and Overlays. A single Application can have multiple Views, but only one View can be active at a time.

  • Layer: Hold Objects and receive Events, these are rendered such that the last Layer in a View is drawn above everything else.

  • Overlay: Identical to Layers, except they are guaranteed to be drawn above all other Layers and receive all Events first, regardless if they are visible or not.

  • Event: Basically containers for application events. Anything that happens to the application is propagated down to the Overlays, then the Surface Engine itself, the Layers, and subsequently all Objects

  • Object: The building blocks of the Application, they are stored inside Layers and Overlays and can basically be anything. The Surface Engine provides a few template Objects that can used as they are or extended with custom classes.

  • Group: This is a built-in type of Object which acts as a container for multiple Objects. More information about this special type will be discussed later.

  • Camera: This is another built-in type of Object, except it is also registered in the View itself. Multiple Cameras can exist, however the ordering of them is crucial to deciding what is rendered and where it is on the screen.

How Events Work

Building a game with the Surface Engine is designed to be very simple, but you still have enough control to turn it into whatever you want. Just to get things straight, here is the model for how events flow throught the Surface Engine.

  1. Event occurs
  2. Derived Application receives event in OnEvent()
  3. All Overlays in the currently active View receive the event in OnEvent() regardless of visibility
  4. Base Application class receives event and could terminate here
  5. All Layers in the currently active View receive the event in OnEvent() only if they are visible

Let's use a thought experiment to better understand the flow of Events. Imagine we have a basic FPS game, and currently there is only one level where the player is standing in front a single enemy on the screen.

In this example, there is a single View, Layer, Overlay and five Objects. The Surface Engine let's you give everything a name, so here is a simple tree view that describes our game:

  • Application "Game"
    • View "World"
      • Overlay "HUD"
        • Object "Cross-hair"
        • Object "Health Bar"
      • Layer "Level 1"
        • Group "Player"
          • Camera "Main"
        • Object "Enemy"

Because we can name everything, it makes everything pretty straight-forward. Below is an example of what happens, and in what order, whenever a player moves their mouse.

  1. A MouseMovedEvent is created by the Application, and is propagated down to all the Overlays and Layers in the "World" View.

  2. The "HUD" Overlay receives the event first. Because, in this game, the "HUD" only has static UI elements, we tell it to completely ignore the MouseMovedEvent and to not pass it down to the Objects.

  3. Layer "Level 1" receives the event last. In this game we definitely want the MouseMovedEvent to be handled by our "Player" Group, so we allow the event to be propagated to all its children.

  4. The "Player" Group receives the event first. In order for the Camera to turn, we have the "Player" update its rotation based on the data contained in the MouseMovedEvent.

  5. The Object named "Enemy" receives the event next. Because we want the "Enemy" to be autonomous and uncontrolled by the player, we tell the "Enemy" to ignore the event.

As a slight modification, we could have marked the event as "inactive" at the end of Step 4, which would have prevented the event from even reaching the "Enemy". This is up to you as a developer, however. It may be beneficial in some situations, like to prevent clicking on a menu option from also triggering the player to fire their weapon. However it could also be good to not do this, such as when changing the rotation of a minimap on your HUD and the player's direction by allowing both to handle the event.

How Rendering (Should) Work

WIP

Next Chapter >> Creating the Application

Previous Chapter << Introduction to Surface

Clone this wiki locally