@mekari/pixel-avatar
Advanced tools
Comparing version 0.1.0 to 0.2.0
@@ -17,2 +17,3 @@ 'use strict'; | ||
* @prop {string|array} borderColor - Border color of avatar. | ||
* @prop {string|array} backgroundColor - Background color of avatar. | ||
*/ | ||
@@ -30,3 +31,4 @@ const useAvatarProps = { | ||
}, | ||
borderColor: [String] | ||
borderColor: [String], | ||
backgroundColor: [String] | ||
}; | ||
@@ -47,20 +49,55 @@ | ||
}; | ||
const sizeStyles = { | ||
sm: { | ||
width: 6, | ||
height: 6, | ||
lineHeight: 'xs', | ||
fontSize: `xs` | ||
}, | ||
md: { | ||
width: 8, | ||
height: 8, | ||
lineHeight: 'sm', | ||
fontSize: `sm` | ||
}, | ||
lg: { | ||
width: 12, | ||
height: 12, | ||
lineHeight: 'xl', | ||
fontSize: `xl` | ||
const sizeStyles = ({ | ||
size, | ||
showBorder, | ||
theme | ||
}) => { | ||
const getSizeCalculation = size => { | ||
if (showBorder) return `calc(${theme.sizes[size]} + 2px)`; | ||
return size; | ||
}; | ||
const variantStyles = { | ||
sm: { | ||
width: getSizeCalculation(6), | ||
height: getSizeCalculation(6), | ||
lineHeight: 'xs', | ||
fontSize: `xs` | ||
}, | ||
md: { | ||
width: getSizeCalculation(8), | ||
height: getSizeCalculation(8), | ||
lineHeight: 'sm', | ||
fontSize: `sm` | ||
}, | ||
lg: { | ||
width: getSizeCalculation(12), | ||
height: getSizeCalculation(12), | ||
lineHeight: 'lg', | ||
fontSize: `lg` | ||
}, | ||
xl: { | ||
width: getSizeCalculation(20), | ||
height: getSizeCalculation(20), | ||
lineHeight: 'xl', | ||
fontSize: `2xl` | ||
} | ||
}; | ||
switch (size) { | ||
case 'sm': | ||
return variantStyles['sm']; | ||
case 'md': | ||
return variantStyles['md']; | ||
case 'lg': | ||
return variantStyles['lg']; | ||
case 'xl': | ||
return variantStyles['xl']; | ||
default: | ||
return variantStyles['md']; | ||
} | ||
@@ -72,10 +109,27 @@ }; | ||
showBorder, | ||
borderColor | ||
borderColor, | ||
backgroundColor, | ||
isClickable, | ||
theme | ||
}) => { | ||
const color = { | ||
gray: 'gray.50', | ||
sky: 'sky.400', | ||
teal: 'teal.400', | ||
violet: 'violet.400', | ||
amber: 'amber.400', | ||
rose: 'rose.400', | ||
stone: 'stone.400', | ||
lime: 'lime.400', | ||
pink: 'pink.400' | ||
}; | ||
return { | ||
backgroundColor: name ? 'gray.50' : 'gray.400', | ||
color: name ? 'gray.600' : 'white', | ||
...(showBorder && borderColor && { | ||
border: '2px', | ||
borderColor: borderColor | ||
bg: name ? color[backgroundColor] : 'gray.400', | ||
color: backgroundColor === 'gray' ? name ? 'gray.600' : 'white' : 'white', | ||
...(showBorder && { | ||
borderWidth: theme.sizes['0.5'], | ||
borderColor: borderColor || 'white' | ||
}), | ||
...(isClickable && { | ||
cursor: 'pointer' | ||
}) | ||
@@ -87,3 +141,3 @@ }; | ||
return { ...baseStyles, | ||
...sizeStyles[props.size], | ||
...sizeStyles(props), | ||
...componentStyles(props) | ||
@@ -105,2 +159,11 @@ }; | ||
}; | ||
const backgroundColor = ['gray', 'sky', 'teal', 'violet', 'amber', 'rose', 'stone', 'lime', 'pink']; | ||
const getRandomBackgroundColor = () => { | ||
const max = backgroundColor.length; | ||
const random = Math.floor(Math.random() * max); | ||
return backgroundColor[random]; | ||
}; | ||
const checkBackgroundColor = color => { | ||
return backgroundColor.includes(color); | ||
}; | ||
@@ -156,3 +219,4 @@ const MpAvatarBadge = { | ||
textTransform: 'uppercase', | ||
fontWeight: 'medium' | ||
fontWeight: 'medium', | ||
userSelect: 'none' | ||
}; | ||
@@ -166,5 +230,3 @@ } | ||
class: this.className, | ||
attrs: { | ||
'aria-label': this.name, | ||
...this.computedAttrs | ||
attrs: { ...this.computedAttrs | ||
}, | ||
@@ -242,3 +304,5 @@ on: this.computedListeners | ||
borderColor: this.borderColor, | ||
colorMode: this.colorMode | ||
backgroundColor: checkBackgroundColor(this.backgroundColor) ? this.backgroundColor : getRandomBackgroundColor() || getRandomBackgroundColor(), | ||
isClickable: !!(this.$listeners && this.$listeners.click), | ||
theme: this.theme | ||
}); | ||
@@ -347,13 +411,9 @@ } | ||
name: 'MpMoreAvatarLabel', | ||
functional: true, | ||
props: { | ||
size: [String, Array], | ||
label: [String] | ||
label: [String], | ||
isClickable: [Boolean] | ||
}, | ||
render(h, { | ||
props, | ||
data, | ||
...rest | ||
}) { | ||
render(h) { | ||
const sizeStyles = { | ||
@@ -363,2 +423,3 @@ sm: { | ||
height: 6, | ||
lineHeight: 'sm', | ||
fontSize: 'sm' | ||
@@ -369,2 +430,3 @@ }, | ||
height: 8, | ||
lineHeight: 'md', | ||
fontSize: 'md' | ||
@@ -375,2 +437,3 @@ }, | ||
height: 12, | ||
lineHeight: 'lg', | ||
fontSize: 'lg' | ||
@@ -381,6 +444,7 @@ }, | ||
height: 20, | ||
fontSize: 'xl' | ||
lineHeight: 'xl', | ||
fontSize: '2xl' | ||
} | ||
}; | ||
return h(pixelFlex.MpFlex, { ...rest, | ||
return h(pixelFlex.MpFlex, { | ||
props: { | ||
@@ -390,13 +454,16 @@ as: 'div' | ||
attrs: { | ||
marginLeft: 2, | ||
align: 'center', | ||
justify: 'center', | ||
color: 'inherit', | ||
border: '2px', | ||
borderColor: 'white', | ||
borderRadius: 'full', | ||
...sizeStyles[props.size], | ||
...data.attrs, | ||
fontWeight: 'semibold', | ||
color: 'blue.400', | ||
backgroundColor: 'blue.50', | ||
userSelect: 'none', | ||
cursor: 'pointer', | ||
...sizeStyles[this.size], | ||
'data-pixel-component': 'MpMoreAvatarLabel' | ||
} | ||
}, props.label); | ||
}, | ||
on: this.$listeners | ||
}, this.label); | ||
} | ||
@@ -407,34 +474,63 @@ | ||
name: 'MpAvatarGroup', | ||
functional: true, | ||
props: { ...useAvatarGroupProps | ||
}, | ||
methods: { | ||
handleMoreClick(e) { | ||
this.$emit('click-more', e); | ||
} | ||
render(h, { | ||
slots, | ||
props, | ||
data, | ||
...rest | ||
}) { | ||
if (typeof props.groupSize !== 'undefined') console.warn('[Pixel warn]: Deprecated on `groupSize` prop and use `size` instead.'); | ||
const children = slots().default.filter(e => e.tag); | ||
}, | ||
created() { | ||
if (typeof this.groupSize !== 'undefined') console.warn('[Pixel warn]: Deprecated on `groupSize` prop and use `size` instead.'); | ||
}, | ||
render(h) { | ||
const children = this.$slots.default.filter(e => e.tag); | ||
const count = children.length; | ||
const max = parseInt(props.max, 10); | ||
const max = parseInt(this.max, 10); | ||
const cloneAllElement = children.map((node, index) => { | ||
const isFirstELement = index === 0; | ||
if (!props.max || max && index < max) { | ||
const { | ||
attrs | ||
} = node.data; | ||
const { | ||
propsData | ||
} = node.componentOptions; | ||
attrs.marginLeft = isFirstELement ? 0 : props.spacing; | ||
attrs.zIndex = count - index; | ||
propsData.size = props.size || props.groupSize; | ||
propsData.showBorder = true; | ||
propsData.borderColor = props.borderColor || attrs.borderColor; | ||
if (!this.max || max && index < max) { | ||
let attrs = {}; | ||
let propsData = {}; | ||
let children = []; | ||
if (node.componentOptions.tag === 'mp-avatar') { | ||
attrs = { | ||
ml: isFirstELement ? 0 : this.spacing, | ||
zIndex: index | ||
}; | ||
propsData = { | ||
size: this.size || this.groupSize, | ||
showBorder: true, | ||
borderColor: this.borderColor || attrs.borderColor | ||
}; | ||
} | ||
if (node.componentOptions.tag === 'mp-tooltip' && node.componentOptions.children) { | ||
let firstChildrenNode = node.componentOptions.children[0]; | ||
const childrenAttrs = { | ||
ml: isFirstELement ? 0 : this.spacing, | ||
zIndex: count - index | ||
}; | ||
firstChildrenNode.data.attrs = { ...firstChildrenNode.data.attrs, | ||
...childrenAttrs | ||
}; | ||
const childrenPropsData = { | ||
size: this.size || this.groupSize, | ||
showBorder: true, | ||
borderColor: this.borderColor || attrs.borderColor | ||
}; | ||
firstChildrenNode.componentOptions.propsData = { ...firstChildrenNode.componentOptions.propsData, | ||
...childrenPropsData | ||
}; | ||
children.push(firstChildrenNode); | ||
} | ||
node.componentOptions.propsData = { ...node.componentOptions.propsData, | ||
...propsData | ||
}; | ||
node.componentOptions.children = children.length === 1 ? children : undefined; | ||
node.data.attrs = { ...node.data.attrs, | ||
@@ -449,7 +545,7 @@ ...attrs | ||
props: { | ||
size: props.size || props.groupSize, | ||
size: this.size || this.groupSize, | ||
label: `+${count - max}` | ||
}, | ||
attrs: { | ||
marginLeft: props.spacing | ||
on: { | ||
click: this.handleMoreClick | ||
} | ||
@@ -459,3 +555,3 @@ }); | ||
}); | ||
return h(pixelFlex.MpFlex, { ...rest, | ||
return h(pixelFlex.MpFlex, { | ||
props: { | ||
@@ -466,3 +562,2 @@ alignItems: 'center' | ||
zIndex: 0, | ||
...data.attrs, | ||
'data-pixel-component': 'MpAvatarGroup' | ||
@@ -469,0 +564,0 @@ } |
@@ -17,2 +17,3 @@ 'use strict'; | ||
* @prop {string|array} borderColor - Border color of avatar. | ||
* @prop {string|array} backgroundColor - Background color of avatar. | ||
*/ | ||
@@ -30,3 +31,4 @@ const useAvatarProps = { | ||
}, | ||
borderColor: [String] | ||
borderColor: [String], | ||
backgroundColor: [String] | ||
}; | ||
@@ -47,20 +49,55 @@ | ||
}; | ||
const sizeStyles = { | ||
sm: { | ||
width: 6, | ||
height: 6, | ||
lineHeight: 'xs', | ||
fontSize: `xs` | ||
}, | ||
md: { | ||
width: 8, | ||
height: 8, | ||
lineHeight: 'sm', | ||
fontSize: `sm` | ||
}, | ||
lg: { | ||
width: 12, | ||
height: 12, | ||
lineHeight: 'xl', | ||
fontSize: `xl` | ||
const sizeStyles = ({ | ||
size, | ||
showBorder, | ||
theme | ||
}) => { | ||
const getSizeCalculation = size => { | ||
if (showBorder) return `calc(${theme.sizes[size]} + 2px)`; | ||
return size; | ||
}; | ||
const variantStyles = { | ||
sm: { | ||
width: getSizeCalculation(6), | ||
height: getSizeCalculation(6), | ||
lineHeight: 'xs', | ||
fontSize: `xs` | ||
}, | ||
md: { | ||
width: getSizeCalculation(8), | ||
height: getSizeCalculation(8), | ||
lineHeight: 'sm', | ||
fontSize: `sm` | ||
}, | ||
lg: { | ||
width: getSizeCalculation(12), | ||
height: getSizeCalculation(12), | ||
lineHeight: 'lg', | ||
fontSize: `lg` | ||
}, | ||
xl: { | ||
width: getSizeCalculation(20), | ||
height: getSizeCalculation(20), | ||
lineHeight: 'xl', | ||
fontSize: `2xl` | ||
} | ||
}; | ||
switch (size) { | ||
case 'sm': | ||
return variantStyles['sm']; | ||
case 'md': | ||
return variantStyles['md']; | ||
case 'lg': | ||
return variantStyles['lg']; | ||
case 'xl': | ||
return variantStyles['xl']; | ||
default: | ||
return variantStyles['md']; | ||
} | ||
@@ -72,10 +109,27 @@ }; | ||
showBorder, | ||
borderColor | ||
borderColor, | ||
backgroundColor, | ||
isClickable, | ||
theme | ||
}) => { | ||
const color = { | ||
gray: 'gray.50', | ||
sky: 'sky.400', | ||
teal: 'teal.400', | ||
violet: 'violet.400', | ||
amber: 'amber.400', | ||
rose: 'rose.400', | ||
stone: 'stone.400', | ||
lime: 'lime.400', | ||
pink: 'pink.400' | ||
}; | ||
return { | ||
backgroundColor: name ? 'gray.50' : 'gray.400', | ||
color: name ? 'gray.600' : 'white', | ||
...(showBorder && borderColor && { | ||
border: '2px', | ||
borderColor: borderColor | ||
bg: name ? color[backgroundColor] : 'gray.400', | ||
color: backgroundColor === 'gray' ? name ? 'gray.600' : 'white' : 'white', | ||
...(showBorder && { | ||
borderWidth: theme.sizes['0.5'], | ||
borderColor: borderColor || 'white' | ||
}), | ||
...(isClickable && { | ||
cursor: 'pointer' | ||
}) | ||
@@ -87,3 +141,3 @@ }; | ||
return { ...baseStyles, | ||
...sizeStyles[props.size], | ||
...sizeStyles(props), | ||
...componentStyles(props) | ||
@@ -105,2 +159,11 @@ }; | ||
}; | ||
const backgroundColor = ['gray', 'sky', 'teal', 'violet', 'amber', 'rose', 'stone', 'lime', 'pink']; | ||
const getRandomBackgroundColor = () => { | ||
const max = backgroundColor.length; | ||
const random = Math.floor(Math.random() * max); | ||
return backgroundColor[random]; | ||
}; | ||
const checkBackgroundColor = color => { | ||
return backgroundColor.includes(color); | ||
}; | ||
@@ -156,3 +219,4 @@ const MpAvatarBadge = { | ||
textTransform: 'uppercase', | ||
fontWeight: 'medium' | ||
fontWeight: 'medium', | ||
userSelect: 'none' | ||
}; | ||
@@ -166,5 +230,3 @@ } | ||
class: this.className, | ||
attrs: { | ||
'aria-label': this.name, | ||
...this.computedAttrs | ||
attrs: { ...this.computedAttrs | ||
}, | ||
@@ -242,3 +304,5 @@ on: this.computedListeners | ||
borderColor: this.borderColor, | ||
colorMode: this.colorMode | ||
backgroundColor: checkBackgroundColor(this.backgroundColor) ? this.backgroundColor : getRandomBackgroundColor() || getRandomBackgroundColor(), | ||
isClickable: !!(this.$listeners && this.$listeners.click), | ||
theme: this.theme | ||
}); | ||
@@ -347,13 +411,9 @@ } | ||
name: 'MpMoreAvatarLabel', | ||
functional: true, | ||
props: { | ||
size: [String, Array], | ||
label: [String] | ||
label: [String], | ||
isClickable: [Boolean] | ||
}, | ||
render(h, { | ||
props, | ||
data, | ||
...rest | ||
}) { | ||
render(h) { | ||
const sizeStyles = { | ||
@@ -363,2 +423,3 @@ sm: { | ||
height: 6, | ||
lineHeight: 'sm', | ||
fontSize: 'sm' | ||
@@ -369,2 +430,3 @@ }, | ||
height: 8, | ||
lineHeight: 'md', | ||
fontSize: 'md' | ||
@@ -375,2 +437,3 @@ }, | ||
height: 12, | ||
lineHeight: 'lg', | ||
fontSize: 'lg' | ||
@@ -381,6 +444,7 @@ }, | ||
height: 20, | ||
fontSize: 'xl' | ||
lineHeight: 'xl', | ||
fontSize: '2xl' | ||
} | ||
}; | ||
return h(pixelFlex.MpFlex, { ...rest, | ||
return h(pixelFlex.MpFlex, { | ||
props: { | ||
@@ -390,13 +454,16 @@ as: 'div' | ||
attrs: { | ||
marginLeft: 2, | ||
align: 'center', | ||
justify: 'center', | ||
color: 'inherit', | ||
border: '2px', | ||
borderColor: 'white', | ||
borderRadius: 'full', | ||
...sizeStyles[props.size], | ||
...data.attrs, | ||
fontWeight: 'semibold', | ||
color: 'blue.400', | ||
backgroundColor: 'blue.50', | ||
userSelect: 'none', | ||
cursor: 'pointer', | ||
...sizeStyles[this.size], | ||
'data-pixel-component': 'MpMoreAvatarLabel' | ||
} | ||
}, props.label); | ||
}, | ||
on: this.$listeners | ||
}, this.label); | ||
} | ||
@@ -407,34 +474,63 @@ | ||
name: 'MpAvatarGroup', | ||
functional: true, | ||
props: { ...useAvatarGroupProps | ||
}, | ||
methods: { | ||
handleMoreClick(e) { | ||
this.$emit('click-more', e); | ||
} | ||
render(h, { | ||
slots, | ||
props, | ||
data, | ||
...rest | ||
}) { | ||
if (typeof props.groupSize !== 'undefined') console.warn('[Pixel warn]: Deprecated on `groupSize` prop and use `size` instead.'); | ||
const children = slots().default.filter(e => e.tag); | ||
}, | ||
created() { | ||
if (typeof this.groupSize !== 'undefined') console.warn('[Pixel warn]: Deprecated on `groupSize` prop and use `size` instead.'); | ||
}, | ||
render(h) { | ||
const children = this.$slots.default.filter(e => e.tag); | ||
const count = children.length; | ||
const max = parseInt(props.max, 10); | ||
const max = parseInt(this.max, 10); | ||
const cloneAllElement = children.map((node, index) => { | ||
const isFirstELement = index === 0; | ||
if (!props.max || max && index < max) { | ||
const { | ||
attrs | ||
} = node.data; | ||
const { | ||
propsData | ||
} = node.componentOptions; | ||
attrs.marginLeft = isFirstELement ? 0 : props.spacing; | ||
attrs.zIndex = count - index; | ||
propsData.size = props.size || props.groupSize; | ||
propsData.showBorder = true; | ||
propsData.borderColor = props.borderColor || attrs.borderColor; | ||
if (!this.max || max && index < max) { | ||
let attrs = {}; | ||
let propsData = {}; | ||
let children = []; | ||
if (node.componentOptions.tag === 'mp-avatar') { | ||
attrs = { | ||
ml: isFirstELement ? 0 : this.spacing, | ||
zIndex: index | ||
}; | ||
propsData = { | ||
size: this.size || this.groupSize, | ||
showBorder: true, | ||
borderColor: this.borderColor || attrs.borderColor | ||
}; | ||
} | ||
if (node.componentOptions.tag === 'mp-tooltip' && node.componentOptions.children) { | ||
let firstChildrenNode = node.componentOptions.children[0]; | ||
const childrenAttrs = { | ||
ml: isFirstELement ? 0 : this.spacing, | ||
zIndex: count - index | ||
}; | ||
firstChildrenNode.data.attrs = { ...firstChildrenNode.data.attrs, | ||
...childrenAttrs | ||
}; | ||
const childrenPropsData = { | ||
size: this.size || this.groupSize, | ||
showBorder: true, | ||
borderColor: this.borderColor || attrs.borderColor | ||
}; | ||
firstChildrenNode.componentOptions.propsData = { ...firstChildrenNode.componentOptions.propsData, | ||
...childrenPropsData | ||
}; | ||
children.push(firstChildrenNode); | ||
} | ||
node.componentOptions.propsData = { ...node.componentOptions.propsData, | ||
...propsData | ||
}; | ||
node.componentOptions.children = children.length === 1 ? children : undefined; | ||
node.data.attrs = { ...node.data.attrs, | ||
@@ -449,7 +545,7 @@ ...attrs | ||
props: { | ||
size: props.size || props.groupSize, | ||
size: this.size || this.groupSize, | ||
label: `+${count - max}` | ||
}, | ||
attrs: { | ||
marginLeft: props.spacing | ||
on: { | ||
click: this.handleMoreClick | ||
} | ||
@@ -459,3 +555,3 @@ }); | ||
}); | ||
return h(pixelFlex.MpFlex, { ...rest, | ||
return h(pixelFlex.MpFlex, { | ||
props: { | ||
@@ -466,3 +562,2 @@ alignItems: 'center' | ||
zIndex: 0, | ||
...data.attrs, | ||
'data-pixel-component': 'MpAvatarGroup' | ||
@@ -469,0 +564,0 @@ } |
@@ -13,2 +13,3 @@ import { MpBox } from '@mekari/pixel-box'; | ||
* @prop {string|array} borderColor - Border color of avatar. | ||
* @prop {string|array} backgroundColor - Background color of avatar. | ||
*/ | ||
@@ -26,3 +27,4 @@ const useAvatarProps = { | ||
}, | ||
borderColor: [String] | ||
borderColor: [String], | ||
backgroundColor: [String] | ||
}; | ||
@@ -43,20 +45,55 @@ | ||
}; | ||
const sizeStyles = { | ||
sm: { | ||
width: 6, | ||
height: 6, | ||
lineHeight: 'xs', | ||
fontSize: `xs` | ||
}, | ||
md: { | ||
width: 8, | ||
height: 8, | ||
lineHeight: 'sm', | ||
fontSize: `sm` | ||
}, | ||
lg: { | ||
width: 12, | ||
height: 12, | ||
lineHeight: 'xl', | ||
fontSize: `xl` | ||
const sizeStyles = ({ | ||
size, | ||
showBorder, | ||
theme | ||
}) => { | ||
const getSizeCalculation = size => { | ||
if (showBorder) return `calc(${theme.sizes[size]} + 2px)`; | ||
return size; | ||
}; | ||
const variantStyles = { | ||
sm: { | ||
width: getSizeCalculation(6), | ||
height: getSizeCalculation(6), | ||
lineHeight: 'xs', | ||
fontSize: `xs` | ||
}, | ||
md: { | ||
width: getSizeCalculation(8), | ||
height: getSizeCalculation(8), | ||
lineHeight: 'sm', | ||
fontSize: `sm` | ||
}, | ||
lg: { | ||
width: getSizeCalculation(12), | ||
height: getSizeCalculation(12), | ||
lineHeight: 'lg', | ||
fontSize: `lg` | ||
}, | ||
xl: { | ||
width: getSizeCalculation(20), | ||
height: getSizeCalculation(20), | ||
lineHeight: 'xl', | ||
fontSize: `2xl` | ||
} | ||
}; | ||
switch (size) { | ||
case 'sm': | ||
return variantStyles['sm']; | ||
case 'md': | ||
return variantStyles['md']; | ||
case 'lg': | ||
return variantStyles['lg']; | ||
case 'xl': | ||
return variantStyles['xl']; | ||
default: | ||
return variantStyles['md']; | ||
} | ||
@@ -68,10 +105,27 @@ }; | ||
showBorder, | ||
borderColor | ||
borderColor, | ||
backgroundColor, | ||
isClickable, | ||
theme | ||
}) => { | ||
const color = { | ||
gray: 'gray.50', | ||
sky: 'sky.400', | ||
teal: 'teal.400', | ||
violet: 'violet.400', | ||
amber: 'amber.400', | ||
rose: 'rose.400', | ||
stone: 'stone.400', | ||
lime: 'lime.400', | ||
pink: 'pink.400' | ||
}; | ||
return { | ||
backgroundColor: name ? 'gray.50' : 'gray.400', | ||
color: name ? 'gray.600' : 'white', | ||
...(showBorder && borderColor && { | ||
border: '2px', | ||
borderColor: borderColor | ||
bg: name ? color[backgroundColor] : 'gray.400', | ||
color: backgroundColor === 'gray' ? name ? 'gray.600' : 'white' : 'white', | ||
...(showBorder && { | ||
borderWidth: theme.sizes['0.5'], | ||
borderColor: borderColor || 'white' | ||
}), | ||
...(isClickable && { | ||
cursor: 'pointer' | ||
}) | ||
@@ -83,3 +137,3 @@ }; | ||
return { ...baseStyles, | ||
...sizeStyles[props.size], | ||
...sizeStyles(props), | ||
...componentStyles(props) | ||
@@ -101,2 +155,11 @@ }; | ||
}; | ||
const backgroundColor = ['gray', 'sky', 'teal', 'violet', 'amber', 'rose', 'stone', 'lime', 'pink']; | ||
const getRandomBackgroundColor = () => { | ||
const max = backgroundColor.length; | ||
const random = Math.floor(Math.random() * max); | ||
return backgroundColor[random]; | ||
}; | ||
const checkBackgroundColor = color => { | ||
return backgroundColor.includes(color); | ||
}; | ||
@@ -152,3 +215,4 @@ const MpAvatarBadge = { | ||
textTransform: 'uppercase', | ||
fontWeight: 'medium' | ||
fontWeight: 'medium', | ||
userSelect: 'none' | ||
}; | ||
@@ -162,5 +226,3 @@ } | ||
class: this.className, | ||
attrs: { | ||
'aria-label': this.name, | ||
...this.computedAttrs | ||
attrs: { ...this.computedAttrs | ||
}, | ||
@@ -238,3 +300,5 @@ on: this.computedListeners | ||
borderColor: this.borderColor, | ||
colorMode: this.colorMode | ||
backgroundColor: checkBackgroundColor(this.backgroundColor) ? this.backgroundColor : getRandomBackgroundColor() || getRandomBackgroundColor(), | ||
isClickable: !!(this.$listeners && this.$listeners.click), | ||
theme: this.theme | ||
}); | ||
@@ -343,13 +407,9 @@ } | ||
name: 'MpMoreAvatarLabel', | ||
functional: true, | ||
props: { | ||
size: [String, Array], | ||
label: [String] | ||
label: [String], | ||
isClickable: [Boolean] | ||
}, | ||
render(h, { | ||
props, | ||
data, | ||
...rest | ||
}) { | ||
render(h) { | ||
const sizeStyles = { | ||
@@ -359,2 +419,3 @@ sm: { | ||
height: 6, | ||
lineHeight: 'sm', | ||
fontSize: 'sm' | ||
@@ -365,2 +426,3 @@ }, | ||
height: 8, | ||
lineHeight: 'md', | ||
fontSize: 'md' | ||
@@ -371,2 +433,3 @@ }, | ||
height: 12, | ||
lineHeight: 'lg', | ||
fontSize: 'lg' | ||
@@ -377,6 +440,7 @@ }, | ||
height: 20, | ||
fontSize: 'xl' | ||
lineHeight: 'xl', | ||
fontSize: '2xl' | ||
} | ||
}; | ||
return h(MpFlex, { ...rest, | ||
return h(MpFlex, { | ||
props: { | ||
@@ -386,13 +450,16 @@ as: 'div' | ||
attrs: { | ||
marginLeft: 2, | ||
align: 'center', | ||
justify: 'center', | ||
color: 'inherit', | ||
border: '2px', | ||
borderColor: 'white', | ||
borderRadius: 'full', | ||
...sizeStyles[props.size], | ||
...data.attrs, | ||
fontWeight: 'semibold', | ||
color: 'blue.400', | ||
backgroundColor: 'blue.50', | ||
userSelect: 'none', | ||
cursor: 'pointer', | ||
...sizeStyles[this.size], | ||
'data-pixel-component': 'MpMoreAvatarLabel' | ||
} | ||
}, props.label); | ||
}, | ||
on: this.$listeners | ||
}, this.label); | ||
} | ||
@@ -403,34 +470,63 @@ | ||
name: 'MpAvatarGroup', | ||
functional: true, | ||
props: { ...useAvatarGroupProps | ||
}, | ||
methods: { | ||
handleMoreClick(e) { | ||
this.$emit('click-more', e); | ||
} | ||
render(h, { | ||
slots, | ||
props, | ||
data, | ||
...rest | ||
}) { | ||
if (typeof props.groupSize !== 'undefined') console.warn('[Pixel warn]: Deprecated on `groupSize` prop and use `size` instead.'); | ||
const children = slots().default.filter(e => e.tag); | ||
}, | ||
created() { | ||
if (typeof this.groupSize !== 'undefined') console.warn('[Pixel warn]: Deprecated on `groupSize` prop and use `size` instead.'); | ||
}, | ||
render(h) { | ||
const children = this.$slots.default.filter(e => e.tag); | ||
const count = children.length; | ||
const max = parseInt(props.max, 10); | ||
const max = parseInt(this.max, 10); | ||
const cloneAllElement = children.map((node, index) => { | ||
const isFirstELement = index === 0; | ||
if (!props.max || max && index < max) { | ||
const { | ||
attrs | ||
} = node.data; | ||
const { | ||
propsData | ||
} = node.componentOptions; | ||
attrs.marginLeft = isFirstELement ? 0 : props.spacing; | ||
attrs.zIndex = count - index; | ||
propsData.size = props.size || props.groupSize; | ||
propsData.showBorder = true; | ||
propsData.borderColor = props.borderColor || attrs.borderColor; | ||
if (!this.max || max && index < max) { | ||
let attrs = {}; | ||
let propsData = {}; | ||
let children = []; | ||
if (node.componentOptions.tag === 'mp-avatar') { | ||
attrs = { | ||
ml: isFirstELement ? 0 : this.spacing, | ||
zIndex: index | ||
}; | ||
propsData = { | ||
size: this.size || this.groupSize, | ||
showBorder: true, | ||
borderColor: this.borderColor || attrs.borderColor | ||
}; | ||
} | ||
if (node.componentOptions.tag === 'mp-tooltip' && node.componentOptions.children) { | ||
let firstChildrenNode = node.componentOptions.children[0]; | ||
const childrenAttrs = { | ||
ml: isFirstELement ? 0 : this.spacing, | ||
zIndex: count - index | ||
}; | ||
firstChildrenNode.data.attrs = { ...firstChildrenNode.data.attrs, | ||
...childrenAttrs | ||
}; | ||
const childrenPropsData = { | ||
size: this.size || this.groupSize, | ||
showBorder: true, | ||
borderColor: this.borderColor || attrs.borderColor | ||
}; | ||
firstChildrenNode.componentOptions.propsData = { ...firstChildrenNode.componentOptions.propsData, | ||
...childrenPropsData | ||
}; | ||
children.push(firstChildrenNode); | ||
} | ||
node.componentOptions.propsData = { ...node.componentOptions.propsData, | ||
...propsData | ||
}; | ||
node.componentOptions.children = children.length === 1 ? children : undefined; | ||
node.data.attrs = { ...node.data.attrs, | ||
@@ -445,7 +541,7 @@ ...attrs | ||
props: { | ||
size: props.size || props.groupSize, | ||
size: this.size || this.groupSize, | ||
label: `+${count - max}` | ||
}, | ||
attrs: { | ||
marginLeft: props.spacing | ||
on: { | ||
click: this.handleMoreClick | ||
} | ||
@@ -455,3 +551,3 @@ }); | ||
}); | ||
return h(MpFlex, { ...rest, | ||
return h(MpFlex, { | ||
props: { | ||
@@ -462,3 +558,2 @@ alignItems: 'center' | ||
zIndex: 0, | ||
...data.attrs, | ||
'data-pixel-component': 'MpAvatarGroup' | ||
@@ -465,0 +560,0 @@ } |
{ | ||
"name": "@mekari/pixel-avatar", | ||
"version": "0.1.0", | ||
"version": "0.2.0", | ||
"description": "Mekari Pixel | Avatar component", | ||
@@ -5,0 +5,0 @@ "homepage": "https://mekari.design/", |
@@ -6,8 +6,8 @@ import { MpFlex } from '@mekari/pixel-flex' | ||
name: 'MpMoreAvatarLabel', | ||
functional: true, | ||
props: { | ||
size: [String, Array], | ||
label: [String] | ||
label: [String], | ||
isClickable: [Boolean] | ||
}, | ||
render(h, { props, data, ...rest }) { | ||
render(h) { | ||
const sizeStyles = { | ||
@@ -17,2 +17,3 @@ sm: { | ||
height: 6, | ||
lineHeight: 'sm', | ||
fontSize: 'sm' | ||
@@ -23,2 +24,3 @@ }, | ||
height: 8, | ||
lineHeight: 'md', | ||
fontSize: 'md' | ||
@@ -29,2 +31,3 @@ }, | ||
height: 12, | ||
lineHeight: 'lg', | ||
fontSize: 'lg' | ||
@@ -35,3 +38,4 @@ }, | ||
height: 20, | ||
fontSize: 'xl' | ||
lineHeight: 'xl', | ||
fontSize: '2xl' | ||
} | ||
@@ -43,17 +47,19 @@ } | ||
{ | ||
...rest, | ||
props: { as: 'div' }, | ||
attrs: { | ||
marginLeft: 2, | ||
align: 'center', | ||
justify: 'center', | ||
color: 'inherit', | ||
border: '2px', | ||
borderColor: 'white', | ||
borderRadius: 'full', | ||
...sizeStyles[props.size], | ||
...data.attrs, | ||
fontWeight: 'semibold', | ||
color: 'blue.400', | ||
backgroundColor: 'blue.50', | ||
userSelect: 'none', | ||
cursor: 'pointer', | ||
...sizeStyles[this.size], | ||
'data-pixel-component': 'MpMoreAvatarLabel' | ||
} | ||
}, | ||
on: this.$listeners | ||
}, | ||
props.label | ||
this.label | ||
) | ||
@@ -65,25 +71,62 @@ } | ||
name: 'MpAvatarGroup', | ||
functional: true, | ||
props: { ...useAvatarGroupProps }, | ||
render(h, { slots, props, data, ...rest }) { | ||
if (typeof props.groupSize !== 'undefined') | ||
methods: { | ||
handleMoreClick(e) { | ||
this.$emit('click-more', e) | ||
} | ||
}, | ||
created() { | ||
if (typeof this.groupSize !== 'undefined') | ||
console.warn('[Pixel warn]: Deprecated on `groupSize` prop and use `size` instead.') | ||
const children = slots().default.filter((e) => e.tag) | ||
}, | ||
render(h) { | ||
const children = this.$slots.default.filter((e) => e.tag) | ||
const count = children.length | ||
const max = parseInt(props.max, 10) | ||
const max = parseInt(this.max, 10) | ||
const cloneAllElement = children.map((node, index) => { | ||
const isFirstELement = index === 0 | ||
if (!props.max || (max && index < max)) { | ||
const { attrs } = node.data | ||
const { propsData } = node.componentOptions | ||
if (!this.max || (max && index < max)) { | ||
let attrs = {} | ||
let propsData = {} | ||
let children = [] | ||
attrs.marginLeft = isFirstELement ? 0 : props.spacing | ||
attrs.zIndex = count - index | ||
if (node.componentOptions.tag === 'mp-avatar') { | ||
attrs = { | ||
ml: isFirstELement ? 0 : this.spacing, | ||
zIndex: index | ||
} | ||
propsData.size = props.size || props.groupSize | ||
propsData.showBorder = true | ||
propsData.borderColor = props.borderColor || attrs.borderColor | ||
propsData = { | ||
size: this.size || this.groupSize, | ||
showBorder: true, | ||
borderColor: this.borderColor || attrs.borderColor | ||
} | ||
} | ||
if (node.componentOptions.tag === 'mp-tooltip' && node.componentOptions.children) { | ||
let firstChildrenNode = node.componentOptions.children[0] | ||
const childrenAttrs = { | ||
ml: isFirstELement ? 0 : this.spacing, | ||
zIndex: count - index | ||
} | ||
firstChildrenNode.data.attrs = { | ||
...firstChildrenNode.data.attrs, | ||
...childrenAttrs | ||
} | ||
const childrenPropsData = { | ||
size: this.size || this.groupSize, | ||
showBorder: true, | ||
borderColor: this.borderColor || attrs.borderColor | ||
} | ||
firstChildrenNode.componentOptions.propsData = { | ||
...firstChildrenNode.componentOptions.propsData, | ||
...childrenPropsData | ||
} | ||
children.push(firstChildrenNode) | ||
} | ||
node.componentOptions.propsData = { | ||
@@ -94,2 +137,4 @@ ...node.componentOptions.propsData, | ||
node.componentOptions.children = children.length === 1 ? children : undefined | ||
node.data.attrs = { | ||
@@ -106,6 +151,8 @@ ...node.data.attrs, | ||
props: { | ||
size: props.size || props.groupSize, | ||
size: this.size || this.groupSize, | ||
label: `+${count - max}` | ||
}, | ||
attrs: { marginLeft: props.spacing } | ||
on: { | ||
click: this.handleMoreClick | ||
} | ||
}) | ||
@@ -118,7 +165,5 @@ } | ||
{ | ||
...rest, | ||
props: { alignItems: 'center' }, | ||
attrs: { | ||
zIndex: 0, | ||
...data.attrs, | ||
'data-pixel-component': 'MpAvatarGroup' | ||
@@ -125,0 +170,0 @@ } |
@@ -5,3 +5,3 @@ import { MpBox } from '@mekari/pixel-box' | ||
import { useAvatarStyles } from './utils/avatar.styles' | ||
import { getInitials } from './utils/avatar.utils' | ||
import { getInitials, getRandomBackgroundColor, checkBackgroundColor } from './utils/avatar.utils' | ||
@@ -53,3 +53,4 @@ export const MpAvatarBadge = { | ||
textTransform: 'uppercase', | ||
fontWeight: 'medium' | ||
fontWeight: 'medium', | ||
userSelect: 'none' | ||
} | ||
@@ -64,3 +65,2 @@ } | ||
attrs: { | ||
'aria-label': this.name, | ||
...this.computedAttrs | ||
@@ -130,3 +130,7 @@ }, | ||
borderColor: this.borderColor, | ||
colorMode: this.colorMode | ||
backgroundColor: checkBackgroundColor(this.backgroundColor) | ||
? this.backgroundColor | ||
: getRandomBackgroundColor() || getRandomBackgroundColor(), | ||
isClickable: !!(this.$listeners && this.$listeners.click), | ||
theme: this.theme | ||
}) | ||
@@ -133,0 +137,0 @@ } |
@@ -9,2 +9,3 @@ /** | ||
* @prop {string|array} borderColor - Border color of avatar. | ||
* @prop {string|array} backgroundColor - Background color of avatar. | ||
*/ | ||
@@ -17,3 +18,4 @@ | ||
showBorder: { type: [Boolean], default: false }, | ||
borderColor: [String] | ||
borderColor: [String], | ||
backgroundColor: [String] | ||
} |
@@ -16,32 +16,79 @@ /** | ||
const sizeStyles = { | ||
sm: { | ||
width: 6, | ||
height: 6, | ||
lineHeight: 'xs', | ||
fontSize: `xs` | ||
}, | ||
md: { | ||
width: 8, | ||
height: 8, | ||
lineHeight: 'sm', | ||
fontSize: `sm` | ||
}, | ||
lg: { | ||
width: 12, | ||
height: 12, | ||
lineHeight: 'xl', | ||
fontSize: `xl` | ||
const sizeStyles = ({ size, showBorder, theme }) => { | ||
const getSizeCalculation = (size) => { | ||
if (showBorder) return `calc(${theme.sizes[size]} + 2px)` | ||
return size | ||
} | ||
const variantStyles = { | ||
sm: { | ||
width: getSizeCalculation(6), | ||
height: getSizeCalculation(6), | ||
lineHeight: 'xs', | ||
fontSize: `xs` | ||
}, | ||
md: { | ||
width: getSizeCalculation(8), | ||
height: getSizeCalculation(8), | ||
lineHeight: 'sm', | ||
fontSize: `sm` | ||
}, | ||
lg: { | ||
width: getSizeCalculation(12), | ||
height: getSizeCalculation(12), | ||
lineHeight: 'lg', | ||
fontSize: `lg` | ||
}, | ||
xl: { | ||
width: getSizeCalculation(20), | ||
height: getSizeCalculation(20), | ||
lineHeight: 'xl', | ||
fontSize: `2xl` | ||
} | ||
} | ||
switch (size) { | ||
case 'sm': | ||
return variantStyles['sm'] | ||
case 'md': | ||
return variantStyles['md'] | ||
case 'lg': | ||
return variantStyles['lg'] | ||
case 'xl': | ||
return variantStyles['xl'] | ||
default: | ||
return variantStyles['md'] | ||
} | ||
} | ||
const componentStyles = ({ name, showBorder, borderColor }) => { | ||
const componentStyles = ({ | ||
name, | ||
showBorder, | ||
borderColor, | ||
backgroundColor, | ||
isClickable, | ||
theme | ||
}) => { | ||
const color = { | ||
gray: 'gray.50', | ||
sky: 'sky.400', | ||
teal: 'teal.400', | ||
violet: 'violet.400', | ||
amber: 'amber.400', | ||
rose: 'rose.400', | ||
stone: 'stone.400', | ||
lime: 'lime.400', | ||
pink: 'pink.400' | ||
} | ||
return { | ||
backgroundColor: name ? 'gray.50' : 'gray.400', | ||
color: name ? 'gray.600' : 'white', | ||
...(showBorder && | ||
borderColor && { | ||
border: '2px', | ||
borderColor: borderColor | ||
}) | ||
bg: name ? color[backgroundColor] : 'gray.400', | ||
color: backgroundColor === 'gray' ? (name ? 'gray.600' : 'white') : 'white', | ||
...(showBorder && { | ||
borderWidth: theme.sizes['0.5'], | ||
borderColor: borderColor || 'white' | ||
}), | ||
...(isClickable && { | ||
cursor: 'pointer' | ||
}) | ||
} | ||
@@ -53,5 +100,5 @@ } | ||
...baseStyles, | ||
...sizeStyles[props.size], | ||
...sizeStyles(props), | ||
...componentStyles(props) | ||
} | ||
} |
@@ -14,1 +14,13 @@ /** | ||
} | ||
const backgroundColor = ['gray', 'sky', 'teal', 'violet', 'amber', 'rose', 'stone', 'lime', 'pink'] | ||
export const getRandomBackgroundColor = () => { | ||
const max = backgroundColor.length | ||
const random = Math.floor(Math.random() * max) | ||
return backgroundColor[random] | ||
} | ||
export const checkBackgroundColor = (color) => { | ||
return backgroundColor.includes(color) | ||
} |
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
License Policy Violation
LicenseThis package is not allowed per your license policy. Review the package's license to ensure compliance.
Found 1 instance in 1 package
53496
2001