I think that @ThanksRoBama has been unduly harsh here, and your response shows the issue with their kind of feedback. You don’t want to compact your code as much as you can because this makes it less readable. Here’s my feedback on your script:
Whilst the points RoBama makes about formatting are correct (don’t abbreviate your variable names, don’t name variables after their datatype, add spacing between arguments etc.) these are not as severe as they’re is making them out to be.
I found that, in general, I could understand the logic of your code, and follow your train of thought.
The one point I will agree with the severity of however is commenting. Any line that isn’t entirely self-explanatory should be explained with comments. In a script this short it isn’t a huge issue, but if you end up with tens of thousands of lines of code you’re gonna lose track of it, and you’re going to regret not commenting.
Concerning the levels of indentation in your program, I think this is due to an ignorance of Curly’s Law: Do One Thing. Also known as the Single-Responsibility Principle (or SRP for short), this is the idea that any part of your code should do exactly one thing.
For example your system:AddItem() method could be split into :AddStackableItem() and :AddUnstackableItem(), and your :AddItem() method would simply determine if the item was stackable or not and call the correct method, for example
if itemD.Stackable == true then
self:AddStackableItem(player, item, amount)
else
self:AddUnstackableItem(player, item, amount)
end
Note that I have assumed that plr is short for player and itemD is short for item data.
To lower the indentations further you could reformat the way you do your assertions. This is best explained through example:
if inventories[player] and itemD.Items[item] then
local inventory = inventories[player]
local itemD = itemData.Items[item]
if amount then
...
end
end
would become
local inventory = inventories[player]
local itemD = itemData[item]
if not inventory then
warn("Player inventory does not exist")
elseif not itemD then
warn("Item does not exist")
elseif not amount then
warn("Amount argument is null")
else
...
end
This makes the code less stacked, and separates the assertions from the logic, making the code more readable. Additionally, if one assertion fails then the rest are not needlessly checked which helps efficiency.
However, it should be noted that since these assertions are necessary and cannot be removed the stacking doesn’t affect code performance, only readability, although the importance of readability cannot be overstated!
The use of warn() and error() are important in debugging, but you’ll want to be careful with these. If warn() is called then an orange output is printed to the console - useful for telling you the developer that a problem has been averted, but you should have a look at it.
error() is different in that it stops the script - this should be used for “oh no, something has seriously gone wrong and if this thread continues then something really bad could happen”. You don’t want this in any game-critical scripts, such as an inventory system.
Speaking to the logic of your script I’m happy to say that it is perfectly fine, there are no obvious changes I would make.
Finally I should recommend that you do not take this feedback as a set of corrections to apply to your script, but as advice to apply to all of your work going forwards. You should be actively looking to write code that this feedback would not apply to.
Best of luck with your game 