[ANN] Preview of Godotcaml for the Godot 4.2 Game Engine

Hi there,

I’ve released a small preview of a project I’ve been working on. It’s bindings to the Godot 4.2 game engine from OCaml.

To keep this announcement short, I’ve posted a longer explanation on my blog:

Here is the git repo:

Here is another short blog post explaining how to get up and started with it:

Do not expect much, I’ve basically just reached the point where Godot and OCaml can call each other. I just thought people might think it’s cool! Open issues or discuss in this thread if you’d like; another blog post will be forthcoming covering the current structure of the code if there seems to be interest.

Best,

Matt

22 Likes
module%gclass MyClass = struct
  [%%ginherits Node]

  let%gfunc succ = 
    [| ClassMethodFlags.default |]
      (module BuiltinClass0.Int)
      (module Class.Node)
      (module BuiltinClass0.Int) 
      (fun i _self -> Int64.(i + 1L))
end

I’m curious why you chose to go this route vs, well, the O in OCaml

2 Likes

Oh, hopefully this isn’t confusing, but the let%gfunc defines a Godot function, using the OCaml function. So, in my view, defining an OCaml function is given by regular let and defining a Godot-compatible (and visible function) from OCaml is given by let%gfunc. Do let me know if this is still confusing though.

I just realized: you might be asking why Objects of Godot are not represented by Objects of OCaml: That requires a little more technical explanation, and my decision might have been wrong, but it’s worked out quite well so far.

First of all, it’s translatability. The object in Godot has the following properties:

  • There are like 30 “primitives” in the Java sense. These include packed vectors of various flavours, ints, bools, and so for, but also more core types like Callable and Signal. These primitives cannot be inherited from. OCaml makes quite a large distinction syntactically between “core types” like algebraic data types, and “object types”, while Godot does not. That is: for a primitive in Godot, you call the builtin methods like prim.meth(), same as obj.meth() for the Godot objects. In OCaml, primitives would need to use prim |> meth syntax (since otherwise I could inherit from them, which would violate the Godot object model) or else be objects too, which isn’t really what they are! Instead, I opted for uniform “functional” syntax, with modules encapsulating objects.
  • Because OCaml is multiple inheritence and Godot is single, it could possibly create confusion if you tried to use OCaml object inheritence semantics and square them with how Godot interprets them. Should multiple inheritence just not be allowed? I found it simpler to just simply represent in OCaml the way Godot does it, and that didn’t really require OCaml objects, so I left them out.
  • Finally, object types in OCaml are slightly different from those of Godot in the sense that in Godot, inheritance is how polymorphism is achieved, and in OCaml is not critical to inherit from a particular class to be polymorphic with other objects of that class, and you can use object expressions to construct compatible objects on the fly that don’t inherit from the base class. This is a pretty significant difference, and I decided that I could just avoid it entirely by avoiding OCaml objects.
1 Like