Making events on objects

I’m thinking of making my own mouse objects for two reasons:

  1. More features than the current Roblox mouse object allows
  2. Potential deprecation of Roblox’s mouse object

Because of this, I’m aiming to basically recreate Roblox’s mouse, and then add more features onto it that I typically use in games. I’m sure there’s modules like this out there, but I want to make my own and I’m interested in learning how I’d make my own events on objects without the use of a BindableEvent.

I understand how to make properties and functions in the objects, but I’m unsure how I would make events. How I imagine it working would be the same as Roblox’s, of course, since my goal is to allow this object to be put in place of anyone’s mouse variable with no other changes necessary.

Here’s an example of how I imagine it working for clarity:

local Mouse = require(game:GetService("ReplicatedStorage"):WaitForChild("Mouse"))
Mouse = Mouse.new()
Mouse.Button1Down:Connect(function() print("MouseButton1Down") end)

More info

When the idea first came to mind, my idea was that I could just keep an array of connected events and run all the functions in the order they were inserted, but this seems messy and I feel there may be a faster way of doing things.

If you’re wondering why I’m going with Mouse.new() rather than only a single mouse object, it’s because different tools may require different settings for the mouse, and I decided this is a cleaner way to go about things. One of the features I’m thinking of adding is an automatic tag filtering array in the mouse, and that’s one example of where different scripts could require different settings.


If anyone has an answer, it’d be much appreciated. :slight_smile:

The cleanest solution I think would be to use a BindableEvent

Otherwise, you could implement your own event class that is similar to Roblox’s.

1 Like

The thing I’m wondering here is this:

A player spawns and has a tool. The tool makes a mouse object using Mouse.new, and so it needs its own BindableEvent. When the player dies, the tool is destroyed and thus the script inside it too. I wouldn’t keep a reference to the mouse object inside the module script, the only reference to it after it is returned is in the script that created the mouse object. Since this mouse object would be garbage collected, would the BindableEvent be garbage collected to? I assume it would, but I’m not very experienced with how the back end of these things work.


I’m fine doing the solution above if it’s cleaner (and probably faster), but this is what I’m curious on how I would make it.

As long as you don’t parent the bindableevent (outside of the tool) then it’ll be taken care of

1 Like

Use a module that returns a table.
Here is an example of how I’d do it

--ModuleScript
EventHolder = {}

BindableEvent = Instance.new("BindableEvent")
EventHolder.Clicked = BindableEvent.Event

--Now you can fire the event with: BindableEvent:Fire()

return EventHolder

This is just an example, I can guarantee, with more time, you could make this script better.

If the BindableEvent is not parented anywhere, then yes it will be garbage collected when the tool is destroyed (when the player dies).

Here’s an example using a BindableEvent:

local Mouse = {}
Mouse.__index = Mouse

function Mouse.new()

	local clickEvent = Instance.new("BindableEvent")

	local self = setmetatable({
		Clicked = clickEvent.Event;
	}, Mouse)

	game:GetService("UserInputService").InputBegan:Connect(function(input, processed)
		if (input.UserInputType == Enum.UserInputType.MouseButton1) then
			clickEvent:Fire()
		end
	end)

	return self

end

return Mouse

Other script:

local mouse = require(mouseModule).new()

mouse.Clicked:Connect(function()
end)
32 Likes