refactor: make design slick@@ -1,5 +1,5 @@
{
- "_generatedAtUnix": 1778595194575,
+ "_generatedAtUnix": 1778610831056,
"_hashAlgorithm": "sha1",
"_version": 2,
"assets": {
@@ -40,13 +40,13 @@
"pathSourceMap": "./public/.islands/PullRequestSourceSelect.bundle.js.map"
},
"RepositoriesList": {
- "hash": "75dbdd8bc65ad5b787235cb8514ed53168744a7d",
+ "hash": "a3cd113acc398feec40cd073f0df597a9e61e6eb",
"pathSource": "./app/islands/RepositoriesList.tsx",
"pathBundle": "./public/.islands/RepositoriesList.bundle.js",
"pathSourceMap": "./public/.islands/RepositoriesList.bundle.js.map"
},
"RepositoryCommitSummaryLine": {
- "hash": "ab3729f98c645091f68deafdab42bec0ffc775c5",
+ "hash": "414c2a20e6c343116d8ce3a5a64f2a493f51d0c7",
"pathSource": "./app/islands/RepositoryCommitSummaryLine.tsx",
"pathBundle": "./public/.islands/RepositoryCommitSummaryLine.bundle.js",
"pathSourceMap": "./public/.islands/RepositoryCommitSummaryLine.bundle.js.map"
@@ -70,7 +70,7 @@
"pathSourceMap": "./public/.islands/RepositoryForkForm.bundle.js.map"
},
"RepositoryHero": {
- "hash": "e291deada81cf96f29cc858d9e686c4f4a0bbe10",
+ "hash": "921b889a0f6a0f33e554def62c54a95096e7cc6f",
"pathSource": "./app/islands/RepositoryHero.tsx",
"pathBundle": "./public/.islands/RepositoryHero.bundle.js",
"pathSourceMap": "./public/.islands/RepositoryHero.bundle.js.map"
@@ -122,15 +122,15 @@
"pathSource": "./app/views/organization/OrganizationDetailsView.tsx"
},
"RepositoryBrowserView": {
- "hash": "6c617e1ebda50ebcf3edf3b644185ac5c687a580",
+ "hash": "b5248afb14d96e71f7350f187c10328c56891765",
"pathSource": "./app/views/repository/RepositoryBrowserView.tsx"
},
"RepositoryCommitsLogView": {
- "hash": "c2883381fbee0b93e165abd38a412d0e802ae65d",
+ "hash": "672d52245a43e68f6ded72e39c4c2fc9ab1bf897",
"pathSource": "./app/views/repository/RepositoryCommitsLogView.tsx"
},
"RepositoryCompareView": {
- "hash": "bf9ab8c3ab4f1d0722ac968b811cc3bf6537ed9f",
+ "hash": "f88489e021baae8b3e55e3b4dbe2c3e4b0af8a29",
"pathSource": "./app/views/repository/RepositoryCompareView.tsx"
},
"RepositoryCreateView": {
@@ -138,7 +138,7 @@
"pathSource": "./app/views/repository/RepositoryCreateView.tsx"
},
"RepositoryDetailsView": {
- "hash": "6e36acdb479b2b69bddc8b35ff7ba65f0b9b812c",
+ "hash": "da0ebcac2dd17cb279732b4654d507c3d7568bca",
"pathSource": "./app/views/repository/RepositoryDetailsView.tsx"
},
"RepositoryExploreView": {
@@ -146,23 +146,23 @@
"pathSource": "./app/views/repository/RepositoryExploreView.tsx"
},
"RepositoryForkView": {
- "hash": "bf9c35ad6b78e50ba79fd4218b3e0754a901995e",
+ "hash": "ae3d083cc6ea0e4fec0dbc719e8916ca3045f987",
"pathSource": "./app/views/repository/RepositoryForkView.tsx"
},
"RepositoryShowObjectView": {
- "hash": "50aab67470271b2c3cb4155cd34282a8419323ae",
+ "hash": "d7207fa7763a330998b1f92c9d38168d82c4cc6b",
"pathSource": "./app/views/repository/RepositoryShowObjectView.tsx"
},
"RepositoryPullRequestCreateView": {
- "hash": "b57e81c31c03e8334069c5df9fb1def8ebda1cf9",
+ "hash": "447d38c5a6c5e1e88caa4fbcbe897f2d7ba0a3f1",
"pathSource": "./app/views/repositoryPullRequests/RepositoryPullRequestCreateView.tsx"
},
"RepositoryPullRequestDetailsView": {
- "hash": "62387edff49216a3c944101530f7904def0269dd",
+ "hash": "bec2821c1c5cebc708479c41d53a57b10f3a67d9",
"pathSource": "./app/views/repositoryPullRequests/RepositoryPullRequestDetailsView.tsx"
},
"RepositoryPullRequestsView": {
- "hash": "5799a8750c280ee3f852bf60c3b93125dfbc7783",
+ "hash": "403b3c7ba81523e900b7bc746ef805c533ba330a",
"pathSource": "./app/views/repositoryPullRequests/RepositoryPullRequestsView.tsx"
},
"SettingsKeyAddView": {
@@ -178,7 +178,7 @@
"pathSource": "./app/views/settings/SettingsKeysListView.tsx"
},
"SettingsView": {
- "hash": "d57608080980620f2458c4931e14983ace10b908",
+ "hash": "f532da9748b4ab68da3942ec6702e7d9d2989211",
"pathSource": "./app/views/settings/SettingsView.tsx"
},
"UserDashboardView": {
@@ -186,7 +186,7 @@
"pathSource": "./app/views/user/UserDashboardView.tsx"
},
"UserDetailsView": {
- "hash": "d2a656ba2a48011e0a2111a6eff6a1484e0ebfed",
+ "hash": "cdf50c6716c65f78a3d01e834f4f8999c85529ad",
"pathSource": "./app/views/user/UserDetailsView.tsx"
}
}
@@ -69,7 +69,13 @@ export const DrawerSettings = ({
marginRight: 8,
}}
/>
- <a href={buildRouteLink(AppRoute.USER_DETAILS, { username })}>
+ <a
+ href={buildRouteLink(
+ AppRoute.USER_DETAILS,
+ { username },
+ { encodeURIComponent: false },
+ )}
+ >
@{username}
</a>
</StyledDrawerListHeader>
@@ -81,7 +81,9 @@ export const PageHeader: VFC<PageHeaderProps & WithThemeSchemeProp> = ({
<StyledBurgerMenu
themeScheme={themeScheme}
onClick={toggleDrawerPrimary}
- />
+ >
+ ☰
+ </StyledBurgerMenu>
<StyledLogoArea themeScheme={themeScheme} forceShowLogo={forceShowLogo}>
<a href={"/"}>
<h1>{Const.APP_NAME}</h1>
@@ -162,6 +164,9 @@ const StyledBurgerMenu = styled.button<WithThemeSchemeProp>`
border: none;
border-radius: 20px;
background: ${NamedColors.CARD_OVERLAY[themeScheme]};
+ font-size: 24px;
+ font-weight: thin;
+ padding-top: -2px;
/*color: red;*/
`}
`;
@@ -10,6 +10,7 @@ import { AppRoute } from "../routes.defs";
import { Card } from "../components/Card.styled";
import { Grid } from "../components/Grid";
import { buildRouteLink } from "../utils/shared";
+import { NamedColors } from "../utils/style";
export interface RepositoriesListProps {
repositories: (Repository & { parentOrg: Organization })[];
@@ -24,7 +25,7 @@ const RepositoriesList: ReactIsland<
<Card
key={repo.id}
themeScheme={themeScheme}
- style={{ marginTop: idx >= 1 ? 16 : 32 }}
+ style={{ marginTop: idx >= 1 ? 4 : 16 }}
>
<Grid.Row fluid nowrap>
<h1 style={{ margin: 0, flex: 1 }}>
@@ -52,7 +53,14 @@ const RepositoriesList: ReactIsland<
<div>
<p style={{ margin: 0, marginTop: 8 }}>{repo.shortDescription}</p>
{repo.lastPushedAt != null && (
- <p style={{ margin: 0, marginTop: 8 }}>
+ <p
+ style={{
+ margin: 0,
+ marginTop: 8,
+ fontSize: 14,
+ color: NamedColors.TEXT_MUTED[themeScheme],
+ }}
+ >
Last push: {new Date(repo.lastPushedAt).toLocaleString()}
</p>
)}
@@ -56,10 +56,10 @@ const RepositoryCommitSummaryLine: ReactIsland<
<Grid.Row
gap={8}
alignItems={"stretch"}
- style={{ flexWrap: "wrap-reverse" }}
+ style={{ flexWrap: "nowrap" }}
onClick={toggleFullSubjectVisibility}
>
- <Grid.Col flex={"1 0 calc(100% - 220px)"} style={{ minWidth: 360 }}>
+ <Grid.Col flex={"1 0 calc(100% - 210px)"} style={{ minWidth: 180 }}>
<strong>{commit.author.name}</strong>
<span style={{ marginTop: 8 }}>
<a
@@ -83,6 +83,7 @@ const RepositoryCommitSummaryLine: ReactIsland<
flex: "1 0 200px",
width: 200,
minWidth: 200,
+ fontSize: 14,
}}
>
<span>
@@ -5,11 +5,16 @@ import React from "react";
// generated via script[generate:prisma]
import type { Organization, Repository } from "@prisma/client";
// app
-import type { RepositoryForkedFromRepoMeta } from "../types";
+import type {
+ RepositoryForkedFromRepoMeta,
+ WithThemeSchemeProp,
+} from "../types";
import { buildRouteLink } from "../utils/shared";
import { ButtonAnchor } from "../components/Button.styled";
import { AppRoute } from "../routes.defs";
import { Grid } from "../components/Grid";
+import { useMediaQuery } from "../utils/hooks/useMediaQuery";
+import { NamedColors } from "../utils/style";
export interface RepositoryHeroProps {
parentOrg: Organization;
@@ -19,9 +24,15 @@ export interface RepositoryHeroProps {
path?: string;
separator?: string;
showForkButton?: boolean;
+ showNewButton?: boolean;
+ newButtonUrl?: string;
+ newButtonText?: string;
}
-const RepositoryHero: ReactIsland<RepositoryHeroProps> = ({
+const RepositoryHero: ReactIsland<
+ RepositoryHeroProps & WithThemeSchemeProp
+> = ({
+ themeScheme,
parentOrg,
repo,
forkedFromRepo = null,
@@ -29,16 +40,27 @@ const RepositoryHero: ReactIsland<RepositoryHeroProps> = ({
path = undefined,
// separator = "∙",
showForkButton = true,
+ showNewButton = false,
+ newButtonUrl = undefined,
+ newButtonText = "New Repository",
}) => {
+ const isMobile = useMediaQuery("sm");
+
return (
- <Grid.Col fluid gap={16}>
- <Grid.Row fluid alignItems={"center"}>
+ <Grid.Col
+ fluid
+ gap={16}
+ style={{
+ borderBottom: `1px solid ${NamedColors.BORDER_DEFAULT[themeScheme]}`,
+ }}
+ >
+ <Grid.Row fluid nowrap alignItems={"flex-start"}>
<Grid.Col
nowrap
- flex={"1 0 468px"}
- style={{ minWidth: 468, marginBottom: 12 }}
+ flex={"1 0 300px"}
+ style={{ minWidth: 300, marginBottom: 12 }}
>
- <h2 style={{ margin: 0 }}>
+ <h2 style={{ margin: 0, fontSize: isMobile ? 20 : 20 }}>
<a
style={{ whiteSpace: "nowrap" }}
href={buildRouteLink(AppRoute.ORGANIZATION_DETAILS, {
@@ -59,7 +81,16 @@ const RepositoryHero: ReactIsland<RepositoryHeroProps> = ({
</a>
</h2>
<div style={{ flex: 1 }}>
- <h3 style={{ whiteSpace: "nowrap", margin: 0, marginTop: 4 }}>
+ <h3
+ style={{
+ whiteSpace: "nowrap",
+ margin: 0,
+ marginTop: 4,
+ fontSize: 16,
+ fontWeight: "700",
+ fontFamily: "monospace",
+ }}
+ >
{path || "Files"}
</h3>
</div>
@@ -119,6 +150,9 @@ const RepositoryHero: ReactIsland<RepositoryHeroProps> = ({
</Grid.Row>
</ButtonAnchor>
)}
+ {showNewButton && (
+ <ButtonAnchor href={newButtonUrl}>{newButtonText}</ButtonAnchor>
+ )}
</Grid.Row>
</Grid.Col>
);
@@ -0,0 +1,4 @@
+import * as React from "react";
+
+export const useIsomorphicLayoutEffect =
+ typeof window === "object" ? React.useLayoutEffect : React.useEffect;
@@ -0,0 +1,33 @@
+import React from "react";
+import { useIsomorphicLayoutEffect } from "./useIsomorphicLayoutEffect";
+
+const breakpoints = {
+ sm: "768px",
+ md: "1024px",
+ lg: "1280px",
+ xl: "1640px",
+} as const;
+
+type Breakpoints = keyof typeof breakpoints;
+
+export function useMediaQuery(query: Breakpoints, type: "min" | "max" = "min") {
+ const [matches, setMatches] = React.useState(false);
+
+ useIsomorphicLayoutEffect(() => {
+ const mediaQuery = window.matchMedia(
+ `(${type}-width: ${breakpoints[query]})`,
+ );
+ setMatches(mediaQuery.matches);
+
+ mediaQuery.addEventListener("change", (event) => {
+ setMatches(event.matches);
+ });
+
+ return () =>
+ mediaQuery.removeEventListener("change", (event) => {
+ setMatches(event.matches);
+ });
+ }, [query]);
+
+ return matches;
+}
@@ -43,7 +43,7 @@ export const loadRepositoryCounters: preHandlerHookHandler = async (
const counters = await repoService.getRepositoryCounters(
orgSlug,
repoSlug,
- username,
+ username?.replace(/^@/, ""),
);
reply.context.layoutCounters = counters;
done();
@@ -68,6 +68,7 @@ const RepositoryBrowserView: ReactView<RepositoryBrowserViewProps> = ({
<PageWrapper>
<IslandWrapper data-islandid={`${RepositoryHero.name}$$0`}>
<RepositoryHero
+ themeScheme={commonProps.themeScheme}
forkedFromRepo={repo.forkedFromRepo}
forksCount={repo.forks.length}
parentOrg={parentOrg}
@@ -46,6 +46,7 @@ const RepositoryCommitsLogView: ReactView<RepositoryCommitsLogViewProps> = ({
<PageWrapper>
<IslandWrapper data-islandid={`${RepositoryHero.name}$$0`}>
<RepositoryHero
+ themeScheme={commonProps.themeScheme}
forkedFromRepo={repo.forkedFromRepo}
forksCount={repo.forks.length}
parentOrg={parentOrg}
@@ -43,6 +43,7 @@ const RepositoryCompareView: ReactView<RepositoryCompareViewProps> = ({
<PageWrapper>
<IslandWrapper data-islandid={`${RepositoryHero.name}$$0`}>
<RepositoryHero
+ themeScheme={commonProps.themeScheme}
forkedFromRepo={repo.forkedFromRepo}
forksCount={repo.forks.length}
parentOrg={parentOrg}
@@ -76,6 +76,7 @@ const RepositoryDetailsView: ReactView<RepositoryDetailsViewProps> = ({
<PageWrapper>
<IslandWrapper data-islandid={`${RepositoryHero.name}$$0`}>
<RepositoryHero
+ themeScheme={commonProps.themeScheme}
forkedFromRepo={forkedFromRepo}
forksCount={repo.forks.length}
parentOrg={parentOrg}
@@ -44,6 +44,7 @@ const RepositoryForkView: ReactView<RepositoryForkViewProps> = ({
<PageWrapper>
<IslandWrapper data-islandid={`${RepositoryHero.name}$$0`}>
<RepositoryHero
+ themeScheme={commonProps.themeScheme}
forkedFromRepo={sourceRepo.forkedFromRepo}
forksCount={sourceRepo.forks.length}
path={`Fork`}
@@ -61,6 +61,7 @@ const RepositoryShowObjectView: ReactView<RepositoryShowObjectViewProps> = ({
<PageWrapper>
<IslandWrapper data-islandid={`${RepositoryHero.name}$$0`}>
<RepositoryHero
+ themeScheme={commonProps.themeScheme}
forkedFromRepo={repo.forkedFromRepo}
forksCount={repo.forks.length}
parentOrg={parentOrg}
@@ -34,11 +34,16 @@ const RepositoryPullRequestCreateView: ReactView<
<PageWrapper>
<IslandWrapper data-islandid={`${RepositoryHero.name}$$0`}>
<RepositoryHero
+ themeScheme={commonProps.themeScheme}
forkedFromRepo={repo.forkedFromRepo}
forksCount={repo.forks.length}
parentOrg={parentOrg}
path={`Pull Requests / New`}
repo={repo}
+ showForkButton={false}
+ showNewButton={false}
+ // showSaveButton
+ // onSaveButtonClick
/>
</IslandWrapper>
<IslandWrapper
@@ -87,11 +87,18 @@ const RepositoryPullRequestDetailsView: ReactView<
<PageWrapper>
<IslandWrapper data-islandid={`${RepositoryHero.name}$$0`}>
<RepositoryHero
+ themeScheme={commonProps.themeScheme}
forkedFromRepo={repo.forkedFromRepo}
forksCount={repo.forks.length}
parentOrg={parentOrg}
path={`Pull Request / #${pr.uid}`}
repo={repo}
+ showForkButton={false}
+ showNewButton={false}
+ // showMergeButton={canMergePullRequest}
+ // onMergeButtonClick
+ // showCloseButton={canClosePullRequest}
+ // onCloseButtonClick
/>
</IslandWrapper>
<Grid.Col fluid style={{ marginTop: 24 }}>
@@ -40,27 +40,29 @@ const RepositoryPullRequestsView: ReactView<
<PageWrapper>
<IslandWrapper data-islandid={`${RepositoryHero.name}$$0`}>
<RepositoryHero
+ themeScheme={commonProps.themeScheme}
forkedFromRepo={repo.forkedFromRepo}
forksCount={repo.forks.length}
parentOrg={parentOrg}
path={`Pull Requests`}
repo={repo}
+ showForkButton={false}
+ showNewButton
+ newButtonText={"New Pull Request"}
+ newButtonUrl={buildRouteLink(
+ AppRoute.REPOSITORY_PULL_REQUEST_CREATE,
+ {
+ orgSlug: parentOrg.slug,
+ repoSlug: repo.slug,
+ },
+ )}
/>
</IslandWrapper>
- <Grid.Col fluid style={{ marginTop: 32 }}>
- <a
- href={buildRouteLink(AppRoute.REPOSITORY_PULL_REQUEST_CREATE, {
- orgSlug: parentOrg.slug,
- repoSlug: repo.slug,
- })}
- >
- New Pull Request
- </a>
- </Grid.Col>
- <Grid.Col fluid style={{ marginTop: 24 }}>
- <Grid.Row fluid alignItems={"center"} gap={16}>
+ <Grid.Col fluid style={{ marginTop: 16 }}>
+ <Grid.Row fluid alignItems={"center"} gap={12}>
<a
style={{
+ fontWeight: "bold",
textDecoration:
pullRequestsFilter === "all" ? "underline" : "none",
}}
@@ -72,6 +74,7 @@ const RepositoryPullRequestsView: ReactView<
</a>
<a
style={{
+ fontWeight: "normal",
textDecoration:
pullRequestsFilter === "opened" ? "underline" : "none",
}}
@@ -83,6 +86,7 @@ const RepositoryPullRequestsView: ReactView<
</a>
<a
style={{
+ fontWeight: "normal",
textDecoration:
pullRequestsFilter === "merged" ? "underline" : "none",
}}
@@ -94,6 +98,7 @@ const RepositoryPullRequestsView: ReactView<
</a>
<a
style={{
+ fontWeight: "normal",
textDecoration:
pullRequestsFilter === "closed" ? "underline" : "none",
}}
@@ -105,7 +110,7 @@ const RepositoryPullRequestsView: ReactView<
</a>
</Grid.Row>
</Grid.Col>
- <Grid.Col fluid style={{ marginTop: 32 }}>
+ <Grid.Col fluid style={{ marginTop: 8 }}>
{pullRequests != null && pullRequests.length >= 1 ? (
pullRequests.map((pr, idx) => (
<Grid.Col
@@ -8,14 +8,9 @@ import { UserSSHKey } from "@prisma/client";
import type { CommonProps } from "../../types";
import { buildRouteLink } from "../../utils/shared";
import { AppRoute } from "../../routes.defs";
-import {
- ButtonAnchor,
- Grid,
- IslandWrapper,
- Layout,
- PageWrapper,
-} from "../../components";
+import { Grid, IslandWrapper, Layout, PageWrapper } from "../../components";
// app islands
+import RepositoryHero from "../../islands/RepositoryHero";
import SSHKeyItem from "../../islands/SSHKeyItem";
export interface SettingsViewProps extends CommonProps {
@@ -33,25 +28,23 @@ const SettingsView: ReactView<SettingsViewProps> = ({
username={commonProps.currentUserUsername!}
>
<PageWrapper>
- <Grid.Col fluid nowrap gap={24}>
- <Grid.Row
- fluid
- nowrap
- justifyContent="space-between"
- gap={8}
- alignItems="center"
- >
- <h1 style={{ margin: 0 }}>SSH Keys</h1>
- <ButtonAnchor
- href={buildRouteLink(
- AppRoute.SETTINGS_KEY_ADD,
- { username: commonProps.currentUserUsername! },
- { encodeURIComponent: 0 },
- )}
- >
- Add
- </ButtonAnchor>
- </Grid.Row>
+ <IslandWrapper data-islandid={`${RepositoryHero.name}$$0`}>
+ <RepositoryHero
+ themeScheme={commonProps.themeScheme}
+ parentOrg={{ slug: commonProps.currentUserUsername! } as any}
+ repo={{ slug: "" } as any}
+ path={`SSH Keys`}
+ showForkButton={false}
+ showNewButton
+ newButtonText={"New SSH Key"}
+ newButtonUrl={buildRouteLink(
+ AppRoute.SETTINGS_KEY_ADD,
+ { username: commonProps.currentUserUsername! },
+ { encodeURIComponent: 0 },
+ )}
+ />
+ </IslandWrapper>
+ <Grid.Col fluid nowrap gap={24} style={{ marginTop: 16 }}>
<Grid.Col fluid nowrap gap={12}>
{sshKeys.map((key, idx) => (
<IslandWrapper
@@ -6,8 +6,9 @@ import React from "react";
import type { Organization, Repository, User } from "@prisma/client";
// app
import type { CommonProps } from "../../types";
-import { Grid, IslandWrapper, Layout, PageWrapper } from "../../components";
+import { IslandWrapper, Layout, PageWrapper } from "../../components";
// app islands
+import RepositoryHero from "../../islands/RepositoryHero";
import RepositoriesList from "../../islands/RepositoriesList";
export interface UserDetailsViewProps extends CommonProps {
@@ -29,18 +30,22 @@ const UserDetailsView: ReactView<UserDetailsViewProps> = ({
username={user.username!}
>
<PageWrapper>
- <Grid.Row fluid gap={8}>
- <Grid.Col fluid nowrap gap={4}>
- <h1 style={{ margin: 0 }}>{user.displayName || user.username}</h1>
- <h2 style={{ margin: 0, opacity: 0.67 }}>
- {currentUser != null && currentUser.id === user.id
- ? "Your repositories"
- : `Public repositories from ${
- user.displayName || user.username
- }`}
- </h2>
- </Grid.Col>
- </Grid.Row>
+ <IslandWrapper data-islandid={`${RepositoryHero.name}$$0`}>
+ <RepositoryHero
+ themeScheme={commonProps.themeScheme}
+ parentOrg={{ slug: user.username } as any}
+ repo={{ slug: "" } as any}
+ path={`Repositories`}
+ showForkButton={false}
+ showNewButton={false}
+ // newButtonText={"New SSH Key"}
+ // newButtonUrl={buildRouteLink(
+ // AppRoute.SETTINGS_KEY_ADD,
+ // { username: commonProps.currentUserUsername! },
+ // { encodeURIComponent: 0 },
+ // )}
+ />
+ </IslandWrapper>
<IslandWrapper data-islandid={`${RepositoriesList.name}$$0`}>
<RepositoriesList
repositories={repositories}