Most recently, I published a post about my small project
tengine . For me, quite unexpected was the fact that many showed interest in his ideas and developments. And since there is interest, this is a reason to continue publishing.
This article is a tutorial on creating a small game. The need for it is obvious: ideologically, to create something in tengine without a level editor (MapEditor3, then me3) is virtually impossible. It is with the help of it that resources are attached to game objects, files with constant identifiers are generated, a scene, sound schemes, etc. are created. And most importantly, me3 generates ready-made binary level files necessary for the tengine logic to work: a file with common data (o-file), files with data for each level (l [0..n] files), and files with text data ( t [0..n] files)
')
Project folder structure:
First, create a folder space_invaders and folder structure inside it:
- _win32
This folder contains project files for MS VS - assets
The following resources are stored in this folder: graphics resources converted by the bmpcvtr.exe utility, graphical resources generated by me3 and sound (* .wav) files - game
This folder contains the source code of our game. - mapeditor
This folder contains the project file me3. For convenience, at the time of the creation of the game, the MapEditor3.exe file from “tengine \ tools \ editor” is transferred to this folder. - rawres
This folder contains non-converted graphic resources (* .bmp or * .png), sounds, font files, etc.
Getting started with me3:
After starting me3, you should configure the paths for working with resources: “File-> Configure paths” and set the path to the “rawres” folder. Then go to the “File-> Editor Settings” and set the global settings: the type of graphic resources. In the current version of me3, it is possible to work only with bmp or png formats. If bpp <32, the color 0xff00ff is considered transparent, if bpp == 32, the alpha channel is responsible for the transparency. Set the resource type to png.
After setting the global settings, you can start creating the scene: “File-> New Project”. Now we create the first scene (map): “Project-> Create Map”. A window appears with the new map settings:
- Screen sizes (in units of map fragments)
Here we customize screen sizes. This value is abstract: for a scroller, screen size does not play a big role, but for single-screen games this is an important parameter. The idea of ​​dividing the map by the number of screens was implemented after the designer’s request, it was easier for him to navigate, creating areas of the game world. Screens in the editor are separated by a grid, but it can be turned off (“View-> Grid”). The default map fragment is 8x8 pixels. Set a height of 38 and a width of 50, let our game screen be 800x600. - Map dimensions (in screens)
The game is planned for us on one screen, but I want to show the map scrolling functionality for demonstration, the stars of the background will move, therefore we set the map: 2 screens in height and one in width. - Number of zones
This setting is used for large maps where gaming zones can be turned on and off. What is this I described in the documentation of tengine. We will not use zones, or rather only one zone.
Level 0 has been created, but I want to highlight one important point. While the card is empty, you need to think about whether we need such small fragments of a map (8x8), with such a large screen. Probably no. Therefore, we will simplify the work of the renderer and increase their size, thereby reducing their number. To do this, go to the menu “Game Background-> Setting background elements”, set the new width and height of the fragment to 32 pixels, put a tick on “Save map size ...” and click “Apply” (I agree, a little inconvenient and not intuitive). You can check whether everything is normal with the dimensions by looking at the map settings: “Project-> Map Settings”.
Some additional information about maps (scenes): tengine can load several maps and draw them at the same time (one on top of the second) onto the specified render plane. Loaded maps in tengine are called logical layers. Architecturally supported up to 4 independent drawing planes (on each platform, the implementation of the drawing plane is different). A theoretically infinite number of logical layers can be attached to a single drawing plane, but only one of them can be the primary layer and can draw background tiles, have objects with loaded animation, play musical schemes (calls of the described functionals in the non-main layers are either ignored or give an assert error). In addition to these features, logical layers do not intersect with each other by logic. An example of using several layers: the game menu layer, the game interface layer and the game layer itself make physically convenient separation of subsystems into independent modules.
Work with background
First, create a background. To do this, go to the background mode: press F2 (or the icon on the panel with the background image). The background palette appears. You can associate empty palette cells with graphics in several ways: elementwise (move the cursor over the desired item and press "Enter" or double-click with the mouse) or use the "cut the finished image" function. We use an easier way: put the cursor on any element of the palette that will be the first element of the cut image, select layer 0 of the mixer (Active layer) and click on the scissors icon. In the menu that appears, select the desired image and click "Apply". As a result, we see a group of cells associated with a graphic resource.
A little bit about the layers of the mixer. The background can consist of multiple layers, for this you need to set the required number of layers in the background settings: “Game Background-> Setting Background Elements”. Layers are drawn in ascending order, or in other words: layer 1 overlaps layer 0. Thus, more interesting tile map combinations can be achieved. The setting “Active layer: all” draws all the layers, showing how they will be drawn on the map.
So, the palette of background objects is ready. They are transferred to the map very simply: select the desired area of ​​objects with the mouse, copy (ctrl + c), put the cursor in the right place on the map and paste (ctrl + v). Moreover, the copy-paste operation also works on the palette itself; you can copy and paste objects anywhere in the palette; you can copy and paste background tiles anywhere on the map. There is one more useful function “propagate” (or “tile”): copy some area of ​​background objects, select another area of ​​the map (or the entire map ctlr + a) and press ctrl + alt + v, as a result - the entire selected area will be filled with repeating fragment copied area.
Some additional information about the background elements: you can set some properties for the background object of the palette. To do this, you need to create the types of background properties in the background properties manager (menu “Game Background-> Types of Background Properties”). In the properties, you can set the logical "permeability" of elements, as well as assign some digital additional parameter that can be used in the game logic. After creating property types, in the background objects palette, you can assign properties by pressing “Enter” or double-click on the selected object and select the desired type in the pop-up window (the Fragment type drop-down list). From this point on, all tiles of a map of this type will have the specified properties (checked by pressing ctrl + p on the highlighted tile under the mouse cursor).
The only condition for all these manipulations: the background mode must be active (the “Background mode” icon in the “pressed” state on the toolbar).
Creating a sound scheme
In order for sounds to appear in the game, you need to create a sound scheme. It has already been described above that sound schemes should be created only on maps that will become the main layers. Also note that the sound schemes belong to the cards, not to the game as a whole: each level requires its own sound scheme, if you plan one set of sounds for the whole game - copy and paste one sound scheme between all the cards that will be game levels.
First, we switch to the object mode: press F1 (or the icon on the panel with the image of objects). In the lower window of the object palette, switch to the System tab, grab the SOUND SCHEME object and drop it to any place on the map. Then go to the properties of the object on the map (ctrl + p or right-click the object's context menu and select "Properties"). In the window that appears, we add sound files, give them identifier names, and set them with the parameters SFX (effect) or BGM (background music).
Creating game objects
Before creating game objects, create a list of animation types and states. To begin, launch the animation type manager (“Project-> Animation Types”) and add two types that should be enough for our small game: “ANIM_ACTIVE” and “ANIM_DAMAGED”. Now we will create state types of objects. We launch the state type manager (“Project-> States”) and add two states: “STATE_ACTIVE” (to which we set the animation “ANIM_ACTIVE”) and “STATE_DAMAGED” (we set the animation “ANIM_DAMAGED”).
Some additional information about states: all the logic of game objects is wrapped around states. It is the states that give the object a logical (logical, since the names "up", "down", "right" and "left" are entered only for dereferencing the four options of directions) direction of movement, especially when the object is attached to the track nodes, and also give the name animation, which now need to play.
The second most important parameters after the states for an object are properties. They are created in the property manager as a template (“Project-> property template”). Add two important properties: "PRP_ENABLE" and "PRP_SPEED". You can think of properties to an object as much as you like, but it is only on these two tengine that the internal logic responds. If "PRP_ENABLE" does not equal 1, the object is not drawn and does not participate in the logic of the game process. The property "PRP_SPEED" sets the speed of movement along the track nodes. If these properties are not created, it is considered that “PRP_ENABLE” == 1, “PRP_SPEED” == 0.
We will also create one event, we will need it, to determine the end of the death animation of the space alien, to know the moment when we can remove it from the scene. To do this, launch the event manager (“Project-> Event Types”) and create the event type “EVENT_END_ANIM_DAMAGE_INVADER”.
It is important to know: you can add or remove animation types, states, events or properties at any time at any stage of the project development.
Now you can create our first type of game object. First, we switch to the object mode: press F1 (or the icon on the panel with the image of objects). In the lower window of the object palette, we switch to any General tab (you can rename it). Right-click in the window, call the context menu and select the item “Add object”. Let the first object we will be a space alien.
The game object creation window consists of two main tabs: General and Animation Editor.
The “General” tab contains settings:
- Object name input field
- Will the object be a decoration. If so, what type: foreground (always drawn before the game objects of the game) or background (always drawn after the objects of the game). The scenery has no properties and does not take part in the game logic.
- Whether to use graphics for this object. Sometimes an object is needed only for some logic of the gameplay (for example, only for the co-region) and does not need a graphical display.
- Whether to ignore the graphic resources used by the object if there is not a single instance of this type of object on the map. By default, when generating map data, optimization is enabled, which adds to the list of downloadable resources only the resources of those objects whose instances are on the map. This option allows you to disable optimization for a specific group of objects.
- Editing the default property values ​​of objects of this type. Each instance of an object of this type, when installed on a map, gets the values ​​set in this template. Important: changing the default property values ​​does not affect the properties of the instance objects of this type already mapped; there is an additional functionality in the drop-down list of the context menu of the objects palette for forcing values ​​to be changed.
- The default state sets the state that is set to the instance of the object mapped.
Name the object SPACE_INVADER, set the default state to it STATE_ACTIVE and go to the second tab, where we can create an animation.
Tab "Animation Editor". The very first thing to do is to select the desired animation name from the list, and create the first frame. Select the “ANIM_ACTIVE” animation, go down just below the animation selection field to the frame window, right-click to open the context menu and select the “Add empty frame” item. We created the first frame of the animation. Now you need to cut the graphic elements for the graphic component of the frame. To the right of the empty frame we see an auxiliary window. Make sure that in this window the active tab "Graphics" contains the active sub-tab "Standard". Right-click on the still empty window-palette of graphic elements, call the context menu and select "Edit". A window for editing the graphic image of the object has appeared. Here are created (cut out) graphic elements from which animation frames will be created. To begin with, we will create a new group, into which we will collect the elements of the aliens. To do this, right-click on the window of groups of graphic elements (the leftmost window with the inscription "General") call the context menu and select "Create group". We call the group "INVADERS". Now we make this group active (left mouse button) and right-click in the group a context menu in which we select “Add” (or press the Insert button). An empty cell appeared in the group. We make it active. Go to the "Source File" window and select the file "characters.png". After that, in the picture that appears, select the area of ​​the alien image of the first phase of the animation (for convenience, use the arrow keys to move the selected area, as well as the ctlr + arrow combination to change the size of the selected area, also use the sliders to change the image scale). Add one more frame to the INVADERS group and select the area of ​​the newcomer image of the second phase of the animation. Click "Apply". We are again in the animation editor. Now is the time to create alien animation frames. Select the desired image of the newcomer in the graphic elements palette, put the mouse on the frame field, right-click on the context menu and select the “Put” option. By analogy with the first frame, add another empty frame and set the second frame of the newcomer. Let's see what we did. Click "Start" of the player and see how our first animation works. Are frames changing too fast? Set the time for each frame. Click "Stop". Switch with the mouse in the frame window for each frame and set the “Frame time” field in the “Current frame” group to 200 (ms). Check again. Now the animation works as it should.
It's time to add a bit of logical component to the frame: a collision-area (collision zone). It will be needed to determine the zone of entry into the alien. It is important to know that in the tengine of the graphics object does not participate in the logic of computing collisions or zones of "visibility". For these needs, two logical parameters are introduced (these concepts are conditional, since tengine does not operate with these zones):
- The working area of ​​the object. It is assumed that the "working area of ​​the object" will serve as a collision zone in the game process, the dimensions of this area are set in each animation frame separately.
- Object visibility. It is assumed that the "visibility zone of the object" is involved in the logic of the interaction of objects or is the frame size of the animation. The size of this zone is one for all frames of the animation.
There is one more way to determine the collision zone: using an additional “collision” raster map. More information about working with this functionality is described in the documentation (prHasAlphaCollideMap () and prGetAlphaCollideMapValue () functions).
Select the first frame of the animation. Switch the tab of the auxiliary window from "Graphics" to "Logic". For convenience, the image graphics disappears. In this case, we need to see the image in order to describe it with a collective-zone. Put a tick on the option "Graphics and Logic" (the lower part of the animation creation window). In the auxiliary window we tick off the “object's working area” properties, thereby activating its editing. Enter the parameters W = 40, H = 30, then grab the resulting rectangle with the mouse and set it so that the “newcomer” is inside it (for the convenience of moving objects, you can use ctrl + arrows). Copy the selected area (if the selection is gone, click with the mouse on the edge of the rectangle, thereby selecting it) using the ctrl + c key combination, switch to the second frame and paste (ctrl + v) the frame area for this frame. In this way, we get an animation of a space alien with a collage zone in each frame.
One trifle remains: create an icon for the object selection palette. Select the first frame, call the context menu of this frame and select the “Create an icon” option. Now that's all, you can click "Apply". Our first object appeared in the object palette.We build on the map of aliens. To do this, grab the object with the mouse and drag it to the map. Since we will have a lot of aliens, you can use the function of the context menu of the object on the map "clone".To simplify working with objects, the editor has an object manager (ctrl + o). It is more convenient to keep track of the number of objects, change their position in the drawing list, properties, etc.By analogy, we create an animation of death for the newcomer ("ANIM_DAMAGED"). The only thing in the last frame of the animation in the “Event” field is to select the value “EVENT_END_ANIM_DAMAGE_INVADER” from the drop-down list. We also create objects for the TURRET cannon, the BASE base and the MISSILE rocket. We put them on the map. Moreover, we put several rockets on the map, set them PRP_ENABLE = 0 properties, we will need them for the pool.A little bit about pools: the tengine ideology prohibits spawning objects. Therefore, all objects that are planned to be “created” during the game must be on the map in sufficient quantity and have the property PRP_ENABLE = 0. Additional logic is also written in the logic of the game to use this pool.Text fields and font creation
Some additional information about working with texts in me3:- Support up to 8 languages. You can set how many languages ​​will be used in the application in the settings tab “File-> Editor settings-> Text editor tab”. Here you can rename the languages ​​(“LNG_0..n”) into more convenient names and tick off which languages ​​are participating in the current project. The width and height of the displayed area - the size of the text box window by default
- Font support (font creation will be discussed a little later)
- Separate editor subsystem for creating text messages
Text fields are dynamic and static. The text of dynamic fields can be changed from the application code using special functions. We do not change the text of static fields; a row identifier is assigned to it, which automatically changes its value depending on the selected current language.Create another map. We will use it to display text messages. This will be the logical layer of the game menu. “Project-> Create a map”, set dimensions 25x19 (800x608), map dimensions - 1x1 screen. Let our game will be available in two languages: Russian and English. Go to the "File-> Editor Settings", select the "Text Editor" tab. Click on the "Edit" button under the window of available languages ​​and in the appeared window change the language "DEFAULT" to "LNG_ENG", "LNG_1" to "LNG_RUS". Then I found an annoying editor error, initially there was no choice of languages ​​in the manager window that appeared. You need to enter in the search box any letter and delete it, only then you can see the list. This will be fixed in the next version of me3. After that, click "Apply" and tick our languages ​​"LNG_ENG" and "LNG_RUS".Click “Apply” again. Now you need to check whether there are fonts available for use in the project. If there are no files with the * .fnt extension in the “rawres” folder, you need to create a font.A little bit about fonts: all fonts for working with tengine and me3 are created by a separate utility “Bitmap font generator”. She was chosen because of its free and easy to learn, located in the folder "tengine \ tools \ BMFont". More information about the utility is described on the website www.angelcode.com/products/bmfont , but in short, creating a font consists of several steps:- “Options-> Font settings”, select the desired font, define the character set: ANSI or Unicode, set the size. More than any values ​​in the settings window does not change.
- , ( «»). Unicode, . , – .
- , , fnt. «Spacing» 0, 0. : , . , tengine me3 , , , , . , «Options->Visualize». 8, 32. 8 , , 0xff00ff . 32 , («Presets») «Outlined text with alpha». «Binary». — png (: me3 «BMP», bmp (32bpp) )
- «Options->Save bitmap font as..». : .fnt .png.
- , , .
Create a text message "Game over": "Project-> Text Editor", switch to the tab "LNG_ENG", click "Create". We call this text “TXT_GAMEOVER”, set the desired font, write the text “GAME OVER”, see how the text will look in the visualizer. Here, in the editor, you can set the alignment, set the color and size of the canvas for the current message. We close the text editor window, switch to the “LNG_RUS” tab, we see that there is no text here yet, click “Edit”, we write “GAME IS OVER”. Thus, we localized the message “TXT_GAMEOVER” into two languages.Now create a text object on the map. Go to the tab "System" palettes of objects, put on the map the object TEXTBOX. This will be the text box for the static text TXT_GAMEOVER. Go to the properties of this object, select "Static text", call it TXTBOX_GAMEOVER, click the "..." button, select the desired text and click "Apply". The object inherits the color and size of the text message canvas, but it can be changed individually for each object using the suggested settings.Create another text object for fps output. Go to its properties, give it the name TXTBOX_FPS, set the item “dynamic text”, “lines” set to 1, “letters per line” - 10. Set the font “system”, then set the background color and size of the area displayed for the tex: 64x18You can change the current language in “View-> Current language”.Generate game maps and constants for use in tengine
We have created everything that we need in the game. It's time to generate maps and constants for tengine. For a start, in “Project-> Map Information” you can see for each map what resources are used and in what quantity. Also, here you can find warnings about potential problems. After this, you need to generate a * .h file with constants. To do this, run the “Project-> List of Variables” and save the constants in the “game” folder as “constants.h”. After that, run “File-> Save Card (s)” and specify the “assets \ data” folder. Now everything is ready to work with tengine, it remains only to convert resources.Resource Conversion
Create an empty “make_res_bmp.bat” file in the root directory of our project with the following contents:for %% i in (rawres \ *. Png) do .. \ .. \ tools \ bmpcvtr.exe %% i -5551 -2n -oassets / datacopy rawres \ arial_28.fnt assets \ data \copy rawres \ system.fnt assets \ data \copy rawres \ *. wav assets \ data \pause
We will convert all * .png files to r5g5b5a1 format, automatically set all sizes to textures multiple to 2 ^ n and copy them to the “assets / data” folder, then copy the font and sound files to the same folder. Note that in the 32bpp resource (arial_28_0.png), when converting to the 5551 format, additional data was created with information about the alpha channel, thus, even with the 5551 format, the translucency is not lost. More information about the parameters of the utility "bmpcvtr.exe" can be found by running it without input parameters. Run the file "make_res_bmp.bat".Writing game code
Now it remains only to write the logic of the game and compile the project. See the sources, more information is in the "tengine \ src \ tengine \ manual".All the sources of this article are in the tengine tengine / samples / space_invadersrepository. The binary of the finished game space_invaders_demo1.zip