#How to have multiple constructors?

13 messages · Page 1 of 1 (latest)

winged patio
#

I created a class, I want to have multiple ways of instantiating the class, can I do something similar to this?

class_name Packet extends RawPacket

func _init(state: State, id: int, fields: Array, compressed = true) -> void:
  pass

func _init(raw: PackedByteArray) -> void:
  pass

For example the Vector3 class can be instantiated in those ways:

regal slate
#

You cannot

winged patio
gleaming blaze
#

For the Vector3 example you could define a set of inputs with default values, then type check on which inputs they filled in - if the first input is a vector3 or vector3i, for example, you do something different than if it is a float.

#

You can't have overrides like c#, but you can have optional inputs on a single function.

winged patio
#

Okay thank you you two 👍

wicked patrol
#

you can actually

#

a constructor just returns the class

#

so you would do ```swift
fun create_from_v3i(v3i: Vector3i) -> MyVector:
pass

...

#

you cant have overloading though

subtle maple
#

This should be possible with callbacks. instead of passing the arguments like this:

class_name Packet extends RawPacket

func _init(state: State, id: int, fields: Array, compressed = true) -> void:
  pass

func _init(raw: PackedByteArray) -> void:
  pass

instead have your chosen function as the arguement with the other arguements bound:

class_name Packet extends RawPacket

func _init(init_name: String, args: Array) -> void:
  var chosen_init = Callable(self, init_name)
  chosen_init.call(args)

func init1(args: Array) -> void:
  var state     : State = args[0]
  var id        :int    = args[1]
  var fields    :Array  = args[2]
  var compressed:bool
  if args.size() == 4:
    compressed   = args[3]
  else:
    compressed = true
  [code]

func init2(args: Array) -> void:
  var raw: PackedByteArray = args[0]
  [code]

usage would look like this:


var maypacket = Packet.new("init1", [<state>, <id>, <fields>, <compressed>])
#

it's a round about way of doing things but if you really want a way to separate the different ways of initialization into separate code blocks it might work for scenarios that might be complex or messy otherwise.

#

optionally, you could forgo the string for the function name by checking the type and number of the arguements in _init and then choosing the appropriate function name internally based on that information.