Scripting Helpers is winding down operations and is now read-only. More info→
Ad
Log in to vote
1

How can one create an event handler that listens for a multitude of the same events?

Asked by 5 years ago
Edited 5 years ago

What I am trying to do is listen for MouseButton1Down from group of TextButtons.

2 answers

Log in to vote
1
Answered by 5 years ago
Edited 5 years ago

General Case

Assuming you want the same callback for each MouseButton1Down listener, simply structure your code such that you can traverse a table of TextButton objects. For example:

-- list of buttons
local buttons = {button1, button2, button3, ...}

-- general case callback for MouseButton1Down
local function onMouseButton1Down()
    print("The button was clicked!")
end

-- traverse the buttons and listen for each MouseButton1Down event
for _, button in pairs(buttons) do
    button.MouseButton1Down:Connect(onMouseButton1Down)
end

This will solve the general case -- that is -- the scenario where each button is doing relatively the same thing (hence, we're using onMouseButton1Down directly as the callback to Connect).

Special Case

Instead of the general case, you may also want a special case. Here, we can make each callback to the listener a little bit more unique to the button that fired the event. For example:

-- list of buttons
local buttons = {button1, button2, button3, ...}

-- specific case callback for MouseButton1Down
local function onMouseButton1Down(button)
    print("The button: " .. button.Name .. " was clicked!")
end

-- traverse the buttons and listen for each MouseButton1Down event
for _, button in pairs(buttons) do
    button.MouseButton1Down:Connect(function()
        onMouseButton1Down(button) -- pass the button that was clicked to the callback
    end)
end

In this case, we can use the same onMouseButton1Down callback for every button, while also receiving some information about what button fired the event.

Technically I'd still consider this a general case, since we get to re-use most of the code here. However, we are passing a different "anonymous" function to Connect every iteration, so that's where I derived "special case" from.

I hope this solved your problem. If you have any questions, let me know.

Comment Question #1

I think I understand what you're asking, but let me reiterate just to make sure. If you have two sets (A and B) of buttons, where each set has a different callback to MouseButton1Down, then you would like to switch the place of the button that was clicked from set A into set B (so that the button now uses the callback for set B.)

Yeah, I wouldn't do that. Instead, I'd keep a single callback and just implement some debounce mechanic. For example:

local buttons = {button1, button2, button3, ...}
local buttonStates = {} -- storage of button states to keep track of what's happening to each button (also useful for debounce mechanics)

local function onMouseButton1Down(button)
    local buttonData = buttonStates[button] -- get the button data

    -- example of other possible use (keep track of times clicked)
    buttonData.timesClicked = buttonData.timesClicked + 1

    -- example of debounce
    if (buttonData.enabled) then
        -- execute code when button is enabled
        print("The button: " .. button.Name .. " was clicked!")
    else
        -- execute code when button is disabled
        print("The button is no longer enabled")
    end

    -- invert enabled state
    buttonData.enabled = not buttonData.enabled
end

for _, button in pairs(buttons) do
    -- structure: { [button (Object)] = {data} }
    buttonStates[button] = {
        -- just some random default data
        enabled = true,
        timesClicked = 0,
    }

    button.MouseButton1Down:Connect(function()
        onMouseButton1Down(button)
    end)
end
0
Now what if, I had two groups of buttons and I wanted them change change to the opposite group when clicked? Would I update the button array accordingly? Stephenthefox 94 — 5y
0
For this example, that wouldn't work. However, I wouldn't recommend doing something like that anyway. If you're just going to toggle the functionality of the button press, I would recommend implementing a sort of debounce in the callback. ScriptGuider 5640 — 5y
0
I'll edit my answer to elaborate on that. ScriptGuider 5640 — 5y
0
Makes since, thank you. Stephenthefox 94 — 5y
0
No problem. I recommend checking out the edit anyway, I think that will help a lot. ScriptGuider 5640 — 5y
Ad
Log in to vote
0
Answered by 5 years ago
Edited 5 years ago

Well you can certainly do this:

Using a Table

local button1 = script.Parent.TextButton1
local button2 = script.Parent.TextButton2

local array = {button1, button2}

local function Fired()
    print("Text Button Activated")
end

for _, button in pairs(array) do
    button.Activated:Connect(Fired)
end

Alternative

local button1 = script.Parent.TextButton1
local button2 = script.Parent.TextButton2

function Fired()
    print("Text Button Activated")
end

button1.Activated:Connect(Fired)
button2.Activated:Connect(Fired)

As a note, I used Activated rather than MouseButton1Down since Activated works for all devices, not just computers.

Localized variables allows you to move the items, while only editing the top lines, in case you need to call the TextButtons within a function of the script.

For Multiple Tables, you could try having two Local Scripts and enabling one when the other fires, like so:

Local Script 1

-- Variables
local button1 = script.Parent.TextButton1
local button2 = script.Parent.TextButton2

local array1 = {button1}
local array2 = {button2}

local other = script.Parent.LocalScript2

-- Functions
local function Fired1()
    print("Text Button Activated")
    other.Disabled = false
    script.Disabled = true
end

local function Fired2()
    print("Text Button Deactivated")
    other.Disabled = false
    script.Disabled = true
end

-- Choose Functionality
    for _, button1 in pairs(array1) do
        button1.Activated:Connect(Fired1)
    end

    for _, button2 in pairs(array2) do
        button2.Activated:Connect(Fired2)
    end

Local Script 2

-- Variables
local button1 = script.Parent.TextButton1
local button2 = script.Parent.TextButton2

local array1 = {button1}
local array2 = {button2}

local other = script.Parent.LocalScript1

-- Functions
local function Fired1()
    print("Text Button Activated")
    other.Disabled = false
    script.Disabled = true
end

local function Fired2()
    print("Text Button Deactivated")
    other.Disabled = false
    script.Disabled = true
end

-- Choose Functionality
    for _, button1 in pairs(array1) do
        button1.Activated:Connect(Fired2)
    end

    for _, button2 in pairs(array2) do
        button2.Activated:Connect(Fired1)
    end

Answer this question