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
e4a5483f
Commit
e4a5483f
authored
Feb 17, 2025
by
tom
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
mud address tab
parent
67f0e1c2
Changes
23
Show whitespace changes
Inline
Side-by-side
Showing
23 changed files
with
317 additions
and
294 deletions
+317
-294
mud-worlds.tsx
pages/mud-worlds.tsx
+2
-2
icon-button.tsx
toolkit/chakra/icon-button.tsx
+1
-1
popover.tsx
toolkit/chakra/popover.tsx
+13
-0
useContractTabs.tsx
ui/address/contract/useContractTabs.tsx
+7
-7
AddressMudBreadcrumbs.tsx
ui/address/mud/AddressMudBreadcrumbs.tsx
+9
-9
AddressMudRecord.tsx
ui/address/mud/AddressMudRecord.tsx
+17
-16
AddressMudRecordValues.tsx
ui/address/mud/AddressMudRecordValues.tsx
+15
-13
AddressMudRecordsKeyFilter.tsx
ui/address/mud/AddressMudRecordsKeyFilter.tsx
+1
-1
AddressMudRecordsKeyFilterContent.tsx
ui/address/mud/AddressMudRecordsKeyFilterContent.tsx
+3
-5
AddressMudRecordsTable.tsx
ui/address/mud/AddressMudRecordsTable.tsx
+40
-39
AddressMudTable.tsx
ui/address/mud/AddressMudTable.tsx
+22
-9
AddressMudTables.tsx
ui/address/mud/AddressMudTables.tsx
+11
-10
AddressMudTablesListItem.tsx
ui/address/mud/AddressMudTablesListItem.tsx
+19
-15
AddressMudTablesTable.tsx
ui/address/mud/AddressMudTablesTable.tsx
+13
-14
AddressMudTablesTableItem.tsx
ui/address/mud/AddressMudTablesTableItem.tsx
+59
-52
MudWorldsListItem.tsx
ui/mudWorlds/MudWorldsListItem.tsx
+7
-7
MudWorldsTable.tsx
ui/mudWorlds/MudWorldsTable.tsx
+12
-13
MudWorldsTableItem.tsx
ui/mudWorlds/MudWorldsTableItem.tsx
+14
-13
Address.tsx
ui/pages/Address.tsx
+6
-6
MudWorlds.tsx
ui/pages/MudWorlds.tsx
+9
-8
ClearButton.tsx
ui/shared/ClearButton.tsx
+1
-0
TableColumnFilter.tsx
ui/shared/filters/TableColumnFilter.tsx
+16
-14
TableColumnFilterWrapper.tsx
ui/shared/filters/TableColumnFilterWrapper.tsx
+20
-40
No files found.
pages/mud-worlds.tsx
View file @
e4a5483f
...
...
@@ -4,12 +4,12 @@ import React from 'react';
import
PageNextJs
from
'
nextjs/PageNextJs
'
;
//
const MudWorlds = dynamic(() => import('ui/pages/MudWorlds'), { ssr: false });
const
MudWorlds
=
dynamic
(()
=>
import
(
'
ui/pages/MudWorlds
'
),
{
ssr
:
false
});
const
Page
:
NextPage
=
()
=>
{
return
(
<
PageNextJs
pathname=
"/mud-worlds"
>
{
/* <MudWorlds/> */
}
<
MudWorlds
/>
</
PageNextJs
>
);
};
...
...
toolkit/chakra/icon-button.tsx
View file @
e4a5483f
...
...
@@ -5,7 +5,7 @@ import { Skeleton } from './skeleton';
export
interface
IconButtonProps
extends
ButtonProps
{}
// TODO @tom2drum variants for icon buttons: prev-next, top-bar, copy-to-clipboard
// TODO @tom2drum variants for icon buttons: prev-next, top-bar, copy-to-clipboard
, filter column
// TODO @tom2drum fix loading state for outlined variant
export
const
IconButton
=
React
.
forwardRef
<
HTMLDivElement
,
IconButtonProps
>
(
...
...
toolkit/chakra/popover.tsx
View file @
e4a5483f
...
...
@@ -51,6 +51,19 @@ export const PopoverCloseTrigger = React.forwardRef<
);
});
export
const
PopoverCloseTriggerWrapper
=
React
.
forwardRef
<
HTMLButtonElement
,
ChakraPopover
.
CloseTriggerProps
>
(
function
PopoverCloseTriggerWrapper
(
props
,
ref
)
{
return
(
<
ChakraPopover
.
CloseTrigger
ref=
{
ref
}
{
...
props
}
asChild
/>
);
});
export
const
PopoverRoot
=
(
props
:
ChakraPopover
.
RootProps
)
=>
{
const
positioning
=
{
placement
:
'
bottom-start
'
as
const
,
...
...
ui/address/contract/useContractTabs.tsx
View file @
e4a5483f
...
...
@@ -95,13 +95,13 @@ export default function useContractTabs(data: Address | undefined, isPlaceholder
title: 'Custom ABI',
component: <ContractMethodsCustom isLoading={ contractQuery.isPlaceholderData }/>,
},
//
hasMudTab && {
//
id: 'mud_system' as const,
//
title: 'MUD System',
//
component: mudSystemsQuery.isPlaceholderData ?
//
<ContentLoader/> :
//
<ContractMethodsMudSystem items={ mudSystemsQuery.data?.items ?? [] }/>,
//
},
hasMudTab && {
id: 'mud_system' as const,
title: 'MUD System',
component: mudSystemsQuery.isPlaceholderData ?
<ContentLoader/> :
<ContractMethodsMudSystem items={ mudSystemsQuery.data?.items ?? [] }/>,
},
].filter(Boolean),
isLoading: contractQuery.isPlaceholderData,
};
...
...
ui/address/mud/AddressMudBreadcrumbs.tsx
View file @
e4a5483f
import
{
Box
,
useColorModeValue
,
chakra
,
Grid
}
from
'
@chakra-ui/react
'
;
import
{
Box
,
chakra
,
Grid
}
from
'
@chakra-ui/react
'
;
import
React
from
'
react
'
;
import
{
route
}
from
'
nextjs-routes
'
;
import
useIsMobile
from
'
lib/hooks/useIsMobile
'
;
import
isBrowser
from
'
lib/isBrowser
'
;
import
{
Link
}
from
'
toolkit/chakra/link
'
;
import
CopyToClipboard
from
'
ui/shared/CopyToClipboard
'
;
import
IconSvg
from
'
ui/shared/IconSvg
'
;
import
LinkInternal
from
'
ui/shared/links/LinkInternal
'
;
import
useAddressQuery
from
'
../utils/useAddressQuery
'
;
...
...
@@ -17,9 +17,11 @@ type TableViewProps = {
hash
:
string
;
tableId
:
string
;
tableName
:
string
;
recordId
?:
never
;
recordName
?:
never
;
};
type
RecordViewProps
=
TableViewProps
&
{
type
RecordViewProps
=
Omit
<
TableViewProps
,
'
recordId
'
|
'
recordName
'
>
&
{
recordId
:
string
;
recordName
:
string
;
};
...
...
@@ -32,8 +34,6 @@ type BreadcrumbItemProps = {
};
const
BreadcrumbItem
=
({
text
,
href
,
isLast
,
scrollRef
}:
BreadcrumbItemProps
)
=>
{
const
iconColor
=
useColorModeValue
(
'
gray.300
'
,
'
gray.600
'
);
const
currentUrl
=
isBrowser
()
?
window
.
location
.
href
:
''
;
const
onLinkClick
=
React
.
useCallback
(()
=>
{
...
...
@@ -60,7 +60,7 @@ const BreadcrumbItem = ({ text, href, isLast, scrollRef }: BreadcrumbItemProps)
return
(
<
Grid
gap=
{
2
}
overflow=
"hidden"
templateColumns=
"auto 24px"
alignItems=
"center"
>
<
Link
Internal
<
Link
href=
{
href
}
onClick=
{
onLinkClick
}
overflow=
"hidden"
...
...
@@ -68,8 +68,8 @@ const BreadcrumbItem = ({ text, href, isLast, scrollRef }: BreadcrumbItemProps)
whiteSpace=
"nowrap"
>
{
text
}
</
Link
Internal
>
{
!
isLast
&&
<
IconSvg
name=
"arrows/east"
boxSize=
{
6
}
color=
{
iconColor
}
/>
}
</
Link
>
{
!
isLast
&&
<
IconSvg
name=
"arrows/east"
boxSize=
{
6
}
color=
{
{
_light
:
'
gray.300
'
,
_dark
:
'
gray.600
'
}
}
/>
}
</
Grid
>
);
};
...
...
@@ -103,7 +103,7 @@ const AddressMudBreadcrumbs = (props: TableViewProps | RecordViewProps) => {
isLast=
{
!
(
'
recordId
'
in
props
)
}
scrollRef=
{
props
.
scrollRef
}
/>
{
(
'
recordId
'
in
props
)
&&
(
{
(
'
recordId
'
in
props
&&
typeof
props
.
recordId
===
'
string
'
)
&&
(
'
recordName
'
in
props
&&
typeof
props
.
recordName
===
'
string
'
)
&&
(
<
BreadcrumbItem
text=
{
props
.
recordName
}
href=
{
route
({
pathname
:
'
/address/[hash]
'
,
query
:
{
...
queryParams
,
table_id
:
props
.
tableId
,
record_id
:
props
.
recordId
}
})
}
...
...
ui/address/mud/AddressMudRecord.tsx
View file @
e4a5483f
import
{
Box
,
Td
,
Tr
,
Flex
,
Text
,
Table
,
Show
,
Hide
,
Divider
,
VStack
}
from
'
@chakra-ui/react
'
;
import
{
Box
,
Flex
,
Separator
,
Text
,
VStack
}
from
'
@chakra-ui/react
'
;
import
{
useRouter
}
from
'
next/router
'
;
import
React
from
'
react
'
;
import
useApiQuery
from
'
lib/api/useApiQuery
'
;
import
dayjs
from
'
lib/date/dayjs
'
;
import
getQueryParamString
from
'
lib/router/getQueryParamString
'
;
import
{
TableRoot
,
TableRow
,
TableCell
}
from
'
toolkit/chakra/table
'
;
import
ContentLoader
from
'
ui/shared/ContentLoader
'
;
import
DataFetchAlert
from
'
ui/shared/DataFetchAlert
'
;
import
TruncatedValue
from
'
ui/shared/TruncatedValue
'
;
...
...
@@ -53,29 +54,29 @@ const AddressMudRecord = ({ tableId, recordId, isQueryEnabled = true, scrollRef
scrollRef=
{
scrollRef
}
/>
)
}
<
Show
above=
"lg"
ssr=
{
false
}
>
<
Table
borderRadius=
"8px"
style=
{
{
tableLayout
:
'
auto
'
}
}
width=
"100%"
overflow=
"hidden"
>
<
Box
hideBelow=
"lg"
>
<
Table
Root
borderRadius=
"8px"
style=
{
{
tableLayout
:
'
auto
'
}
}
width=
"100%"
overflow=
"hidden"
>
{
data
?.
schema
.
key_names
.
length
&&
data
?.
schema
.
key_names
.
map
((
keyName
,
index
)
=>
(
<
T
r
key=
{
keyName
}
borderBottomStyle=
{
index
===
data
.
schema
.
key_names
.
length
-
1
?
'
hidden
'
:
'
solid
'
}
>
<
T
d
fontWeight=
{
600
}
whiteSpace=
"nowrap"
fontSize=
"sm"
>
<
T
ableRow
key=
{
keyName
}
borderBottomStyle=
{
index
===
data
.
schema
.
key_names
.
length
-
1
?
'
hidden
'
:
'
solid
'
}
>
<
T
ableCell
fontWeight=
{
600
}
whiteSpace=
"nowrap"
fontSize=
"sm"
>
{
keyName
}
(
{
data
.
schema
.
key_types
[
index
]
}
)
</
T
d
>
<
T
d
colSpan=
{
2
}
fontSize=
"sm"
>
</
T
ableCell
>
<
T
ableCell
colSpan=
{
2
}
fontSize=
"sm"
>
<
Flex
justifyContent=
"space-between"
>
<
TruncatedValue
value=
{
getValueString
(
data
.
record
.
decoded
[
keyName
])
}
mr=
{
2
}
/>
{
index
===
0
&&
<
Box
color=
"text_secondary"
>
{
dayjs
(
data
.
record
.
timestamp
).
format
(
'
lll
'
)
}
</
Box
>
}
</
Flex
>
</
T
d
>
</
T
r
>
</
T
ableCell
>
</
T
ableRow
>
))
}
<
AddressMudRecordValues
data=
{
data
}
/>
</
Table
>
</
Show
>
<
Hide
above=
"lg"
ssr=
{
false
}
>
</
Table
Root
>
</
Box
>
<
Box
hideFrom=
"lg"
>
<>
{
data
?.
schema
.
key_names
.
length
&&
data
?.
schema
.
key_names
.
map
((
keyName
,
index
)
=>
(
<
VStack
gap=
{
1
}
key=
{
keyName
}
alignItems=
"start"
fontSize=
"sm"
>
<
Divide
r
/>
<
Separato
r
/>
<
Text
fontWeight=
{
600
}
whiteSpace=
"nowrap"
>
{
keyName
}
(
{
data
.
schema
.
key_types
[
index
]
}
)
</
Text
>
...
...
@@ -83,11 +84,11 @@ const AddressMudRecord = ({ tableId, recordId, isQueryEnabled = true, scrollRef
{
index
===
0
&&
<
Box
color=
"text_secondary"
>
{
dayjs
(
data
.
record
.
timestamp
).
format
(
'
lll
'
)
}
</
Box
>
}
</
VStack
>
))
}
<
Table
borderRadius=
"8px"
style=
{
{
tableLayout
:
'
auto
'
}
}
width=
"100%"
mt=
{
2
}
overflow=
"hidden"
>
<
Table
Root
borderRadius=
"8px"
style=
{
{
tableLayout
:
'
auto
'
}
}
width=
"100%"
mt=
{
2
}
overflow=
"hidden"
>
<
AddressMudRecordValues
data=
{
data
}
/>
</
Table
>
</
Table
Root
>
</>
</
Hide
>
</
Box
>
</>
);
};
...
...
ui/address/mud/AddressMudRecordValues.tsx
View file @
e4a5483f
import
{
Box
,
Td
,
Tr
,
useColorModeValue
}
from
'
@chakra-ui/react
'
;
import
{
Box
}
from
'
@chakra-ui/react
'
;
import
React
from
'
react
'
;
import
type
{
AddressMudRecord
}
from
'
types/api/address
'
;
import
{
TableCell
,
TableRow
}
from
'
toolkit/chakra/table
'
;
import
{
getValueString
}
from
'
./utils
'
;
type
Props
=
{
...
...
@@ -10,7 +12,7 @@ type Props = {
};
const
AddressMudRecordValues
=
({
data
}:
Props
)
=>
{
const
valuesBgColor
=
useColorModeValue
(
'
blackAlpha.50
'
,
'
whiteAlpha.50
'
)
;
const
valuesBgColor
=
{
_light
:
'
blackAlpha.50
'
,
_dark
:
'
whiteAlpha.50
'
}
;
if
(
!
data
?.
schema
.
value_names
.
length
)
{
return
null
;
...
...
@@ -18,22 +20,22 @@ const AddressMudRecordValues = ({ data }: Props) => {
return
(
<>
<
T
r
backgroundColor=
{
valuesBgColor
}
borderBottomStyle=
"hidden"
>
<
T
d
fontWeight=
{
600
}
w=
"100px"
fontSize=
"sm"
>
Field
</
Td
>
<
T
d
fontWeight=
{
600
}
w=
"90px"
fontSize=
"sm"
>
Type
</
Td
>
<
T
d
fontWeight=
{
600
}
fontSize=
"sm"
>
Value
</
Td
>
</
T
r
>
<
T
ableRow
backgroundColor=
{
valuesBgColor
}
borderBottomStyle=
"hidden"
>
<
T
ableCell
fontWeight=
{
600
}
w=
"100px"
fontSize=
"sm"
>
Field
</
TableCell
>
<
T
ableCell
fontWeight=
{
600
}
w=
"90px"
fontSize=
"sm"
>
Type
</
TableCell
>
<
T
ableCell
fontWeight=
{
600
}
fontSize=
"sm"
>
Value
</
TableCell
>
</
T
ableRow
>
{
data
?.
schema
.
value_names
.
map
((
valName
,
index
)
=>
(
<
T
r
key=
{
valName
}
backgroundColor=
{
valuesBgColor
}
borderBottomStyle=
"hidden"
>
<
T
d
fontWeight=
{
400
}
w=
"100px"
py=
{
0
}
pb=
{
4
}
pr=
{
0
}
wordBreak=
"break-all"
>
{
valName
}
</
Td
>
<
T
d
fontWeight=
{
400
}
w=
"90px"
py=
{
0
}
pb=
{
4
}
wordBreak=
"break-all"
>
{
data
.
schema
.
value_types
[
index
]
}
</
Td
>
<
T
d
fontWeight=
{
400
}
wordBreak=
"break-word"
py=
{
0
}
pb=
{
4
}
>
<
T
ableRow
key=
{
valName
}
backgroundColor=
{
valuesBgColor
}
borderBottomStyle=
"hidden"
>
<
T
ableCell
fontWeight=
{
400
}
w=
"100px"
py=
{
0
}
pb=
{
4
}
pr=
{
0
}
wordBreak=
"break-all"
>
{
valName
}
</
TableCell
>
<
T
ableCell
fontWeight=
{
400
}
w=
"90px"
py=
{
0
}
pb=
{
4
}
wordBreak=
"break-all"
>
{
data
.
schema
.
value_types
[
index
]
}
</
TableCell
>
<
T
ableCell
fontWeight=
{
400
}
wordBreak=
"break-word"
py=
{
0
}
pb=
{
4
}
>
<
Box
>
{
getValueString
(
data
.
record
.
decoded
[
valName
])
}
</
Box
>
</
T
d
>
</
T
r
>
</
T
ableCell
>
</
T
ableRow
>
))
}
</>
...
...
ui/address/mud/AddressMudRecordsKeyFilter.tsx
View file @
e4a5483f
...
...
@@ -16,7 +16,7 @@ const AddressMudRecordsKeyFilter = ({ value = '', handleFilterChange, columnName
return
(
<
TableColumnFilterWrapper
columnName=
{
columnName
}
isActive
=
{
Boolean
(
value
)
}
selected
=
{
Boolean
(
value
)
}
isLoading=
{
isLoading
}
w=
"350px"
>
...
...
ui/address/mud/AddressMudRecordsKeyFilterContent.tsx
View file @
e4a5483f
...
...
@@ -8,10 +8,9 @@ type Props = {
handleFilterChange
:
(
val
:
string
)
=>
void
;
title
:
string
;
columnName
:
string
;
onClose
?:
()
=>
void
;
};
const
AddressMudRecordsKeyFilter
=
({
value
=
''
,
handleFilterChange
,
columnName
,
title
,
onClos
e
}:
Props
)
=>
{
const
AddressMudRecordsKeyFilter
Content
=
({
value
=
''
,
handleFilterChange
,
columnName
,
titl
e
}:
Props
)
=>
{
const
[
filterValue
,
setFilterValue
]
=
React
.
useState
<
string
>
(
value
);
const
onFilter
=
React
.
useCallback
(()
=>
{
...
...
@@ -23,11 +22,10 @@ const AddressMudRecordsKeyFilter = ({ value = '', handleFilterChange, columnName
title=
{
title
}
isFilled=
{
filterValue
!==
value
}
onFilter=
{
onFilter
}
onClose=
{
onClose
}
>
<
FilterInput
initialValue=
{
value
}
size=
"
xs
"
size=
"
sm
"
onChange=
{
setFilterValue
}
placeholder=
{
columnName
}
/>
...
...
@@ -35,4 +33,4 @@ const AddressMudRecordsKeyFilter = ({ value = '', handleFilterChange, columnName
);
};
export
default
AddressMudRecordsKeyFilter
;
export
default
AddressMudRecordsKeyFilter
Content
;
ui/address/mud/AddressMudRecordsTable.tsx
View file @
e4a5483f
import
type
{
StyleProps
}
from
'
@chakra-ui/react
'
;
import
{
Box
,
Link
,
Table
,
Tbody
,
Td
,
Th
,
Tr
,
Flex
,
useColorModeValue
,
useBoolean
,
Tooltip
}
from
'
@chakra-ui/react
'
;
import
{
Box
,
Flex
}
from
'
@chakra-ui/react
'
;
import
{
useRouter
}
from
'
next/router
'
;
import
React
from
'
react
'
;
...
...
@@ -10,10 +9,13 @@ import { route } from 'nextjs-routes';
import
capitalizeFirstLetter
from
'
lib/capitalizeFirstLetter
'
;
import
dayjs
from
'
lib/date/dayjs
'
;
import
useIsMobile
from
'
lib/hooks/useIsMobile
'
;
import
{
middot
}
from
'
lib/html-entities
'
;
import
{
Link
}
from
'
toolkit/chakra/link
'
;
import
{
TableBody
,
TableCell
,
TableColumnHeader
,
TableHeaderSticky
,
TableRoot
,
TableRow
}
from
'
toolkit/chakra/table
'
;
import
type
{
TableColumnHeaderProps
}
from
'
toolkit/chakra/table
'
;
import
{
Tooltip
}
from
'
toolkit/chakra/tooltip
'
;
import
CopyToClipboard
from
'
ui/shared/CopyToClipboard
'
;
import
IconSvg
from
'
ui/shared/IconSvg
'
;
import
LinkInternal
from
'
ui/shared/links/LinkInternal
'
;
import
{
default
as
Thead
}
from
'
ui/shared/TheadSticky
'
;
import
AddressMudRecordsKeyFilter
from
'
./AddressMudRecordsKeyFilter
'
;
import
{
getNameTypeText
,
getValueString
}
from
'
./utils
'
;
...
...
@@ -49,8 +51,8 @@ const AddressMudRecordsTable = ({
const
totalColsCut
=
data
.
schema
.
key_names
.
length
+
data
.
schema
.
value_names
.
length
;
const
isMobile
=
useIsMobile
(
false
);
const
[
colsCutCount
,
setColsCutCount
]
=
React
.
useState
<
number
>
(
isMobile
?
MIN_CUT_COUNT
:
0
);
const
[
isOpened
,
setIsOpened
]
=
useBoolean
(
false
);
const
[
hasCut
,
setHasCut
]
=
useBoolean
(
isMobile
?
totalColsCut
>
MIN_CUT_COUNT
:
true
);
const
[
isOpened
,
setIsOpened
]
=
React
.
useState
(
false
);
const
[
hasCut
,
setHasCut
]
=
React
.
useState
(
isMobile
?
totalColsCut
>
MIN_CUT_COUNT
:
true
);
const
containerRef
=
React
.
useRef
<
HTMLTableElement
>
(
null
);
const
tableRef
=
React
.
useRef
<
HTMLTableElement
>
(
null
);
...
...
@@ -59,7 +61,7 @@ const AddressMudRecordsTable = ({
const
toggleIsOpen
=
React
.
useCallback
(()
=>
{
isOpened
&&
tableRef
.
current
?.
scroll
({
left
:
0
});
setIsOpened
.
toggle
(
);
setIsOpened
((
prev
)
=>
!
prev
);
toggleTableHasHorizontalScroll
();
},
[
setIsOpened
,
toggleTableHasHorizontalScroll
,
isOpened
]);
...
...
@@ -95,15 +97,13 @@ const AddressMudRecordsTable = ({
[
toggleSorting
],
);
const
keyBgColor
=
useColorModeValue
(
'
blackAlpha.50
'
,
'
whiteAlpha.50
'
);
React
.
useEffect
(()
=>
{
if
(
hasCut
&&
!
colsCutCount
&&
containerRef
.
current
)
{
const
count
=
Math
.
floor
((
containerRef
.
current
.
getBoundingClientRect
().
width
-
CUT_COL_WIDTH
)
/
COL_MIN_WIDTH
);
if
(
totalColsCut
>
MIN_CUT_COUNT
&&
count
-
1
<
totalColsCut
)
{
setColsCutCount
(
count
-
1
);
}
else
{
setHasCut
.
off
(
);
setHasCut
(
false
);
}
}
},
[
colsCutCount
,
data
.
schema
,
hasCut
,
setHasCut
,
totalColsCut
]);
...
...
@@ -114,7 +114,7 @@ const AddressMudRecordsTable = ({
const
values
=
(
isOpened
||
!
hasCut
)
?
data
.
schema
.
value_names
:
data
.
schema
.
value_names
.
slice
(
0
,
colsCutCount
-
data
.
schema
.
key_names
.
length
);
const
colsCount
=
(
isOpened
||
!
hasCut
)
?
totalColsCut
:
colsCutCount
;
const
tdStyles
:
Style
Props
=
{
const
tdStyles
:
TableColumnHeader
Props
=
{
wordBreak
:
'
break-word
'
,
whiteSpace
:
'
normal
'
,
minW
:
`
${
colW
}
px`
,
...
...
@@ -130,23 +130,23 @@ const AddressMudRecordsTable = ({
}
const
cutButton
=
(
<
T
h
width=
{
`${ CUT_COL_WIDTH }px `
}
verticalAlign=
"baseline"
>
<
Tooltip
label
=
{
isOpened
?
'
Hide columns
'
:
'
Show all columns
'
}
>
<
Link
onClick=
{
toggleIsOpen
}
aria
-
label=
"show/hide columns"
>
...
</
Link
>
<
T
ableColumnHeader
width=
{
`${ CUT_COL_WIDTH }px `
}
verticalAlign=
"baseline"
>
<
Tooltip
content
=
{
isOpened
?
'
Hide columns
'
:
'
Show all columns
'
}
>
<
Link
onClick=
{
toggleIsOpen
}
aria
-
label=
"show/hide columns"
>
{
middot
}{
middot
}{
middot
}
</
Link
>
</
Tooltip
>
</
T
h
>
</
T
ableColumnHeader
>
);
return
(
// can't implement both horizontal table scroll and sticky header
<
Box
maxW=
"100%"
overflowX=
{
hasHorizontalScroll
?
'
scroll
'
:
'
unset
'
}
whiteSpace=
"nowrap"
ref=
{
tableRef
}
>
<
Table
style=
{
{
tableLayout
:
'
fixed
'
}
}
>
<
T
head
top=
{
hasHorizontalScroll
?
0
:
top
}
display=
{
hasHorizontalScroll
?
'
table
'
:
'
table-header-group
'
}
w=
"100%"
>
<
T
r
>
<
Table
Root
style=
{
{
tableLayout
:
'
fixed
'
}
}
>
<
T
ableHeaderSticky
top=
{
hasHorizontalScroll
?
0
:
top
}
display=
{
hasHorizontalScroll
?
'
table
'
:
'
table-header-group
'
}
w=
"100%"
>
<
T
ableRow
>
{
keys
.
map
((
keyName
,
index
)
=>
{
const
text
=
getNameTypeText
(
keyName
,
data
.
schema
.
key_types
[
index
]);
return
(
<
T
h
key=
{
keyName
}
{
...
tdStyles
}
>
<
T
ableColumnHeader
key=
{
keyName
}
{
...
tdStyles
}
>
{
index
<
2
?
(
<
Flex
alignItems=
"center"
>
<
Link
...
...
@@ -178,46 +178,47 @@ const AddressMudRecordsTable = ({
</
Box
>
</
Flex
>
)
:
text
}
</
T
h
>
</
T
ableColumnHeader
>
);
})
}
{
values
.
map
((
valName
,
index
)
=>
(
<
T
h
key=
{
valName
}
{
...
tdStyles
}
>
<
T
ableColumnHeader
key=
{
valName
}
{
...
tdStyles
}
>
{
capitalizeFirstLetter
(
valName
)
}
(
{
data
.
schema
.
value_types
[
index
]
}
)
</
T
h
>
</
T
ableColumnHeader
>
))
}
{
hasCut
&&
!
isOpened
&&
cutButton
}
<
T
h
{
...
tdStyles
}
w=
{
`${ colW }px`
}
>
Modified
</
Th
>
<
T
ableColumnHeader
{
...
tdStyles
}
w=
{
`${ colW }px`
}
>
Modified
</
TableColumnHeader
>
{
hasCut
&&
isOpened
&&
cutButton
}
</
T
r
>
</
T
head
>
<
T
b
ody
display=
{
hasHorizontalScroll
?
'
table
'
:
'
table-row-group
'
}
w=
"100%"
>
</
T
ableRow
>
</
T
ableHeaderSticky
>
<
T
ableB
ody
display=
{
hasHorizontalScroll
?
'
table
'
:
'
table-row-group
'
}
w=
"100%"
>
{
data
.
items
.
map
((
item
)
=>
(
<
T
r
key=
{
item
.
id
}
>
<
T
ableRow
key=
{
item
.
id
}
>
{
keys
.
map
((
keyName
,
index
)
=>
(
<
T
d
key=
{
keyName
}
backgroundColor=
{
keyBgColor
}
{
...
tdStyles
}
>
<
T
ableCell
key=
{
keyName
}
backgroundColor=
{
{
_light
:
'
blackAlpha.50
'
,
_dark
:
'
whiteAlpha.50
'
}
}
{
...
tdStyles
}
>
{
index
===
0
?
(
<
Link
Internal
<
Link
onClick=
{
onRecordClick
}
data
-
id=
{
item
.
id
}
fontWeight=
{
700
}
href=
{
route
({
pathname
:
'
/address/[hash]
'
,
query
:
{
hash
,
tab
:
'
mud
'
,
table_id
:
data
.
table
.
table_id
,
record_id
:
item
.
id
}
})
}
display=
"inline"
>
{
getValueString
(
item
.
decoded
[
keyName
])
}
</
Link
Internal
>
</
Link
>
)
:
getValueString
(
item
.
decoded
[
keyName
])
}
<
CopyToClipboard
text=
{
item
.
decoded
[
keyName
]
}
/>
</
T
d
>
<
CopyToClipboard
text=
{
String
(
item
.
decoded
[
keyName
])
}
/>
</
T
ableCell
>
))
}
{
values
.
map
((
valName
)
=>
<
T
d
key=
{
valName
}
{
...
tdStyles
}
>
{
getValueString
(
item
.
decoded
[
valName
])
}
</
Td
>)
}
{
hasCut
&&
!
isOpened
&&
<
T
d
width=
{
`${ CUT_COL_WIDTH }px `
}
></
Td
>
}
<
T
d
{
...
tdStyles
}
color=
"text_secondary"
w=
{
`${ colW }px`
}
>
{
dayjs
(
item
.
timestamp
).
format
(
'
lll
'
)
}
</
Td
>
{
hasCut
&&
isOpened
&&
<
T
d
width=
{
`${ CUT_COL_WIDTH }px `
}
></
Td
>
}
</
T
r
>
<
T
ableCell
key=
{
valName
}
{
...
tdStyles
}
>
{
getValueString
(
item
.
decoded
[
valName
])
}
</
TableCell
>)
}
{
hasCut
&&
!
isOpened
&&
<
T
ableCell
width=
{
`${ CUT_COL_WIDTH }px `
}
></
TableCell
>
}
<
T
ableCell
{
...
tdStyles
}
color=
"text.secondary"
w=
{
`${ colW }px`
}
>
{
dayjs
(
item
.
timestamp
).
format
(
'
lll
'
)
}
</
TableCell
>
{
hasCut
&&
isOpened
&&
<
T
ableCell
width=
{
`${ CUT_COL_WIDTH }px `
}
></
TableCell
>
}
</
T
ableRow
>
))
}
</
T
b
ody
>
</
Table
>
</
T
ableB
ody
>
</
Table
Root
>
</
Box
>
);
};
...
...
ui/address/mud/AddressMudTable.tsx
View file @
e4a5483f
import
{
Box
,
HStack
,
Tag
,
TagCloseButton
,
chakra
,
useBoolean
}
from
'
@chakra-ui/react
'
;
import
{
Box
,
HStack
,
chakra
}
from
'
@chakra-ui/react
'
;
import
{
useRouter
}
from
'
next/router
'
;
import
React
from
'
react
'
;
...
...
@@ -7,6 +7,7 @@ import type { AddressMudRecordsFilter, AddressMudRecordsSorting } from 'types/ap
import
useIsMobile
from
'
lib/hooks/useIsMobile
'
;
import
{
apos
,
nbsp
}
from
'
lib/html-entities
'
;
import
getQueryParamString
from
'
lib/router/getQueryParamString
'
;
import
{
Tag
}
from
'
toolkit/chakra/tag
'
;
import
ActionBar
,
{
ACTION_BAR_HEIGHT_DESKTOP
}
from
'
ui/shared/ActionBar
'
;
import
ContentLoader
from
'
ui/shared/ContentLoader
'
;
import
DataListDisplay
from
'
ui/shared/DataListDisplay
'
;
...
...
@@ -36,7 +37,7 @@ const AddressMudTable = ({ scrollRef, tableId, isQueryEnabled = true }: Props) =
React
.
useState
<
AddressMudRecordsSorting
|
undefined
>
(
getSortParamsFromQuery
<
AddressMudRecordsSorting
>
(
router
.
query
,
SORT_SEQUENCE
));
const
[
filters
,
setFilters
]
=
React
.
useState
<
AddressMudRecordsFilter
>
({});
const
isMobile
=
useIsMobile
();
const
[
tableHasHorizontalScroll
,
setTableHasHorizontalScroll
]
=
useBoolean
(
isMobile
);
const
[
tableHasHorizontalScroll
,
setTableHasHorizontalScroll
]
=
React
.
useState
(
isMobile
);
const
hash
=
getQueryParamString
(
router
.
query
.
hash
);
...
...
@@ -52,6 +53,10 @@ const AddressMudTable = ({ scrollRef, tableId, isQueryEnabled = true }: Props) =
},
});
const
handleTableHasHorizontalScroll
=
React
.
useCallback
(()
=>
{
setTableHasHorizontalScroll
((
prev
)
=>
!
prev
);
},
[]);
const
toggleSorting
=
React
.
useCallback
((
val
:
AddressMudRecordsSorting
[
'
sort
'
])
=>
{
const
newSorting
=
{
sort
:
val
,
order
:
getNextOrderValue
(
sorting
?.
sort
===
val
?
sorting
.
order
:
undefined
)
};
setSorting
(
newSorting
);
...
...
@@ -83,15 +88,22 @@ const AddressMudTable = ({ scrollRef, tableId, isQueryEnabled = true }: Props) =
{
Object
.
entries
(
filters
).
map
(([
key
,
value
])
=>
{
const
index
=
key
as
FilterKeys
===
'
filter_key0
'
?
0
:
1
;
return
(
<
Tag
display=
"inline-flex"
key=
{
key
}
maxW=
"360px"
colorScheme=
"blue"
>
<
chakra
.
span
color=
"text_secondary"
>
{
<
Tag
display=
"inline-flex"
key=
{
key
}
maxW=
"360px"
// TODO @tom2drum style filter tags
colorScheme=
"blue"
closable
onClose=
{
onRemoveFilterClick
(
key
as
FilterKeys
)
}
>
<
chakra
.
span
color=
"text.secondary"
>
{
getNameTypeText
(
data
?.
schema
.
key_names
[
index
]
||
''
,
data
?.
schema
.
key_types
[
index
]
||
''
)
}
</
chakra
.
span
>
<
chakra
.
span
color=
"text"
overflow=
"hidden"
textOverflow=
"ellipsis"
whiteSpace=
"nowrap"
>
{
nbsp
}
{
value
}
</
chakra
.
span
>
<
TagCloseButton
onClick=
{
onRemoveFilterClick
(
key
as
FilterKeys
)
}
/>
</
Tag
>
);
})
}
...
...
@@ -126,7 +138,7 @@ const AddressMudTable = ({ scrollRef, tableId, isQueryEnabled = true }: Props) =
toggleSorting=
{
toggleSorting
}
setFilters=
{
setFilters
}
filters=
{
filters
}
toggleTableHasHorizontalScroll=
{
setTableHasHorizontalScroll
.
toggle
}
toggleTableHasHorizontalScroll=
{
handleTableHasHorizontalScroll
}
scrollRef=
{
scrollRef
}
hash=
{
hash
}
/>
...
...
@@ -146,17 +158,18 @@ const AddressMudTable = ({ scrollRef, tableId, isQueryEnabled = true }: Props) =
)
}
<
DataListDisplay
isError=
{
isError
}
items
=
{
data
?.
items
}
items
Num=
{
data
?.
items
.
length
}
emptyText=
{
emptyText
}
filterProps=
{
{
emptyFilteredText
:
`Couldn${ apos }t find records that match your filter query.`
,
hasActiveFilters
:
Object
.
values
(
filters
).
some
(
Boolean
),
}
}
content=
{
content
}
actionBar=
{
actionBar
}
showActionBarIfEmpty=
{
!
isMobile
}
mt=
{
data
?.
items
.
length
?
0
:
2
}
/>
>
{
content
}
</
DataListDisplay
>
</>
);
};
...
...
ui/address/mud/AddressMudTables.tsx
View file @
e4a5483f
import
{
Hide
,
Show
}
from
'
@chakra-ui/react
'
;
import
{
Box
}
from
'
@chakra-ui/react
'
;
import
{
useRouter
}
from
'
next/router
'
;
import
React
from
'
react
'
;
...
...
@@ -50,11 +50,11 @@ const AddressMudTables = ({ scrollRef, isQueryEnabled = true }: Props) => {
<
FilterInput
w=
{
{
base
:
'
100%
'
,
lg
:
'
360px
'
}
}
minW=
{
{
base
:
'
auto
'
,
lg
:
'
250px
'
}
}
size=
"
xs
"
size=
"
sm
"
onChange=
{
setSearchTerm
}
placeholder=
"Search by name, namespace or table ID..."
initialValue=
{
searchTerm
}
isL
oading=
{
isInitialLoading
}
l
oading=
{
isInitialLoading
}
/>
);
...
...
@@ -67,7 +67,7 @@ const AddressMudTables = ({ scrollRef, isQueryEnabled = true }: Props) => {
const
content
=
data
?.
items
?
(
<>
<
Hide
below=
"lg"
ssr=
{
false
}
>
<
Box
hideBelow=
"lg"
>
<
AddressMudTablesTable
items=
{
data
.
items
}
isLoading=
{
isPlaceholderData
}
...
...
@@ -75,8 +75,8 @@ const AddressMudTables = ({ scrollRef, isQueryEnabled = true }: Props) => {
scrollRef=
{
scrollRef
}
hash=
{
hash
}
/>
</
Hide
>
<
Show
below=
"lg"
ssr=
{
false
}
>
</
Box
>
<
Box
hideFrom=
"lg"
>
{
data
.
items
.
map
((
item
,
index
)
=>
(
<
AddressMudTablesListItem
key=
{
item
.
table
.
table_id
+
(
isPlaceholderData
?
String
(
index
)
:
''
)
}
...
...
@@ -85,22 +85,23 @@ const AddressMudTables = ({ scrollRef, isQueryEnabled = true }: Props) => {
hash=
{
hash
}
/>
))
}
</
Show
>
</
Box
>
</>
)
:
null
;
return
(
<
DataListDisplay
isError=
{
isError
}
items
=
{
data
?.
items
}
items
Num=
{
data
?.
items
?.
length
}
emptyText=
"There are no tables for this address."
filterProps=
{
{
emptyFilteredText
:
`Couldn${ apos }t find tables that match your filter query.`
,
hasActiveFilters
:
Boolean
(
searchTerm
),
}
}
content=
{
content
}
actionBar=
{
actionBar
}
/>
>
{
content
}
</
DataListDisplay
>
);
};
...
...
ui/address/mud/AddressMudTablesListItem.tsx
View file @
e4a5483f
import
{
Divider
,
Text
,
useBoolean
,
Flex
,
Link
,
VStack
,
chakra
,
Box
,
Grid
,
GridItem
}
from
'
@chakra-ui/react
'
;
import
{
Text
,
Flex
,
VStack
,
chakra
,
Box
,
Grid
,
GridItem
,
Separator
}
from
'
@chakra-ui/react
'
;
import
{
useRouter
}
from
'
next/router
'
;
import
React
from
'
react
'
;
...
...
@@ -6,11 +6,11 @@ import type { AddressMudTableItem } from 'types/api/address';
import
{
route
}
from
'
nextjs-routes
'
;
import
Skeleton
from
'
ui/shared/chakra/Skeleton
'
;
import
Tag
from
'
ui/shared/chakra/Tag
'
;
import
{
Badge
}
from
'
toolkit/chakra/badge
'
;
import
{
Link
}
from
'
toolkit/chakra/link
'
;
import
{
Skeleton
}
from
'
toolkit/chakra/skeleton
'
;
import
HashStringShorten
from
'
ui/shared/HashStringShorten
'
;
import
IconSvg
from
'
ui/shared/IconSvg
'
;
import
LinkInternal
from
'
ui/shared/links/LinkInternal
'
;
import
ListItemMobile
from
'
ui/shared/ListItemMobile/ListItemMobile
'
;
type
Props
=
{
...
...
@@ -21,10 +21,14 @@ type Props = {
};
const
AddressMudTablesListItem
=
({
item
,
isLoading
,
scrollRef
,
hash
}:
Props
)
=>
{
const
[
isOpened
,
setIsOpened
]
=
useBoolean
(
false
);
const
[
isOpened
,
setIsOpened
]
=
React
.
useState
(
false
);
const
router
=
useRouter
();
const
handleIconClick
=
React
.
useCallback
(()
=>
{
setIsOpened
((
prev
)
=>
!
prev
);
},
[]);
const
onTableClick
=
React
.
useCallback
((
e
:
React
.
MouseEvent
)
=>
{
if
(
e
.
metaKey
||
e
.
ctrlKey
)
{
// Allow opening in a new tab/window with right-click or ctrl/cmd+click
...
...
@@ -48,14 +52,14 @@ const AddressMudTablesListItem = ({ item, isLoading, scrollRef, hash }: Props) =
return
(
<
ListItemMobile
rowGap=
{
3
}
fontSize=
"sm"
py=
{
3
}
>
<
Flex
w=
"100%"
>
<
Skeleton
isLoaded=
{
!
isLoading
}
>
<
Skeleton
loading=
{
isLoading
}
>
<
Link
display=
"block"
>
<
IconSvg
name=
"arrows/east-mini"
transform=
{
isOpened
?
'
rotate(270deg)
'
:
'
rotate(180deg)
'
}
boxSize=
{
6
}
cursor=
"pointer"
onClick=
{
setIsOpened
.
toggle
}
onClick=
{
handleIconClick
}
transitionDuration=
"faster"
aria
-
label=
"View schema"
/>
...
...
@@ -63,21 +67,21 @@ const AddressMudTablesListItem = ({ item, isLoading, scrollRef, hash }: Props) =
</
Skeleton
>
<
Box
flexGrow=
"1"
>
<
Flex
justifyContent=
"space-between"
height=
{
6
}
alignItems=
"center"
mb=
{
3
}
>
<
Skeleton
isLoaded=
{
!
isLoading
}
>
<
Link
Internal
<
Skeleton
loading=
{
isLoading
}
>
<
Link
onClick=
{
onTableClick
}
data
-
id=
{
item
.
table
.
table_id
}
fontWeight=
{
500
}
href=
{
route
({
pathname
:
'
/address/[hash]
'
,
query
:
{
hash
,
tab
:
'
mud
'
,
table_id
:
item
.
table
.
table_id
}
})
}
>
{
item
.
table
.
table_full_name
}
</
Link
Internal
>
</
Link
>
</
Skeleton
>
<
Skeleton
isLoaded=
{
!
isLoading
}
color=
"text_
secondary"
>
<
Skeleton
loading=
{
isLoading
}
color=
"text.
secondary"
>
{
item
.
table
.
table_type
}
</
Skeleton
>
</
Flex
>
<
Skeleton
isLoaded=
{
!
isLoading
}
color=
"text_
secondary"
>
<
Skeleton
loading=
{
isLoading
}
color=
"text.
secondary"
>
<
HashStringShorten
hash=
{
item
.
table
.
table_id
}
type=
"long"
/>
</
Skeleton
>
</
Box
>
...
...
@@ -90,14 +94,14 @@ const AddressMudTablesListItem = ({ item, isLoading, scrollRef, hash }: Props) =
<
Text
lineHeight=
"24px"
>
Key
</
Text
>
<
VStack
gap=
{
1
}
alignItems=
"start"
>
{
item
.
schema
.
key_names
.
map
((
name
,
index
)
=>
(
<
Tag
key=
{
name
}
>
<
Badge
key=
{
name
}
>
<
chakra
.
span
fontWeight=
{
700
}
>
{
item
.
schema
.
key_types
[
index
]
}
</
chakra
.
span
>
{
name
}
</
Tag
>
</
Badge
>
))
}
</
VStack
>
</>
)
}
<
GridItem
colSpan=
{
2
}
><
Divide
r
/></
GridItem
>
<
GridItem
colSpan=
{
2
}
><
Separato
r
/></
GridItem
>
<
Text
lineHeight=
"24px"
>
Value
</
Text
>
<
VStack
gap=
{
1
}
alignItems=
"start"
>
{
item
.
schema
.
value_names
.
map
((
name
,
index
)
=>
(
...
...
ui/address/mud/AddressMudTablesTable.tsx
View file @
e4a5483f
import
{
Table
,
Tbody
,
Th
,
Tr
}
from
'
@chakra-ui/react
'
;
import
React
from
'
react
'
;
import
type
{
AddressMudTables
}
from
'
types/api/address
'
;
import
{
default
as
Thead
}
from
'
ui/shared/TheadSticky
'
;
import
{
TableBody
,
TableColumnHeader
,
TableHeaderSticky
,
TableRoot
,
TableRow
}
from
'
toolkit/chakra/table
'
;
import
AddressMudTablesTableItem
from
'
./AddressMudTablesTableItem
'
;
...
...
@@ -18,16 +17,16 @@ type Props = {
//sorry for the naming
const
AddressMudTablesTable
=
({
items
,
isLoading
,
top
,
scrollRef
,
hash
}:
Props
)
=>
{
return
(
<
Table
style=
{
{
tableLayout
:
'
auto
'
}
}
>
<
T
head
top=
{
top
}
>
<
T
r
>
<
T
h
width=
"24px"
></
Th
>
<
T
h
>
Full name
</
Th
>
<
T
h
>
Table ID
</
Th
>
<
T
h
>
Type
</
Th
>
</
T
r
>
</
T
head
>
<
T
b
ody
>
<
Table
Root
style=
{
{
tableLayout
:
'
auto
'
}
}
>
<
T
ableHeaderSticky
top=
{
top
}
>
<
T
ableRow
>
<
T
ableColumnHeader
width=
"24px"
></
TableColumnHeader
>
<
T
ableColumnHeader
>
Full name
</
TableColumnHeader
>
<
T
ableColumnHeader
>
Table ID
</
TableColumnHeader
>
<
T
ableColumnHeader
>
Type
</
TableColumnHeader
>
</
T
ableRow
>
</
T
ableHeaderSticky
>
<
T
ableB
ody
>
{
items
.
map
((
item
,
index
)
=>
(
<
AddressMudTablesTableItem
key=
{
item
.
table
.
table_id
+
(
isLoading
?
String
(
index
)
:
''
)
}
...
...
@@ -37,8 +36,8 @@ const AddressMudTablesTable = ({ items, isLoading, top, scrollRef, hash }: Props
hash=
{
hash
}
/>
))
}
</
T
b
ody
>
</
Table
>
</
T
ableB
ody
>
</
Table
Root
>
);
};
...
...
ui/address/mud/AddressMudTablesTableItem.tsx
View file @
e4a5483f
import
{
T
d
,
Tr
,
Text
,
useBoolean
,
Link
,
Table
,
VStack
,
chakra
}
from
'
@chakra-ui/react
'
;
import
{
T
ext
,
VStack
,
chakra
}
from
'
@chakra-ui/react
'
;
import
{
useRouter
}
from
'
next/router
'
;
import
React
from
'
react
'
;
...
...
@@ -6,10 +6,11 @@ import type { AddressMudTableItem } from 'types/api/address';
import
{
route
}
from
'
nextjs-routes
'
;
import
Skeleton
from
'
ui/shared/chakra/Skeleton
'
;
import
Tag
from
'
ui/shared/chakra/Tag
'
;
import
{
Badge
}
from
'
toolkit/chakra/badge
'
;
import
{
Link
}
from
'
toolkit/chakra/link
'
;
import
{
Skeleton
}
from
'
toolkit/chakra/skeleton
'
;
import
{
TableBody
,
TableCell
,
TableRoot
,
TableRow
}
from
'
toolkit/chakra/table
'
;
import
IconSvg
from
'
ui/shared/IconSvg
'
;
import
LinkInternal
from
'
ui/shared/links/LinkInternal
'
;
type
Props
=
{
item
:
AddressMudTableItem
;
...
...
@@ -19,10 +20,14 @@ type Props = {
};
const
AddressMudTablesTableItem
=
({
item
,
isLoading
,
scrollRef
,
hash
}:
Props
)
=>
{
const
[
isOpened
,
setIsOpened
]
=
useBoolean
(
false
);
const
[
isOpened
,
setIsOpened
]
=
React
.
useState
(
false
);
const
router
=
useRouter
();
const
handleIconClick
=
React
.
useCallback
(()
=>
{
setIsOpened
((
prev
)
=>
!
prev
);
},
[]);
const
onTableClick
=
React
.
useCallback
((
e
:
React
.
MouseEvent
)
=>
{
if
(
e
.
metaKey
||
e
.
ctrlKey
)
{
// Allow opening in a new tab/window with right-click or ctrl/cmd+click
...
...
@@ -44,67 +49,68 @@ const AddressMudTablesTableItem = ({ item, isLoading, scrollRef, hash }: Props)
return
(
<>
<
T
r
borderBottomStyle=
{
isOpened
?
'
hidden
'
:
'
unset
'
}
>
<
T
d
verticalAlign=
"middle"
>
<
Skeleton
isLoaded=
{
!
isLoading
}
>
<
T
ableRow
borderBottomStyle=
{
isOpened
?
'
hidden
'
:
'
unset
'
}
>
<
T
ableCell
verticalAlign=
"middle"
>
<
Skeleton
loading=
{
isLoading
}
>
<
Link
display=
"block"
>
<
IconSvg
name=
"arrows/east-mini"
transform=
{
isOpened
?
'
rotate(270deg)
'
:
'
rotate(180deg)
'
}
boxSize=
{
6
}
cursor=
"pointer"
onClick=
{
setIsOpened
.
toggle
}
onClick=
{
handleIconClick
}
transitionDuration=
"faster"
aria
-
label=
"View schema"
/>
</
Link
>
</
Skeleton
>
</
T
d
>
<
T
d
verticalAlign=
"middle"
>
<
Skeleton
isLoaded=
{
!
isLoading
}
>
<
Link
Internal
</
T
ableCell
>
<
T
ableCell
verticalAlign=
"middle"
>
<
Skeleton
loading=
{
isLoading
}
>
<
Link
href=
{
route
({
pathname
:
'
/address/[hash]
'
,
query
:
{
hash
,
tab
:
'
mud
'
,
table_id
:
item
.
table
.
table_id
}
})
}
data
-
id=
{
item
.
table
.
table_id
}
onClick=
{
onTableClick
}
fontWeight=
{
700
}
>
{
item
.
table
.
table_full_name
}
</
Link
Internal
>
</
Link
>
</
Skeleton
>
</
T
d
>
<
T
d
verticalAlign=
"middle"
>
<
Skeleton
isLoaded=
{
!
isLoading
}
>
</
T
ableCell
>
<
T
ableCell
verticalAlign=
"middle"
>
<
Skeleton
loading=
{
isLoading
}
>
{
item
.
table
.
table_id
}
</
Skeleton
>
</
T
d
>
<
T
d
verticalAlign=
"middle"
>
<
Skeleton
isLoaded=
{
!
isLoading
}
>
</
T
ableCell
>
<
T
ableCell
verticalAlign=
"middle"
>
<
Skeleton
loading=
{
isLoading
}
>
{
item
.
table
.
table_type
}
</
Skeleton
>
</
T
d
>
</
T
r
>
</
T
ableCell
>
</
T
ableRow
>
{
isOpened
&&
(
<
Tr
>
<
Td
pt=
{
0
}
></
Td
>
<
Td
colSpan=
{
3
}
pt=
{
0
}
>
<
Table
>
<
TableRow
>
<
TableCell
pt=
{
0
}
></
TableCell
>
<
TableCell
colSpan=
{
3
}
pt=
{
0
}
>
<
TableRoot
>
<
TableBody
>
{
Boolean
(
item
.
schema
.
key_names
.
length
)
&&
(
<
Tr
>
<
Td
width=
"80px"
fontSize=
"sm"
fontWeight=
{
600
}
py=
{
2
}
pl=
{
0
}
verticalAlign=
"middle"
>
Key
</
Td
>
<
Td
py=
{
2
}
>
<
TableRow
>
<
TableCell
width=
"80px"
fontSize=
"sm"
fontWeight=
{
600
}
py=
{
2
}
pl=
{
0
}
verticalAlign=
"middle"
>
Key
</
TableCell
>
<
TableCell
py=
{
2
}
>
<
VStack
gap=
{
1
}
alignItems=
"start"
>
{
item
.
schema
.
key_names
.
map
((
name
,
index
)
=>
(
<
Tag
key=
{
name
}
>
<
Badge
key=
{
name
}
>
<
chakra
.
span
fontWeight=
{
700
}
>
{
item
.
schema
.
key_types
[
index
]
}
</
chakra
.
span
>
{
name
}
</
Tag
>
</
Badge
>
))
}
</
VStack
>
</
Td
>
</
Tr
>
</
TableCell
>
</
TableRow
>
)
}
<
Tr
borderBottomStyle=
"hidden"
>
<
Td
width=
"80px"
fontSize=
"sm"
fontWeight=
{
600
}
py=
{
2
}
pl=
{
0
}
>
Value
</
Td
>
<
Td
fontSize=
"sm"
py=
{
2
}
>
<
TableRow
borderBottomStyle=
"hidden"
>
<
TableCell
width=
"80px"
fontSize=
"sm"
fontWeight=
{
600
}
py=
{
2
}
pl=
{
0
}
>
Value
</
TableCell
>
<
TableCell
fontSize=
"sm"
py=
{
2
}
>
<
VStack
gap=
{
1
}
alignItems=
"start"
>
{
item
.
schema
.
value_names
.
map
((
name
,
index
)
=>
(
<
Text
key=
{
name
}
>
...
...
@@ -112,11 +118,12 @@ const AddressMudTablesTableItem = ({ item, isLoading, scrollRef, hash }: Props)
</
Text
>
))
}
</
VStack
>
</
Td
>
</
Tr
>
</
Table
>
</
Td
>
</
Tr
>
</
TableCell
>
</
TableRow
>
</
TableBody
>
</
TableRoot
>
</
TableCell
>
</
TableRow
>
)
}
</>
);
...
...
ui/mudWorlds/MudWorldsListItem.tsx
View file @
e4a5483f
...
...
@@ -6,7 +6,7 @@ import type { MudWorldItem } from 'types/api/mudWorlds';
import
config
from
'
configs/app
'
;
import
{
currencyUnits
}
from
'
lib/units
'
;
import
Skeleton
from
'
ui/shared/chakra/S
keleton
'
;
import
{
Skeleton
}
from
'
toolkit/chakra/s
keleton
'
;
import
AddressEntity
from
'
ui/shared/entities/address/AddressEntity
'
;
import
ListItemMobile
from
'
ui/shared/ListItemMobile/ListItemMobile
'
;
...
...
@@ -31,15 +31,15 @@ const MudWorldsListItem = ({
mr=
{
2
}
truncation=
"constant_long"
/>
<
HStack
spacing
=
{
3
}
maxW=
"100%"
alignItems=
"flex-start"
>
<
Skeleton
isLoaded=
{
!
isLoading
}
fontSize=
"sm"
fontWeight=
{
500
}
flexShrink=
{
0
}
>
{
`Balance ${ currencyUnits.ether }`
}
</
Skeleton
>
<
Skeleton
isLoaded=
{
!
isLoading
}
fontSize=
"sm"
color=
"text_secondary"
minW=
"0"
whiteSpace=
"pre-wrap"
>
<
HStack
gap
=
{
3
}
maxW=
"100%"
alignItems=
"flex-start"
>
<
Skeleton
loading=
{
isLoading
}
fontSize=
"sm"
fontWeight=
{
500
}
flexShrink=
{
0
}
>
{
`Balance ${ currencyUnits.ether }`
}
</
Skeleton
>
<
Skeleton
loading=
{
isLoading
}
fontSize=
"sm"
color=
"text_secondary"
minW=
"0"
whiteSpace=
"pre-wrap"
>
<
span
>
{
addressBalance
.
dp
(
8
).
toFormat
()
}
</
span
>
</
Skeleton
>
</
HStack
>
<
HStack
spacing
=
{
3
}
>
<
Skeleton
isLoaded=
{
!
isLoading
}
fontSize=
"sm"
fontWeight=
{
500
}
>
Txn count
</
Skeleton
>
<
Skeleton
isLoaded=
{
!
isLoading
}
fontSize=
"sm"
color=
"text_secondary"
>
<
HStack
gap
=
{
3
}
>
<
Skeleton
loading=
{
isLoading
}
fontSize=
"sm"
fontWeight=
{
500
}
>
Txn count
</
Skeleton
>
<
Skeleton
loading=
{
isLoading
}
fontSize=
"sm"
color=
"text_secondary"
>
<
span
>
{
Number
(
item
.
transaction_count
).
toLocaleString
()
}
</
span
>
</
Skeleton
>
</
HStack
>
...
...
ui/mudWorlds/MudWorldsTable.tsx
View file @
e4a5483f
import
{
Table
,
Tbody
,
Th
,
Tr
}
from
'
@chakra-ui/react
'
;
import
React
from
'
react
'
;
import
type
{
MudWorldItem
}
from
'
types/api/mudWorlds
'
;
import
{
currencyUnits
}
from
'
lib/units
'
;
import
{
default
as
Thead
}
from
'
ui/shared/TheadSticky
'
;
import
{
TableBody
,
TableColumnHeader
,
TableHeaderSticky
,
TableRoot
,
TableRow
}
from
'
toolkit/chakra/table
'
;
import
MudWorldsTableItem
from
'
./MudWorldsTableItem
'
;
...
...
@@ -16,15 +15,15 @@ type Props = {
const
MudWorldsTable
=
({
items
,
top
,
isLoading
}:
Props
)
=>
{
return
(
<
Table
style=
{
{
tableLayout
:
'
auto
'
}
}
>
<
T
head
top=
{
top
}
>
<
T
r
>
<
T
h
>
Address
</
Th
>
<
T
h
isNumeric
>
{
`Balance ${ currencyUnits.ether }`
}
</
Th
>
<
T
h
isNumeric
>
Txn count
</
Th
>
</
T
r
>
</
T
head
>
<
T
b
ody
>
<
Table
Root
style=
{
{
tableLayout
:
'
auto
'
}
}
>
<
T
ableHeaderSticky
top=
{
top
}
>
<
T
ableRow
>
<
T
ableColumnHeader
>
Address
</
TableColumnHeader
>
<
T
ableColumnHeader
isNumeric
>
{
`Balance ${ currencyUnits.ether }`
}
</
TableColumnHeader
>
<
T
ableColumnHeader
isNumeric
>
Txn count
</
TableColumnHeader
>
</
T
ableRow
>
</
T
ableHeaderSticky
>
<
T
ableB
ody
>
{
items
.
map
((
item
,
index
)
=>
(
<
MudWorldsTableItem
key=
{
String
(
item
.
address
.
hash
)
+
(
isLoading
?
index
:
''
)
}
...
...
@@ -32,8 +31,8 @@ const MudWorldsTable = ({ items, top, isLoading }: Props) => {
isLoading=
{
isLoading
}
/>
))
}
</
T
b
ody
>
</
Table
>
</
T
ableB
ody
>
</
Table
Root
>
);
};
...
...
ui/mudWorlds/MudWorldsTableItem.tsx
View file @
e4a5483f
import
{
Text
,
Td
,
Tr
}
from
'
@chakra-ui/react
'
;
import
{
Text
}
from
'
@chakra-ui/react
'
;
import
BigNumber
from
'
bignumber.js
'
;
import
React
from
'
react
'
;
import
type
{
MudWorldItem
}
from
'
types/api/mudWorlds
'
;
import
config
from
'
configs/app
'
;
import
Skeleton
from
'
ui/shared/chakra/Skeleton
'
;
import
{
Skeleton
}
from
'
toolkit/chakra/skeleton
'
;
import
{
TableCell
,
TableRow
}
from
'
toolkit/chakra/table
'
;
import
AddressEntity
from
'
ui/shared/entities/address/AddressEntity
'
;
type
Props
=
{
item
:
MudWorldItem
;
isLoading
?:
boolean
};
...
...
@@ -15,22 +16,22 @@ const MudWorldsTableItem = ({ item, isLoading }: Props) => {
const
addressBalanceChunks
=
addressBalance
.
dp
(
8
).
toFormat
().
split
(
'
.
'
);
return
(
<
T
r
>
<
T
d
verticalAlign=
"middle"
>
<
T
ableRow
>
<
T
ableCell
verticalAlign=
"middle"
>
<
AddressEntity
address=
{
item
.
address
}
isLoading=
{
isLoading
}
fontWeight=
{
700
}
/>
</
T
d
>
<
T
d
isNumeric
>
<
Skeleton
isLoaded=
{
!
isLoading
}
display=
"inline-block"
maxW=
"100%"
>
</
T
ableCell
>
<
T
ableCell
isNumeric
>
<
Skeleton
loading=
{
isLoading
}
display=
"inline-block"
maxW=
"100%"
>
<
Text
lineHeight=
"24px"
as=
"span"
>
{
addressBalanceChunks
[
0
]
+
(
addressBalanceChunks
[
1
]
?
'
.
'
:
''
)
}
</
Text
>
<
Text
lineHeight=
"24px"
variant=
"
secondary"
as=
"span"
>
{
addressBalanceChunks
[
1
]
}
</
Text
>
<
Text
lineHeight=
"24px"
color=
"text.
secondary"
as=
"span"
>
{
addressBalanceChunks
[
1
]
}
</
Text
>
</
Skeleton
>
</
T
d
>
<
T
d
isNumeric
>
<
Skeleton
isLoaded=
{
!
isLoading
}
display=
"inline-block"
lineHeight=
"24px"
>
</
T
ableCell
>
<
T
ableCell
isNumeric
>
<
Skeleton
loading=
{
isLoading
}
display=
"inline-block"
lineHeight=
"24px"
>
{
Number
(
item
.
transaction_count
).
toLocaleString
()
}
</
Skeleton
>
</
T
d
>
</
T
r
>
</
T
ableCell
>
</
T
ableRow
>
);
};
...
...
ui/pages/Address.tsx
View file @
e4a5483f
...
...
@@ -153,12 +153,12 @@ const AddressPageContent = () => {
const tabs: Array<TabItemRegular> = React.useMemo(() => {
return [
//
config.features.mudFramework.isEnabled && mudTablesCountQuery.data && mudTablesCountQuery.data > 0 && {
//
id: 'mud',
//
title: 'MUD',
//
count: mudTablesCountQuery.data,
//
component: <AddressMud scrollRef={ tabsScrollRef } shouldRender={ !isTabsLoading } isQueryEnabled={ areQueriesEnabled }/>,
//
},
config.features.mudFramework.isEnabled && mudTablesCountQuery.data && mudTablesCountQuery.data > 0 && {
id: 'mud',
title: 'MUD',
count: mudTablesCountQuery.data,
component: <AddressMud scrollRef={ tabsScrollRef } shouldRender={ !isTabsLoading } isQueryEnabled={ areQueriesEnabled }/>,
},
{
id: 'txs',
title: 'Transactions',
...
...
ui/pages/MudWorlds.tsx
View file @
e4a5483f
import
{
Hide
,
Show
}
from
'
@chakra-ui/react
'
;
import
{
Box
}
from
'
@chakra-ui/react
'
;
import
React
from
'
react
'
;
import
{
MUD_WORLD
}
from
'
stubs/mud
'
;
...
...
@@ -30,7 +30,7 @@ const MudWorlds = () => {
const
content
=
data
?.
items
?
(
<>
<
Show
below=
"lg"
ssr=
{
false
}
>
<
Box
hideFrom=
"lg"
>
{
data
.
items
.
map
(((
item
,
index
)
=>
(
<
MudWorldsListItem
key=
{
item
.
address
.
hash
+
(
isPlaceholderData
?
String
(
index
)
:
''
)
}
...
...
@@ -38,10 +38,10 @@ const MudWorlds = () => {
isLoading=
{
isPlaceholderData
}
/>
)))
}
</
Show
>
<
Hide
below=
"lg"
ssr=
{
false
}
>
</
Box
>
<
Box
hideBelow=
"lg"
>
<
MudWorldsTable
items=
{
data
.
items
}
top=
{
pagination
.
isVisible
?
ACTION_BAR_HEIGHT_DESKTOP
:
0
}
isLoading=
{
isPlaceholderData
}
/>
</
Hide
>
</
Box
>
</>
)
:
null
;
...
...
@@ -56,11 +56,12 @@ const MudWorlds = () => {
<
PageTitle
title=
"MUD worlds"
withTextAd
/>
<
DataListDisplay
isError=
{
isError
}
items
=
{
data
?.
items
}
items
Num=
{
data
?.
items
.
length
}
emptyText=
"There are no MUD worlds."
content=
{
content
}
actionBar=
{
actionBar
}
/>
>
{
content
}
</
DataListDisplay
>
</>
);
};
...
...
ui/shared/ClearButton.tsx
View file @
e4a5483f
...
...
@@ -21,6 +21,7 @@ const ClearButton = ({ onClick, isDisabled, isVisible = true, className }: Props
size=
"sm"
onClick=
{
onClick
}
opacity=
{
isVisible
?
1
:
0
}
visibility=
{
isVisible
?
'
visible
'
:
'
hidden
'
}
>
<
IconSvg
name=
"status/error"
...
...
ui/shared/filters/TableColumnFilter.tsx
View file @
e4a5483f
...
...
@@ -2,11 +2,13 @@ import {
chakra
,
Flex
,
Text
,
Link
,
Button
,
}
from
'
@chakra-ui/react
'
;
import
React
from
'
react
'
;
import
{
Button
}
from
'
toolkit/chakra/button
'
;
import
{
Link
}
from
'
toolkit/chakra/link
'
;
import
{
PopoverCloseTriggerWrapper
}
from
'
toolkit/chakra/popover
'
;
type
Props
=
{
title
:
string
;
isFilled
?:
boolean
;
...
...
@@ -14,19 +16,17 @@ type Props = {
hasReset
?:
boolean
;
onFilter
:
()
=>
void
;
onReset
?:
()
=>
void
;
onClose
?:
()
=>
void
;
children
:
React
.
ReactNode
;
};
const
TableColumnFilter
=
({
title
,
isFilled
,
isTouched
,
hasReset
,
onFilter
,
onReset
,
onClose
,
children
}:
Props
)
=>
{
const
TableColumnFilter
=
({
title
,
isFilled
,
isTouched
,
hasReset
,
onFilter
,
onReset
,
children
}:
Props
)
=>
{
const
onFilterClick
=
React
.
useCallback
(()
=>
{
onClose
&&
onClose
();
onFilter
();
},
[
on
Close
,
on
Filter
]);
},
[
onFilter
]);
return
(
<>
<
Flex
alignItems=
"center"
justifyContent=
"space-between"
>
<
Text
color=
"text
_
secondary"
fontWeight=
"600"
>
{
title
}
</
Text
>
<
Text
color=
"text
.
secondary"
fontWeight=
"600"
>
{
title
}
</
Text
>
{
hasReset
&&
(
<
Link
onClick=
{
onReset
}
...
...
@@ -41,13 +41,15 @@ const TableColumnFilter = ({ title, isFilled, isTouched, hasReset, onFilter, onR
)
}
</
Flex
>
{
children
}
<
PopoverCloseTriggerWrapper
>
<
Button
isD
isabled=
{
!
isTouched
}
d
isabled=
{
!
isTouched
}
onClick=
{
onFilterClick
}
w=
"fit-content"
>
Filter
</
Button
>
</
PopoverCloseTriggerWrapper
>
</>
);
};
...
...
ui/shared/filters/TableColumnFilterWrapper.tsx
View file @
e4a5483f
import
{
PopoverTrigger
,
PopoverContent
,
PopoverBody
,
useDisclosure
,
chakra
,
Portal
,
Button
,
}
from
'
@chakra-ui/react
'
;
import
{
chakra
}
from
'
@chakra-ui/react
'
;
import
React
from
'
react
'
;
import
Popover
from
'
ui/shared/chakra/Popover
'
;
import
{
Button
}
from
'
toolkit/chakra/button
'
;
import
{
PopoverBody
,
PopoverContent
,
PopoverRoot
,
PopoverTrigger
}
from
'
toolkit/chakra/popover
'
;
import
IconSvg
from
'
ui/shared/IconSvg
'
;
interface
Props
{
columnName
:
string
;
isActive
?:
boolean
;
isLoading
?:
boolean
;
selected
?:
boolean
;
className
?:
string
;
children
:
React
.
ReactNode
;
value
?:
string
;
}
const
TableColumnFilterWrapper
=
({
columnName
,
isActive
,
className
,
children
,
isLoading
,
value
}:
Props
)
=>
{
const
{
isOpen
,
onToggle
,
onClose
}
=
useDisclosure
();
const
content
=
React
.
Children
.
only
(
children
)
as
React
.
ReactElement
&
{
ref
?:
React
.
Ref
<
React
.
ReactNode
>
;
};
const
modifiedContent
=
React
.
cloneElement
(
content
,
{
onClose
},
);
const
TableColumnFilterWrapper
=
({
columnName
,
className
,
children
,
isLoading
,
selected
,
value
}:
Props
)
=>
{
return
(
<
Popover
isOpen=
{
isOpen
}
onClose=
{
onClose
}
placement=
"bottom-start"
isLazy
lazyBehavior=
"unmount"
>
<
Popover
Root
>
<
PopoverTrigger
>
<
Button
onClick=
{
onToggle
}
aria
-
label=
{
`filter by ${ columnName }`
}
variant=
"ghost"
variant=
"dropdown"
borderWidth=
"0"
h=
"20px"
isActive=
{
Boolean
(
value
)
||
isActive
}
isDisabled=
{
isLoading
}
minW=
"auto"
disabled=
{
isLoading
}
selected=
{
selected
}
borderRadius=
"4px"
color=
"text_secondary"
fontSize=
"sm"
size=
"sm"
fontWeight=
{
500
}
leftIcon=
{
<
IconSvg
name=
"filter"
w=
"19px"
h=
"19px"
/>
}
padding=
{
0
}
sx
=
{
{
css
=
{
{
'
span:only-child
'
:
{
mx
:
0
,
},
...
...
@@ -58,17 +39,16 @@ const TableColumnFilterWrapper = ({ columnName, isActive, className, children, i
},
}
}
>
<
IconSvg
name=
"filter"
w=
"19px"
h=
"19px"
/>
{
Boolean
(
value
)
&&
<
chakra
.
span
>
{
value
}
</
chakra
.
span
>
}
</
Button
>
</
PopoverTrigger
>
<
Portal
>
<
PopoverContent
className=
{
className
}
>
<
PopoverBody
px=
{
4
}
py=
{
6
}
display=
"flex"
flexDir=
"column"
rowGap=
{
3
}
>
{
modifiedContent
}
<
PopoverBody
display=
"flex"
flexDir=
"column"
rowGap=
{
3
}
>
{
children
}
</
PopoverBody
>
</
PopoverContent
>
</
Portal
>
</
Popover
>
</
PopoverRoot
>
);
};
...
...
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