Can you change a type in Roblox TS?

Hi,

So is there a way to change a type of value in a table? I’m asking because with this signal module I’m using, you can call :Connect which accepts a function like so:

image

So to access this type, I exported it like so:
image

Then in a separate script, if I want to change type signal to be a function that takes a function that accepts certain parameters, how would I do that?

For example, let’s say I’m creating a signal that needs to take a function with the parameter “number”, how do I do this?

I could do something like this:

self.Idled = signal.new() :: signal.Signal & {Connect: ((number: number) -> (any)) -> signal.Connection}

However when indexing the table.Idled, it doesn’t replace the function with the typechecker, it instead gives me the option between (any) → (any) and (number) → (any) as if there were multiple options. Any ideas?

If you mean you want two different datatypes for a variable you can use |.

--!strict
local thisVarHasTwoValidDatatypes: string | number = "abc"
thisVarHasTwoValidDatatypes: string | number = 123  --> doesn't warn

Union types


If it’s a value from the table, you can use :::

--!strict

local t = {}
t.thisVarHasTwoValidDatatypes = "abc" :: number | string

t.thisVarHasTwoValidDatatypes = 123 --> doesn't warn

Type casts

1 Like

Sorta, I’m wondering if there’s a way to modify the type for the single object. I think this works:

self.Idled.Connect = self.Idled.Connect :: ((number: number) -> (any)) -> signal.Connection

However I was wondering if there was a way to do this without literally assigning self.Idled.Connect to be self.Idled.Connect
Also note self.Idled is a non-native signal object but works identically to RBXScriptSignal.

Sorry, I don’t fully understand. May you elaborate a bit? Preferably, can you show examples of the problem?

Okay, so I’m making an extension of the humanoid which offers a way to tell if the humanoid idled, which is the humanoid.Idled event here:

function module.new(humanoid: Humanoid)
	local self = {}
	self._extends = humanoid
	self.Idled = signal.new() -- returns a generic signal object but doesn't have anything special about it
	self.Idled.Connect = self.Idled.Connect :: (self: typeof(self.Idled), () -> ()) -> (signal.Connection)

So, in Luau, when you go to pass a function to signal:Connect, it tells you the parameters to put into that function:

I’m trying to replicate that and I’ve gotten pretty much exactly what I want to do with this line:

	self.Idled.Connect = self.Idled.Connect :: (typeof(self.Idled), () -> ()) -> (signal.Connection)

The problem is that I’m assigning a new value to self.Idled.Connect when I do this, even though the new value is the same as the old value, particularly this line:

self.Idled.Connect = self.Idled.Connect

So I’m wondering if there’s any way to modify the type without assigning a new value to self.Idled.Connect

I don’t think you can modify an already existing type. If you want to create a dynamic type you can use <>:

--!strict

local function foo<a>(A: a, B: a)

end

foo("1", 1) --> expects the second parameter to be a string as well

Type packs


I’m not too sure what you can do to “redefine” a type. Possibly type casting it again when referencing?

2 Likes

Yeah that’s what I thought, I guess I have to stick with the way I mentioned in my post. I’ll also look at the type packs document you posted. Thanks!

1 Like