New editor features: change class of any component, shortcuts to tools, multi-selection of transforms

Posted on

Multiple selection of lights

We continue to improve the editor to make it easier to design large 3D and 2D games.

  1. Context menu of each component (available if you click with right mouse button on a component in the hierarchy panel, on the left) contains now a menu “Change Class…”. This allows to change:

    • any TCastleUserInterface class to another TCastleUserInterface class (for example change empty group to a color rectangle),
    • any TCastleTransform class to another (for example change light type between point / spot / directional),
    • any TCastleBehavior class to another (for example, change collider between sphere / box / mesh etc. in the upcoming physics work),
    • any non-visual class to another (for example, change font class to a family of fonts with different bold / italic etc. versions).
  2. You can now select multiple TCastleTransform instances by clicking on them with Ctrl key held down in the design (middle) panel (which shows 3D view in case of 3D viewports).

    Multiple selected transformations are also better shown now.

    This is great to select e.g. a number of light sources or scenes and change their properties (e.g. intensity or color of the lights).

    Note: For now, you cannot transform (move/rotate/scale) a multi-selection using a gizmo. But we have made now a first step to enable this too in the future:)

  3. You can now add TCastleBehavior from right-click menu when another TCastleBehavior is selected. Esp. useful when adding collider alongside rigid body — this is great for upcoming physics.

  4. Use Alt+1, Alt+2 etc. key shortcuts to quickly switch between interact / select / move / rotate / scale tools.

  5. Use Escape key shortcut to reliably focus the design (middle) panel. This is great if you want to use e.g. F (focus) or 1 / 3 / 7 key shortcuts. In case you stand on an edit box, the Escape key will reliably switch focus to the design.

Comments on the forum ➤

Faster compilation with cache

Posted on

Compilation cache effect

You can speed up the compilation of all future projects if you initialize “compilation cache”. Underneath, it means we will just compile all CGE units to a special “cache” directory (stored inside user directory, independent from the current project) and we start compilation of each project by taking all CGE precompiled units from this cache.

The effect: your compilation can be lighting fast. In my tests, if the cache is initialized,

  • It takes 2.5 seconds to build a Linux application.
  • It takes 10 seconds to build an Android APK.

And these are times of the first build, on a newly created project.

How to initialize cache?

In CGE editor, use the menu command “Run -> Cache (Precompile Engine For Current Platform)”. By default it will cache compilation for current platform (e.g. Linux or Windows where you run the editor). Switch the platform using “Run -> Platform (To Build And Run) -> …” menu item, and redo the “Run -> Cache (Precompile Engine For Current Platform)” for each platform.

Note: The menu commands to initialize the cache are only available when you have some project, any project, open. This is just a consequence of our current UI (we already have output console, and platform choice, when the project is open). But the created cache is actually independent from the project.

Or you can do it using the command-line CGE build tool, if you prefer (and your compiler, like FPC, is available on PATH environment variable). Just execute something like this:

castle-engine cache # cache for current platform
castle-engine cache --target=android # add cache for Android, both 32-bit and 64-bit

Why like this?

Right now: Without the cache if you compile the project for the first time, we actually always compile the engine too. Moreover (with or without the cache) all the compilation output (like .o, .ppu files) is stored in project-specific castle-engine-output.

Why?

  • This makes things simple. It means that we just provide to the compilers your main source code (program or library) and the paths to all sources (of your project, and of the engine). And the compiler (FPC or Delphi) just does whatever is necessary.

  • It means that switching compilers, FPC versions etc. is not an issue. Again, the compiler will just do what it should. E.g. the compiler should realize that standard units have changed compared to previous compilation.

  • It is friendly to engine developers 🙂 Changing the engine unit has the same effect as changing your project source code. In both cases, the compiler just figures out the minimal set of units to recompile.

  • The debug/release modes change not only the compilation options of your application, but also of CGE units. This is helpful e.g. to activate certain additional assertions and range checks in the engine.

  • It allows you to set, within each project, some defines that affect engine compilation. For example you can change CastleWindow backend by using appropriate define. In general we want to make this use-case not important (it would be e.g. cleaner to switch CastleWindow backend by using a particular unit, it would also make it better for cache) but it is still practically useful for now.

We have designed the cache mechanism to not interfere with these advantages:

  1. The current cache contents (.o, .ppu files) are copied over but without overwriting the current .o, .ppu files in the project. So the precompiled units from cache are a starting point to your project’s compilation directory. But the precompiled units do not overwrite the existing ones, moreover the compiler will overwrite them (in the project) if e.g. you have changed CGE since making the cache. So the cache tries hard not to conflict with what you’re doing.

  2. There is a separate cache for each mode (debug,release,valgrind).

Comments on the forum ➤

Wireframe view in editor, camera improvements: navigation under any transformation, zoom in Walk mode

Posted on

Wireframe + Polygons view
Wireframe view
Regular (Polygons) view of new castle demo
  1. Use Viewport -> Wireframe mode menu, or just hit Alt+Z shortcut, to toggle between viewing:

    • Polygons,
    • Wireframe or
    • Polygons + Wireframe (internally known as weSolidWireframe).
  2. At design-time, in “Fly” mode, mouse scroll wheel now does zoom (if you don’t have right mouse button pressed; when right mouse button is pressed, it changes moving speed, as before).

    More details:

    Zoom (by mouse scroll wheel) is now available for all navigation modes, including TCastleWalkNavigation. Although it is disabled on TCastleWalkNavigation by default, but you can just enable it by MyWalkNavigation.ZoomEnabled := true (or clicking on ZoomEnabled checkbox in editor).

    Editor and view3dscene enable this zoom by default.

    Also, zoom-in now honors collision detection. Though at design-time we disable collision detection.

  3. We’ve done a few fixes to make TCastleWalkNavigation navigation, including mouse look, work even when the camera is a child of some other TCastleTransform with some transformation.

    This gives you more flexibility where do you place TCastleCamera in the transformation hierarchy.

Comments on the forum ➤

Concept art teaser: Huge graphical (and functional) upgrade to our FPS game is coming

Posted on

Concept art by Adrianna Matejek for new FPS game demo

Together with artists from our company Cat-astrophe Games we are working now on a big upgrade to “FPS game” example! Please welcome Adrianna Matejek (concept art, 2D, UI) and Alya Vaneskehyan (3D, textures). They will commit lots of things to fps-game-upgrade branch in the upcoming weeks 🙂

Together we have a great plan how to turn this small example into a cool and impressive short 3D game.

Along with graphical upgrades, there will be functional upgrades. The “easy creature AI, as behaviors” will finally be done along with this rework.

Here’s a teaser — first 2 concept arts from Ada!

Note: I uploaded a really high-res version of these concept arts here. You can click on the image and download a full version.

If you like this, please support us on Patreon. This is exactly why we need your support — to afford to hire more and more talented people to work on CGE!

Comments on the forum ➤

CGE downloads now come bundled with latest stable version of FPC

Posted on

FPC logo

Our default downloads are now bundled with latest stable version of FPC (Free Pascal Compiler, an open-source cross-platform compiler that we love and recommend).

The goal is to make Castle Game Engine work out-of-the-box. Building and running a newly-created project from CGE editor will now work out-of-the-box, users don’t need to install their own FPC version. Downloading CGE gives you all you need to perform basic “workflow” with CGE editor: create new project from template, open and edit some design, hit F9 and see it build + run.

This should be great for users that don’t come with existing knowledge of Pascal ecosystem, who don’t want to (or maybe, just today, don’t care) about what FPC or Delphi version they use — they “just want to build CGE application”. Now they don’t need to learn how to install FPC, Lazarus or Delphi. They can just use CGE to build projects immediately. This is also great for people who may not need to edit the game — e.g. if you cooperate on a project with artists, who test the game in the editor, then they just want to edit some designs, and run the game by F9.

Note: You don’t need to use this “bundled” version of FPC of course. You can still use your own FPC or Delphi, we still support many compiler versions. You can still install them however you want (e.g. maybe using fpcupdeluxe). In this case, you also don’t need to download the “bundled” version, just download the unbundled versions from GitHub releases.

Underneath, the “bundled” FPC is stored in tools/contrib/fpc/ . If we don’t find other FPC installation, we will use this one. Moreover, we automatically pass proper -Fu for the compiler in such “bundled” subdirectory (as it doesn’t have any useful FPC config).

Comments on the forum (2) ➤

Published state fields are now automatically initialized, no need in most cases for DesignedComponent calls

Posted on

Van Gogh , Bedroom in Arles , night - by ruslans3d from https://sketchfab.com/3d-models/van-gogh-bedroom-in-arles-night-7c28126099404406bd0f5c150d809394

This is another important “quality of life” improvement for developers:

You no longer need to explicitly initialize the components you want to access using DesignedComponent method. You just need to move your fields to the published section to make them initialized automatically.

Detailed explanation of the difference

All (or most) of the calls like below can be now removed:

LabelFps := DesignedComponent('LabelFps') as TCastleLabel;

Previously, we advised to organize your state like this:

type
  TStateMain = class(TUIState)
  private
    { Components designed using CGE editor, loaded from gamestatemain.castle-user-interface. }
    LabelFps: TCastleLabel;
  public
    constructor Create(AOwner: TComponent); override;
    procedure Start; override;
  end;
 
constructor TStateMain.Create(AOwner: TComponent);
begin
  inherited;
  DesignUrl := 'castle-data:/gamestatemain.castle-user-interface';
end;
 
procedure TStateMain.Start;
begin
  inherited;
  { Find components, by name, that we need to access from code }
  LabelFps := DesignedComponent('LabelFps') as TCastleLabel;
end;

Now, we advise a simpler approach:

type
  TStateMain = class(TUIState)
  published
    { Components designed using CGE editor.
      These fields will be automatically initialized at Start. }
    LabelFps: TCastleLabel;
  public
    constructor Create(AOwner: TComponent); override;
  end;
 
constructor TStateMain.Create(AOwner: TComponent);
begin
  inherited;
  DesignUrl := 'castle-data:/gamestatemain.castle-user-interface';
end;

Of course you may still find it useful to define Start method, to initialize various things about your state. But there’s no need for it if it was only doing DesignedComponent calls.

What’s going on under the hood

The published fields of the TUIState descendants are now automatically initialized when the design is loaded. Right before Start, the published fields (that have names matching some object in the design) are now automatically set to the corresponding objects. At Stop (when design is unloaded) these fields are set to nil.

As a bonus (advantage over previous solution) this avoids having dangling references after Stop. While previously you could set all your references to nil manually in Stop method… likely nobody did it, as it was a tiresome and usually pointless job. Now they are nil after Stop automatically, so accessing them will result in clearer errors (and can be safeguarded by X <> nil reliably).

I should also mention one disadvantage from the previous approach: if you make a typo in component name, e.g. declare BabelFps instead of LabelFps, then the mistakenly-named field will just remain uninitialized. Nothing will make an automatic exception like “BabelFps not initialized!”. Of course any code doing BabelFps.Caption := 'aaa'; will crash and the debugger should clearly show that BabelFps is nil. And you can write something like Assert(BabelFps <> nil); in Start to get explicit exception in case of mistake.

This is very consistent with how Delphi VCL and Lazarus LCL initialize their form fields.

Our conventions — where to put the published section?

I admit I had a little discussion with myself about “where to put the published section”?

Following our usual conventions for writing components, the published section should go as last. We usually write private, then public, then published. So I wanted to have section in the increasing order of “being exposed”:

type
  TStateMain = class(TUIState)
  // MOST INTERNAL
  private
    MyInternalStuff: Integer;
  // EXPOSED TO OUTSIDE WORLD
  public
    constructor Create(AOwner: TComponent); override;
  // EXPOSED TO OUTSIDE WORLD ALSO THROUGH RTTI
  published
    { Components designed using CGE editor.
      These fields will be automatically initialized at Start. }
    LabelFps: TCastleLabel;
  end;

But eventually I came to the conclusion that it is a bit unnatural in this case. Basically, Delphi VCL and Lazarus LCL are right to put it at the beginning. Because in the usual case, you don’t think about this published section as “the most exposed identifiers for outside code”. You think about it as “internal components I need to access to implement my design”.

And it’s kind of an “unfortunate but sensible limitation” that it means that these things have to be also exposed to everything from the outside. This fact makes sense if you realize that the automatic initialization requires RTTI (RunTime Type Information, known also as reflection in various other languages). Things that RTTI has access to are naturally available to the outside world, through RTTI. So it would not be consistent for compiler to “hide” the fields in the published section while still making these identifiers available through RTTI.

Yet, when creating Delphi VCL form, or Lazarus LCL form, or CGE state, you usually don’t really want to “expose” these fields to the outside world. You want to access them right within your form / state. Thus, having them at the beginning of the state makes sense. And is consistent with Delphi VCL / Lazarus LCL as a bonus.

Still I decided to explicitly spell the published section name everywhere. This allows me to easily say in documentation “put your field in the published section”. I don’t need to say “initial section” or “automatic section” and users don’t need to understand how it works and how {$M+} in Pascal works and whether TUIState was compiled with {$M+}. So, in the end, I propose to write:

type
  TStateMain = class(TUIState)
  published
    { Components designed using CGE editor.
      These fields will be automatically initialized at Start. }
    LabelFps: TCastleLabel;
  private
    MyInternalStuff: Integer;
  public
    constructor Create(AOwner: TComponent); override;
  end;

Have fun with this! I have already updated our templates, our manual like here, and some (but not all!) examples to follow the new convention.

Comments on the forum (13) ➤

Hacktoberfest for Castle Game Engine!

Posted on

hacktober

Hacktoberfest is an annual event dedicated to promoting Open Source software development and to help developers from all the world (regardless of their experience level) to contribute to open source projects.

Now you can also participate in the event by contributing to Castle Game Engine! Many related projects at Castle Engine (GitHub org) received a hacktoberfest tag 🙂 Feel free to look around!

First of all, of course it’s a good idea to check out main repository of Castle Game Engine:

A good beginner task (whether you want to participate in hacktoberfest or not :)) is to browse our examples. Just download CGE and navigate to projects in examples subdirectory. By testing examples you will:

  • learn how to do various things using the engine
  • undoubtedly notice places to improve.

The examples are being constantly added and improved, but it is also a never-ending work 🙂

Many examples could use a better 3D, 2D graphics or even just better presentation of the content. This doesn’t necessarily mean that you have to create your own art from the scratch. Using / extending assets with open-source licenses is absolutely welcome and even encouraged. See e.g. Castle Game Engine Assets, OpenGameArt, Kenney, Quaternius etc. — we have lots of people already doing pretty things. In a lot of cases, you can just use / remix them for the purpose of CGE example and create something much prettier than some of the current demos 🙂

Adding various small functionalities is also welcome. With CGE editor, editing a lot of these things to be more functional/prettier is really easy.

Note that we don’t want to over-complicate the examples — each example is deliberately limited in scope. Some examples are deliberately simple. The primary point is to show “how feature X of CGE works, what are the main properties of this feature”. We usually do not show every possible variation of X, alternative of X, property of X — we focus on most important stuff around X. This is of course very subjective — so when in doubt (“should I extend this example with Y?”) just ask on any of our channels (Discord, Forum etc.)

And if you find some example that seems outdated (e.g. doesn’t use CGE editor to design UI, or has missing README.md) — that is also (probably — ask if in doubt!) something to update.

Moreover, non-trivial examples definitely can be published as a demo on Itch.Io Page and Google Play Store (Android).

We did it with examples/platformer. However, some examples may deserve it too, for example:

You can also browse API docs. Surely there are some places that lack description or maybe their description is unclear or could be improved by examples. All these API docs are just taken from comments in units’ interface — to improve those, just edit the appropriate unit’s comments. They are processed by Pasdoc, check PasDoc documentation to see what formatting features are available.

Comments on the forum ➤

Slides, movies and thoughts from my GIC 2022 presentation

Posted on

GIC 2022

Last Sunday, I gave a presentation about Castle Game Engine at the Game Industry Conference. I think it went really well — a lot of people came, I had a lot of positive feedback and good questions. I felt that a lot of work we put lately into making the engine not only packed with features, but also really easy to use, paid off!

The slides from the presentation are available here, and embedded in them are 4 short movies (physics, 3D game, 2D game, code). Enjoy!

Note that I used physics branch to demonstrate the physics components (not yet merged to master, just due to my obsession to review everything perfectly 🙂 ). Everything else you see there is available on CGE master already.

I also bring back some thoughts and conclusions:

  • Confirmed TODO: The hierarchy on the left is getting a little overcrowded when we put lots of behaviors (like rigid bodies and colliders) together with transformations. The current state may be acceptable at start, but eventually we should improve this. This is a UI thing — we can organize it better and we will, we already talked with Andrzej Kilijański about it.

  • Confirmed TODO: WebGL port is important 🙂

  • My new idea (this one is not from feedback to my CGE talk, but it is a combination of 2 ideas from 2 talks I had at GIC):

    We should have a demo in CGE showing a huge city and loading neighboring pieces of the city asynchronously. This idea came to me during “Open World Streaming in Dying Light 2” talk — I believe the core idea is something completely doable in CGE (and testable on a 3D big city generated from ready buildings (with interiors) in CGE example).

    This idea clicked with something I learned thanks to meeting Grzegorz Wojciechowski also at GIC. He’s doing amazing things with OpenGL, among them — spreading work into multiple processes and threads at the engine layer. He made me aware that you can load things asynchronously, in another thread, into OpenGL!, if you do this in another OpenGL context that is shared with your main (rendering) context. And in CGE our TCastleWindow and TCastleControl already always do sharing (because it makes caching natural for multi-window applications), so we got this!

    This is a very possible and within-reach solution to a promise “Asynchronous loading will be possible some day” made in our Threads usage manual chapter.

Comments on the forum (4) ➤

Teaser: Physics joints in Castle Game Engine: hinge, ball, grab, rope

Posted on

A quick video demonstrating new Castle Game Engine physics joints!

Joints presented:

  • hinge (rotation around an axis)

  • ball (free rotation)

  • grab (follow a specified point)

  • rope (one object is tied to another with an invisible rope – it can move and rotate, as long as the rope distance is preserved).

We can design and simulate everything in CGE editor. This is all open-source, on Castle Game Engine physics_j branch.

Andrzej Kilijański and Michalis Kamburelis work on making it merged to CGE master 🙂 If you like this work, please support us.

We use physics engine Kraft for the underlying computation by Benjamin ‘BeRo’ Rosseaux.

Comments on the forum (3) ➤