TS+react自建元件庫 01
Hello World元件測試
import {FC} from 'react' interface IHello { message?: string; } const Hello:FC<IHello> = function(props){ let {message} = props; return ( <h2>{message}</h2> ) } Hello.defaultProps = { message : 'Hello World' } export default Hello;
點贊按鈕元件測試
import {FC,useState} from 'react' const GiveLike:FC = () => { let [like, setLike] = useState(0); return ( <button onClick = {() => setLike(like + 1)}> 👍{like} </button> ) } export default GiveLike;
滑鼠坐标元件測試
import {FC, useState, useEffect} from 'react' const MousePosition : FC = () => { const [positions,setPosition] = useState({x:0,y:0}) const updatePosition = (e:MouseEvent) => { setPosition({x:e.clientX,y:e.clientY}) } useEffect(() =>{ document.addEventListener('click',updatePosition) return( () => { document.removeEventListener('click',updatePosition) } ) }) return ( <div> 滑鼠坐标:X:{positions.x},Y:{positions.y} </div> ) } export default MousePosition;
KGD的樣式解決方案
①Inline CSS
②CSS in JS
③Sass/Less(KGD選擇的解決方案)
樣式系統檔案結構:
styles/ _variables.scss //各種變量以及可配置設定 _mixins.scss //全局mixins _functions.scss //全局functions components/ Button/ index.scss //元件的單獨樣式 ...
KGD的色彩體系
系統色闆 - 基礎色闆 + 中性色闆
産品色闆 - 品牌色 + 功能色
// 中性色彩 $white: #fff !default; // !default 關鍵字表示定義該變量後其不會被重新指派 $gray-100: #f8f9fa !default; $gray-200: #e9ecef !default; $gray-300: #dee2e6 !default; $gray-400: #ced4da !default; $gray-500: #adb5db !default; $gray-600: #6c757d !default; $gray-700: #495057 !default; $gray-800: #343a40 !default; $gray-900: #212529 !default; $black: #000 !default; // 基礎色闆 $blue: #0d6efd !default; $indigo: #6610f2 !default; $purple: #6f42c1 !default; $pink: #d63384 !default; $red: #dc3545 !default; $orange: #fd7e14 !default; $yellow: #fadb14 !default; $green: #52c41a !default; $teal: #20c997 !default; $cyan: #17a2b8 !default; // 系統色闆 $primary: $blue !default; $secondary: $gray-600 !default; $success: $green !default; $info: $cyan !default; $warning: $yellow !default; $danger: $red !default; $light: $gray-100 !default; $dark: $gray-800 !default;
KGD的樣式變量分類
tips:node-sass版本為5.0.0
- 基礎色彩系統
- 字型系統
- 表單
- 按鈕
- 邊框和陰影
- 可配置開關
Failed to compile. ./src/styles/index.scss (./node_modules/css-loFailed to compile. ./src/styles/index.scss (./node_modules/css-loFailed to compile. ./src/styles/index.scss (./node_modules/css-loFailed to compile. ./src/styles/index.scss (./node_modules/css-loader/dist/cjs.js??ref--5-oneOf-6-1!./node_modules/postcss-loader/src??postcss!./node_modules/resolve-url-loader??ref--5-oneOf-6-3!./node_modules/sass-loader/dist/cjs.js??ref--5-oneOf-6-4!./src/styles/index.scss) Node Sass version 6.0.1 is incompatible with ^4.0.0 || ^5.0.0. //版本不相容,此時node-sass版本為6.0.1
KGD的第一個元件-Button
需求分析
類型分析-type:主按鈕、預設按鈕、危險按鈕、連結按鈕
大小分析-size:預設按鈕、小型按鈕、大型按鈕
按鈕狀态:能否點選
樣式:高亮,文字居中,顔色
設計實作
插件引入:classnames --一個簡單的JavaScript工具,用于有條件地連接配接類名。
安裝指令:yarn add classnames @types/classnames --save
github位址
使用方式:
Button元件classNames('foo', 'bar'); // => 'foo bar' classNames('foo', { bar: true }); // => 'foo bar' classNames({ 'foo-bar': true }); // => 'foo-bar' classNames({ 'foo-bar': false }); // => '' classNames({ foo: true }, { bar: true }); // => 'foo bar' classNames({ foo: true, bar: true }); // => 'foo bar' // lots of arguments of various types classNames('foo', { bar: true, duck: false }, 'baz', { quux: true }); // => 'foo bar baz quux' // other falsy values are just ignored classNames(null, false, 'bar', undefined, 0, 1, { baz: null }, ''); // => 'bar 1'
import React, {FC} from 'react' import classNames from 'classnames' export enum ButtonType { Primary = 'primary', Danger = 'danger', Default = 'default', Link = 'link', } export enum ButtonSize { Large = 'lg', Small = 'sm', } interface BaseButton { className ?: string, btnType ?: ButtonType, size ?: ButtonSize, children ?: React.ReactNode, disabled ?: boolean, href ?: string, } type NativeButtonProps = BaseButton & React.ButtonHTMLAttributes<HTMLButtonElement> //擷取button原本具有的屬性并與自定義button元件類型合并 //交叉類型是将多個類型合并為一個類型 type AnchorButtonProps = BaseButton & React.AnchorHTMLAttributes<HTMLAnchorElement> //擷取a原本具有的屬性并與自定義button元件類型合并 type ButtonProps = Partial<NativeButtonProps & AnchorButtonProps> //映射類型:将一個已知的類型每個屬性都變為可選的 const Button : FC<ButtonProps> = (props) => { const { className, btnType, size, children, disabled, href, ...restProps //擷取所有原屬性 } = props //className允許使用者自定義className const classes = classNames('btn', className, { [`btn-${btnType}`] : btnType, [`btn-${size}`] : size, 'disabled' : btnType === ButtonType.Link && disabled, }) return btnType === ButtonType.Link && href ? ( <a className = {classes} href = {href} {...restProps} > {children} </a> ) : ( <button className = {classes} disabled = {disabled} {...restProps} > {children} </button> ) } Button.defaultProps = { disabled: false, btnType: ButtonType.Default } export default Button;