Przeglądaj źródła

Cleaning up styles in RecipeForm

Tatiana Inama 7 lat temu
rodzic
commit
8a92bae88f

+ 30 - 1
recipes/src/components/Input/index.tsx

@@ -3,7 +3,7 @@ import TextField, { HelperText, Input as Field } from '@material/react-text-fiel
 import classNames from 'classnames';
 import Button from 'components/Button';
 import Icon from '../Icon';
-
+import {FieldProps} from 'Formik';
 import '@material/react-text-field/dist/text-field.css';
 import './styles.scss';
 
@@ -84,4 +84,33 @@ const Input = ({
 		</div>
 )};
 
+interface LightInputProps extends FieldProps {
+	label?: string,
+	type?: 'textarea' | 'text' | 'number',
+};
+
+export const LightInput = (label?: string, type = 'text') => ({ field }: FieldProps) => {
+	const Tag = type === 'textarea' ? 'textarea' : 'input';
+
+	return (
+		<div className="cbk-light-input">
+			{ label && (<label>{label}</label>)}
+			<Tag
+				className={field.value ? 'has-value': ''}
+				type={type}
+				onChange={field.onChange}
+				name={field.name}
+				onBlur={field.onBlur} 
+			/>
+			{/* {
+				type === 'text' ?
+				(<input className={field.value ? 'has-value': ''} type="text" onChange={field.onChange} name={field.name} onBlur={field.onBlur} />) :
+				(<textarea className={field.value ? 'has-value': ''} onChange={field.onChange} name={field.name} onBlur={field.onBlur} />)
+			} */}
+			
+			<span></span>
+		</div>
+	);
+};
+
 export default Input;

+ 5 - 0
recipes/src/components/Input/styles.scss

@@ -60,3 +60,8 @@
 .mdc-text-field:hover::before {
   opacity: 0;
 }
+
+
+.cbk-light-input {
+  @include lightInput();
+}

+ 21 - 36
recipes/src/components/RecipeForm/index.tsx

@@ -1,32 +1,17 @@
 import React, { useState } from 'react';
-import { Formik, Field, FieldArray, FormikActions, FormikProps, FieldArrayRenderProps } from 'formik';
+import { Formik, Field, FieldArray, FormikActions, FormikProps, FieldProps } from 'formik';
 import Recipe, { Ingredient, SubRecipe, Suggestion, _ingredient } from 'types/recipes';
 import { Grid, Row, Cell } from '@material/react-layout-grid';
 import './styles.scss';
 import sample_image from 'sample.png';
 import { MeasuresTypes } from 'services/measurements';
-
-type IngredientsListProps = {
-  ingredients: SubRecipe[],
-}
+import { LightInput as Input } from 'components/Input';
+import Button from 'components/Button';
 
 type RecipeFormProps = {
   initialValues: Recipe
 }
 
-const custom = (label: string, component = 'text') => ({field}: any) => (
-  <span>
-    <label>
-      {label}
-    </label>
-    {
-      component === 'text' ? 
-        <input {...field}/> :
-        <textarea {...field}/>
-    }
-  </span>
-);
-
 const convertIngredient = (ingredient: Ingredient, suggestion: Suggestion): Ingredient => {
   if (ingredient.unit === suggestion.referenceUnit) {
     return {
@@ -57,21 +42,22 @@ const SubrecipeForm = (props: any) => {
               <div className='tab__content' onClick={()=> setSelectedTab(subrecipeIdx)}> 
                 <Field name={`ingredients[${subrecipeIdx}].name`}/>
               </div>
-              <button type='button' onClick={()=> remove(subrecipeIdx)}>X</button>
+              <Button className='remove' type='button' icon='clear' onClick={() => remove(subrecipeIdx)}></Button>
+              <span></span>
             </li>
           ))
         }
         <li className='tab tab--add'>
-          <button type='button' onClick={()=> push({name: '', ingredients: []})}>+</button>
+          <Button type='button' icon='add' onClick={() => push({name: '', ingredients: []})}></Button>
         </li>
       </ul>
       <div className='ingredients-form'>
         <div className='ingredients-form-header'>
-          <span>Ingredient Name</span>
-          <span>Quantity</span>
-          <span>Unit</span>
-          <span>Notes</span>
-          <span>Original</span>
+          <div>Ingredient Name</div>
+          <div>Quantity</div>
+          <div>Unit</div>
+          <div>Notes</div>
+          <div>Original</div>
         </div>
         <FieldArray
           name={`ingredients[${selectedTab}].ingredients`}
@@ -82,7 +68,7 @@ const SubrecipeForm = (props: any) => {
                   form.values.ingredients[selectedTab].ingredients.map((ingredient: Ingredient, index: number) => (
                     <div key={index}>
                       <div className='ingredients-form-item'>
-                        <Field name={`ingredients[${selectedTab}].ingredients[${index}].name`} />
+                        <Field name={`ingredients[${selectedTab}].ingredients[${index}].name`}/>
                         <Field name={`ingredients[${selectedTab}].ingredients[${index}].quantity`}/>
                         <Field component='select' name={`ingredients[${selectedTab}].ingredients[${index}].unit`}>
                           {
@@ -92,6 +78,7 @@ const SubrecipeForm = (props: any) => {
                           }
                           <option value=''></option>
                         </Field>
+                        <Field name={`ingredients[${selectedTab}].ingredients[${index}].notes`}/>
                         <Field name={`ingredients[${selectedTab}].ingredients[${index}]._original`} disabled/>
                         <button type='button' onClick={() => ingredientHelpers.remove(index)}>x</button>
                       </div>
@@ -138,9 +125,9 @@ const RenderForm = ({
           <img src={sample_image} style={{ width: '100%' }}/>
         </Cell>
         <Cell columns={10}>
-          <Field name='name' render={custom('name')}/>
+          <Field name='name' render={Input('name')}/>
   
-          <Field name='summary' render={custom('summary', 'textarea')}/>
+          <Field name='summary' render={Input('summary', 'textarea')}/>
         </Cell>
       </Row>
       
@@ -148,10 +135,10 @@ const RenderForm = ({
       <section>
         <Row>
           <Cell columns={3}>
-            <Field name='author.name'/>
+            <Field name='author.name' render={Input('name')}/>
           </Cell>
           <Cell columns={3}>
-            <Field name='author.website'/>
+            <Field name='author.website' render={Input('website')}/>
           </Cell>
         </Row>
       </section>
@@ -160,18 +147,16 @@ const RenderForm = ({
       <section>
         <Row>
           <Cell columns={3}>
-            <Field name='details.preparationTime'/>
+            <Field name='details.preparationTime' render={Input('preparation time')}/>
           </Cell>
           <Cell columns={3}>
-            <Field name='details.cookingTime'/>
+            <Field name='details.cookingTime' render={Input('cooking time')}/>
           </Cell>
           <Cell columns={3}>
-            <Field name='details.servings' type='number'/>
+            <Field name='details.servings' render={Input('servings', 'number')}/>
           </Cell>
           <Cell columns={3}>
-            <Field name='details.url'/>
-          </Cell>
-          <Cell columns={12}>
+            <Field name='details.url' render={Input('recipe url')}/>
           </Cell>
         </Row>
       </section>

+ 79 - 9
recipes/src/components/RecipeForm/styles.scss

@@ -1,8 +1,9 @@
+@import 'styles/_variables.scss';
+
 .cbk-recipe-form {
   width: 100%;
-
-  input,
-  textarea {
+  
+  input {
     width: 100%;
     border: 0;
     padding: 4px 0;
@@ -11,30 +12,93 @@
   }
 
   .subrecipe-tabs {
-    
     ul.tab-header {
       display: flex;
       width: 100%;
       justify-content: space-evenly;
 
       .tab {
+        padding: 0 $spacing-small;
         width: 100%;
         display: flex;
         justify-content: space-between;
         cursor: pointer;
         align-self: center;
+        position: relative;
+        
+        &:hover {
+          background-color: rgb(248, 248, 248);
+          cursor: pointer;
+        }
+    
+        &--selected {
+          background-color: rgb(248, 248, 248);
+        }
+
+        &--selected.tab span::before {
+          width: 100%;
+        }
+
+        span {
+          position: absolute;
+          display: block;
+          width: 100%;
+          height: 100%;
+          top: 0;
+          left: 0;
+          pointer-events: none;
+        }
+
+        span::before {
+          content: "";
+          display: block;
+          position: absolute;
+          bottom: -2px;
+          left: 0;
+          width: 0;
+          height: 2px;
+        
+          -webkit-transition: all 0.4s;
+          -o-transition: all 0.4s;
+          -moz-transition: all 0.4s;
+          transition: all 0.4s;
+        
+          background: #7f7f7f;
+        }
+
+        input {
+          @include button();
+          font-family: 'Roboto';
+          border-bottom: 0;
+        }
 
         &__content {
-          padding: 20px;
           flex-basis: 90%;
+          width: 100;
+          cursor: pointer;
         }
 
         &--add {
           flex-basis: 0;
         }
 
-        button {
-          margin: 20px;
+        &--add:hover {
+          background: transparent;
+        }
+
+        button.remove {
+          align-self: center;
+          --mdc-ripple-fg-size: 14px;
+          --mdc-ripple-left: 5px;
+          --mdc-ripple-top: 5px;
+          width: 24px;
+          height: 24px;
+          padding: 6px;
+          font-size: 12px;
+  
+          .material-icons {
+            font-size: 12px;
+          }
         }
       }
     }
@@ -42,10 +106,16 @@
   }
 
   .ingredients-form {
+    min-height: 400px;
+    
     &-header {
       display: flex;
-      justify-content: space-around;
-      padding: 10px
+      color: $grey-600;
+      & > * {
+        flex: 1;
+        align-self: center;
+        @include button();
+      }
     }
 
     &-item {

+ 53 - 1
recipes/src/styles/_ui.scss

@@ -1 +1,53 @@
-$box-shadow: 0 2px 2px 0 rgba(0,0,0,.16), 0 0 2px 0 rgba(0,0,0,.12);
+$box-shadow: 0 2px 2px 0 rgba(0,0,0,.16), 0 0 2px 0 rgba(0,0,0,.12);
+
+@mixin lightInput() {
+  width: 100%;
+  position: relative;
+  margin-bottom: $spacing-regular;
+
+  input,
+  textarea {
+    width: 100%;
+    border: 0;
+    padding: 4px 0;
+    border-bottom: 1px solid #ccc;
+    background-color: transparent;
+  }
+
+  span {
+    position: absolute;
+    display: block;
+    width: 100%;
+    height: 100%;
+    top: 0;
+    left: 0;
+    pointer-events: none;
+  }
+  
+  span::before {
+    content: "";
+    display: block;
+    position: absolute;
+    bottom: -2px;
+    left: 0;
+    width: 0;
+    height: 2px;
+  
+    -webkit-transition: all 0.4s;
+    -o-transition: all 0.4s;
+    -moz-transition: all 0.4s;
+    transition: all 0.4s;
+  
+    background: #7f7f7f;
+  }
+  
+  input:focus + span::before,
+  textarea:focus + span::before {
+    width: 100%;
+  }
+  
+  input.has-value + span::before,
+  textarea.has-value + span::before {
+    width: 100%;
+  }
+}

+ 1 - 1
recipes/src/styles/_variables.scss

@@ -1,5 +1,5 @@
 @import './_colors.scss';
 @import './_fonts.scss';
 @import './_mixins.scss';
-@import './ui.scss';
+@import './_ui.scss';
 @import './spacing.scss';

+ 33 - 0
recipes/src/styles/app.scss

@@ -73,3 +73,36 @@ code {
   }
 
 }
+
+input,
+label,
+textarea
+{
+	margin:0;
+	border:0;
+	padding:0;
+	display:inline-block;
+	vertical-align:middle;
+	white-space:normal;
+	background:none;
+	line-height:1;
+}
+
+/* Remove the stupid outer glow in Webkit */
+input:focus,
+textarea:focus
+{
+	outline:0;
+}
+
+/* Box Sizing Reset
+-----------------------------------------------*/
+
+/* All of our custom controls should be what we expect them to be */
+input,
+textarea
+{
+	-webkit-box-sizing:content-box;
+	-moz-box-sizing:content-box;
+	box-sizing:content-box;
+}