mirror of
https://github.com/tusen-ai/naive-ui.git
synced 2024-12-03 04:21:34 +08:00
feat(rate): basic rate
This commit is contained in:
parent
92fb6928e4
commit
a5f73be880
0
demo/documentation/components/rate/index.entry
Normal file
0
demo/documentation/components/rate/index.entry
Normal file
4
demo/documentation/components/rate/zhCN/basic.demo.md
Normal file
4
demo/documentation/components/rate/zhCN/basic.demo.md
Normal file
@ -0,0 +1,4 @@
|
||||
# 基础用法
|
||||
```html
|
||||
<n-rate />
|
||||
```
|
14
demo/documentation/components/rate/zhCN/index.demo-entry.md
Normal file
14
demo/documentation/components/rate/zhCN/index.demo-entry.md
Normal file
@ -0,0 +1,14 @@
|
||||
# 评分 Rate
|
||||
|
||||
## 演示
|
||||
```demo
|
||||
basic
|
||||
```
|
||||
|
||||
## Props
|
||||
|名称|类型|默认值|说明|
|
||||
|-|-|-|-|
|
||||
|count|`number`|`5`||
|
||||
|value|`number`|`undefined`||
|
||||
|default-value|`number`|`0`||
|
||||
|on-update:value|`(value: number) => any`|`undefined`||
|
@ -248,6 +248,12 @@ export default function (instance) {
|
||||
titleExtra: 'Radio',
|
||||
path: `/${lang}/${theme}/doc` + '/n-radio'
|
||||
},
|
||||
{
|
||||
name: 'Rate',
|
||||
title: '评分',
|
||||
titleExtra: 'Rate',
|
||||
path: `/${lang}/${theme}/doc` + '/n-rate'
|
||||
},
|
||||
{
|
||||
name: 'Select',
|
||||
title: '选择器',
|
||||
@ -659,6 +665,10 @@ export default function (instance) {
|
||||
name: 'Radio',
|
||||
path: `/${lang}/${theme}/doc` + '/n-radio'
|
||||
},
|
||||
{
|
||||
name: 'Rate',
|
||||
path: `/${lang}/${theme}/doc` + '/n-rate'
|
||||
},
|
||||
{
|
||||
name: 'Select',
|
||||
path: `/${lang}/${theme}/doc` + '/n-select'
|
||||
|
@ -76,6 +76,7 @@ import code from '../documentation/components/code'
|
||||
import upload from '../documentation/components/upload'
|
||||
import table from '../documentation/components/table'
|
||||
import space from '../documentation/components/space'
|
||||
import rate from '../documentation/components/rate'
|
||||
|
||||
import Documentation from '../Documentation'
|
||||
|
||||
@ -156,6 +157,7 @@ export const childRoutes = withPrefix('/:lang/:theme/doc', [
|
||||
{ path: '/n-upload', component: upload },
|
||||
{ path: '/n-table', component: table },
|
||||
{ path: '/n-space', component: space },
|
||||
{ path: '/n-rate', component: rate },
|
||||
// deprecated
|
||||
{ path: '/n-nimbus-service-layout', component: nimbusServiceLayout }
|
||||
])
|
||||
|
@ -48,6 +48,7 @@ import Popselect from './popselect'
|
||||
import Popup from './popover'
|
||||
import Progress from './progress'
|
||||
import Radio from './radio'
|
||||
import Rate from './rate'
|
||||
import Result from './result'
|
||||
import Select from './select'
|
||||
import Scrollbar from './scrollbar'
|
||||
@ -201,6 +202,8 @@ import descriptionsLightStyle from './descriptions/styles/light'
|
||||
import descriptionsDarkStyle from './descriptions/styles/dark'
|
||||
import formLightStyle from './form/styles/light'
|
||||
import formDarkStyle from './form/styles/dark'
|
||||
import rateLightStyle from './rate/styles/light'
|
||||
import rateDarkStyle from './rate/styles/dark'
|
||||
|
||||
// Can be remove after refactoring
|
||||
import baseSelectionLightStyle from './_base/selection/styles/light'
|
||||
@ -294,6 +297,7 @@ export default create({
|
||||
InputGroupLabelStyle,
|
||||
DynamicTags,
|
||||
Space,
|
||||
Rate,
|
||||
// Deprecated
|
||||
NimbusServiceLayout,
|
||||
NimbusFormCard,
|
||||
@ -430,6 +434,8 @@ export default create({
|
||||
formDarkStyle,
|
||||
spaceDarkStyle,
|
||||
spaceLightStyle,
|
||||
rateDarkStyle,
|
||||
rateLightStyle,
|
||||
// Can be remove after refactoring
|
||||
baseSelectionLightStyle,
|
||||
baseSelectionDarkStyle
|
||||
|
8
src/rate/index.js
Normal file
8
src/rate/index.js
Normal file
@ -0,0 +1,8 @@
|
||||
/* istanbul ignore file */
|
||||
import Rate from './src/Rate.vue'
|
||||
|
||||
Rate.install = function (app, naive) {
|
||||
app.component(naive.componentPrefix + Rate.name, Rate)
|
||||
}
|
||||
|
||||
export default Rate
|
118
src/rate/src/Rate.vue
Normal file
118
src/rate/src/Rate.vue
Normal file
@ -0,0 +1,118 @@
|
||||
<template>
|
||||
<div
|
||||
class="n-rate"
|
||||
:class="{
|
||||
[`n-${mergedTheme}-theme`]: mergedTheme
|
||||
}"
|
||||
@mouseleave="handleMouseLeave(index)"
|
||||
>
|
||||
<div
|
||||
v-for="index in count"
|
||||
:key="index"
|
||||
class="n-rate__item"
|
||||
:class="{
|
||||
'n-rate__item--active':
|
||||
hoverIndex !== null
|
||||
? index <= hoverIndex
|
||||
: index < mergedValue
|
||||
}"
|
||||
@click="handleClick(index)"
|
||||
@mouseenter="handleMouseEnter(index)"
|
||||
>
|
||||
<n-icon>
|
||||
<star-icon />
|
||||
</n-icon>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
|
||||
<script>
|
||||
import {
|
||||
configurable,
|
||||
themeable,
|
||||
usecssr,
|
||||
asformitem
|
||||
} from '../../_mixins'
|
||||
import {
|
||||
toRef,
|
||||
ref
|
||||
} from 'vue'
|
||||
import {
|
||||
useMergedState
|
||||
} from 'vooks'
|
||||
import {
|
||||
call
|
||||
} from '../../_utils'
|
||||
import styles from './styles'
|
||||
import StarIcon from './StarIcon.vue'
|
||||
import NIcon from '../../icon'
|
||||
|
||||
export default {
|
||||
name: 'Rate',
|
||||
components: {
|
||||
NIcon,
|
||||
StarIcon
|
||||
},
|
||||
mixins: [
|
||||
configurable,
|
||||
themeable,
|
||||
asformitem(),
|
||||
usecssr(styles)
|
||||
],
|
||||
props: {
|
||||
count: {
|
||||
type: Number,
|
||||
default: 5
|
||||
},
|
||||
value: {
|
||||
type: Number,
|
||||
default: undefined
|
||||
},
|
||||
defaultValue: {
|
||||
type: Number,
|
||||
default: 0
|
||||
},
|
||||
// eslint-disable-next-line vue/prop-name-casing
|
||||
'onUpdate:value': {
|
||||
type: [Function, Array],
|
||||
default: undefined
|
||||
}
|
||||
},
|
||||
setup (props) {
|
||||
const controlledValueRef = toRef(props, 'value')
|
||||
const uncontrolledValueRef = ref(props.defaultValue)
|
||||
return {
|
||||
mergedValue: useMergedState(
|
||||
controlledValueRef,
|
||||
uncontrolledValueRef
|
||||
),
|
||||
uncontrolledValue: uncontrolledValueRef,
|
||||
hoverIndex: ref(null)
|
||||
}
|
||||
},
|
||||
methods: {
|
||||
doUpdateValue (value) {
|
||||
const {
|
||||
'onUpdate:value': onUpdateValue,
|
||||
nTriggerFormChange,
|
||||
nTriggerFormInput
|
||||
} = this
|
||||
if (onUpdateValue) {
|
||||
call(onUpdateValue, value)
|
||||
}
|
||||
this.uncontrolledValue = value
|
||||
nTriggerFormChange()
|
||||
nTriggerFormInput()
|
||||
},
|
||||
handleMouseEnter (index) {
|
||||
this.hoverIndex = index
|
||||
},
|
||||
handleMouseLeave (index) {
|
||||
this.hoverIndex = null
|
||||
},
|
||||
handleClick (index) {
|
||||
this.doUpdateValue(index + 1)
|
||||
}
|
||||
}
|
||||
}
|
||||
</script>
|
9
src/rate/src/StarIcon.vue
Normal file
9
src/rate/src/StarIcon.vue
Normal file
@ -0,0 +1,9 @@
|
||||
<template>
|
||||
<svg viewBox="0 0 28 28" version="1.1" xmlns="http://www.w3.org/2000/svg" xmlns:xlink="http://www.w3.org/1999/xlink">
|
||||
<g stroke="none" stroke-width="1" fill-rule="evenodd">
|
||||
<g fill-rule="nonzero">
|
||||
<path d="M14.4373398,3.10348696 C14.6345524,3.20081719 14.7941799,3.36044472 14.8915102,3.55765732 L17.8153782,9.48206111 L24.353346,10.4320834 C24.8998908,10.511501 25.2785723,11.0189439 25.1991547,11.5654888 C25.1675302,11.7831258 25.065043,11.9842682 24.9075593,12.1377768 L20.1766414,16.749282 L21.2934597,23.2608319 C21.3868207,23.8051684 21.0212328,24.3221243 20.4768964,24.4154853 C20.2601388,24.4526621 20.0371707,24.4173475 19.8425102,24.3150084 L13.9947741,21.2406716 L8.14703796,24.3150084 C7.65819337,24.5720092 7.05356621,24.3840627 6.79656541,23.8952181 C6.69422634,23.7005576 6.65891166,23.4775895 6.69608851,23.2608319 L7.81290673,16.749282 L3.08198882,12.1377768 C2.68650524,11.7522756 2.67841294,11.1191623 3.06391415,10.7236788 C3.21742275,10.5661951 3.41856517,10.4637079 3.6362022,10.4320834 L10.1741699,9.48206111 L13.098038,3.55765732 C13.3424603,3.06240366 13.9420861,2.85906466 14.4373398,3.10348696 Z" />
|
||||
</g>
|
||||
</g>
|
||||
</svg>
|
||||
</template>
|
11
src/rate/src/styles/index.js
Normal file
11
src/rate/src/styles/index.js
Normal file
@ -0,0 +1,11 @@
|
||||
import themedBaseStyle from './themed-base.cssr.js'
|
||||
|
||||
export default [
|
||||
{
|
||||
key: 'mergedTheme',
|
||||
watch: [
|
||||
'mergedTheme'
|
||||
],
|
||||
CNode: themedBaseStyle
|
||||
}
|
||||
]
|
51
src/rate/src/styles/themed-base.cssr.js
Normal file
51
src/rate/src/styles/themed-base.cssr.js
Normal file
@ -0,0 +1,51 @@
|
||||
import { c, cTB, cB, cE, cM } from '../../../_utils/cssr'
|
||||
|
||||
export default c([
|
||||
({ props }) => {
|
||||
const {
|
||||
itemColor,
|
||||
itemColorActive
|
||||
} = props.$local
|
||||
const {
|
||||
cubicBezierEaseInOut
|
||||
} = props.$base
|
||||
return cTB('rate', {
|
||||
display: 'inline-flex',
|
||||
flexWrap: 'no-wrap'
|
||||
}, [
|
||||
cE('item', {
|
||||
transition: `transform .1s ${cubicBezierEaseInOut}`,
|
||||
transform: 'scale(1)'
|
||||
}, [
|
||||
c('&:hover', {
|
||||
transform: 'scale(1.05)'
|
||||
}, [
|
||||
cB('icon', {
|
||||
transition: `
|
||||
fill .1s ${cubicBezierEaseInOut},
|
||||
stroke .1s ${cubicBezierEaseInOut}
|
||||
`
|
||||
})
|
||||
]),
|
||||
c('&:active', {
|
||||
transform: 'scale(0.96)'
|
||||
}),
|
||||
c('&:not(:first-child)', {
|
||||
marginLeft: '2px'
|
||||
}),
|
||||
cB('icon', {
|
||||
fontSize: '24px',
|
||||
cursor: 'pointer',
|
||||
fill: itemColor,
|
||||
stroke: itemColor
|
||||
}),
|
||||
cM('active', [
|
||||
cB('icon', {
|
||||
fill: itemColorActive,
|
||||
stroke: itemColorActive
|
||||
})
|
||||
])
|
||||
])
|
||||
])
|
||||
}
|
||||
])
|
16
src/rate/styles/dark.js
Normal file
16
src/rate/styles/dark.js
Normal file
@ -0,0 +1,16 @@
|
||||
import create from '../../_styles/utils/create-component-base'
|
||||
import iconStyle from '../../icon/styles/dark'
|
||||
|
||||
export default create({
|
||||
theme: 'dark',
|
||||
name: 'Rate',
|
||||
peer: [
|
||||
iconStyle
|
||||
],
|
||||
getDerivedVariables ({ base, derived }) {
|
||||
return {
|
||||
itemColor: derived.railColor,
|
||||
itemColorActive: derived.primaryColor
|
||||
}
|
||||
}
|
||||
})
|
16
src/rate/styles/light.js
Normal file
16
src/rate/styles/light.js
Normal file
@ -0,0 +1,16 @@
|
||||
import create from '../../_styles/utils/create-component-base'
|
||||
import iconStyle from '../../icon/styles/dark'
|
||||
|
||||
export default create({
|
||||
theme: 'light',
|
||||
name: 'Rate',
|
||||
peer: [
|
||||
iconStyle
|
||||
],
|
||||
getDerivedVariables ({ base, derived }) {
|
||||
return {
|
||||
itemColor: derived.railColor,
|
||||
itemColorActive: derived.primaryColor
|
||||
}
|
||||
}
|
||||
})
|
Loading…
Reference in New Issue
Block a user