Skip to content

Instantly share code, notes, and snippets.

@hew
Last active April 29, 2019 19:32
Show Gist options
  • Save hew/3d2b8c00b62e58fd45fb73fefc71d203 to your computer and use it in GitHub Desktop.
Save hew/3d2b8c00b62e58fd45fb73fefc71d203 to your computer and use it in GitHub Desktop.
Reason React Native Styled System (Beta)

Reason React Native Styled System (Beta)

[@bs.module "react-native-responsive-fontsize"]
external rf: float => float = "default";
module type Config = {let scale: array(int);};
module TextMaker = (Config: Config) => {
open Belt.Option;
let systemize = shorthand =>
shorthand->mapWithDefault(0, m =>
switch (m) {
| 1
| 2
| 3
| 4
| 5 => Config.scale[m]
| _ => m
}
)
|> float_of_int;
let systemizeFont = v =>
v->mapWithDefault(16, m =>
switch (m) {
| 1
| 2
| 3
| 4
| 5 => Config.scale[m]
| _ => m
}
)
|> float_of_int;
let systemizeSize = v => v |> systemize |> Style.Size.pct;
let systemizeMargin = v => v |> systemize |> Style.Margin.pct;
[@react.component]
let make =
(
~py=?,
~px=?,
~p=?,
~mt=?,
~mb=?,
~ml=?,
~mr=?,
~size=?,
~style as styl: Style.t=?,
~color as clr=?,
~weight=?,
~align=?,
~children,
(),
) =>
<Text
style=Style.(
listOption([
mt->isSome
? Some(style(~marginTop=systemizeMargin(mt), ())) : None,
mb->isSome
? Some(style(~marginBottom=systemizeMargin(mb), ())) : None,
ml->isSome
? Some(style(~marginLeft=systemizeMargin(ml), ())) : None,
mr->isSome
? Some(style(~marginRight=systemizeMargin(mr), ())) : None,
p->isSome ? Some(style(~padding=systemizeSize(p), ())) : None,
py->isSome
? Some(style(~paddingTop=systemizeSize(py), ())) : None,
py->isSome
? Some(style(~paddingBottom=systemizeSize(py), ())) : None,
px->isSome
? Some(style(~paddingLeft=systemizeSize(px), ())) : None,
px->isSome
? Some(style(~paddingRight=systemizeSize(px), ())) : None,
size->isSome
? Some(style(~fontSize=systemizeFont(size), ())) : None,
clr->isSome
? Some(
style(
~color=clr->mapWithDefault("black", v => v) |> color,
(),
),
)
: None,
weight->isSome
? Some(
style(
~fontWeight=weight->mapWithDefault(`normal, w => w),
(),
),
)
: None,
align->isSome
? Some(
style(~textAlign=align->mapWithDefault(`center, w => w), ()),
)
: None,
Some(styl),
])
)>
children
</Text>;
};
module BoxMaker = (Config: Config) => {
open Belt.Option;
let systemize = shorthand =>
shorthand->mapWithDefault(0, m =>
switch (m) {
| 1
| 2
| 3
| 4
| 5 => Config.scale[m]
| _ => m
}
)
|> float_of_int;
let systemizeSize = v => v |> systemize |> rf |> Style.Size.pt;
let systemizeMargin = v => v |> systemize |> rf |> Style.Margin.pt;
[@react.component]
let make =
(
~py=?,
~px=?,
~p=?,
~mt=?,
~mb=?,
~ml=?,
~mr=?,
~bgColor=?,
~width=?,
~flex=?,
~content=?,
~direction=?,
~style as styl: Style.t=?,
~children=?,
(),
) =>
<View
style=Style.(
listOption([
mt->isSome
? Some(style(~marginTop=systemizeMargin(mt), ())) : None,
mb->isSome
? Some(style(~marginBottom=systemizeMargin(mb), ())) : None,
ml->isSome
? Some(style(~marginLeft=systemizeMargin(ml), ())) : None,
mr->isSome
? Some(style(~marginRight=systemizeMargin(mr), ())) : None,
p->isSome ? Some(style(~padding=systemizeSize(p), ())) : None,
py->isSome
? Some(style(~paddingTop=systemizeSize(py), ())) : None,
py->isSome
? Some(style(~paddingBottom=systemizeSize(py), ())) : None,
px->isSome
? Some(style(~paddingLeft=systemizeSize(px), ())) : None,
px->isSome
? Some(style(~paddingRight=systemizeSize(px), ())) : None,
width->isSome
? Some(
style(
~width=width->mapWithDefault(100., v => v) |> Size.pct,
(),
),
)
: None,
bgColor->isSome
? Some(
style(
~backgroundColor=
bgColor->mapWithDefault("black", v => v) |> color,
(),
),
)
: None,
content->isSome
? Some(
style(
~justifyContent=content->mapWithDefault(`flexStart, w => w),
(),
),
)
: None,
direction->isSome
? Some(
style(
~flexDirection=direction->mapWithDefault(`column, w => w),
(),
),
)
: None,
flex->isSome
? Some(style(~flex=flex->mapWithDefault(1., w => w), ())) : None,
Some(styl),
])
)>
{switch (children) {
| Some(child) => child
| None => React.null
}}
</View>;
};
module Box =
BoxMaker({
let scale = System.Scale.space;
});
module Txt =
TextMaker({
let scale = System.Scale.font;
});
@hew
Copy link
Author

hew commented Apr 24, 2019

I think I understand now. the global open only adds like 4 more things to the namespace, but Belt.Option has a bunch of functions, and opening it floods any given namespace with all of them. I'll default to something like let Opt = Belt.Option in the future.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment