Skip to content

Commit

Permalink
UI polish (#184)
Browse files Browse the repository at this point in the history
* fix execution status handling

* fix breadcrumbs content shift

* cleanup tables

* remove snapshot action from blocks table

* remove execution status from transactions table

* minor table tweaks

* fix transaction name overflow

* rename transaction "name" to "description", add more row spacing to details card

* fix tab label overflow

* simplify middle ellipsis logic

* fix interactions page overflow

* fix interaction templates layout

* fix left tabs spacings

* fix full screen loading

* fix table responsivness
  • Loading branch information
bartolomej authored Aug 28, 2023
1 parent a261c0b commit 6883c0a
Show file tree
Hide file tree
Showing 28 changed files with 95 additions and 209 deletions.
10 changes: 8 additions & 2 deletions backend/src/data-processing/processor.service.ts
Original file line number Diff line number Diff line change
Expand Up @@ -290,7 +290,7 @@ export class ProcessorService implements ProjectContextLifecycle {
transactionId,
TransactionStatus.fromJSON({
errorMessage: newStatus.errorMessage,
grcpStatus: newStatus.statusCode,
grcpStatus: this.reMapGrcpStatus(newStatus.statusCode),
executionStatus: newStatus.status,
})
)
Expand Down Expand Up @@ -856,13 +856,19 @@ export class ProcessorService implements ProjectContextLifecycle {
),
status: TransactionStatus.fromJSON({
errorMessage: flowTransactionStatus.errorMessage,
grcpStatus: flowTransactionStatus.statusCode,
grcpStatus: this.reMapGrcpStatus(flowTransactionStatus.statusCode),
executionStatus: flowTransactionStatus.status,
}),
payer: undefined,
});
}

private reMapGrcpStatus(statusCode: number) {
// Older versions of the emulator use incorrect statusCode values.
// See: https://github.com/onflow/flow-go/issues/4494#issuecomment-1601995168
return [0, 1].includes(statusCode) ? statusCode : 1;
}

private deserializeSignableObjects(signableObjects: FlowSignableObject[]) {
return signableObjects.map((signable) =>
SignableObject.fromJSON({
Expand Down
3 changes: 1 addition & 2 deletions frontend/src/components/breadcrumbs/Breadcrumbs.module.scss
Original file line number Diff line number Diff line change
Expand Up @@ -5,8 +5,7 @@

.root {
display: flex;
height: 50px;
padding: 0 $spacing-base;
padding: $spacing-s $spacing-base;
border-radius: $border-radius-card;
align-items: center;

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@
.column {
display: flex;
flex-direction: column;
row-gap: $spacing-s;
row-gap: $spacing-base;

& > div {
display: flex;
Expand Down
52 changes: 10 additions & 42 deletions frontend/src/components/ellipsis/MiddleEllipsis.tsx
Original file line number Diff line number Diff line change
@@ -1,60 +1,28 @@
import React, { FunctionComponent, useEffect, useRef, useState } from "react";
import React, { FunctionComponent, useRef } from "react";

export type EllipsisProps = {
children: string;
ellipsis?: string;
delimiter?: string;
className?: string;
style?: React.CSSProperties;
};

const MiddleEllipsis: FunctionComponent<EllipsisProps> = ({
children,
ellipsis = "...",
delimiter = "...",
className,
style,
}) => {
const elRef = useRef<HTMLSpanElement>(null);
const [show, setShow] = useState(false);
const [state, setState] = useState(children);

const makeEllipsis = () => {
const offsetWidth = elRef.current ? elRef.current.offsetWidth : 0;
const scrollWidth = elRef.current ? elRef.current.scrollWidth : 0;
if (offsetWidth < scrollWidth) {
const charWidth = Math.ceil(scrollWidth / children.length);
const textHalf = Math.ceil(offsetWidth / charWidth / 2);
const ellipsisHalf = Math.ceil(ellipsis.length / charWidth / 2);
const half = textHalf - ellipsisHalf - 2; // safety 2 :)
const ellipsisText =
children.substr(0, half) +
ellipsis +
children.substring(children.length - half);
setState(ellipsisText);
}
setShow(true);
};

const resize = () => {
setState(children);
// Wait for browser to write DOM updates from setState call (on next event loop)
setTimeout(() => makeEllipsis(), 0);
};

useEffect(() => {
resize();
window.addEventListener("resize", resize);
return () => {
window.removeEventListener("resize", resize);
};
}, [children]);
const pieceLength = 10;
const ellipsisText =
children.substring(0, pieceLength) +
delimiter +
children.substring(children.length - pieceLength, children.length);

return (
<span
ref={elRef}
className={className}
style={{ ...style, opacity: show ? 1 : 0, transition: "0.3s ease" }}
>
{state}
<span ref={elRef} className={className} style={style}>
{ellipsisText}
</span>
);
};
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -10,7 +10,9 @@ type FullScreenLoadingProps = {
const FullScreenLoading: FC<FullScreenLoadingProps> = ({ className }) => {
return (
<div className={classNames(classes.container, className)}>
<Spinner className={classes.logo} size={60} borderWidth={6} />
<div className={classes.logo}>
<Spinner size={60} borderWidth={6} />
</div>
<p className={classes.text}>Loading</p>
</div>
);
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -6,7 +6,6 @@
.root {
display: flex;
align-items: center;
@include fadeInAnimation(0.3s);

border: $gray-50 1px solid;
background: transparent;
Expand Down
7 changes: 4 additions & 3 deletions frontend/src/components/layout/Layout.module.scss
Original file line number Diff line number Diff line change
Expand Up @@ -28,15 +28,16 @@ $side-nav-width: 80px;
}

.body {
height: 100%;
overflow: scroll;
color: $gray-10;
align-items: stretch;
display: flex;
flex-direction: column;
flex: 1;
}

.bodyWithMargin {
margin: $spacing-l;
.bodyWithBorderSpacing {
padding: $spacing-l;
}

.logs {
Expand Down
2 changes: 1 addition & 1 deletion frontend/src/components/layout/Layout.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -42,7 +42,7 @@ const ProjectLayout: FunctionComponent = ({ children }) => {
<Breadcrumbs className={classes.breadcrumbs} />
<div
className={classNames(classes.body, {
[classes.bodyWithMargin]: showMargin,
[classes.bodyWithBorderSpacing]: showMargin,
})}
>
{children}
Expand Down
1 change: 1 addition & 0 deletions frontend/src/components/status/GrcpStatus.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -12,6 +12,7 @@ export type GrcpStatusProps = {

export function GrcpStatus({ status }: GrcpStatusProps): ReactElement {
const { grcpStatus } = status ?? {};
console.log(grcpStatus);
const statusName = FlowUtils.getGrcpStatusName(grcpStatus);
return (
<div className={classes.root}>
Expand Down
2 changes: 2 additions & 0 deletions frontend/src/components/table/Table.module.scss
Original file line number Diff line number Diff line change
Expand Up @@ -16,12 +16,14 @@
padding-bottom: $spacing-base * 0.8;
padding-top: $spacing-base * 0.8;
background: transparentize($gray-80, 0.2);
column-gap: $spacing-base;

& > div {
display: flex;
flex: 1;
width: 100%;
justify-content: flex-start;
align-items: center;
overflow: hidden;
}
}
9 changes: 6 additions & 3 deletions frontend/src/components/tabs/Tabs.module.scss
Original file line number Diff line number Diff line change
Expand Up @@ -10,14 +10,15 @@
.tabWrapper {
display: flex;
align-items: center;
overflow-x: scroll;
@include hiddenScrollbars();
.label {
font-size: $font-size-normal;
font-weight: bold;
color: $color-grey;
margin: 0 $spacing-l;
overflow: hidden;
white-space: nowrap;
text-overflow: ellipsis;
}
.tabButton {
flex: 1;
Expand Down Expand Up @@ -71,7 +72,9 @@
}
}
}
.body {
height: 100%;
.content {
flex: 1;
overflow: scroll;
@include hiddenScrollbars();
}
}
5 changes: 4 additions & 1 deletion frontend/src/components/tabs/Tabs.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -87,7 +87,10 @@ export function Tabs(props: TabsProps): ReactElement {
</button>
)}
</div>
<div className={props.contentClassName} style={{ flex: 1 }}>
<div
className={classNames(props.contentClassName, classes.content)}
style={{ flex: 1 }}
>
{currentTab?.content}
</div>
</div>
Expand Down
11 changes: 0 additions & 11 deletions frontend/src/components/time-ago/TimeAgo.module.scss

This file was deleted.

19 changes: 0 additions & 19 deletions frontend/src/components/time-ago/TimeAgo.tsx

This file was deleted.

62 changes: 3 additions & 59 deletions frontend/src/pages/blocks/main/Main.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -8,31 +8,15 @@ import { useNavigation } from "../../../hooks/use-navigation";
import { createColumnHelper } from "@tanstack/table-core";
import Table from "../../../components/table/Table";
import { Block } from "@flowser/shared";
import {
useGetPollingBlocks,
useGetPollingEmulatorSnapshots,
} from "../../../hooks/use-api";
import { SimpleButton } from "../../../components/buttons/simple-button/SimpleButton";
import { ReactComponent as SnapshotIcon } from "../../../assets/icons/snapshot.svg";
import { useGetPollingBlocks } from "../../../hooks/use-api";
import ReactTimeago from "react-timeago";
import { useProjectActions } from "../../../contexts/project.context";
import { DecoratedPollingEntity } from "contexts/timeout-polling.context";

const columnHelper = createColumnHelper<DecoratedPollingEntity<Block>>();

const Main: FunctionComponent = () => {
const { showNavigationDrawer } = useNavigation();
const { checkoutBlock } = useProjectActions();

const { data: blocks, firstFetch, error } = useGetPollingBlocks();
const { data: emulatorSnapshots } = useGetPollingEmulatorSnapshots();
const snapshotLookupByBlockId = useMemo(
() =>
new Map(
emulatorSnapshots.map((snapshot) => [snapshot.blockId, snapshot])
),
[emulatorSnapshots]
);

useEffect(() => {
showNavigationDrawer(false);
Expand All @@ -41,7 +25,7 @@ const Main: FunctionComponent = () => {
const columns = useMemo(
() => [
columnHelper.accessor("id", {
header: () => <Label variant="medium">ID</Label>,
header: () => <Label variant="medium">IDENTIFIER</Label>,
meta: {
className: classes.blockID,
},
Expand All @@ -62,20 +46,6 @@ const Main: FunctionComponent = () => {
},
cell: (info) => <Value>{info.getValue()}</Value>,
}),
columnHelper.accessor("blockSeals", {
header: () => <Label variant="medium">SEALS COUNT</Label>,
meta: {
className: classes.blockSeals,
},
cell: (info) => <Value>{info.getValue()?.length}</Value>,
}),
columnHelper.accessor("signatures", {
header: () => <Label variant="medium">SIGS COUNT</Label>,
meta: {
className: classes.signatures,
},
cell: (info) => <Value>{info.getValue()?.length}</Value>,
}),
columnHelper.accessor("timestamp", {
header: () => <Label variant="medium">CREATED</Label>,
meta: {
Expand All @@ -87,34 +57,8 @@ const Main: FunctionComponent = () => {
</Value>
),
}),
columnHelper.display({
id: "snapshot",
header: () => <Label variant="medium">SNAPSHOT</Label>,
meta: {
className: classes.snapshot,
},
cell: (info) => {
const block = info.row.original;
const latestBlock = blocks[0];
const isLatestBlock = latestBlock.height === block.height;
const snapshot = snapshotLookupByBlockId.get(block.id);
return (
<Value>
{!isLatestBlock && (
<SimpleButton
style={{ marginRight: 10 }}
onClick={() => checkoutBlock(block.id)}
>
<SnapshotIcon />
</SimpleButton>
)}
{snapshot?.description}
</Value>
);
},
}),
],
[snapshotLookupByBlockId, blocks, checkoutBlock]
[blocks]
);

return (
Expand Down
2 changes: 1 addition & 1 deletion frontend/src/pages/contracts/main/ContractsTable.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ const columns = [
),
}),
columnHelper.accessor("accountAddress", {
header: () => <Label variant="medium">ACCOUNT</Label>,
header: () => <Label variant="medium">DEPLOYED ON</Label>,
cell: (info) => (
<Value>
<AccountLink address={info.getValue()} />
Expand Down
5 changes: 2 additions & 3 deletions frontend/src/pages/events/EventsTable.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,6 @@ import ReactTimeago from "react-timeago";
import classNames from "classnames";
import { DecoratedPollingEntity } from "contexts/timeout-polling.context";
import { Ellipsis } from "../../components/ellipsis/Ellipsis";
import { useNavigation } from "../../hooks/use-navigation";

const subTableColumnHelper = createColumnHelper<ComputedEventData>();
const subTableColumns = [
Expand Down Expand Up @@ -65,7 +64,7 @@ export function EventsTable(props: EventsTableProps): ReactElement {
const columns = useMemo(
() => [
columnHelper.accessor("blockId", {
header: () => <Label variant="medium">BLOCK ID</Label>,
header: () => <Label variant="medium">BLOCK</Label>,
cell: (info) => (
<Value>
<NavLink to={`/blocks/details/${info.getValue()}`}>
Expand All @@ -77,7 +76,7 @@ export function EventsTable(props: EventsTableProps): ReactElement {
),
}),
columnHelper.accessor("transactionId", {
header: () => <Label variant="medium">TX ID</Label>,
header: () => <Label variant="medium">TRANSACTION</Label>,
cell: (info) => (
<Value>
<NavLink to={`/transactions/details/${info.getValue()}`}>
Expand Down
Loading

0 comments on commit 6883c0a

Please sign in to comment.