As a result I've been trying to create a wrapper f...
# javascript
m
As a result I've been trying to create a wrapper for https://github.com/ValentinH/react-easy-sort/blob/main/src/index.tsx . The typescript has a default export and named exports. I created this following the same pattern as the MUI wrappers:
Copy code
@file:JsModule("react-easy-sort")
@file:JsNonModule

package com.ustadmobile.view.components

import react.PropsWithChildren
import react.ReactNode

external interface SortableListProps: PropsWithChildren {

    var onSortEnd: (oldIndex: Int, newIndex: Int) -> Unit

    var draggedItemClassName: String?

    var lockAxis: String?

    var allowDrag: Boolean

}


external val SortableList: react.FC<SortableListProps>


//See <https://betterprogramming.pub/understanding-the-difference-between-named-and-default-exports-in-react-2d253ca9fc22>
external interface ItemProps: PropsWithChildren {
    override var children: ReactNode?
}

external val SortableItem: react.FC<ItemProps>
If I use only SortableList or SortableItem, the components seem to be found as expected. When I try to use both together, I get an exception "You likely forgot to export your component from the file it's defined in, or you might have mixed up default and named imports.". Is there a procedure that can allow making a wrapper for typescript where there is both a default export and named exports?
t
What I expect according documentation:
Copy code
@JsName("default")
external val SortableList: react.FC<SortableListProps>
m
I had tried using @JsName("default") like with other modules... and I still got "You likely forgot to export your component from the file it's defined in, or you might have mixed up default and named imports." When I looked at the error stack more closely, the problem was the children property: It had:
export const SortableItem = ({ children }: ItemProps)
I had tried using PropsWithChildren as follows:
external interface ItemProps: PropsWithChildren {
override var children: ReactNode?
}
SortableItem { + "One" } That resulted in an exception being thrown when it tried to access children, even when there were children in the node. Using a "normal" property, and then setting it like this worked:
external interface ItemProps: Props {
var children: ReactNode? } external val SortableItem: react.FC<ItemProps> SortableItem { children = div.create { + "One" } } ItemProps now looks the same as PropsWithChildren, Is props.children supposed to be set somehow based on the children of the component? I think I can make this wrapper cooperate now, thanks! I'll share a Github Gist once it's all in order.
I have made a Github Gist for a wrapper for react-easy-sort (in case it is of use for anyone else). Thanks to @turansky https://gist.github.com/mikedawson/0cb46de72daf142bb6069b9bc8692583
🙂 1
t
Copy code
external interface ItemProps: Props {
    var children: ReactElement?
}
?
m
Because this is what is in the typescript:
type ItemProps = {    children: React.ReactElement   }
t
PropsWithChildren
will work in such case
Copy code
SortableItem {
    div {
        + "One"
    }
}
m
As per the project's doc : SortableItem This component doesn't take any other props than its child. This child should be a single React element that can receives a ref. If you pass a component as a child, it needs to be wrapped with React.forwardRef(). Seem to me like the use of "children" on their side is misleading. Just adding children to the node normally won't work
t
We have similar cases in MUI wrappers
We use
PropsWithChildren
in such cases
m
Will test this to see if SortableItem { div { } } works...
Yep it works
I guess it just wants exactly one child which is an actual html element
t
PropsWithChildren
- isn’t strict solution right now, but it’s right direction
👍 1
m
Thanks again for your guidance on this. Much appreciated. I also updated the gist.