Skip to content
←
05 / Selected Work — Case StudyPersonal Project

A dashboard for multi-store commerce.

I built NyxBoard around the orders queue: filter across stores, inspect an order without losing your place, and see a status change reflected across the dashboard.

Year
2026
Type
Personal Project
Core Stack
React + TypeScript
Focus
Operational UI & State Design
Primary Interface Proof // Desktop OperationsOrders Workspace // Desktop Table View
NyxBoard Orders workspace table view showing faceted status tabs, debounced search bar, and sortable table columns
01Pending

Awaiting an operations decision before fulfillment proceeds.

02Unshipped

Order is active and awaiting fulfillment work.

03Shipped

Dispatched with tracking assigned; shipped count increments and fulfillment rate rises.

04Canceled

Marked canceled and excluded from active revenue calculations.

01 / Problem

Keeping the dashboard from becoming a mess

NyxBoard has a lot going on: filters, sorting, order details, status updates, and multiple stores. The problem was making all of that usable without cramming everything into the screen.

So I kept most actions in the same workspace. You can filter orders, open one, check the details, update its status, and keep going without jumping between pages or losing where you were.

02 / Scan

The Operations Overview

The overview and queue use the same saved order state. Cancelled orders drop out of active revenue.

Primary Interface Proof // Desktop OperationsOperations Overview // Desktop View
NyxBoard Operations Overview desktop interface showing KPI summary cards, sales volume trajectory, and status distribution
01 / Store Scope

Store Filtering

Switching stores scopes the dashboard without breaking the comparison between them.

02 / Metric Hierarchy

Fulfillment Health

The top row keeps the numbers that need attention first: revenue, total orders, pending review, queue size, and fulfillment rate.

03 / Visual Trajectory

Volume & Distribution

Shipping an order changes the status split, while the 14-day revenue trend stays the same.

04 / State Sync

Synchronized Metrics

The overview and queue use the same saved order state. Cancelled orders drop out of active revenue.

03 / Filter

The Orders Workspace

Search, store, status, sort, and page state live in the URL. Refreshing or sharing the workspace keeps the same view instead of sending you back to the full orders list.

?status=unshipped&store=all&sort=date
Filter State Flow
04 / Inspect & Act

Opening a separate order page would throw away the exact filter and scroll position that got you there. NyxBoard keeps the list in place and opens the order in a drawer, so review and fulfillment happen without leaving the queue.

01 / 03

Filtered Context

The Unshipped view narrows the list to orders that still need action, while the active filters stay in the URL.

Workflow Progression // 01Filtered Context // Unshipped Queue
Orders workspace filtered to nine Unshipped orders, including ORD-98420.
02 / 03

Inspect in Place

ORD-98420 opens in a drawer while the filtered list stays visible behind it.

Workflow Progression // 02In-Place Review // Slide-Over Drawer
Order ORD-98420 open in a slide-over drawer over the filtered Unshipped list, with Mark as Shipped available.
Order ORD-98420 drawer showing its Unshipped status before fulfillment
03 / 03

Updated State

Marking the order shipped changes its status, adds a generated tracking reference, and updates the fulfillment counts from the same saved demo state.

Workflow Progression // 03Recomputed State // Order Shipped
Order ORD-98420 marked Shipped with a generated carrier and tracking reference; the filtered Unshipped list remains behind the drawer.
Order ORD-98420 drawer showing Shipped status, carrier, and tracking reference
05 / Responsive

Responsive Prioritization

I kept the table on smaller screens instead of replacing every row with cards. Lower-priority columns disappear first, while the information needed to identify and act on an order stays visible.

Column Priority Breakdown

What stays visible as space gets tighter.

Order IDP1 Core

Always visible and remains the primary order trigger.

StoreTier 2

Returns at xl when there is room for store context.

Customer & AccountFolded

Folds into the Order ID cell on compact screens.

Items SummaryTier 2

Returns at 2xl where the table has enough width.

Order DateTier 2

Returns at lg.

Ship BeforeTier 2

Returns at xl.

TotalP1 Core

Always visible.

StatusP1 Core

Always visible.

ActionsTier 2

Explicit action on larger screens; the row opens the order on mobile.

Column Priority BreakdownMobile Orders // Viewport 390px
NyxBoard mobile orders view demonstrating condensed table layout and progressive column prioritization
06 / Engineering

Built Deliberately

Most of the work here is invisible in a screenshot. Filters need to survive refreshes, order changes need to reach every view that depends on them, and the drawer has to return focus to the right place.

Shared State Refresh

01 / Event TriggerUser Action

User triggers “Mark as Shipped” in Drawer

Updates the local demo state with a short inline loading state for action feedback.

02 / Persist & RefreshbumpVersion()

orderService.markAsShipped(id) → version++

Saves the changed order locally and increments the version counter.

03 / Synchronized View UpdatesDependent Views Update
Architecture & State Boundaries

React + Strict TypeScript

Keeps order, filter, and mutation shapes explicit across the app.

URL-Backed Workspace State

Search, store, status, sort, and page state live in the URL and are validated before use.

Shared State & Refresh

After an order changes, OrdersContext refreshes the derived data used by the table, counts, sidebar, and overview.OrdersContext

Service Layer

orderService.ts owns filtering, sorting, pagination, KPI calculations, and local order mutations.orderService.ts

Persistence & Loading

localStorage keeps demo changes between reloads, while routes and charts are loaded only when needed.localStorage

Operational Status TokensText + Color

Status uses both text and color, with contrast checked for every badge.

Shipped Status BehaviorDispatched with tracking assigned; shipped count increments and fulfillment rate rises.
#047857 on #ecfdf5
Status remains readable without colorContrast checked per badge

NyxBoard itself uses a light, high-contrast workspace. The dark ink, violet, and cyan treatment belongs to this case study, not the product UI.

Accessibility Engineering

The order drawer and its confirmation dialog both need a predictable keyboard path.

Trigger→Focus In→Trapped→Escape→Restored
  • Semantic Dialogs & TablesNative table structure and labelled dialog semantics stay intact instead of being rebuilt from generic divs.
  • Keyboard Navigation & Skip LinkOrders can be opened without a mouse, Escape dismisses the active layer, and the app shell includes a skip link.
  • Focus RestorationClosing the drawer returns focus to the order that opened it; closing the confirmation returns focus to its trigger.
  • Reduced MotionDrawer transitions and charts respect prefers-reduced-motion.prefers-reduced-motion
  • Accessible ChartsCharts expose concise text summaries instead of relying only on SVG visuals.
07 / Reflection

What worked

I would keep the queue at the centre of the product. The overview helps spot work, but the table and drawer are where an order is actually reviewed and updated.

If this were production

NyxBoard is still a front-end project. The data is seeded, persistence happens in the browser, and authentication is simulated. A real version would need a proper backend, real permissions, and integrations with the systems behind the interface.

01

Backend API

Move order data and updates out of orderService.ts and into authenticated API endpoints.orderService.ts

02

Server-side data

Handle filtering, sorting, and pagination on the server once the dataset gets too large for the browser.

03

Permissions

Control who can ship, cancel, or export orders instead of giving everyone the same demo access.

04

Real integrations

Replace the generated shipping states with actual carrier or commerce events.