11import cls from 'classnames' ;
22import { observer } from 'mobx-react-lite' ;
3- import React , { useCallback , useEffect , useMemo , useState } from 'react' ;
3+ import React , { useCallback , useEffect , useMemo , useRef , useState } from 'react' ;
44
5- import {
6- BasicRecycleTree ,
7- CheckBox ,
8- IBasicTreeData ,
9- ICompositeTreeNode ,
10- ITreeNodeOrCompositeTreeNode ,
11- } from '@opensumi/ide-components' ;
5+ import { BasicRecycleTree , CheckBox , IBasicTreeData , ICompositeTreeNode } from '@opensumi/ide-components' ;
126import { Badge } from '@opensumi/ide-components' ;
137import {
148 useInjectable ,
@@ -19,6 +13,7 @@ import {
1913 Disposable ,
2014 ViewState ,
2115 Event ,
16+ isUndefined ,
2217} from '@opensumi/ide-core-browser' ;
2318import { DebugProtocol } from '@opensumi/vscode-debugprotocol/lib/debugProtocol' ;
2419
@@ -33,6 +28,7 @@ import {
3328} from '../../breakpoint' ;
3429import { DebugSessionManager } from '../../debug-session-manager' ;
3530
31+ import { BreakpointsTreeNode } from './debug-breakpoints-tree.model' ;
3632import styles from './debug-breakpoints.module.less' ;
3733import { DebugBreakpointsService } from './debug-breakpoints.service' ;
3834
@@ -47,66 +43,74 @@ export interface BreakpointItem {
4743export const DebugBreakpointView = observer ( ( { viewState } : React . PropsWithChildren < { viewState : ViewState } > ) => {
4844 const debugBreakpointsService : DebugBreakpointsService = useInjectable ( DebugBreakpointsService ) ;
4945 const { enable, toggleBreakpointEnable } = debugBreakpointsService ;
46+ const isDisposed = useRef < boolean > ( false ) ;
5047 const [ treeData , setTreeData ] = useState < IBasicTreeData [ ] > ( [ ] ) ;
5148
52- useEffect ( ( ) => {
53- const dispose = new Disposable ( ) ;
54-
55- dispose . addDispose (
56- debugBreakpointsService . onDidChangeBreakpointsTreeNode ( ( nodes ) => {
57- const { roots } = debugBreakpointsService ;
58- const breakpointTreeData : IBasicTreeData [ ] = [ ] ;
59-
60- Array . from ( nodes . entries ( ) ) . forEach ( ( [ uri , items ] ) => {
61- const isException = EXCEPTION_BREAKPOINT_URI . toString ( ) === uri ;
62-
63- if ( isException ) {
64- items . forEach ( ( item ) => {
65- breakpointTreeData . push ( {
66- label : '' ,
67- expandable : false ,
68- children : [ ] ,
69- description : (
70- < BreakpointItem
71- toggle = { ( ) => toggleBreakpointEnable ( item . breakpoint ) }
72- breakpointEnabled = { enable }
73- data = { item . rawData }
74- isDebugMode = { debugBreakpointsService . inDebugMode }
75- > </ BreakpointItem >
76- ) ,
77- } ) ;
78- } ) ;
79- } else {
80- const toURI = URI . parse ( uri ) ;
81- const parent = roots . filter ( ( root ) => root . isEqualOrParent ( toURI ) ) [ 0 ] ;
82-
49+ const updateTreeData = useCallback (
50+ ( nodes : [ string , BreakpointsTreeNode [ ] ] [ ] ) => {
51+ const { roots } = debugBreakpointsService ;
52+ const breakpointTreeData : IBasicTreeData [ ] = [ ] ;
53+ nodes . forEach ( ( [ uri , items ] ) => {
54+ const isException = EXCEPTION_BREAKPOINT_URI . toString ( ) === uri ;
55+ if ( isException ) {
56+ items . forEach ( ( item ) => {
8357 breakpointTreeData . push ( {
84- label : parent ? parent . relative ( toURI ) ! . toString ( ) : URI . parse ( uri ) . displayName ,
85- expandable : true ,
86- iconClassName : getIcon ( 'file-text' ) ,
87- expanded : true ,
88- children : items . map ( ( item ) => ( {
89- ...item ,
90- label : '' ,
91- expandable : false ,
92- description : (
93- < BreakpointItem
94- toggle = { ( ) => toggleBreakpointEnable ( item . breakpoint ) }
95- breakpointEnabled = { enable }
96- data = { item . rawData }
97- isDebugMode = { debugBreakpointsService . inDebugMode }
98- > </ BreakpointItem >
99- ) ,
100- } ) ) ,
58+ label : '' ,
59+ expandable : false ,
60+ children : [ ] ,
61+ description : (
62+ < BreakpointItem
63+ toggle = { ( ) => toggleBreakpointEnable ( item . breakpoint ) }
64+ breakpointEnabled = { enable }
65+ data = { item . rawData }
66+ isDebugMode = { debugBreakpointsService . inDebugMode }
67+ > </ BreakpointItem >
68+ ) ,
10169 } ) ;
102- }
103- } ) ;
70+ } ) ;
71+ } else {
72+ const toURI = URI . parse ( uri ) ;
73+ const parent = roots . filter ( ( root ) => root . isEqualOrParent ( toURI ) ) [ 0 ] ;
10474
75+ breakpointTreeData . push ( {
76+ label : parent ? parent . relative ( toURI ) ?. toString ( ) || '' : URI . parse ( uri ) . displayName ,
77+ expandable : true ,
78+ iconClassName : getIcon ( 'file-text' ) ,
79+ expanded : true ,
80+ children : items . map ( ( item ) => ( {
81+ ...item ,
82+ label : '' ,
83+ expandable : false ,
84+ description : (
85+ < BreakpointItem
86+ toggle = { ( ) => toggleBreakpointEnable ( item . breakpoint ) }
87+ breakpointEnabled = { enable }
88+ data = { item . rawData }
89+ isDebugMode = { debugBreakpointsService . inDebugMode }
90+ > </ BreakpointItem >
91+ ) ,
92+ } ) ) ,
93+ } ) ;
94+ }
95+ } ) ;
96+ if ( ! isDisposed . current ) {
10597 setTreeData ( breakpointTreeData ) ;
98+ }
99+ } ,
100+ [ treeData ] ,
101+ ) ;
102+
103+ useEffect ( ( ) => {
104+ const dispose = new Disposable ( ) ;
105+ updateTreeData ( Array . from ( debugBreakpointsService . treeNodeMap . entries ( ) ) ) ;
106+ dispose . addDispose (
107+ debugBreakpointsService . onDidChangeBreakpointsTreeNode ( ( nodes : Map < string , BreakpointsTreeNode [ ] > ) => {
108+ updateTreeData ( Array . from ( nodes . entries ( ) ) ) ;
106109 } ) ,
107110 ) ;
108111
109112 return ( ) => {
113+ isDisposed . current = true ;
110114 dispose . dispose ( ) ;
111115 } ;
112116 } , [ ] ) ;
@@ -120,11 +124,10 @@ export const DebugBreakpointView = observer(({ viewState }: React.PropsWithChild
120124 } , [ treeData ] ) ;
121125
122126 const getItemClassName = useCallback ( ( item : ICompositeTreeNode ) => {
123- if ( ! item . children ) {
127+ if ( ! item . children && isUndefined ( ( item as any ) . expandable ) ) {
124128 return styles . debug_breakpoints_item_tree_node ;
125129 }
126130 } , [ ] ) ;
127-
128131 return (
129132 < div className = { cls ( styles . debug_breakpoints , ! enable && styles . debug_breakpoints_disabled ) } >
130133 < BasicRecycleTree treeData = { treeData } height = { viewState . height } getItemClassName = { getItemClassName } />
0 commit comments