Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Support
Submit feedback
Contribute to GitLab
Sign in
Toggle navigation
F
frontend
Project
Project
Details
Activity
Releases
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Boards
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
vicotor
frontend
Commits
20d8c0cd
Unverified
Commit
20d8c0cd
authored
Mar 04, 2024
by
tom goriunov
Committed by
GitHub
Mar 04, 2024
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
improve perf of highlighting same address in lists (#1662)
Fixes #1661
parent
82b7f3dd
Changes
4
Hide whitespace changes
Inline
Side-by-side
Showing
4 changed files
with
59 additions
and
28 deletions
+59
-28
addressHighlight.tsx
lib/contexts/addressHighlight.tsx
+15
-6
global.ts
theme/global.ts
+2
-0
address-entity.ts
theme/globals/address-entity.ts
+37
-0
AddressEntity.tsx
ui/shared/entities/address/AddressEntity.tsx
+5
-22
No files found.
lib/contexts/addressHighlight.tsx
View file @
20d8c0cd
...
@@ -5,7 +5,6 @@ interface AddressHighlightProviderProps {
...
@@ -5,7 +5,6 @@ interface AddressHighlightProviderProps {
}
}
interface
TAddressHighlightContext
{
interface
TAddressHighlightContext
{
highlightedAddress
:
string
|
null
;
onMouseEnter
:
(
event
:
React
.
MouseEvent
)
=>
void
;
onMouseEnter
:
(
event
:
React
.
MouseEvent
)
=>
void
;
onMouseLeave
:
(
event
:
React
.
MouseEvent
)
=>
void
;
onMouseLeave
:
(
event
:
React
.
MouseEvent
)
=>
void
;
}
}
...
@@ -13,30 +12,40 @@ interface TAddressHighlightContext {
...
@@ -13,30 +12,40 @@ interface TAddressHighlightContext {
export
const
AddressHighlightContext
=
React
.
createContext
<
TAddressHighlightContext
|
null
>
(
null
);
export
const
AddressHighlightContext
=
React
.
createContext
<
TAddressHighlightContext
|
null
>
(
null
);
export
function
AddressHighlightProvider
({
children
}:
AddressHighlightProviderProps
)
{
export
function
AddressHighlightProvider
({
children
}:
AddressHighlightProviderProps
)
{
const
[
highlightedAddress
,
setHighlightedAddress
]
=
React
.
useState
<
string
|
null
>
(
null
);
const
timeoutId
=
React
.
useRef
<
number
|
null
>
(
null
);
const
timeoutId
=
React
.
useRef
<
number
|
null
>
(
null
);
const
hashRef
=
React
.
useRef
<
string
|
null
>
(
null
);
const
onMouseEnter
=
React
.
useCallback
((
event
:
React
.
MouseEvent
)
=>
{
const
onMouseEnter
=
React
.
useCallback
((
event
:
React
.
MouseEvent
)
=>
{
const
hash
=
event
.
currentTarget
.
getAttribute
(
'
data-hash
'
);
const
hash
=
event
.
currentTarget
.
getAttribute
(
'
data-hash
'
);
if
(
hash
)
{
if
(
hash
)
{
hashRef
.
current
=
hash
;
timeoutId
.
current
=
window
.
setTimeout
(()
=>
{
timeoutId
.
current
=
window
.
setTimeout
(()
=>
{
setHighlightedAddress
(
hash
);
// for better performance we update DOM-nodes directly bypassing React reconciliation
const
nodes
=
window
.
document
.
querySelectorAll
(
`[data-hash="
${
hashRef
.
current
}
"]`
);
for
(
const
node
of
nodes
)
{
node
.
classList
.
add
(
'
address-entity_highlighted
'
);
}
},
100
);
},
100
);
}
}
},
[]);
},
[]);
const
onMouseLeave
=
React
.
useCallback
(()
=>
{
const
onMouseLeave
=
React
.
useCallback
(()
=>
{
setHighlightedAddress
(
null
);
if
(
hashRef
.
current
)
{
const
nodes
=
window
.
document
.
querySelectorAll
(
`[data-hash="
${
hashRef
.
current
}
"]`
);
for
(
const
node
of
nodes
)
{
node
.
classList
.
remove
(
'
address-entity_highlighted
'
);
}
hashRef
.
current
=
null
;
}
typeof
timeoutId
.
current
===
'
number
'
&&
window
.
clearTimeout
(
timeoutId
.
current
);
typeof
timeoutId
.
current
===
'
number
'
&&
window
.
clearTimeout
(
timeoutId
.
current
);
},
[]);
},
[]);
const
value
=
React
.
useMemo
(()
=>
{
const
value
=
React
.
useMemo
(()
=>
{
return
{
return
{
highlightedAddress
,
onMouseEnter
,
onMouseEnter
,
onMouseLeave
,
onMouseLeave
,
};
};
},
[
highlightedAddress
,
onMouseEnter
,
onMouseLeave
]);
},
[
onMouseEnter
,
onMouseLeave
]);
React
.
useEffect
(()
=>
{
React
.
useEffect
(()
=>
{
return
()
=>
{
return
()
=>
{
...
...
theme/global.ts
View file @
20d8c0cd
...
@@ -2,6 +2,7 @@ import type { StyleFunctionProps } from '@chakra-ui/theme-tools';
...
@@ -2,6 +2,7 @@ import type { StyleFunctionProps } from '@chakra-ui/theme-tools';
import
{
mode
}
from
'
@chakra-ui/theme-tools
'
;
import
{
mode
}
from
'
@chakra-ui/theme-tools
'
;
import
scrollbar
from
'
./foundations/scrollbar
'
;
import
scrollbar
from
'
./foundations/scrollbar
'
;
import
addressEntity
from
'
./globals/address-entity
'
;
import
getDefaultTransitionProps
from
'
./utils/getDefaultTransitionProps
'
;
import
getDefaultTransitionProps
from
'
./utils/getDefaultTransitionProps
'
;
const
global
=
(
props
:
StyleFunctionProps
)
=>
({
const
global
=
(
props
:
StyleFunctionProps
)
=>
({
...
@@ -23,6 +24,7 @@ const global = (props: StyleFunctionProps) => ({
...
@@ -23,6 +24,7 @@ const global = (props: StyleFunctionProps) => ({
w
:
'
100%
'
,
w
:
'
100%
'
,
},
},
...
scrollbar
(
props
),
...
scrollbar
(
props
),
...
addressEntity
(
props
),
});
});
export
default
global
;
export
default
global
;
theme/globals/address-entity.ts
0 → 100644
View file @
20d8c0cd
import
{
mode
}
from
'
@chakra-ui/theme-tools
'
;
import
type
{
StyleFunctionProps
}
from
'
@chakra-ui/theme-tools
'
;
const
styles
=
(
props
:
StyleFunctionProps
)
=>
{
return
{
'
.address-entity
'
:
{
'
&.address-entity_highlighted
'
:
{
_before
:
{
content
:
`" "`
,
position
:
'
absolute
'
,
py
:
1
,
pl
:
1
,
pr
:
0
,
top
:
'
-5px
'
,
left
:
'
-5px
'
,
width
:
`100%`
,
height
:
'
100%
'
,
borderRadius
:
'
base
'
,
borderColor
:
mode
(
'
blue.200
'
,
'
blue.600
'
)(
props
),
borderWidth
:
'
1px
'
,
borderStyle
:
'
dashed
'
,
bgColor
:
mode
(
'
blue.50
'
,
'
blue.900
'
)(
props
),
zIndex
:
-
1
,
},
},
},
'
.address-entity_no-copy
'
:
{
'
&.address-entity_highlighted
'
:
{
_before
:
{
pr
:
2
,
},
},
},
};
};
export
default
styles
;
ui/shared/entities/address/AddressEntity.tsx
View file @
20d8c0cd
import
type
{
As
}
from
'
@chakra-ui/react
'
;
import
type
{
As
}
from
'
@chakra-ui/react
'
;
import
{
Box
,
Flex
,
Skeleton
,
Tooltip
,
chakra
,
VStack
,
useColorModeValue
}
from
'
@chakra-ui/react
'
;
import
{
Box
,
Flex
,
Skeleton
,
Tooltip
,
chakra
,
VStack
}
from
'
@chakra-ui/react
'
;
import
_omit
from
'
lodash/omit
'
;
import
_omit
from
'
lodash/omit
'
;
import
React
from
'
react
'
;
import
React
from
'
react
'
;
...
@@ -148,33 +148,16 @@ const AddressEntry = (props: EntityProps) => {
...
@@ -148,33 +148,16 @@ const AddressEntry = (props: EntityProps) => {
const
partsProps
=
_omit
(
props
,
[
'
className
'
,
'
onClick
'
]);
const
partsProps
=
_omit
(
props
,
[
'
className
'
,
'
onClick
'
]);
const
context
=
useAddressHighlightContext
();
const
context
=
useAddressHighlightContext
();
const
highlightedBgColor
=
useColorModeValue
(
'
blue.50
'
,
'
blue.900
'
);
const
highlightedBorderColor
=
useColorModeValue
(
'
blue.200
'
,
'
blue.600
'
);
return
(
return
(
<
Container
<
Container
className=
{
props
.
className
}
// we have to use the global classnames here, see theme/global.ts
data
-
hash=
{
props
.
address
.
hash
}
// otherwise, if we use sx prop, Chakra will generate the same styles for each instance of the component on the page
className=
{
`${ props.className } address-entity ${ props.noCopy ? 'address-entity_no-copy' : '' }`
}
data
-
hash=
{
context
&&
!
props
.
isLoading
?
props
.
address
.
hash
:
undefined
}
onMouseEnter=
{
context
?.
onMouseEnter
}
onMouseEnter=
{
context
?.
onMouseEnter
}
onMouseLeave=
{
context
?.
onMouseLeave
}
onMouseLeave=
{
context
?.
onMouseLeave
}
position=
"relative"
position=
"relative"
_before=
{
!
props
.
isLoading
&&
context
?.
highlightedAddress
===
props
.
address
.
hash
?
{
content
:
`" "`
,
position
:
'
absolute
'
,
py
:
1
,
pl
:
1
,
pr
:
props
.
noCopy
?
2
:
0
,
top
:
'
-5px
'
,
left
:
'
-5px
'
,
width
:
`100%`
,
height
:
'
100%
'
,
borderRadius
:
'
base
'
,
borderColor
:
highlightedBorderColor
,
borderWidth
:
'
1px
'
,
borderStyle
:
'
dashed
'
,
bgColor
:
highlightedBgColor
,
zIndex
:
-
1
,
}
:
undefined
}
>
>
<
Icon
{
...
partsProps
}
/>
<
Icon
{
...
partsProps
}
/>
<
Link
{
...
linkProps
}
>
<
Link
{
...
linkProps
}
>
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment