Well, you need 3 things to achieve:
- Extract the underlying type from the array type.
- Split the union type
- And merge the split type into one.
The first one is an easy one which includes mapped types and infer
keyword:
type UnderlyingType<T> = T extends Array<infer R> ? R : T;
For the second one, you must refer to this question.
And the third one is a little bit advanced and you should refer to this question.
And finally, you will have something like below :
type U1 = UnderlyingType<Params>
type SplitTyped = SplitType<U1>
type FinalType = Spread<SplitTyped[0],SplitTyped[1]>
Playground Link
Edit: For unknown numbers of type arguments (which is limited up to somewhere) you can utilize a SpreadTuple
type map to achieve
type SpreadTuple<T extends any[], L extends number = T['length']> = L extends 0 ? never
: L extends 1 ? T[0]
: L extends 2 ? Spread<T[0], T[1]>
: L extends 3 ? Spread<T[0], Spread<T[1], T[2]>>
: L extends 4 ? Spread<T[0], Spread<T[1],Spread<T[2],T[3]>>>
: never; // continiue to somewhere
And then you can use it as you require:
type FinalType = SpreadTuple<SplitTyped>
Playground Link