docs: copy import string when cell clicked

This commit is contained in:
unix
2020-05-03 00:12:57 +08:00
parent ed8d36897d
commit 9b8b046015
2 changed files with 105 additions and 45 deletions

View File

@@ -0,0 +1,71 @@
import React from 'react'
import { Text, useTheme } from 'components'
export const getFileName = (name: string): string => {
return name.replace(/^(.)/, g => g.toLowerCase())
}
export const getImportString = (name: string) => {
const fileName = getFileName(name)
const single = `import ${name} from '@zeit-ui/react-icons/${fileName}'`
const normal = `import { ${name} } from '@zeit-ui/react-icons'`
return {
single, normal,
}
}
interface Props {
component: React.ComponentType<any>
name: string
onClick: (name: string) => void
}
const IconsCell: React.FC<Props> = ({
component: Component, name, onClick
}) => {
const theme = useTheme()
return (
<div className="icon-item" key={name} onClick={() => onClick(name)}>
<Component />
<Text type="secondary" small>{name}</Text>
<style jsx>{`
.icon-item {
display: flex;
flex-direction: column;
align-items: center;
justify-content: space-evenly;
flex-grow: 0;
flex-basis: 125px;
min-width: 0px;
height: 95px;
margin: 12px 5px;
border-radius: ${theme.layout.radius};
box-sizing: border-box;
cursor: pointer;
user-select: none;
transition: all 150ms ease-in-out;
}
.icon-item > :global(small) {
display: inline-block;
width: 90%;
text-align: center;
overflow: hidden;
text-overflow: ellipsis;
}
.icon-item:hover {
box-shadow: ${theme.expressiveness.shadowMedium};
}
@media only screen and (max-width: ${theme.layout.breakpointMobile}) {
.icon-item {
flex-basis: 30%;
}
}
`}</style>
</div>
)
}
export default React.memo(IconsCell)

View File

@@ -1,15 +1,32 @@
import React from 'react'
import { Card, Input, Text, useInput, useTheme } from 'components'
import React, { useState } from 'react'
import { Card, Input, useInput, Modal, useModal, Snippet } from 'components'
import * as Icon from '@zeit-ui/react-icons'
import IconsCell, { getImportString } from './icons-cell'
const ImportSnippet: React.FC<React.PropsWithChildren<{}>> = ({ children }) => {
return (
<Snippet>
{children}
<style jsx>{`
:global(pre:before) {
display: none;
}
`}</style>
</Snippet>
)
}
const Icons: React.FC = () => {
const theme = useTheme()
const { setVisible, bindings: modalBindings } = useModal()
const { state: query, bindings } = useInput('')
const [importStr, setImportStr] = useState({ title: '', single: '', normal: '' })
const icons = Object.entries(Icon).filter(
([name]) => !query || name.toLowerCase().includes(query.toLowerCase())
)
const clickHandler = (name: string) => {
console.log(name)
const onCellClick = (name: string) => {
const { single, normal } = getImportString(name)
setImportStr({ title: name, single, normal })
setVisible(true)
}
return (
@@ -18,13 +35,20 @@ const Icons: React.FC = () => {
<Card>
<Input width="100%" icon={<Icon.Search />} placeholder="Search" {...bindings} />
<div className="icons-grid">
{icons.map(([name, Component]) => (
<div className="icon-item" key={name} onClick={() => clickHandler(name)}>
<Component />
<Text type="secondary" small>{name}</Text>
</div>
{icons.map(([name, component], index) => (
<IconsCell name={name} component={component} key={`${name}-${index}`}
onClick={onCellClick} />
))}
</div>
<Modal {...modalBindings}>
<Modal.Title>{importStr.title}</Modal.Title>
<Modal.Content>
<p>Import:</p>
<ImportSnippet>{importStr.normal}</ImportSnippet>
<p>Import single component:</p>
<ImportSnippet>{importStr.single}</ImportSnippet>
</Modal.Content>
</Modal>
</Card>
<style jsx>{`
.title {
@@ -43,41 +67,6 @@ const Icons: React.FC = () => {
margin-top: 8pt;
justify-content: space-around;
}
.icon-item {
display: flex;
flex-direction: column;
align-items: center;
justify-content: space-evenly;
flex-grow: 0;
flex-basis: 125px;
min-width: 0px;
height: 95px;
margin: 12px 5px;
border-radius: ${theme.layout.radius};
box-sizing: border-box;
cursor: pointer;
user-select: none;
transition: all 150ms ease-in-out;
}
.icon-item > :global(small) {
display: inline-block;
width: 90%;
text-align: center;
overflow: hidden;
text-overflow: ellipsis;
}
.icon-item:hover {
box-shadow: ${theme.expressiveness.shadowMedium};
}
@media only screen and (max-width: ${theme.layout.breakpointMobile}) {
.icon-item {
flex-basis: 30%;
}
}
`}</style>
</>
)