Skip to content

Commit

Permalink
feat: Add Fabric implementation of inset logical properties (#35692)
Browse files Browse the repository at this point in the history
Summary:
This PR implements `inset` logical properties as requested on #34425. This implementation includes the addition of the following style properties

- `inset`, equivalent to `top`, `bottom`, `right` and `left`.
- `insetBlock`, equivalent to `top` and `bottom`.
- `insetBlockEnd`, equivalent to `bottom`.
- `insetBlockStart`, equivalent to `top`.
- `insetInline`, equivalent to `right` and `left`.
- `insetInlineEnd`, equivalent to `right` or `left`.
- `insetInlineStart`, equivalent to `right` or `left`.

## Changelog

[GENERAL] [ADDED] - Add Fabric implementation of inset logical properties

Pull Request resolved: #35692

Test Plan:
1. Open the RNTester app and navigate to the `View` page
2. Test the new style properties through the `Insets` section

<table>
<tr>
    <td>Android</td>
    <td>iOS</td>
</tr>
  <tr>
    <td><img src="https://user-images.githubusercontent.com/11707729/208821212-fbbac6ed-09a4-43f4-ba98-dfd2cbabf044.png"  alt="1" width="360px"   />
    </td>
<td>
<img src="https://user-images.githubusercontent.com/11707729/208816997-ef044140-8824-4b1b-a77b-085f18ea9e0e.png" alt="2" width="360px"  />
</td>
   </tr>
</table>

Reviewed By: NickGerleman

Differential Revision: D42193661

Pulled By: ryancat

fbshipit-source-id: 3db8bcd2c4db0ef4886b9ec49a46424d57362620
  • Loading branch information
gabrieldonadel authored and facebook-github-bot committed Dec 22, 2022
1 parent 1542d71 commit 9669c10
Show file tree
Hide file tree
Showing 9 changed files with 217 additions and 0 deletions.
7 changes: 7 additions & 0 deletions Libraries/Components/View/ReactNativeStyleAttributes.js
Original file line number Diff line number Diff line change
Expand Up @@ -46,6 +46,13 @@ const ReactNativeStyleAttributes: {[string]: AnyAttributeType, ...} = {
flexWrap: true,
gap: true,
height: true,
inset: true,
insetBlock: true,
insetBlockEnd: true,
insetBlockStart: true,
insetInline: true,
insetInlineEnd: true,
insetInlineStart: true,
justifyContent: true,
left: true,
margin: true,
Expand Down
8 changes: 8 additions & 0 deletions Libraries/NativeComponent/BaseViewConfig.android.js
Original file line number Diff line number Diff line change
Expand Up @@ -258,6 +258,14 @@ const validAttributesForNonEventProps = {
top: true,
bottom: true,

inset: true,
insetBlock: true,
insetBlockEnd: true,
insetBlockStart: true,
insetInline: true,
insetInlineEnd: true,
insetInlineStart: true,

position: true,

style: ReactNativeStyleAttributes,
Expand Down
8 changes: 8 additions & 0 deletions Libraries/NativeComponent/BaseViewConfig.ios.js
Original file line number Diff line number Diff line change
Expand Up @@ -232,6 +232,14 @@ const validAttributesForNonEventProps = {
bottom: true,
left: true,

inset: true,
insetBlock: true,
insetBlockEnd: true,
insetBlockStart: true,
insetInline: true,
insetInlineEnd: true,
insetInlineStart: true,

width: true,
height: true,

Expand Down
7 changes: 7 additions & 0 deletions Libraries/StyleSheet/StyleSheetTypes.d.ts
Original file line number Diff line number Diff line change
Expand Up @@ -59,6 +59,13 @@ export interface FlexStyle {
flexShrink?: number | undefined;
flexWrap?: 'wrap' | 'nowrap' | 'wrap-reverse' | undefined;
height?: number | string | undefined;
inset?: number | string | undefined;
insetBlock?: number | string | undefined;
insetBlockEnd?: number | string | undefined;
insetBlockStart?: number | string | undefined;
insetInline?: number | string | undefined;
insetInlineEnd?: number | string | undefined;
insetInlineStart?: number | string | undefined;
justifyContent?:
| 'flex-start'
| 'flex-end'
Expand Down
16 changes: 16 additions & 0 deletions Libraries/StyleSheet/StyleSheetTypes.js
Original file line number Diff line number Diff line change
Expand Up @@ -132,6 +132,22 @@ type ____LayoutStyle_Internal = $ReadOnly<{
*/
top?: DimensionValue,

/** `inset` is a shorthand that corresponds to the top, right, bottom, and/or left properties.
*
* It works similarly to `inset` in CSS, but in React Native you
* must use points or percentages. Ems and other units are not supported.
*
* See https://developer.mozilla.org/en-US/docs/Web/CSS/inset
* for more details of how `inset` affects layout.
*/
inset?: DimensionValue,
insetBlock?: DimensionValue,
insetBlockEnd?: DimensionValue,
insetBlockStart?: DimensionValue,
insetInline?: DimensionValue,
insetInlineEnd?: DimensionValue,
insetInlineStart?: DimensionValue,

/** `minWidth` is the minimum width for this component, in logical pixels.
*
* It works similarly to `min-width` in CSS, but in React Native you
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -333,6 +333,21 @@ void YogaLayoutableShadowNode::updateYogaProps() {
YGStyle result{baseStyle};

// Aliases with precedence
if (!props.inset.isUndefined()) {
result.position()[YGEdgeAll] = props.inset;
}
if (!props.insetBlock.isUndefined()) {
result.position()[YGEdgeVertical] = props.insetBlock;
}
if (!props.insetInline.isUndefined()) {
result.position()[YGEdgeHorizontal] = props.insetInline;
}
if (!props.insetInlineEnd.isUndefined()) {
result.position()[YGEdgeEnd] = props.insetInlineEnd;
}
if (!props.insetInlineStart.isUndefined()) {
result.position()[YGEdgeStart] = props.insetInlineStart;
}
if (!props.marginInline.isUndefined()) {
result.margin()[YGEdgeHorizontal] = props.marginInline;
}
Expand All @@ -359,6 +374,12 @@ void YogaLayoutableShadowNode::updateYogaProps() {
}

// Aliases without precedence
if (CompactValue(result.position()[YGEdgeBottom]).isUndefined()) {
result.position()[YGEdgeBottom] = props.insetBlockEnd;
}
if (CompactValue(result.position()[YGEdgeTop]).isUndefined()) {
result.position()[YGEdgeTop] = props.insetBlockStart;
}
if (CompactValue(result.margin()[YGEdgeTop]).isUndefined()) {
result.margin()[YGEdgeTop] = props.marginBlockStart;
}
Expand Down
55 changes: 55 additions & 0 deletions ReactCommon/react/renderer/components/view/YogaStylableProps.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -134,6 +134,19 @@ void YogaStylableProps::setProp(
REBUILD_FIELD_YG_EDGES(border, "border", "Width");

// Aliases
RAW_SET_PROP_SWITCH_CASE(inset, "inset", CompactValue::ofUndefined());
RAW_SET_PROP_SWITCH_CASE(
insetBlock, "insetBlock", CompactValue::ofUndefined());
RAW_SET_PROP_SWITCH_CASE(
insetBlockEnd, "insetBlockEnd", CompactValue::ofUndefined());
RAW_SET_PROP_SWITCH_CASE(
insetBlockStart, "insetBlockStart", CompactValue::ofUndefined());
RAW_SET_PROP_SWITCH_CASE(
insetInline, "insetInline", CompactValue::ofUndefined());
RAW_SET_PROP_SWITCH_CASE(
insetInlineEnd, "insetInlineEnd", CompactValue::ofUndefined());
RAW_SET_PROP_SWITCH_CASE(
insetInlineStart, "insetInlineStart", CompactValue::ofUndefined());
RAW_SET_PROP_SWITCH_CASE(
marginInline, "marginInline", CompactValue::ofUndefined());
RAW_SET_PROP_SWITCH_CASE(
Expand Down Expand Up @@ -245,6 +258,48 @@ void YogaStylableProps::convertRawPropAliases(
const PropsParserContext &context,
YogaStylableProps const &sourceProps,
RawProps const &rawProps) {
inset = convertRawProp(
context,
rawProps,
"inset",
sourceProps.inset,
CompactValue::ofUndefined());
insetBlock = convertRawProp(
context,
rawProps,
"insetBlock",
sourceProps.insetBlock,
CompactValue::ofUndefined());
insetBlockEnd = convertRawProp(
context,
rawProps,
"insetBlockEnd",
sourceProps.insetBlockEnd,
CompactValue::ofUndefined());
insetBlockStart = convertRawProp(
context,
rawProps,
"insetBlockStart",
sourceProps.insetBlockStart,
CompactValue::ofUndefined());
insetInline = convertRawProp(
context,
rawProps,
"insetInline",
sourceProps.insetInline,
CompactValue::ofUndefined());
insetInlineEnd = convertRawProp(
context,
rawProps,
"insetInlineEnd",
sourceProps.insetInlineEnd,
CompactValue::ofUndefined());
insetInlineStart = convertRawProp(
context,
rawProps,
"insetInlineStart",
sourceProps.insetInlineStart,
CompactValue::ofUndefined());
marginInline = convertRawProp(
context,
rawProps,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -43,6 +43,11 @@ class YogaStylableProps : public Props {

// Duplicates of existing properties with different names, taking
// precendence. E.g. "marginBlock" instead of "marginVertical"
CompactValue inset;
CompactValue insetInline;
CompactValue insetInlineEnd;
CompactValue insetInlineStart;

CompactValue marginInline;
CompactValue marginInlineStart;
CompactValue marginInlineEnd;
Expand All @@ -56,6 +61,10 @@ class YogaStylableProps : public Props {
// BlockEnd/BlockStart map to top/bottom (no writing mode), but we preserve
// Yoga's precedence and prefer specific edges (e.g. top) to ones which are
// flow relative (e.g. blockStart).
CompactValue insetBlock;
CompactValue insetBlockEnd;
CompactValue insetBlockStart;

CompactValue marginBlockStart;
CompactValue marginBlockEnd;

Expand Down
86 changes: 86 additions & 0 deletions packages/rn-tester/js/examples/View/ViewExample.js
Original file line number Diff line number Diff line change
Expand Up @@ -652,4 +652,90 @@ exports.examples = [
return <FlexGapExample />;
},
},
{
title: 'Insets',
render(): React.Node {
return (
<View style={{rowGap: 10}}>
<View style={{position: 'relative', height: 50, borderWidth: 1}}>
<View
style={{
backgroundColor: '#527FE4',
padding: 5,
position: 'absolute',
inset: 10,
}}>
<Text style={{fontSize: 11}}>inset 10</Text>
</View>
</View>
<View style={{position: 'relative', height: 50, borderWidth: 1}}>
<View
style={{
backgroundColor: '#527FE4',
padding: 5,
position: 'absolute',
insetBlock: 5,
}}>
<Text style={{fontSize: 11}}>insetBlock 5</Text>
</View>
</View>
<View style={{position: 'relative', height: 50, borderWidth: 1}}>
<View
style={{
backgroundColor: '#527FE4',
padding: 5,
position: 'absolute',
insetBlockEnd: 5,
}}>
<Text style={{fontSize: 11}}>insetBlockEnd 5</Text>
</View>
</View>
<View style={{position: 'relative', height: 50, borderWidth: 1}}>
<View
style={{
backgroundColor: '#527FE4',
padding: 5,
position: 'absolute',
insetBlockStart: 5,
}}>
<Text style={{fontSize: 11}}>insetBlockStart 5</Text>
</View>
</View>
<View style={{position: 'relative', height: 50, borderWidth: 1}}>
<View
style={{
backgroundColor: '#527FE4',
padding: 5,
position: 'absolute',
insetInline: 5,
}}>
<Text style={{fontSize: 11}}>insetInline 5</Text>
</View>
</View>
<View style={{position: 'relative', height: 50, borderWidth: 1}}>
<View
style={{
backgroundColor: '#527FE4',
padding: 5,
position: 'absolute',
insetInlineEnd: 5,
}}>
<Text style={{fontSize: 11}}>insetInlineEnd 5</Text>
</View>
</View>
<View style={{position: 'relative', height: 50, borderWidth: 1}}>
<View
style={{
backgroundColor: '#527FE4',
padding: 5,
position: 'absolute',
insetInlineStart: 5,
}}>
<Text style={{fontSize: 11}}>insetInlineStart 5</Text>
</View>
</View>
</View>
);
},
},
];

0 comments on commit 9669c10

Please sign in to comment.