How would I go about drawing the same object multiple times?
Forum rules
Before you make a thread asking for help, read this.
Before you make a thread asking for help, read this.
How would I go about drawing the same object multiple times?
I mean I am aware I could just copy and paste a `love.image.draw()` function multiple times, but lets say I wanted to draw an image wherever the mouse is clicked at. How would I go about making it so it draw said item every time I clicked. If I only clicked twice it would draw two objects, and if I clicked it 500 times it would draw 500 items, without having to have 500 different draw functions?
- Sir_Silver
- Party member
- Posts: 286
- Joined: Mon Aug 22, 2016 2:25 pm
- Contact:
Re: How would I go about drawing the same object multiple times?
Don't have the time to explain the many ways you could do that at the moment, but here is some example code that you might be able to understand.
Code: Select all
local entity = {
w = 50,
h = 50,
color = {255, 0, 0}
}
entity.__index = entity
function entity:draw()
love.graphics.setColor(self.color)
love.graphics.rectangle("fill", self.x, self.y, self.w, self.h)
end
local entities = {}
function love.draw()
for i = 1, #entities do
entities[i]:draw()
end
end
function love.mousepressed(x, y)
local entity = setmetatable({}, entity)
entities[#entities + 1] = entity
entity.x, entity.y = x, y
end
Re: How would I go about drawing the same object multiple times?
I wish I could say I understand what is going on there. I am mostly self taught in Love2d which I hate because I have really weird terrible ways of doing things any pretty much every single line of code you just posted just completely flew over my head. If you have time to explain I would love to see what you have to saySir_Silver wrote: ↑Sun Aug 27, 2017 1:44 am Don't have the time to explain the many ways you could do that at the moment, but here is some example code that you might be able to understand.
Code: Select all
local entity = { w = 50, h = 50, color = {255, 0, 0} } entity.__index = entity function entity:draw() love.graphics.setColor(self.color) love.graphics.rectangle("fill", self.x, self.y, self.w, self.h) end local entities = {} function love.draw() for i = 1, #entities do entities[i]:draw() end end function love.mousepressed(x, y) local entity = setmetatable({}, entity) entities[#entities + 1] = entity entity.x, entity.y = x, y end
- Sir_Silver
- Party member
- Posts: 286
- Joined: Mon Aug 22, 2016 2:25 pm
- Contact:
Re: How would I go about drawing the same object multiple times?
Yeah, so in the function love.draw, we aren't writing hundreds of lines of code to draw each individual thing we want to draw, instead, we iterate over a table which contains all of the things we want to draw (which could be anywhere from 0 to a million or more things).
The for loop inside of love.draw calls the "draw" function for each one of the entities:
Notice that love.graphics.rectangle doesn't take hard coded arguments, instead it uses variables that are stored on the self. The self.x and self.y variables of the entity are given during the love.mousepressed callback:
This creates an "instance" of an entity, stores the instance of an entity inside of the entities table (which we use for drawing all of the entities in love.draw), and finally gives the entity the necessary x and y variable for determining where to draw it.
I don't have time to proofread this right now, so I'll edit later if it's wrong, let me know if this helps! =)
The for loop inside of love.draw calls the "draw" function for each one of the entities:
Code: Select all
function entity:draw()
love.graphics.setColor(self.color)
love.graphics.rectangle("fill", self.x, self.y, self.w, self.h)
end
Code: Select all
function love.mousepressed(x, y)
local entity = setmetatable({}, entity)
entities[#entities + 1] = entity
entity.x, entity.y = x, y
end
I don't have time to proofread this right now, so I'll edit later if it's wrong, let me know if this helps! =)
Re: How would I go about drawing the same object multiple times?
thank you for the explanation. could you explain some of the more specific elements? such as the `#`, `setmetatable` and `.__index`Sir_Silver wrote: ↑Sun Aug 27, 2017 1:58 am Yeah, so in the function love.draw, we aren't writing hundreds of lines of code to draw each individual thing we want to draw, instead, we iterate over a table which contains all of the things we want to draw (which could be anywhere from 0 to a million or more things).
The for loop inside of love.draw calls the "draw" function for each one of the entities:
Notice that love.graphics.rectangle doesn't take hard coded arguments, instead it uses variables that are stored on the self. The self.x and self.y variables of the entity are given during the love.mousepressed callback:Code: Select all
function entity:draw() love.graphics.setColor(self.color) love.graphics.rectangle("fill", self.x, self.y, self.w, self.h) end
This creates an "instance" of an entity, stores the instance of an entity inside of the entities table (which we use for drawing all of the entities in love.draw), and finally gives the entity the necessary x and y variable for determining where to draw it.Code: Select all
function love.mousepressed(x, y) local entity = setmetatable({}, entity) entities[#entities + 1] = entity entity.x, entity.y = x, y end
I don't have time to proofread this right now, so I'll edit later if it's wrong, let me know if this helps! =)
Re: How would I go about drawing the same object multiple times?
With # you calculate the length of the table. When you create a new element you want to create it as the last element in the table. So #table +1.
Metatables are needed for oop.
Like self.x, self.y.
Just check them out!
Metatables are needed for oop.
Like self.x, self.y.
Just check them out!
Re: How would I go about drawing the same object multiple times?
You can read about metatables and metamethods (like __index) in the PiL (Programming in Lua) and then revisit the code to see how it works. Being self-taught is not a problem by the way, most people here probably are.
Re: How would I go about drawing the same object multiple times?
thank you for the reply. i appreciate you trying to explain it but if im being honest I just don't understand. I get the "#", that stuff is pretty simple, and I think using "self" just referes to the class of the function that "self" is being referenced in right? I googled a ton on .__index but I'm not sure if I get it. Basically if you attempt to reference an element that doesn't exist its creates it wherever you called __index? I know nothing about classes so sorry if that makes no sense
- Sir_Silver
- Party member
- Posts: 286
- Joined: Mon Aug 22, 2016 2:25 pm
- Contact:
Re: How would I go about drawing the same object multiple times?
When you try to access an index of a table whose value is nil,, if that table has a metatable which has an __index metamethod, it will invoke the __index metamethod. Here's what happens without the use of a metatable:
However, if we set the metatable of my_table to a table that has an __index metamethod, something different will happen:
In this example, we try to print out the value of my_table[1]. There is no value there - it is nil - so it checks if my_table has a metatable.
It does have a metatable, so it checks if it has a __index metamethod which it does have, and then calls that function.
In this example, the __index metamethod prints out, "You have just used __index metamethod", and then returns whatever value is inside
the my_metatable table at the same index that was nil for the table we originally tried to index.
It is worth noting that
Is functionally the same as
Btw, I admire you for being self taught. I had the luxury of being taught nearly 1-on-1 for nearly two years. I'm here to to answer any more questions or help you out if you need it.
Code: Select all
local my_table = {}
print(my_table[1]) --prints nil, because there is no value at index 1
Code: Select all
local my_metatable = {
1
}
function my_metatable.__index(t, k)
print("You have just used __index metamethod")
return rawget(my_metatable, k)
end
local my_table = setmetatable({}, my_metatable)
print(my_table[1]) --[[
prints out:
You have just used __index metamethod
1
]]
It does have a metatable, so it checks if it has a __index metamethod which it does have, and then calls that function.
In this example, the __index metamethod prints out, "You have just used __index metamethod", and then returns whatever value is inside
the my_metatable table at the same index that was nil for the table we originally tried to index.
It is worth noting that
Code: Select all
local my_metatable = {
1
}
function my_metatable.__index(t, k)
return rawget(my_metatable, k)
end
Code: Select all
local my_metatable = {
1
}
my_metatable.__index = my_metatable
Re: How would I go about drawing the same object multiple times?
thank you for the reply, that makes sense. being self taught is kinda fun but it makes reading other peoples code absolute hell. i can barely even understand beginners guides because they normally have a totally different approach of doing everything. i really should "start over" and try to relearn from scratch but i dont have the patienceSir_Silver wrote: ↑Tue Aug 29, 2017 1:31 am When you try to access an index of a table whose value is nil,, if that table has a metatable which has an __index metamethod, it will invoke the __index metamethod. Here's what happens without the use of a metatable:
However, if we set the metatable of my_table to a table that has an __index metamethod, something different will happen:Code: Select all
local my_table = {} print(my_table[1]) --prints nil, because there is no value at index 1
In this example, we try to print out the value of my_table[1]. There is no value there - it is nil - so it checks if my_table has a metatable.Code: Select all
local my_metatable = { 1 } function my_metatable.__index(t, k) print("You have just used __index metamethod") return rawget(my_metatable, k) end local my_table = setmetatable({}, my_metatable) print(my_table[1]) --[[ prints out: You have just used __index metamethod 1 ]]
It does have a metatable, so it checks if it has a __index metamethod which it does have, and then calls that function.
In this example, the __index metamethod prints out, "You have just used __index metamethod", and then returns whatever value is inside
the my_metatable table at the same index that was nil for the table we originally tried to index.
It is worth noting that
Is functionally the same asCode: Select all
local my_metatable = { 1 } function my_metatable.__index(t, k) return rawget(my_metatable, k) end
Btw, I admire you for being self taught. I had the luxury of being taught nearly 1-on-1 for nearly two years. I'm here to to answer any more questions or help you out if you need it.Code: Select all
local my_metatable = { 1 } my_metatable.__index = my_metatable
Who is online
Users browsing this forum: Ahrefs [Bot] and 6 guests