Not sure how best to explain this, but basically, rather than putting a bunch of NumberValues or ObjectValues into an object, allow the ability to create custom properties for instances like ‘Model’ or ‘Part’. This way you also wouldn’t have to do something like…
workspace.Zombie.Health.Value = 100
In case you didn’t want to use the humanoid object for whatever reason. Instead, you could just add a new property to the ‘Model’ instance, in int value called ‘Health’
workspace.Zombie.Health = 100
I’m not quite sure how this would be done (i.e. if you would just edit every Model instance or if you could create a brand new instance altogether), but I think it would be a useful feature to have, rather than putting a bunch of Value objects everywhere.
–
tl;dr - Add the option of using custom properties in Instances rather than relying on NumberValues or ObjectValues
I think it would be better using ModuleScripts as ‘classes’ which ‘wrap’ your real instances.
For example: (this is not a completely working example; just pseudocode)
local zombie = {}
local zombieMT = {} -- metamethods
local zombiePropGetters = {} -- property getters (e.g. print(zombie.Health))
local zombiePropSetters = {} -- property setters (e.g. zombie.Health = 10)
local zombieMethods = {} -- methods (e.g. zombie:TakeDamage(10))
zombieMT.__metatable = "Locked metatable" -- prevent edits
zombieMT.__index = function(self, key)
-- go through prop getters, methods and then error if not found
-- if we found a prop getter, call it using 'self' and return what it returns
-- if we found a method, return it
end
zombieMT.__newindex = function(self, key, value)
-- go through prop setters and then error if not found
-- if we found a prop setter, call it using 'self' and 'value'
end
function zombie.new(inGameCharacter)
local inst = {}
setmetatable(inst, zombieMT)
return inst
end
return zombie
Here’s a good tutorial of how to make your own instances, scroll to the bottom to see how to properly make properties for your custom instances by learning from my problems. (They really should of been covered in the OP, oh well.)
I’ve been using classes with other programming languages for now, but I’ve got a bit of a hard time grasping it in this.
Like, at the bare minimum, the results of it should make certain things easier to do rather than FAR more convoluted. Like, that’s the whole point of having classes to begin with, isn’t it? To neatly separate consistent methods, object properties, maybe events into predefined things?
No it doesn’t. You don’t need a library and you can set up a class in about 15 lines. It’s essentially setting up a struct and adding a trait/interface to it if you’ve covered those in other languages.
You can define a class in a modulescript like this:
Class = {}
Class.__index = Class
function Class.new()
local newObject = {}
setmetatable(newObject, Class)
newObject.X = "Example value"
return newObject
end
function Class:ExampleMethod()
self.X = "New example value"
end
return Class
And then you can implement it into another script with this:
Class = require(game.ReplicatedStorage.Class)
newObject = Class.new()
newObject:ExampleMethod()
Only reason my tutorial is so long is because it tries to explain how this actually works, I guess I’m just not very good at explaining Does that make it seem less intimidating?
You can also implement Static variables by doing Class.VariableName if you want to.
I’m glad ^-^. Prepare for a whole new load of fun using Lua.
Also I should quickly mention inheritance is very easy to implement too. You just do this.
InheritedClass = require(game.ReplicatedStorage.InheritedClass)
Class = {}
Class.__index = Class
setmetatable(Class, InheritedClass) --<<<<
function Class.new()
local newObject = InheritedClass.new() --<<<<
setmetatable(newObject, Class)
newObject.X = "Example value"
return newObject
end
return Class
And you can then call all the functions of InheritedClass on it too. As well as any inherited by that class. Once you get more used to using this, I would recommend looking at how metatables work as it will let you do even more crazy things such as operator overloads.
If you create a serialization interface to your classes you can do some pretty neat stuff such as transferring them directly across remote functions and saving them in dataStores. I created a module which your class can inherit and it then handles all the serialization and de-serialization for you, as well as ensuring id’s are consistent across clients. It came with my auto-replication module which would let your classes functions replicate themselves automatically. It works but can definetly be improved, I just lost interest in it I can go find it if you guys would be interested in that.