Skip to content

Commit 8959b0a

Browse files
authored
[dashboard] Update workspaces, settings, and header layout (#3521)
1 parent 4d65ed1 commit 8959b0a

17 files changed

+85
-65
lines changed

components/dashboard/src/Login.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -67,7 +67,7 @@ export function Login() {
6767
</div>
6868
<div className="mx-auto text-center pb-8 space-y-2">
6969
<h1 className="text-3xl">Log in to Gitpod</h1>
70-
<h2 className="uppercase text-sm">ALWAYS READY-TO-CODE</h2>
70+
<h2 className="uppercase text-sm text-gray-400">ALWAYS READY-TO-CODE</h2>
7171
</div>
7272
<div className="flex flex-col space-y-3">
7373
{authProviders.map(ap => {

components/dashboard/src/components/DropDown.tsx

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@ export interface DropDownProps {
1111
}
1212

1313
function Arrow(props: {up: boolean}) {
14-
return <span className="mx-2 border-gray-400" style={{ margin: 2, padding: 3, border: 'solid black', borderWidth: '0 2px 2px 0', display: 'inline-block', transform: `rotate(${props.up ? '-135deg' : '45deg'})`}}></span>
14+
return <span className="mx-2 border-gray-400 group-hover:border-gray-600" style={{ margin: 2, padding: 3, border: 'solid black', borderWidth: '0 2px 2px 0', display: 'inline-block', transform: `rotate(${props.up ? '-135deg' : '45deg'})`}}></span>
1515
}
1616

1717
function DropDown(props: DropDownProps) {
@@ -26,7 +26,7 @@ function DropDown(props: DropDownProps) {
2626
}
2727
}
2828
})
29-
const font = "text-gray-400 text-sm leading-1"
29+
const font = "text-gray-400 text-sm leading-1 group hover:text-gray-600"
3030
return (
3131
<ContextMenu menuEntries={enhancedEntries} width={props.contextMenuWidth}>
3232
<span className={`py-2 cursor-pointer ${font}`}>{props.prefix}{current}<Arrow up={false}/></span>

components/dashboard/src/components/Header.tsx

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -7,10 +7,10 @@ export interface HeaderProps {
77

88
export default function Header(p: HeaderProps) {
99
return <div className="lg:px-28 px-10 border-gray-200">
10-
<div className="flex py-8">
10+
<div className="flex pb-8 pt-6">
1111
<div className="">
12-
<h1 className="">{p.title}</h1>
13-
<h2 className="pt-1">{p.subtitle}</h2>
12+
<h1 className="tracking-tight">{p.title}</h1>
13+
<h2 className="tracking-wide">{p.subtitle}</h2>
1414
</div>
1515
</div>
1616
<Separator />

components/dashboard/src/components/Menu.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -60,7 +60,7 @@ function Menu(props: { left: Entry[], right: Entry[] }) {
6060
{props.right.map(MenuItem)}
6161
</ul>
6262
</nav>
63-
<div className="lg:ml-3 flex items-center justify-start lg:mb-0 mb-4 pointer-cursor m-l-auto rounded-full border-2 border-white hover:border-gray-200 p-0.5">
63+
<div className="lg:ml-3 flex items-center justify-start lg:mb-0 mb-4 pointer-cursor m-l-auto rounded-full border-2 border-white hover:border-gray-200 p-0.5 font-medium">
6464
<ContextMenu menuEntries={[
6565
{
6666
title: (user && User.getPrimaryEmail(user)) || '',

components/dashboard/src/index.css

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@
2929

3030
@layer components {
3131
button {
32-
@apply cursor-pointer px-3 py-1 my-auto bg-green-600 hover:bg-green-700 border-2 border-green-800 text-gray-100 text-sm rounded-md;
32+
@apply cursor-pointer px-4 py-2 my-auto bg-green-600 hover:bg-green-700 border-2 border-green-800 text-gray-100 text-sm rounded-md focus:outline-none focus:ring focus:border-blue-300;
3333
}
3434

3535
input[type=text] {
@@ -44,4 +44,4 @@
4444
@apply bg-gray-100 border-2 border-gray-300 text-gray-400;
4545
}
4646

47-
}
47+
}

components/dashboard/src/settings/Account.tsx

Lines changed: 10 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -12,15 +12,18 @@ export default function Account() {
1212
const close = () => setModal(false);
1313
return <div>
1414
<Modal visible={modal} onClose={close}>
15-
<h3>Do you really want to delete your account?</h3>
16-
<p>This action will remove all the data associated with your account in Gitpod and cannot be reversed.</p>
17-
<div className="flex justify-end pt-6">
15+
<h3 className="pb-2">Delete Account</h3>
16+
<div className="border-t border-b border-gray-200 mt-2 -mx-6 px-6 py-2">
17+
<p className="mt-1 mb-2 text-base">Are you sure you want to delete your account? This action will remove all the data associated with your account in Gitpod and cannot be reversed.</p>
18+
</div>
19+
<div className="flex justify-end mt-6">
1820
<button className="border-red-900 bg-red-500 hover:bg-red-700" onClick={close}>Delete Account</button>
1921
</div>
2022
</Modal>
2123

22-
<SettingsPage title='Account' subtitle='Profile details'>
24+
<SettingsPage title='Account' subtitle='Manage account and git configuration.'>
2325
<h3>Profile</h3>
26+
<p className="text-base text-gray-500 pb-4">The following information will be used to set up git configuration. You can override git author name and email per project by using the default environment variables <span className="text-gitpod-kumquat-dark bg-gitpod-kumquat-light px-1.5 py-1 rounded-md text-sm font-mono">GIT_AUTHOR_NAME</span> and <span className="text-gitpod-kumquat-dark bg-gitpod-kumquat-light px-1.5 py-1 rounded-md text-sm font-mono">GIT_COMMITTER_EMAIL</span>.</p>
2427
<div className="flex flex-col lg:flex-row">
2528
<div>
2629
<div className="mt-4">
@@ -35,14 +38,14 @@ export default function Account() {
3538
<div className="lg:pl-14">
3639
<div className="mt-4">
3740
<h4>Avatar</h4>
38-
<img className="rounded-full w-24 h-24 border-2 border-transparent hover:border-indigo-400"
41+
<img className="rounded-full w-24 h-24"
3942
src={user!.avatarUrl} alt={user!.name} />
4043
</div>
4144
</div>
4245
</div>
4346
<h3 className="mt-12">Delete Account</h3>
44-
<p className="text-sm text-gray-400 pb-4">This action will remove all the data associated with your account in Gitpod.</p>
45-
<button className="border-red-600 text-red-600 bg-white hover:border-red-800 hover:text-red-800" onClick={() => setModal(true)}>Delete Account</button>
47+
<p className="text-base text-gray-500 pb-4">This action will remove all the data associated with your account in Gitpod.</p>
48+
<button className="border-red-600 text-red-600 bg-white hover:border-red-800 hover:text-red-800 font-medium" onClick={() => setModal(true)}>Delete Account</button>
4649
</SettingsPage>
4750
</div>;
4851
}

components/dashboard/src/settings/EnvironmentVariables.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ import { SettingsPage } from "./SettingsPage";
22

33
export default function EnvVars() {
44
return <div>
5-
<SettingsPage title='Environment Variables' subtitle='Configure environment variables for your workspaces'>
5+
<SettingsPage title='Variables' subtitle='Configure environment variables for all workspaces.'>
66
<h3>Environment Variables</h3>
77
</SettingsPage>
88
</div>;

components/dashboard/src/settings/GitIntegrations.tsx

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2,8 +2,8 @@ import { SettingsPage } from "./SettingsPage";
22

33
export default function GitIntegrations() {
44
return <div>
5-
<SettingsPage title='Git Integrations' subtitle='Manage integration with your Git hosters'>
6-
<h3>Git Hoster Access Control</h3>
5+
<SettingsPage title='Integrations' subtitle='Manage permissions for git providers and integrations.'>
6+
<h3>Git Providers</h3>
77
</SettingsPage>
88
</div>;
99
}

components/dashboard/src/settings/Notifications.tsx

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -53,9 +53,9 @@ export default function Notifications() {
5353

5454
function CheckBox(props: {title: string, desc: string, checked: boolean, onChange: () => void}) {
5555
return <div className="flex mt-4">
56-
<input className={"h-5 w-5 focus:ring-0 mt-1 rounded cursor-pointer border-2 "+(props.checked?'bg-gray-800':'')} type="checkbox" checked={props.checked} onChange={props.onChange}/>
56+
<input className={"h-4 w-4 focus:ring-0 mt-1 rounded cursor-pointer border-2 "+(props.checked?'bg-gray-800':'')} type="checkbox" checked={props.checked} onChange={props.onChange}/>
5757
<div className="flex flex-col ml-2">
58-
<div className="text-gray-700 text-md font-semibold">{props.title}</div>
58+
<div className="text-gray-800 text-md font-semibold tracking-wide">{props.title}</div>
5959
<div className="text-gray-400 text-md">{props.desc}</div>
6060
</div>
6161
</div>

components/dashboard/src/settings/Plans.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2,7 +2,7 @@ import { SettingsPage } from "./SettingsPage";
22

33
export default function Plans() {
44
return <div>
5-
<SettingsPage title='Plans' subtitle='Plans and Usage'>
5+
<SettingsPage title='Plans' subtitle='Manage account usage and billing.'>
66
<h3>Plans</h3>
77
</SettingsPage>
88
</div>;

components/dashboard/src/settings/Preferences.tsx

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@ export default function Preferences() {
2121
}
2222

2323
return <div>
24-
<SettingsPage title='Preferences' subtitle='Configure your Default IDE for all workspaces.'>
24+
<SettingsPage title='Preferences' subtitle='Configure user preferences.'>
2525
<h3>Default IDE</h3>
2626
<p className="text-base">Choose which IDE you want to use.</p>
2727
<div className="mt-4 space-x-4 flex">

components/dashboard/src/settings/SettingsPage.tsx

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -9,13 +9,13 @@ export interface Props {
99
}
1010

1111
export function SettingsPage(p: Props) {
12-
return <div>
12+
return <div className="max-w-6xl">
1313
<Header title={p.title} subtitle={p.subtitle}/>
1414
<div className='lg:px-28 px-10 flex pt-9'>
1515
<div>
16-
<ul className="flex flex-col text-sm text-gray-500 pt-4 lg:pt-0 w-48 space-y-2">
16+
<ul className="flex flex-col text tracking-wide text-gray-500 pt-4 lg:pt-0 w-48 space-y-2">
1717
{settingsMenu.map(e => {
18-
let classes = "flex block py-2 font-sm px-4 rounded-md";
18+
let classes = "flex block py-2 px-4 rounded-md";
1919
if (e.link.toLowerCase() === window.location.pathname) {
2020
classes += " bg-gray-800 text-gray-50";
2121
} else {

components/dashboard/src/start/CreateWorkspace.tsx

Lines changed: 1 addition & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -111,14 +111,11 @@ export class CreateWorkspace extends React.Component<CreateWorkspaceProps, Creat
111111
<p className="text-base text-black font-bold">{w.workspace.id}</p>
112112
<p>{w.workspace.contextURL}</p>
113113
</div>
114-
<div className="flex">
115-
<button>Open</button>
116-
</div>
117114
</a>
118115
)}
119116
</>
120117
</div>
121-
<div className="flex justify-end mt-4">
118+
<div className="flex justify-end mt-6">
122119
<button onClick={() => this.createWorkspace(CreateWorkspaceMode.Default)}>New Workspace</button>
123120
</div>
124121
</Modal>;

components/dashboard/src/start/StartWorkspace.tsx

Lines changed: 6 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -200,11 +200,11 @@ export default class StartWorkspace extends React.Component<StartWorkspaceProps,
200200
case "stopping":
201201
phase = StartPhase.Stopping;
202202
statusMessage = <div>
203-
<div className="flex space-x-3 items-center rounded-xl py-2 px-4 h-16 w-72 mt-4 bg-gray-100">
203+
<div className="flex space-x-3 items-center rounded-xl m-auto px-4 h-16 w-72 mt-4 bg-gray-100">
204204
<div className="rounded-full w-3 h-3 text-sm bg-gitpod-kumquat">&nbsp;</div>
205205
<div>
206206
<p className="text-gray-700 font-semibold">{this.state.workspaceInstance.workspaceId}</p>
207-
<p>{this.state.contextUrl}</p>
207+
<p className="w-56 truncate">{this.state.contextUrl}</p>
208208
</div>
209209
</div>
210210
</div>;
@@ -214,16 +214,16 @@ export default class StartWorkspace extends React.Component<StartWorkspaceProps,
214214
case "stopped":
215215
phase = StartPhase.Stopped;
216216
statusMessage = <div>
217-
<div className="flex space-x-3 items-center rounded-xl py-2 px-4 h-16 w-72 mt-4 bg-gray-100">
217+
<div className="flex space-x-3 items-center rounded-xl m-auto px-4 h-16 w-72 mt-4 bg-gray-100">
218218
<div className="rounded-full w-3 h-3 text-sm bg-gray-300">&nbsp;</div>
219219
<div>
220220
<p className="text-gray-700 font-semibold">{this.state.workspaceInstance.workspaceId}</p>
221-
<p>{this.state.contextUrl}</p>
221+
<p className="w-56 truncate">{this.state.contextUrl}</p>
222222
</div>
223223
</div>
224224
<div className="mt-10 flex space-x-2">
225-
<button className="px-4 py-2 text-gray-500 bg-white font-semibold border-gray-500" onClick={() => this.redirectTo(gitpodHostUrl.asDashboard().toString())}>Go to Dashboard</button>
226-
<button className="px-4 py-2 text-gray-50 bg-green-600 font-semibold border-green-800" onClick={() => this.redirectTo(gitpodHostUrl.asStart(this.state.workspaceInstance?.workspaceId).toString())}>Open Workspace</button>
225+
<button className="px-4 py-2 text-gray-500 bg-white font-semibold border-gray-500 hover:text-gray-700 hover:border-gray-700 hover:bg-gray-100" onClick={() => this.redirectTo(gitpodHostUrl.asDashboard().toString())}>Go to Dashboard</button>
226+
<button className="px-4 py-2 text-gray-50 bg-green-600 font-semibold border-green-800 hover:bg-green-700" onClick={() => this.redirectTo(gitpodHostUrl.asStart(this.state.workspaceInstance?.workspaceId).toString())}>Open Workspace</button>
227227
</div>
228228
</div>;
229229
break;

components/dashboard/src/tailwind.output.css

Lines changed: 30 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -862,17 +862,42 @@ button:hover {
862862
button {
863863
--tw-border-opacity: 1;
864864
border-color: rgba(63, 98, 18, var(--tw-border-opacity));
865+
}
866+
867+
button:focus {
868+
--tw-border-opacity: 1;
869+
border-color: rgba(147, 197, 253, var(--tw-border-opacity));
870+
}
871+
872+
button {
865873
border-radius: 0.375rem;
866874
border-width: 2px;
867875
cursor: pointer;
868876
font-size: 0.875rem;
869877
line-height: 1.25rem;
870878
margin-top: auto;
871879
margin-bottom: auto;
872-
padding-top: 0.25rem;
873-
padding-bottom: 0.25rem;
874-
padding-left: 0.75rem;
875-
padding-right: 0.75rem;
880+
}
881+
882+
button:focus {
883+
outline: 2px solid transparent;
884+
outline-offset: 2px;
885+
}
886+
887+
button {
888+
padding-top: 0.5rem;
889+
padding-bottom: 0.5rem;
890+
padding-left: 1rem;
891+
padding-right: 1rem;
892+
}
893+
894+
button:focus {
895+
--tw-ring-offset-shadow: var(--tw-ring-inset) 0 0 0 var(--tw-ring-offset-width) var(--tw-ring-offset-color);
896+
--tw-ring-shadow: var(--tw-ring-inset) 0 0 0 calc(3px + var(--tw-ring-offset-width)) var(--tw-ring-color);
897+
box-shadow: var(--tw-ring-offset-shadow), var(--tw-ring-shadow), var(--tw-shadow, 0 0 #0000);
898+
}
899+
900+
button {
876901
--tw-text-opacity: 1;
877902
color: rgba(245, 245, 244, var(--tw-text-opacity));
878903
}
@@ -200362,4 +200387,4 @@ input[disabled] {
200362200387
-webkit-filter: grayscale(1) !important;
200363200388
filter: grayscale(1) !important;
200364200389
}
200365-
}
200390+
}

components/dashboard/src/workspaces/WorkspaceEntry.tsx

Lines changed: 10 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -28,7 +28,7 @@ export function WorkspaceEntry({ desc, model }: { desc: WorkspaceInfo, model: Wo
2828
break;
2929
}
3030
default: {
31-
stateClassName += ' bg-gitpod-kumquat'
31+
stateClassName += ' bg-gitpod-kumquat animate-pulse'
3232
break;
3333
}
3434
}
@@ -94,37 +94,37 @@ export function WorkspaceEntry({ desc, model }: { desc: WorkspaceInfo, model: Wo
9494
setChangesModalVisible(true);
9595
}
9696
return <div>
97-
<a className="rounded-xl whitespace-nowrap flex space-x-2 py-6 px-6 w-full justify-between hover:bg-gray-100 cursor-pointer" href={startUrl.toString()}>
97+
<a className="rounded-xl whitespace-nowrap flex space-x-2 py-6 px-6 w-full justify-between hover:bg-gray-100 focus:bg-gitpod-kumquat-light cursor-pointer group" href={startUrl.toString()}>
9898
<div className="pr-3 self-center">
9999
<div className={stateClassName}>
100100
&nbsp;
101101
</div>
102102
</div>
103103
<div className="flex flex-col w-3/12">
104-
<div className="font-medium text-gray-800 truncate hover:underline">{ws.id}</div>
105-
<a href={project ? 'https://' + project : undefined}><div className="text-sm overflow-ellipsis truncate text-gray-400 truncate">{project || 'Unknown'}</div></a>
104+
<div className="font-medium text-gray-800 truncate">{ws.id}</div>
105+
<a href={project ? 'https://' + project : undefined}><div className="text-sm overflow-ellipsis truncate text-gray-400">{project || 'Unknown'}</div></a>
106106
</div>
107107
<div className="flex w-4/12 truncate overflow-ellipsis">
108108
<div className="flex flex-col">
109-
<div className="font-medium text-gray-500 truncate">{ws.description}</div>
110-
<div className="text-sm text-gray-400 truncate">{ws.contextURL}</div>
109+
<div className="font-medium text-gray-500 overflow-ellipsis truncate">{ws.description}</div>
110+
<div className="text-sm text-gray-400 overflow-ellipsis truncate">{ws.contextURL}</div>
111111
</div>
112112
</div>
113113
<div className="flex w-2/12 truncate" onClick={numberOfChanges > 0 ? showChanges : undefined}>
114114
<div className="flex flex-col">
115115
<div className="font-medium text-gray-500 truncate">{currentBranch}</div>
116116
{
117117
numberOfChanges > 0 ?
118-
<div className={"text-sm text-red truncate cursor-pointer hover:underline"} onClick={showChanges}>{changesLabel}</div>
118+
<div className={"text-sm text-red-600 truncate cursor-pointer bg-red-50 group-hover:bg-red-100 hover:text-red-800 px-1.5 py-0.5 relative rounded-md -top-0.5"} onClick={showChanges}>{changesLabel}</div>
119119
:
120-
<div className="text-sm text-gray-400 truncate">No Changes</div>
120+
<div className="text-sm text-gray-500 truncate ">No Changes</div>
121121
}
122122
</div>
123123
</div>
124124
<div className="flex w-2/12 self-center space-x-2 truncate">
125125
<div className="text-sm text-gray-400 truncate">{moment(WorkspaceInfo.lastActiveISODate(desc)).fromNow()}</div>
126126
</div>
127-
<div className="flex w-8 self-center hover:bg-gray-300 rounded-md cursor-pointer">
127+
<div className="flex w-8 self-center hover:bg-gray-200 rounded-md cursor-pointer">
128128
<ContextMenu menuEntries={menuEntries}>
129129
<img className="w-8 h-8 p-1" src={ThreeDots} alt="Actions" />
130130
</ContextMenu>
@@ -135,7 +135,7 @@ export function WorkspaceEntry({ desc, model }: { desc: WorkspaceInfo, model: Wo
135135
</Modal>
136136
<Modal visible={isModalVisible} onClose={() => setModalVisible(false)} onEnter={() => {model.deleteWorkspace(ws.id); return true;}}>
137137
<div>
138-
<h3>Delete Workspace</h3>
138+
<h3 className="pb-2">Delete Workspace</h3>
139139
<div className="border-t border-b border-gray-200 mt-2 -mx-6 px-6 py-2">
140140
<p className="mt-1 mb-2 text-base">Are you sure you want to delete this workspace?</p>
141141
<div className="w-full p-4 mb-2 bg-gray-100 rounded-xl group bg-gray-100">

0 commit comments

Comments
 (0)