Sfoglia il codice sorgente

First step of implementing design

Jeremie Pardou-Piquemal 3 anni fa
parent
commit
4b3925cb9e
6 ha cambiato i file con 183 aggiunte e 181 eliminazioni
  1. 1 5
      public/index.html
  2. 10 1
      src/i18n/en.json
  3. 11 3
      src/i18n/fr.json
  4. 11 10
      src/index.css
  5. 52 71
      src/views/GameListItem.js
  6. 98 91
      src/views/GameListView.js

+ 1 - 5
public/index.html

@@ -11,11 +11,7 @@
     <meta name="description" content="Play board game online" />
     <link rel="apple-touch-icon" href="%PUBLIC_URL%/logo192.png" />
     <link rel="stylesheet" href="https://unpkg.com/chota@latest">
-    <link
-      href="https://fonts.googleapis.com/css2?family=Gloria+Hallelujah&display=swap"
-      rel="stylesheet"
-    />
-
+    
     <!--
       manifest.json provides metadata used when your web app is installed on a
       user's mobile device or desktop. See https://developers.google.com/web/fundamentals/web-app-manifest/

+ 10 - 1
src/i18n/en.json

@@ -151,5 +151,14 @@
   "Move mode": "Move mode",
   "Switch to move mode": "Switch to move mode",
   "Select mode": "Select mode",
-  "Switch to select mode": "Switch to select mode"
+  "Switch to select mode": "Switch to select mode",
+  "Color 1": "__NOT_TRANSLATED__",
+  "Color 2": "__NOT_TRANSLATED__",
+  "Column count": "__NOT_TRANSLATED__",
+  "Row count": "__NOT_TRANSLATED__",
+  "Pawn": "__NOT_TRANSLATED__",
+  "Checkerboard": "__NOT_TRANSLATED__",
+  "Magnetic Grid size": "__NOT_TRANSLATED__",
+  "Start a game now": "__NOT_TRANSLATED__",
+  "<0>Play board games online<1></1>with your friends - for free!</0><1>Choose from our selection or create your own.<1></1>No need to sign up. Just start a game and share the link with your friends.</1>": "<0>Play board games online<1></1>with your friends - for free!</0><1>Choose from our selection or create your own.<1></1>No need to sign up. Just start a game and share the link with your friends.</1>"
 }

+ 11 - 3
src/i18n/fr.json

@@ -99,7 +99,6 @@
   "Sending file...": "Envoi en cours…",
   "Click or drag'n'drop file here": "Cliquez ou déposez des fichiers dans cette zone",
   "Create new game": "Créer un jeu",
-  "Play your favorite games online with your friends": "Jouez à vos jeux favoris en ligne avec vos amis",
   "Game loading...": "Chargement…",
   "Go to home": "Accueil",
   "Configure game": "Configurer le jeu",
@@ -151,5 +150,14 @@
   "Move mode": "Mode déplacement",
   "Switch to move mode": "Basculer vers le mode déplacement",
   "Select mode": "Mode sélection",
-  "Switch to select mode": "Basculer vers le mode sélection"
-}
+  "Switch to select mode": "Basculer vers le mode sélection",
+  "Color 1": "Couleur 1",
+  "Color 2": "Couleur 2",
+  "Column count": "Nombre de colonne",
+  "Row count": "Nombre de ligne",
+  "Pawn": "Pion",
+  "Checkerboard": "Damier",
+  "Magnetic Grid size": "Taille de la grille",
+  "Start a game now": "Commencez à jouer",
+  "baseline": "<0>Jouez aux jeux de société en ligne<1></1>avec vos amis - gratuitement !</0><1>Choisissez parmi notre sélection ou ajoutez le votre.<1></1>Pas besoin de compte, démarrez un jeu et partagez le lien avec vos amis.</1>"
+}

+ 11 - 10
src/index.css

@@ -1,4 +1,4 @@
-@import url("https://fonts.googleapis.com/css2?family=Merriweather+Sans:wght@300;500;700;800&display=block");
+@import url("https://fonts.googleapis.com/css2?family=Roboto:wght@100;300;400;500;700;900&display=swap");
 
 body {
   margin: 0;
@@ -6,20 +6,21 @@ body {
 }
 
 :root {
-  --bg-color: #2a2a2aff;
-  --bg-secondary-color: #404040ff;
-  --font-color: #f9fbfaff;
-  --color-darkGrey: #2a2a2aff;
-  --color-lightGrey: #888886ff;
-  --color-grey: #404040ff;
-  --color-primary: #db5034ff;
+  --bg-color: #000000;
+  --bg-secondary-color: #121212;
+  --font-color: #f9fbfa;
+  --font-color2: #b3b3b3;
+  --color-darkGrey: #121212;
+  --color-lightGrey: #90969d;
+  --color-grey: #454545;
+  --color-primary: #db5034;
   --color-secondary: #00a698ff;
   --color-error: #d43939;
   --color-success: #28bd14;
   --grid-maxWidth: 120rem;
   --grid-gutter: 2rem;
   --font-size: 1.6rem;
-  --font-family-sans: sans-serif;
+  --font-family-sans: "Roboto", sans-serif;
   --font-family-mono: monaco, "Consolas", "Lucida Console", monospace;
 }
 
@@ -52,7 +53,7 @@ h2,
 h3,
 h4,
 h5 {
-  font-family: "Merriweather Sans", sans-serif;
+  font-family: var(--font-family-sans);
 }
 
 .tabs a {

+ 52 - 71
src/views/GameListItem.js

@@ -5,45 +5,28 @@ import { useTranslation } from "react-i18next";
 import { getBestTranslationFromConfig } from "../utils/api";
 
 const Game = styled.li`
-  width: 100%;
-  background-color: var(--bg-secondary-color);
   position: relative;
-  min-width: 250px;
-  max-width: 440px;
-  height: 150px;
-  padding: 0.5em;
-  margin: 0.3em;
-  flex: 1 1 0%;
-  box-shadow: rgba(0, 0, 0, 0.16) 0px 1px 4px;
-  background: ${(props) =>
-    props.back
-      ? `url(${props.back}), rgba(255, 255, 255, 0.6)`
-      : "var(--bg-secondary-color)"};
-  background-blend-mode: screen;
-  background-position: center;
-  background-size: cover;
-  background-repeat: no-repeat;
-
-  /*&:before {
-    position: absolute;
-    content: " ";
-    top: 0;
-    left: 0;
-    width: 100%;
-    height: 100%;
-    z-index: 0;
-    background-color: rgba(0, 0, 0, 0.5);
-  }*/
+  //min-width: 240px;
+  //max-width: 22%;
+  //height: 150px;
+  padding: 0em;
+  //margin: 0.3em;
+  margin: 0px;
+  margin-bottom: 3em;
+  flex: 1;
+  //box-shadow: rgba(0, 0, 0, 0.16) 0px 1px 4px;
+
+  //border: 1px dashed blue;
 
   & .game-name {
-    margin: 0;
     max-width: 80%;
-    text-overflow: ellipsis;
-    white-space: nowrap;
+    /*text-overflow: ellipsis;
+    white-space: nowrap;*/
     line-height: 1.2em;
     overflow: hidden;
     margin-bottom: 3px;
-    font-size: 1.5em;
+    margin: 0.2em 0 0.5em 0;
+    font-size: 2.5vw;
   }
 
   & .unpublished {
@@ -75,16 +58,31 @@ const Game = styled.li`
     display: block;
   }
 
+  & .img {
+    //max-width: 25vw;
+    width: 100%;
+    min-width: 300px;
+    max-width: 600px;
+    //padding-top: 60%;
+    background-color: #333;
+  }
+
   & .details {
     display: flex;
-    flex-direction: column;
-    color: var(--color-lightGrey);
-    font-size: 0.8em;
+    flex-direction: row;
+    color: var(--font-color2);
+    font-size: 12px;
+    padding-top: 1em;
   }
   & .details > span {
     display: flex;
     align-items: center;
-    padding: 1px;
+    padding-right: 5px;
+    margin-right: 5px;
+    border-right: 1px solid var(--font-color2);
+  }
+  & .details > span:last-child {
+    border: none;
   }
   & .details img {
     margin-right: 0.5em;
@@ -154,7 +152,13 @@ const GameListItem = ({
 
   return (
     <Game back={backgroundImage ? imageUrl : null}>
-      <h2 className="game-name">{translation.name}</h2>
+      <Link to={`/game/${id}/session/`}>
+        {imageUrl ? (
+          <img className="img" src={imageUrl} />
+        ) : (
+          <img className="img" src="/default.png" />
+        )}
+      </Link>
       {!published && (
         <img
           className="unpublished"
@@ -165,10 +169,6 @@ const GameListItem = ({
       <div className="details">
         {playerCount && (
           <span>
-            <img
-              src="https://icongr.am/entypo/users.svg?size=16&color=888886"
-              alt={t("Players count")}
-            />{" "}
             {playerCountDisplay.length === 2 &&
               t("{{min}} - {{max}} players", {
                 min: playerCountDisplay[0],
@@ -180,37 +180,12 @@ const GameListItem = ({
               })}
           </span>
         )}
-        {duration && (
-          <span>
-            <img
-              src="https://icongr.am/entypo/hour-glass.svg?size=16&color=888886"
-              alt={t("Duration")}
-            />{" "}
-            {durationDisplay}
-          </span>
-        )}
-        {minAge !== undefined && (
-          <span>
-            <img
-              src="https://icongr.am/entypo/man.svg?size=16&color=888886"
-              alt={t("Minimum age")}
-            />{" "}
-            {minAge}+
-          </span>
-        )}
-        {materialLanguage !== undefined && (
-          <span>
-            <img
-              src="https://icongr.am/entypo/globe.svg?size=16&color=888886"
-              alt={t("Material language")}
-            />{" "}
-            {materialLanguageDisplay}
-          </span>
-        )}
+        {duration && <span>{durationDisplay} mins</span>}
+        {minAge !== undefined && <span>age {minAge}+</span>}
       </div>
-      <Link to={`/game/${id}/session/`} className="button play">
-        {t("Play")}
-      </Link>
+
+      <h2 className="game-name">{translation.name}</h2>
+
       {userId && (userId === owner || !owner) && (
         <div className="extra-actions">
           <Link to={`/game/${id}/edit`} className="button edit icon-only">
@@ -225,4 +200,10 @@ const GameListItem = ({
   );
 };
 
+/*
+      <Link to={`/game/${id}/session/`} className="button play">
+        {t("Play")}
+      </Link>;
+*/
+
 export default GameListItem;

+ 98 - 91
src/views/GameListView.js

@@ -1,6 +1,6 @@
 import React from "react";
 import { Link, useLocation } from "react-router-dom";
-import { useTranslation } from "react-i18next";
+import { useTranslation, Trans } from "react-i18next";
 import styled from "styled-components";
 import CookieConsent from "react-cookie-consent";
 
@@ -16,113 +16,106 @@ import GameListItem from "./GameListItem";
 
 import AboutModal from "./AboutModal";
 
-const Header = styled.div`
-  height: 15em;
-  padding-top: 1em;
-  margin-bottom: 2em;
-  background-color: var(--bg-secondary-color);
-  background-image: url(${header});
-  position: relative;
-  & .baseline {
-    font-family: "Merriweather Sans", sans-serif;
+const GameView = styled.div`
+  min-height: 100vh;
+  flex-direction: column;
+  & > footer {
+    width: 100%;
+    grid-column: 1 / 4;
+    margin-top: 1em;
+    padding: 0.5em 0;
     text-align: center;
-    position: absolute;
-    bottom: 0px;
     background-color: #00000099;
-    width: 100%;
-    margin: 0;
-  }
-  & .login {
-    float: right;
-    margin-right: 0.5em;
   }
-  & .login button {
-    background-color: var(--color-primary);
+`;
+
+const Brand = styled.div`
+  position: relative;
+  display: inline-block;
+  margin-bottom: 12vh;
+  & h1 {
+    font-weight: 700;
+    font-size: 32px;
+    & a {
+      color: var(--font-color);
+    }
   }
-  & .new-game {
+  & .beta {
     position: absolute;
-    right: 0.5em;
-    top: 4em;
-    background-color: var(--color-secondary);
+    top: 5px;
+    right: -40px;
+    text-transform: uppercase;
+    font-weight: 300;
   }
+
   @media screen and (max-width: 640px) {
     & {
-      height: 10em;
-    }
-    & .new-game {
-      display: none;
     }
-    & .login {
-      display: none;
-    }
-    & .baseline {
-      font-size: 1em;
+    & h1 {
     }
   }
 `;
 
-const Brand = styled.div`
-  background-color: var(--color-secondary);
-  display: flex;
-  width: 550px;
-  align-items: center;
-  padding: 0 1em;
+const Header = styled.div`
+  padding-top: 1em;
+  margin-bottom: 12vh;
+  background-color: var(--bg-color);
   position: relative;
-  & h1 {
-    font-size: 4em;
-    margin: 0;
-    padding: 0;
-    line-height: 75px;
-    margin-left: 0em;
-    letter-spacing: -4px;
-    font-weight: bold;
-    padding-left: 0.2em;
+  padding: 0 5%;
+  & .baseline {
+    font-weigth: 800;
+    font-size: 3.5vw;
+    line-height: 1.2em;
   }
-  & img {
-    height: 55px;
-    margin-top: 8px;
+  & .subbaseline {
+    color: var(--font-color2);
+    font-size: 1.5vw;
   }
-  & .beta {
+  & .login {
     position: absolute;
-    top: 3px;
-    right: 33px;
-    font-weight: 700;
-    color: hsl(168, 83%, 62%);
+    right: 0;
+  }
+  & .login button {
+  }
+  & .new-game {
+    position: absolute;
+    top: 2em;
+    right: 0;
   }
-
   @media screen and (max-width: 640px) {
     & {
-      width: 290px;
     }
-    & h1 {
-      font-size: 2em;
+    & .new-game {
+    }
+    & .login {
+    }
+    & .baseline {
     }
   }
 `;
 
-const GameView = styled.div`
-  min-height: 100vh;
-  display: flex;
-  flex-direction: column;
-  & > footer {
-    margin-top: 1em;
-    padding: 0.5em 0;
+const Filter = styled.div`
+  & .incentive {
+    width: 100%;
     text-align: center;
-    background-color: #00000099;
+    font-size: 3.5vw;
+    padding: 0.5em;
   }
 `;
 
+const Content = styled.div`
+  background-color: var(--bg-secondary-color);
+`;
+
 const GameList = styled.ul`
-  width: 100%;
-  max-width: 960px;
   list-style: none;
   margin: 0;
-  margin: 0 auto;
-  padding: 0 2em;
-  flex: 1;
+  padding: 0 5%;
   display: flex;
   flex-wrap: wrap;
-  align-content: flex-start;
+  align-items: flex-start;
+  justify-content: space-between;
+  gap: 5%;
 
   @media screen and (max-width: 640px) {
   }
@@ -191,26 +184,40 @@ const GameListView = () => {
           )}
           <Account className="login" disabled={!cookieConsent} />
           <Brand className="brand">
-            <a href="/">
-              <img src={logo} alt="logo" />
-            </a>
-            <h1>Air Board Game</h1>
+            <h1>
+              <a href="/">Air Board Game</a>
+            </h1>
             <span className="beta">Beta</span>
           </Brand>
-          <h2 className="baseline">
-            {t("Play your favorite games online with your friends")}
-          </h2>
+          <Trans i18nKey="baseline">
+            <h2 className="baseline">
+              Play board games online
+              <br />
+              with your friends - for free!
+            </h2>
+            <p className="subbaseline">
+              Choose from our selection or create your own.
+              <br />
+              No need to sign up. Just start a game and share the link with your
+              friends.
+            </p>
+          </Trans>
         </Header>
-        <GameList>
-          {gameList
-            .filter(
-              ({ published, owner }) =>
-                published || (userId && (!owner || owner === userId))
-            )
-            .map((game) => (
-              <GameListItem key={game.id} game={game} userId={userId} />
-            ))}
-        </GameList>
+        <Content>
+          <Filter>
+            <h2 className="incentive">{t("Start a game now")}</h2>
+          </Filter>
+          <GameList>
+            {gameList
+              .filter(
+                ({ published, owner }) =>
+                  published || (userId && (!owner || owner === userId))
+              )
+              .map((game) => (
+                <GameListItem key={game.id} game={game} userId={userId} />
+              ))}
+          </GameList>
+        </Content>
         <footer>
           <button
             className="button clear"