Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Bugfix: clean treeselectionview type and fix a initial state check grid samples issue #5053

Merged
merged 8 commits into from
Nov 6, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ import ExpandMoreIcon from "@mui/icons-material/ExpandMore";
import { Box, Checkbox, FormControlLabel, IconButton } from "@mui/material";
import React, { useEffect } from "react";
import { ViewPropsType } from "../utils/types";
import { useUnboundState } from "@fiftyone/state";

interface CheckedState {
[key: string]: {
Expand Down Expand Up @@ -70,6 +71,8 @@ export default function TreeSelectionView(props: ViewPropsType) {
const [checkedState, setCheckedState] =
React.useState<CheckedState>(initialCheckedState);

const unboundState = useUnboundState(checkedState);

// Initialize collapsed state for all parents
const initialCollapsedState: CollapsedState = React.useMemo(() => {
const state: CollapsedState = {};
Expand Down Expand Up @@ -192,6 +195,16 @@ export default function TreeSelectionView(props: ViewPropsType) {
return idx === -1 ? 0 : idx + 1;
};

useEffect(() => {
const sampleIds = view?.data.flatMap(([parentId, children]) => {
return children.map((childId) =>
typeof childId === "string" ? childId : childId[0]
);
});
onChange(path, sampleIds);
// eslint-disable-next-line react-hooks/exhaustive-deps
}, []);
Comment on lines +198 to +206
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue

Refactor duplicate initialization logic and fix effect dependencies

The useEffect duplicates the initialization logic from the early return block and has several issues:

  1. Potential race condition with the early return logic
  2. Missing dependencies in the effect's dependency array
  3. Unconditional state update on mount

Consider refactoring to:

- useEffect(() => {
-   const sampleIds = view?.data.flatMap(([parentId, children]) => {
-     return children.map((childId) =>
-       typeof childId === "string" ? childId : childId[0]
-     );
-   });
-   onChange(path, sampleIds);
-   // eslint-disable-next-line react-hooks/exhaustive-deps
- }, []);

+ useEffect(() => {
+   if (data === undefined && view?.data) {
+     const sampleIds = view.data.flatMap(([parentId, children]) => {
+       return children.map((childId) =>
+         typeof childId === "string" ? childId : childId[0]
+       );
+     });
+     onChange(path, sampleIds);
+   }
+ }, [data, view?.data, path, onChange]);

Committable suggestion skipped: line range outside the PR's diff.


// CheckboxView: Represents a single checkbox (either parent or child)
function CheckboxView({
id,
Expand Down
6 changes: 2 additions & 4 deletions fiftyone/operators/types.py
Original file line number Diff line number Diff line change
Expand Up @@ -610,18 +610,16 @@ def tuple(self, name, *items, **kwargs):
self.define_property(name, tuple_type, view=tuple_view, **kwargs)
return tuple_type

def tree(self, name, *items, **kwargs):
def tree(self, name, **kwargs):
"""Defines a tree property on the object.

Args:
name: the name of the property
*items: the types of the items in the tree

Returns:
a :class:`Tree`
"""
tree_selection_view = TreeSelectionView(**kwargs)
tree_type = Object(*items)
tree_type = List(String())
self.define_property(
name, tree_type, view=tree_selection_view, **kwargs
)
Expand Down
Loading