A few mini-fixes for the accessibility layout inspector
Summary: - fix mutual selection of elements in ax and non-ax tree (simplifies linkedNode logic as well) - remove unneeded extraInfo attributes (focused, nonAXwithAXchild, & hasAXNode were not/no longer being used) - use 50/50 fixed width view for trees when both are visible Reviewed By: jknoxville Differential Revision: D16390355 fbshipit-source-id: bbf9ea887f8f1035df8b4b0562ddcc4de291f004
This commit is contained in:
committed by
Facebook Github Bot
parent
3ed71680a1
commit
f591475f85
@@ -551,7 +551,7 @@ public class InspectorFlipperPlugin implements FlipperPlugin {
|
|||||||
|
|
||||||
private boolean hasAXNode(FlipperObject node) {
|
private boolean hasAXNode(FlipperObject node) {
|
||||||
FlipperObject extraInfo = node.getObject("extraInfo");
|
FlipperObject extraInfo = node.getObject("extraInfo");
|
||||||
return extraInfo != null && extraInfo.getBoolean("hasAXNode");
|
return extraInfo != null && extraInfo.getBoolean("linkedNode");
|
||||||
}
|
}
|
||||||
|
|
||||||
public SearchResultNode searchTree(String query, Object obj, boolean axEnabled) throws Exception {
|
public SearchResultNode searchTree(String query, Object obj, boolean axEnabled) throws Exception {
|
||||||
|
|||||||
@@ -216,7 +216,8 @@ public class ApplicationDescriptor extends NodeDescriptor<ApplicationWrapper> {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public FlipperObject getExtraInfo(ApplicationWrapper node) {
|
public FlipperObject getExtraInfo(ApplicationWrapper node) {
|
||||||
return new FlipperObject.Builder().put("hasAXNode", true).build();
|
// Application node is it's own linkedNode because it shows up in both the ax and non-ax tree
|
||||||
|
return new FlipperObject.Builder().put("linkedNode", getId(node)).build();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
|
|||||||
@@ -77,7 +77,7 @@ public class FragmentDescriptor extends NodeDescriptor<Fragment> {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public FlipperObject getExtraInfo(Fragment node) {
|
public FlipperObject getExtraInfo(Fragment node) {
|
||||||
return new FlipperObject.Builder().put("nonAXWithAXChild", true).build();
|
return new FlipperObject.Builder().put("expandWithParent", true).build();
|
||||||
}
|
}
|
||||||
|
|
||||||
@Nullable
|
@Nullable
|
||||||
|
|||||||
@@ -445,10 +445,9 @@ public class ViewDescriptor extends NodeDescriptor<View> {
|
|||||||
|
|
||||||
@Override
|
@Override
|
||||||
public FlipperObject getExtraInfo(View node) {
|
public FlipperObject getExtraInfo(View node) {
|
||||||
return new FlipperObject.Builder()
|
// Views of all kinds are their own linked node because they show up in both the ax and non-ax
|
||||||
.put("focused", AccessibilityUtil.isAXFocused(node))
|
// tree
|
||||||
.put("hasAXNode", true)
|
return new FlipperObject.Builder().put("linkedNode", getId(node)).build();
|
||||||
.build();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
@Nullable
|
@Nullable
|
||||||
|
|||||||
@@ -307,13 +307,13 @@ public class DebugComponentDescriptor extends NodeDescriptor<DebugComponent> {
|
|||||||
|
|
||||||
if (hostView != null) {
|
if (hostView != null) {
|
||||||
try {
|
try {
|
||||||
extraInfo.put("linkedAXNode", descriptor.getId(hostView));
|
extraInfo.put("linkedNode", descriptor.getId(hostView));
|
||||||
} catch (Exception ignored) {
|
} catch (Exception ignored) {
|
||||||
// doesn't have linked node descriptor
|
// doesn't have linked node descriptor
|
||||||
}
|
}
|
||||||
} else if (lithoView != null) {
|
} else if (lithoView != null) {
|
||||||
try {
|
try {
|
||||||
extraInfo.put("linkedAXNode", descriptor.getId(lithoView));
|
extraInfo.put("linkedNode", descriptor.getId(lithoView)).put("expandWithParent", true);
|
||||||
} catch (Exception ignored) {
|
} catch (Exception ignored) {
|
||||||
// doesn't add linked node descriptor
|
// doesn't add linked node descriptor
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -101,7 +101,9 @@ public class InspectorFlipperPluginTest {
|
|||||||
.put("children", new FlipperArray.Builder().put("test"))
|
.put("children", new FlipperArray.Builder().put("test"))
|
||||||
.put("attributes", new FlipperArray.Builder())
|
.put("attributes", new FlipperArray.Builder())
|
||||||
.put("decoration", (String) null)
|
.put("decoration", (String) null)
|
||||||
.put("extraInfo", new FlipperObject.Builder().put("hasAXNode", true))
|
.put(
|
||||||
|
"extraInfo",
|
||||||
|
new FlipperObject.Builder().put("linkedNode", "com.facebook.flipper"))
|
||||||
.build()));
|
.build()));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
File diff suppressed because one or more lines are too long
@@ -15,7 +15,7 @@ const TEST_TIMEOUT_MS = 30 * 1000;
|
|||||||
const layoutPathsToExcludeFromSnapshots = [
|
const layoutPathsToExcludeFromSnapshots = [
|
||||||
'id',
|
'id',
|
||||||
'children.*',
|
'children.*',
|
||||||
'extraInfo.linkedAXNode',
|
'extraInfo.linkedNode',
|
||||||
'data.View.*.value',
|
'data.View.*.value',
|
||||||
'data.View.*.*.value',
|
'data.View.*.*.value',
|
||||||
'data.View.*.*.*.value',
|
'data.View.*.*.*.value',
|
||||||
@@ -197,7 +197,7 @@ test('test layout snapshot stripping', () => {
|
|||||||
id: 2,
|
id: 2,
|
||||||
children: [1, 2, 3],
|
children: [1, 2, 3],
|
||||||
extraInfo: {
|
extraInfo: {
|
||||||
linkedAXNode: 55,
|
linkedNode: 55,
|
||||||
somethingElse: 44,
|
somethingElse: 44,
|
||||||
},
|
},
|
||||||
data: {View: {bounds: {something: {value: 4}}}},
|
data: {View: {bounds: {something: {value: 4}}}},
|
||||||
@@ -216,7 +216,7 @@ test('test layout snapshot stripping', () => {
|
|||||||
id: 'PLACEHOLDER',
|
id: 'PLACEHOLDER',
|
||||||
children: ['PLACEHOLDER', 'PLACEHOLDER', 'PLACEHOLDER'],
|
children: ['PLACEHOLDER', 'PLACEHOLDER', 'PLACEHOLDER'],
|
||||||
extraInfo: {
|
extraInfo: {
|
||||||
linkedAXNode: 'PLACEHOLDER',
|
linkedNode: 'PLACEHOLDER',
|
||||||
somethingElse: 44,
|
somethingElse: 44,
|
||||||
},
|
},
|
||||||
data: {View: {bounds: {something: {value: 'PLACEHOLDER'}}}},
|
data: {View: {bounds: {something: {value: 'PLACEHOLDER'}}}},
|
||||||
|
|||||||
@@ -147,26 +147,28 @@ export default class Inspector extends Component<Props> {
|
|||||||
|
|
||||||
if (
|
if (
|
||||||
ax &&
|
ax &&
|
||||||
selectedElement !== prevProps.selectedElement &&
|
selectedElement &&
|
||||||
selectedElement
|
selectedElement !== prevProps.selectedElement
|
||||||
) {
|
) {
|
||||||
// selected element changed, find linked AX element
|
// selected element in non-AX tree changed, find linked element in AX tree
|
||||||
const linkedAXNode: ?ElementID = this.props.persistedState.elements[
|
const newlySelectedElem = this.props.persistedState.elements[
|
||||||
selectedElement
|
selectedElement
|
||||||
]?.extraInfo?.linkedAXNode;
|
];
|
||||||
this.props.onSelect(linkedAXNode);
|
if (newlySelectedElem) {
|
||||||
|
this.props.onSelect(newlySelectedElem.extraInfo?.linkedNode);
|
||||||
|
}
|
||||||
} else if (
|
} else if (
|
||||||
!ax &&
|
!ax &&
|
||||||
selectedAXElement !== prevProps.selectedAXElement &&
|
selectedAXElement &&
|
||||||
selectedAXElement
|
selectedAXElement !== prevProps.selectedAXElement
|
||||||
) {
|
) {
|
||||||
// selected AX element changed, find linked element
|
// selected element in AX tree changed, find linked element in non-AX tree
|
||||||
// $FlowFixMe Object.values retunes mixed type
|
const newlySelectedAXElem = this.props.persistedState.AXelements[
|
||||||
const linkedNode: ?Element = Object.values(
|
selectedAXElement
|
||||||
this.props.persistedState.elements,
|
];
|
||||||
// $FlowFixMe it's an Element not mixed
|
if (newlySelectedAXElem) {
|
||||||
).find((e: Element) => e.extraInfo?.linkedAXNode === selectedAXElement);
|
this.props.onSelect(newlySelectedAXElem.extraInfo?.linkedNode);
|
||||||
this.props.onSelect(linkedNode?.id);
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -20,6 +20,7 @@ import {
|
|||||||
Toolbar,
|
Toolbar,
|
||||||
Sidebar,
|
Sidebar,
|
||||||
DetailSidebar,
|
DetailSidebar,
|
||||||
|
VerticalRule,
|
||||||
} from 'flipper';
|
} from 'flipper';
|
||||||
import Inspector from './Inspector';
|
import Inspector from './Inspector';
|
||||||
import ToolbarIcon from './ToolbarIcon';
|
import ToolbarIcon from './ToolbarIcon';
|
||||||
@@ -168,6 +169,17 @@ export default class Layout extends FlipperPlugin<State, void, PersistedState> {
|
|||||||
/>
|
/>
|
||||||
);
|
);
|
||||||
|
|
||||||
|
const axInspector = this.state.inAXMode && (
|
||||||
|
<Inspector
|
||||||
|
{...inspectorProps}
|
||||||
|
onSelect={selectedAXElement => this.setState({selectedAXElement})}
|
||||||
|
showsSidebar={true}
|
||||||
|
ax
|
||||||
|
/>
|
||||||
|
);
|
||||||
|
|
||||||
|
const divider = this.state.inAXMode && <VerticalRule />;
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<FlexColumn grow={true}>
|
<FlexColumn grow={true}>
|
||||||
{this.state.init && (
|
{this.state.init && (
|
||||||
@@ -211,23 +223,9 @@ export default class Layout extends FlipperPlugin<State, void, PersistedState> {
|
|||||||
</Toolbar>
|
</Toolbar>
|
||||||
|
|
||||||
<FlexRow grow={true}>
|
<FlexRow grow={true}>
|
||||||
{this.state.inAXMode ? (
|
{inspector}
|
||||||
<>
|
{divider}
|
||||||
<Sidebar position="left" maxWidth={Infinity}>
|
{axInspector}
|
||||||
{inspector}
|
|
||||||
</Sidebar>
|
|
||||||
<Inspector
|
|
||||||
{...inspectorProps}
|
|
||||||
onSelect={selectedAXElement =>
|
|
||||||
this.setState({selectedAXElement})
|
|
||||||
}
|
|
||||||
showsSidebar={true}
|
|
||||||
ax
|
|
||||||
/>
|
|
||||||
</>
|
|
||||||
) : (
|
|
||||||
inspector
|
|
||||||
)}
|
|
||||||
</FlexRow>
|
</FlexRow>
|
||||||
<DetailSidebar>
|
<DetailSidebar>
|
||||||
<InspectorSidebar
|
<InspectorSidebar
|
||||||
|
|||||||
@@ -36,9 +36,8 @@ export type ElementAttribute = {|
|
|||||||
|};
|
|};
|
||||||
|
|
||||||
export type ElementExtraInfo = {|
|
export type ElementExtraInfo = {|
|
||||||
nonAXWithAXChild?: boolean,
|
linkedNode?: string, // id of linked node in opposite tree
|
||||||
linkedAXNode?: string,
|
expandWithParent?: boolean,
|
||||||
focused?: boolean,
|
|
||||||
|};
|
|};
|
||||||
|
|
||||||
export type Element = {|
|
export type Element = {|
|
||||||
@@ -86,21 +85,19 @@ export default class ElementsInspector extends Component<{
|
|||||||
} = this.props;
|
} = this.props;
|
||||||
|
|
||||||
return (
|
return (
|
||||||
<FlexRow grow={true}>
|
<Elements
|
||||||
<Elements
|
onElementExpanded={onElementExpanded}
|
||||||
onElementExpanded={onElementExpanded}
|
onElementSelected={onElementSelected}
|
||||||
onElementSelected={onElementSelected}
|
onElementHovered={onElementHovered}
|
||||||
onElementHovered={onElementHovered}
|
selected={selected}
|
||||||
selected={selected}
|
focused={focused}
|
||||||
focused={focused}
|
searchResults={searchResults}
|
||||||
searchResults={searchResults}
|
root={root}
|
||||||
root={root}
|
elements={elements}
|
||||||
elements={elements}
|
alternateRowColor={alternateRowColor}
|
||||||
alternateRowColor={alternateRowColor}
|
contextMenuExtensions={contextMenuExtensions}
|
||||||
contextMenuExtensions={contextMenuExtensions}
|
decorateRow={decorateRow}
|
||||||
decorateRow={decorateRow}
|
/>
|
||||||
/>
|
|
||||||
</FlexRow>
|
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user