refactor: replace sass with postcss

This commit is contained in:
Haishan 2019-04-14 22:56:14 +08:00
parent 4a4f58c88a
commit 7dac1d44c7
53 changed files with 181 additions and 953 deletions

View file

@ -81,11 +81,12 @@
"husky": "^1.3.0",
"lint-staged": "^8.1.3",
"mini-css-extract-plugin": "^0.5.0",
"node-sass": "^4.10.0",
"postcss-extend-rule": "^2.0.0",
"postcss-import": "^12.0.1",
"postcss-loader": "^3.0.0",
"postcss-nested": "^4.1.2",
"prettier": "^1.16.4",
"react-hot-loader": "^4.6.3",
"sass-loader": "^7.0.1",
"style-loader": "^0.23.0",
"svg-sprite-loader": "^4.1.2",
"terser-webpack-plugin": "^1.2.2",

View file

@ -5,7 +5,7 @@ import Field from 'c/Field';
import Button from 'c/Button';
import SvgYacd from './SvgYacd';
import s0 from './APIConfig.module.scss';
import s0 from './APIConfig.module.css';
import { getClashAPIConfig, updateClashAPIConfig } from 'd/app';

View file

@ -7,7 +7,7 @@ import APIConfig from 'c/APIConfig';
import { closeModal } from 'd/modals';
import { fetchConfigs } from 'd/configs';
import s0 from './APIDiscovery.module.scss';
import s0 from './APIDiscovery.module.css';
const mapStateToProps = s => ({
modals: s.modals

View file

@ -1,7 +1,7 @@
import React from 'react';
import PropTypes from 'prop-types';
import s0 from 'c/Button.module.scss';
import s0 from 'c/Button.module.css';
const noop = () => {};
const Button = React.memo(function Button({ label, onClick = noop }) {

View file

@ -14,7 +14,7 @@
background: #387cec;
border: 1px solid #387cec;
color: #fff;
// background: darken(#555, 3%);
/* background: darken(#555, 3%); */
}
&:active {
transform: scale(0.97);

View file

@ -8,7 +8,7 @@ import ContentHeader from 'c/ContentHeader';
import Switch from 'c/Switch';
import ToggleSwitch from 'c/ToggleSwitch';
import Input from 'c/Input';
import s0 from 'c/Config.module.scss';
import s0 from 'c/Config.module.css';
const optionsRule = [
{

View file

@ -1,7 +1,7 @@
import React from 'react';
import PropTypes from 'prop-types';
import s0 from './ContentHeader.module.scss';
import s0 from './ContentHeader.module.css';
function ContentHeader({ title }) {
return (

View file

@ -3,7 +3,7 @@ import Icon from 'c/Icon';
import SvgYacd from './SvgYacd';
import github from 's/github.svg';
import s0 from './ErrorBoundaryFallback.module.scss';
import s0 from './ErrorBoundaryFallback.module.css';
const yacdRepoIssueUrl = 'https://github.com/haishanh/yacd/issues';
function ErrorBoundaryFallback() {

View file

@ -1,7 +1,7 @@
import React from 'react';
import PropTypes from 'prop-types';
import cx from 'classnames';
import s from './Field.module.scss';
import s from './Field.module.css';
const { useCallback } = React;

View file

@ -4,7 +4,7 @@
input {
-webkit-appearance: none;
background-color: transparent;
// background-color: var(--color-input-bg);
/* background-color: var(--color-input-bg); */
background-image: none;
border: none;
border-radius: 0;

View file

@ -4,7 +4,7 @@ import ContentHeader from 'c/ContentHeader';
import TrafficChart from 'c/TrafficChart';
import TrafficNow from 'c/TrafficNow';
import Loading from 'c/Loading';
import s0 from 'c/Home.module.scss';
import s0 from 'c/Home.module.css';
export default function Home() {
return (

View file

@ -1,7 +1,7 @@
import React from 'react';
import PropTypes from 'prop-types';
import s0 from './Input.module.scss';
import s0 from './Input.module.css';
export default function Input(props) {
return <input className={s0.input} {...props} />;

View file

@ -1,7 +1,7 @@
import React from 'react';
import PropTypes from 'prop-types';
import s0 from './Loading.module.scss';
import s0 from './Loading.module.css';
const Loading = ({ height }) => {
const style = height ? { height } : {};

View file

@ -1,7 +1,3 @@
// $color1: #2a477a;
$color1: #dddddd;
$size: 40px;
.loading {
width: 100%;
@ -12,10 +8,12 @@ $size: 40px;
}
.pulse {
width: $size;
height: $size;
--color1: #dddddd;
--size: 40px;
width: var(--size);
height: var(--size);
margin: 10px;
background-color: $color1;
background-color: var(--color1);
border-radius: 100%;
animation: pulseScaleOut 1s infinite ease-in-out;
}

View file

@ -13,7 +13,7 @@ import { fetchLogs } from '../api/logs';
import LogSearch from './LogSearch';
import { getLogsForDisplay, appendLog } from 'd/logs';
import s0 from 'c/Logs.module.scss';
import s0 from 'c/Logs.module.css';
const paddingBottom = 30;
const colors = {
debug: 'none',

View file

@ -1,6 +1,3 @@
$colorf: #eee;
$heightHeader: 76px;
.logMeta {
display: flex;
align-items: center;
@ -10,7 +7,7 @@ $heightHeader: 76px;
}
.logType {
color: $colorf;
color: #eee;
flex-shrink: 0;
text-align: center;
width: 66px;
@ -32,13 +29,13 @@ $heightHeader: 76px;
font-family: 'Roboto Mono', Menlo, monospace;
align-items: center;
padding: 8px 0;
// force wrap
/* force wrap */
width: 100%;
white-space: pre;
overflow: auto;
}
//////////
/*******************/
.logsWrapper {
margin: 0;
@ -59,7 +56,7 @@ $heightHeader: 76px;
padding: 10px 40px;
}
/////////
/*******************/
.logPlaceholder {
display: flex;

View file

@ -3,7 +3,7 @@ import PropTypes from 'prop-types';
import Modal from 'react-modal';
import cx from 'classnames';
import s0 from './Modal.module.scss';
import s0 from './Modal.module.css';
function ModalAPIConfig({
isOpen,

View file

@ -1,11 +1,9 @@
.overlay {
position: fixed;
// z-index: 1000;
top: 0;
right: 0;
left: 0;
bottom: 0;
// background: rgba(255, 255, 255, 0.5);
background: #444;
}
@ -18,6 +16,5 @@
transform: translate(-50%, -50%);
background: #444;
padding: 20px;
// border: 1px solid #ccc;
border-radius: 10px;
}

View file

@ -5,7 +5,7 @@ import ContentHeader from 'c/ContentHeader';
import ProxyGroup from 'c/ProxyGroup';
import Button from 'c/Button';
import s0 from 'c/Proxies.module.scss';
import s0 from 'c/Proxies.module.css';
import {
getProxies,

View file

@ -14,7 +14,7 @@ import direct from 's/direct.svg';
import http from 's/http.svg';
import group from 's/group.svg';
import s0 from './Proxy.module.scss';
import s0 from './Proxy.module.css';
import { getDelay, getProxies } from 'd/proxies';

View file

@ -5,7 +5,7 @@ import { useActions, useStoreState } from 'm/store';
import Proxy from 'c/Proxy';
import s0 from './ProxyGroup.module.scss';
import s0 from './ProxyGroup.module.css';
import { getProxies, switchProxy } from 'd/proxies';

View file

@ -20,7 +20,6 @@
width: 300px;
padding: 10px 5px;
transition: transform 0.2s ease-in-out;
// transition: transform 0.4s ease, color 0.4s ease;
&.proxySelectable {
cursor: pointer;
&:hover {

View file

@ -1,7 +1,7 @@
import React, { useMemo } from 'react';
import PropTypes from 'prop-types';
import s0 from './ProxyLatency.module.scss';
import s0 from './ProxyLatency.module.css';
const colorMap = {
good: '#67C23A',

View file

@ -1,8 +1,6 @@
.proxyLatency {
border-radius: 20px;
margin: 10px 0;
// padding: 3px 5px;
padding: 3px 0;
color: #eee;
// background: #ccc;
}

View file

@ -1,4 +1,3 @@
// this font-family only covers latin
@font-face {
font-family: 'Roboto Mono';
font-style: normal;

View file

@ -10,8 +10,8 @@ import Logs from 'c/Logs';
import Config from 'c/Config';
import APIDiscovery from 'c/APIDiscovery';
import { store } from '../store/configureStore';
import './Root.scss';
import s0 from './Root.module.scss';
import './Root.css';
import s0 from './Root.module.css';
const Proxies = React.lazy(() =>
import(/* webpackChunkName: "proxies" */

View file

@ -0,0 +1,33 @@
.app {
display: flex;
background: var(--color-background);
color: var(--color-text);
min-height: 300px;
height: 100vh;
@media (max-width: 768px) {
flex-direction: column;
}
}
.content {
flex-grow: 1;
overflow: auto;
/*
$w: 7px;
&::-webkit-scrollbar {
width: $w;
}
&::-webkit-scrollbar-thumb {
border-radius: 20px;
background-color: rgba(221, 221, 221, 0.7);
}
&::-webkit-scrollbar-corner {
background: transparent;
}
*/
}

View file

@ -1,30 +0,0 @@
.app {
display: flex;
background: var(--color-background);
color: var(--color-text);
min-height: 300px;
height: 100vh;
@media (max-width: 768px) {
flex-direction: column;
}
}
.content {
flex-grow: 1;
overflow: auto;
// background: #202020;
// $w: 7px;
// &::-webkit-scrollbar {
// width: $w;
// }
// &::-webkit-scrollbar-thumb {
// border-radius: 20px;
// background-color: rgba(221, 221, 221, 0.7);
// }
// &::-webkit-scrollbar-corner {
// background: transparent;
// }
}

View file

@ -1,7 +1,7 @@
import React from 'react';
import PropTypes from 'prop-types';
import s0 from './Rule.module.scss';
import s0 from './Rule.module.css';
const colorMap = {
_default: '#59caf9',
@ -26,9 +26,7 @@ function Rule({ type, payload, proxy, id }) {
<div className={s0.b}>{payload}</div>
<div className={s0.a}>
<div className={s0.type}>{type}</div>
<div className={s0.proxy} style={styleProxy}>
{proxy}
</div>
<div style={styleProxy}>{proxy}</div>
</div>
</div>
</div>

View file

@ -15,7 +15,6 @@
display: flex;
align-items: center;
font-size: 12px;
opacity: 0.8;
}
@ -28,11 +27,3 @@
.type {
width: 110px;
}
.proxy {
// background: #f5bc41;
// background: #eee;
// color: #eee;
// padding: 5px;
// border-radius: 5px;
}

View file

@ -10,7 +10,7 @@ import useRemainingViewPortHeight from '../hooks/useRemainingViewPortHeight';
import { getRules, fetchRules, fetchRulesOnce } from 'd/rules';
import s0 from './Rules.module.scss';
import s0 from './Rules.module.css';
const paddingBottom = 30;
const mapStateToProps = s => ({

View file

@ -6,7 +6,7 @@ import { useActions, useStoreState } from 'm/store';
import debounce from 'lodash-es/debounce';
import s0 from './Search.module.scss';
import s0 from './Search.module.css';
function getSerachComponent({ mapStateToProps, actions }) {
return memo(function RuleSearch() {

View file

@ -1,9 +1,5 @@
.RuleSearch {
// width: 100%;
// padding: 0 40px;
// height: 40px;
padding: 0 40px 5px;
// height: 40px;
}
.RuleSearchContainer {

View file

@ -17,7 +17,7 @@ import SvgCommand from './SvgCommand';
import SvgSettings from './SvgSettings';
import SvgFile from './SvgFile';
import s from 'c/SideBar.module.scss';
import s from 'c/SideBar.module.css';
const icons = {
activity: SvgActivity,

View file

@ -45,7 +45,7 @@
}
}
// a router link
/* a router link */
.row {
color: var(--color-text);
text-decoration: none;
@ -56,7 +56,6 @@
@media (max-width: 768px) {
flex-direction: column;
// display: flex;
}
svg {
@ -82,7 +81,7 @@
}
.themeSwitchContainer {
$sz: 50px;
--sz: 50px;
@media (max-width: 768px) {
display: none;
@ -92,8 +91,8 @@
bottom: 0;
left: 50%;
transform: translateX(-50%);
width: $sz;
height: $sz;
width: var(--sz);
height: var(--sz);
padding: 20px 0;
display: flex;
justify-content: center;

View file

@ -1,7 +1,7 @@
import React from 'react';
import PropTypes from 'prop-types';
import s0 from 'c/Switch.module.scss';
import s0 from 'c/Switch.module.css';
const noop = () => {};
function Switch({ checked = false, onChange = noop, name = '' }) {

View file

@ -1,17 +1,16 @@
// steal from https://codepen.io/joshnh/pen/hjbuH
$white: #fff;
// $green: #53d76a;
$grey: #d3d3d3;
$color-theme: #047aff;
/* steal from https://codepen.io/joshnh/pen/hjbuH */
input.switch[type='checkbox'] {
--white: #fff;
--grey: #d3d3d3;
--color-theme: #047aff;
appearance: none;
outline: none;
background-color: darken($white, 2%);
border: 1px solid $grey;
background-color: darken(var(--white), 2%);
border: 1px solid var(--grey);
border-radius: 26px;
box-shadow: inset 0 0 0 1px $grey;
box-shadow: inset 0 0 0 1px var(--grey);
cursor: pointer;
height: 28px;
position: relative;
@ -20,8 +19,8 @@ input.switch[type='checkbox'] {
vertical-align: top;
&:after {
background-color: $white;
border: 1px solid $grey;
background-color: var(--white);
border: 1px solid var(--grey);
border-radius: 24px;
box-shadow: inset 0 -3px 3px hsla(0, 0%, 0%, 0.025),
0 1px 4px hsla(0, 0%, 0%, 0.15), 0 4px 4px hsla(0, 0%, 0%, 0.1);
@ -35,13 +34,13 @@ input.switch[type='checkbox'] {
transition: border 0.25s 0.15s, left 0.25s 0.1s, right 0.15s 0.175s;
}
&:checked {
border-color: $color-theme;
box-shadow: inset 0 0 0 13px $color-theme;
border-color: var(--color-theme);
box-shadow: inset 0 0 0 13px var(--color-theme);
padding-left: 18px;
transition: border 0.25s, box-shadow 0.25s, padding 0.25s 0.15s;
&:after {
border-color: $color-theme;
border-color: var(--color-theme);
left: 16px;
right: 0;
transition: border 0.25s, left 0.15s 0.25s, right 0.25s 0.175s;

View file

@ -1,7 +1,7 @@
import React, { useMemo } from 'react';
import PropTypes from 'prop-types';
import s0 from 'c/ToggleSwitch.module.scss';
import s0 from 'c/ToggleSwitch.module.css';
function ToggleSwitch({ options, value, name, onChange }) {
const idxSelected = useMemo(() => options.map(o => o.value).indexOf(value), [

View file

@ -5,7 +5,7 @@ import { useStoreState } from 'm/store';
import { getClashAPIConfig } from 'd/app';
import { fetchData } from '../api/traffic';
import s0 from 'c/TrafficNow.module.scss';
import s0 from 'c/TrafficNow.module.css';
export default function TrafficNow() {
const { upStr, downStr } = useSpeed();
@ -26,20 +26,17 @@ export default function TrafficNow() {
function useSpeed() {
const [speed, setSpeed] = useState({ upStr: '0 B/s', downStr: '0 B/s' });
const { hostname, port, secret } = useStoreState(getClashAPIConfig);
useEffect(
() => {
return fetchData({
hostname,
port,
secret
}).subscribe(o =>
setSpeed({
upStr: prettyBytes(o.up) + '/s',
downStr: prettyBytes(o.down) + '/s'
})
);
},
[hostname, port, secret]
);
useEffect(() => {
return fetchData({
hostname,
port,
secret
}).subscribe(o =>
setSpeed({
upStr: prettyBytes(o.up) + '/s',
downStr: prettyBytes(o.down) + '/s'
})
);
}, [hostname, port, secret]);
return speed;
}

View file

@ -2,7 +2,6 @@
const path = require('path');
const webpack = require('webpack');
// const { rules } = require('./webpack.common');
const TerserPlugin = require('terser-webpack-plugin');
const CopyPlugin = require('copy-webpack-plugin');
const CleanPlugin = require('clean-webpack-plugin');
@ -96,11 +95,15 @@ const loaders = {
postcss: {
loader: 'postcss-loader',
options: {
plugins: () => [require('autoprefixer'), require('cssnano')()]
plugins: () =>
[
require('postcss-import')(),
require('postcss-nested')(),
require('autoprefixer')(),
require('postcss-extend-rule')(),
isDev ? false : require('cssnano')()
].filter(Boolean)
}
},
sass: {
loader: 'sass-loader'
}
};
@ -123,27 +126,6 @@ const rulesCssModules = {
].filter(Boolean)
};
const rulesSassModules = {
test: /\.module\.scss$/,
use: [
isDev ? loaders.style : MiniCssExtractPlugin.loader,
loaders.cssModule,
loaders.postcss,
loaders.sass
].filter(Boolean)
};
const rulesSass = {
test: /\.scss$/,
exclude: /\.module\.scss$/,
use: [
isDev ? loaders.style : MiniCssExtractPlugin.loader,
loaders.css,
loaders.postcss,
loaders.sass
].filter(Boolean)
};
const cssExtractPlugin = new MiniCssExtractPlugin({
filename: isDev ? '[name].bundle.css' : '[name].[chunkhash].css'
});
@ -202,9 +184,7 @@ module.exports = {
]
},
rulesCss,
rulesCssModules,
rulesSass,
rulesSassModules
rulesCssModules
]
},
optimization: {

864
yarn.lock

File diff suppressed because it is too large Load diff