Progress
This commit is contained in:
parent
5efe40f301
commit
03de4c4fea
|
@ -41,14 +41,20 @@ export function submitSearch() {
|
|||
}).then(response => {
|
||||
if (response.data.accounts) {
|
||||
dispatch(importFetchedAccounts(response.data.accounts));
|
||||
dispatch(fetchRelationships(response.data.accounts.map(item => item.id)));
|
||||
}
|
||||
|
||||
if (response.data.statuses) {
|
||||
dispatch(importFetchedStatuses(response.data.statuses));
|
||||
}
|
||||
|
||||
console.log("response.data.", response.data)
|
||||
|
||||
// if (response.data.groups) {
|
||||
// dispatch(importFetchedStatuses(response.data.statuses));
|
||||
// }
|
||||
|
||||
dispatch(fetchSearchSuccess(response.data));
|
||||
dispatch(fetchRelationships(response.data.accounts.map(item => item.id)));
|
||||
}).catch(error => {
|
||||
dispatch(fetchSearchFail(error));
|
||||
});
|
||||
|
|
|
@ -1,5 +1,5 @@
|
|||
const ErrorIcon = ({
|
||||
className = _s.fillColorPrimary,
|
||||
className = _s.fillPrimary,
|
||||
size = '32px',
|
||||
title = 'Error',
|
||||
}) => (
|
||||
|
|
|
@ -0,0 +1,39 @@
|
|||
const ExploreIcon = ({
|
||||
className = '',
|
||||
size = '12px',
|
||||
title = 'Explore',
|
||||
}) => (
|
||||
<svg
|
||||
className={className}
|
||||
version='1.1'
|
||||
xmlns='http://www.w3.org/2000/svg'
|
||||
x='0px'
|
||||
y='0px'
|
||||
width={size}
|
||||
height={size}
|
||||
viewBox='0 0 24 24'
|
||||
xmlSpace='preserve'
|
||||
aria-label={title}
|
||||
>
|
||||
<g>
|
||||
<path d='M 11.296875 23.875 L 11.296875 18.773438 C 10.019531 18.824219 8.753906 19.003906 7.550781 19.300781 C 7.742188 19.769531 7.957031 20.21875 8.183594 20.640625 C 9.101562 22.332031 10.242188 23.5 11.296875 23.875 Z M 11.296875 23.875' />
|
||||
<path d='M 15.8125 20.640625 C 16.042969 20.21875 16.257812 19.769531 16.449219 19.300781 C 15.246094 19.003906 13.980469 18.824219 12.703125 18.773438 L 12.703125 23.875 C 13.757812 23.5 14.898438 22.332031 15.8125 20.640625 Z M 15.8125 20.640625' />
|
||||
<path d='M 11.296875 17.367188 L 11.296875 12.6875 L 6.167969 12.6875 C 6.234375 14.515625 6.546875 16.332031 7.066406 17.976562 C 8.425781 17.625 9.855469 17.417969 11.296875 17.367188 Z M 11.296875 17.367188' />
|
||||
<path d='M 11.296875 11.28125 L 11.296875 6.601562 C 9.855469 6.550781 8.425781 6.34375 7.066406 5.996094 C 6.546875 7.640625 6.234375 9.457031 6.167969 11.28125 Z M 11.296875 11.28125' />
|
||||
<path d='M 17.808594 4.273438 C 18.664062 3.984375 19.476562 3.632812 20.222656 3.222656 C 18.914062 1.996094 17.328125 1.054688 15.574219 0.507812 C 16.097656 1.101562 16.597656 1.820312 17.050781 2.65625 C 17.328125 3.167969 17.582031 3.710938 17.808594 4.273438 Z M 17.808594 4.273438' />
|
||||
<path d='M 8.1875 3.328125 C 7.957031 3.75 7.742188 4.199219 7.550781 4.667969 C 8.753906 4.96875 10.019531 5.148438 11.296875 5.195312 L 11.296875 0.09375 C 10.242188 0.46875 9.101562 1.636719 8.1875 3.328125 Z M 8.1875 3.328125' />
|
||||
<path d='M 12.703125 12.6875 L 12.703125 17.367188 C 14.144531 17.417969 15.574219 17.625 16.933594 17.976562 C 17.453125 16.332031 17.765625 14.515625 17.832031 12.6875 Z M 12.703125 12.6875' />
|
||||
<path d='M 12.703125 6.601562 L 12.703125 11.28125 L 17.832031 11.28125 C 17.765625 9.457031 17.453125 7.640625 16.933594 5.996094 C 15.574219 6.34375 14.144531 6.550781 12.703125 6.601562 Z M 12.703125 6.601562' />
|
||||
<path d='M 5.714844 18.375 C 5.152344 16.605469 4.824219 14.667969 4.761719 12.6875 L 0 12.6875 C 0.152344 15.34375 1.175781 17.773438 2.78125 19.691406 C 3.679688 19.171875 4.667969 18.730469 5.714844 18.375 Z M 5.714844 18.375' />
|
||||
<path d='M 17.808594 19.699219 C 17.582031 20.261719 17.328125 20.800781 17.050781 21.3125 C 16.597656 22.148438 16.097656 22.871094 15.574219 23.464844 C 17.328125 22.914062 18.914062 21.976562 20.222656 20.746094 C 19.476562 20.335938 18.664062 19.988281 17.808594 19.699219 Z M 17.808594 19.699219' />
|
||||
<path d='M 6.191406 19.699219 C 5.335938 19.988281 4.523438 20.335938 3.777344 20.746094 C 5.085938 21.976562 6.671875 22.914062 8.425781 23.464844 C 7.902344 22.871094 7.402344 22.148438 6.949219 21.3125 C 6.671875 20.800781 6.417969 20.261719 6.191406 19.699219 Z M 6.191406 19.699219' />
|
||||
<path d='M 18.285156 5.59375 C 18.847656 7.363281 19.175781 9.300781 19.238281 11.28125 L 24 11.28125 C 23.847656 8.625 22.824219 6.199219 21.21875 4.277344 C 20.320312 4.796875 19.332031 5.238281 18.285156 5.59375 Z M 18.285156 5.59375' />
|
||||
<path d='M 18.285156 18.375 C 19.332031 18.730469 20.320312 19.171875 21.21875 19.691406 C 22.824219 17.773438 23.847656 15.34375 24 12.6875 L 19.238281 12.6875 C 19.175781 14.667969 18.847656 16.605469 18.285156 18.375 Z M 18.285156 18.375' />
|
||||
<path d='M 12.703125 0.09375 L 12.703125 5.195312 C 13.980469 5.148438 15.246094 4.96875 16.449219 4.667969 C 16.257812 4.199219 16.042969 3.75 15.8125 3.328125 C 14.898438 1.636719 13.757812 0.46875 12.703125 0.09375 Z M 12.703125 0.09375' />
|
||||
<path d='M 5.714844 5.59375 C 4.667969 5.238281 3.679688 4.796875 2.78125 4.277344 C 1.175781 6.199219 0.152344 8.625 0 11.28125 L 4.761719 11.28125 C 4.824219 9.300781 5.152344 7.363281 5.714844 5.59375 Z M 5.714844 5.59375' />
|
||||
<path d='M 6.191406 4.273438 C 6.417969 3.710938 6.671875 3.167969 6.949219 2.65625 C 7.402344 1.820312 7.902344 1.101562 8.425781 0.507812 C 6.671875 1.054688 5.085938 1.996094 3.777344 3.222656 C 4.523438 3.632812 5.335938 3.984375 6.191406 4.273438 Z M 6.191406 4.273438' />
|
||||
</g>
|
||||
</svg>
|
||||
)
|
||||
|
||||
export default ExploreIcon
|
|
@ -1,6 +1,5 @@
|
|||
const GabLogo = ({
|
||||
className = _s.fillColorBrand,
|
||||
size = '50px',
|
||||
className = _s.fillBrand,
|
||||
}) => (
|
||||
<svg
|
||||
className={className}
|
||||
|
@ -8,8 +7,8 @@ const GabLogo = ({
|
|||
xmlns='http://www.w3.org/2000/svg'
|
||||
x='0px'
|
||||
y='0px'
|
||||
width={size}
|
||||
height={size}
|
||||
width='50px'
|
||||
height='30px'
|
||||
viewBox='0 0 50 30'
|
||||
xmlSpace='preserve'
|
||||
>
|
||||
|
|
|
@ -1,4 +1,3 @@
|
|||
// : todo : fill, stroke colors
|
||||
const GlobeIcon = ({
|
||||
className = '',
|
||||
size = '12px',
|
||||
|
|
|
@ -13,7 +13,7 @@ const LoadingIcon = ({
|
|||
>
|
||||
<g transform='translate(82,50)'>
|
||||
<g transform='rotate(0)'>
|
||||
<circle cx='0' cy='0' r='6' className={_s.fillColorSecondary} fillOpacity='1' transform='scale(1.03405 1.03405)'>
|
||||
<circle cx='0' cy='0' r='6' className={_s.fillSecondary} fillOpacity='1' transform='scale(1.03405 1.03405)'>
|
||||
<animateTransform attributeName='transform' type='scale' begin='-1.0294117647058822s' values='1.5 1.5;1 1' keyTimes='0;1' dur='1.176470588235294s' repeatCount='indefinite'></animateTransform>
|
||||
<animate attributeName='fill-opacity' keyTimes='0;1' dur='1.176470588235294s' repeatCount='indefinite' values='1;0' begin='-1.0294117647058822s'></animate>
|
||||
</circle>
|
||||
|
@ -21,7 +21,7 @@ const LoadingIcon = ({
|
|||
</g>
|
||||
<g transform='translate(72.62741699796952,72.62741699796952)'>
|
||||
<g transform='rotate(45)'>
|
||||
<circle cx='0' cy='0' r='6' className={_s.fillColorSecondary} fillOpacity='0.875' transform='scale(1.09655 1.09655)'>
|
||||
<circle cx='0' cy='0' r='6' className={_s.fillSecondary} fillOpacity='0.875' transform='scale(1.09655 1.09655)'>
|
||||
<animateTransform attributeName='transform' type='scale' begin='-0.8823529411764705s' values='1.5 1.5;1 1' keyTimes='0;1' dur='1.176470588235294s' repeatCount='indefinite'></animateTransform>
|
||||
<animate attributeName='fill-opacity' keyTimes='0;1' dur='1.176470588235294s' repeatCount='indefinite' values='1;0' begin='-0.8823529411764705s'></animate>
|
||||
</circle>
|
||||
|
@ -29,7 +29,7 @@ const LoadingIcon = ({
|
|||
</g>
|
||||
<g transform='translate(50,82)'>
|
||||
<g transform='rotate(90)'>
|
||||
<circle cx='0' cy='0' r='6' className={_s.fillColorSecondary} fillOpacity='0.75' transform='scale(1.15905 1.15905)'>
|
||||
<circle cx='0' cy='0' r='6' className={_s.fillSecondary} fillOpacity='0.75' transform='scale(1.15905 1.15905)'>
|
||||
<animateTransform attributeName='transform' type='scale' begin='-0.7352941176470588s' values='1.5 1.5;1 1' keyTimes='0;1' dur='1.176470588235294s' repeatCount='indefinite'></animateTransform>
|
||||
<animate attributeName='fill-opacity' keyTimes='0;1' dur='1.176470588235294s' repeatCount='indefinite' values='1;0' begin='-0.7352941176470588s'></animate>
|
||||
</circle>
|
||||
|
@ -37,7 +37,7 @@ const LoadingIcon = ({
|
|||
</g>
|
||||
<g transform='translate(27.37258300203048,72.62741699796952)'>
|
||||
<g transform='rotate(135)'>
|
||||
<circle cx='0' cy='0' r='6' className={_s.fillColorSecondary} fillOpacity='0.625' transform='scale(1.22155 1.22155)'>
|
||||
<circle cx='0' cy='0' r='6' className={_s.fillSecondary} fillOpacity='0.625' transform='scale(1.22155 1.22155)'>
|
||||
<animateTransform attributeName='transform' type='scale' begin='-0.588235294117647s' values='1.5 1.5;1 1' keyTimes='0;1' dur='1.176470588235294s' repeatCount='indefinite'></animateTransform>
|
||||
<animate attributeName='fill-opacity' keyTimes='0;1' dur='1.176470588235294s' repeatCount='indefinite' values='1;0' begin='-0.588235294117647s'></animate>
|
||||
</circle>
|
||||
|
@ -45,7 +45,7 @@ const LoadingIcon = ({
|
|||
</g>
|
||||
<g transform='translate(18,50)'>
|
||||
<g transform='rotate(180)'>
|
||||
<circle cx='0' cy='0' r='6' className={_s.fillColorSecondary} fillOpacity='0.5' transform='scale(1.28405 1.28405)'>
|
||||
<circle cx='0' cy='0' r='6' className={_s.fillSecondary} fillOpacity='0.5' transform='scale(1.28405 1.28405)'>
|
||||
<animateTransform attributeName='transform' type='scale' begin='-0.4411764705882352s' values='1.5 1.5;1 1' keyTimes='0;1' dur='1.176470588235294s' repeatCount='indefinite'></animateTransform>
|
||||
<animate attributeName='fill-opacity' keyTimes='0;1' dur='1.176470588235294s' repeatCount='indefinite' values='1;0' begin='-0.4411764705882352s'></animate>
|
||||
</circle>
|
||||
|
@ -53,7 +53,7 @@ const LoadingIcon = ({
|
|||
</g>
|
||||
<g transform='translate(27.372583002030474,27.37258300203048)'>
|
||||
<g transform='rotate(225)'>
|
||||
<circle cx='0' cy='0' r='6' className={_s.fillColorSecondary} fillOpacity='0.375' transform='scale(1.34655 1.34655)'>
|
||||
<circle cx='0' cy='0' r='6' className={_s.fillSecondary} fillOpacity='0.375' transform='scale(1.34655 1.34655)'>
|
||||
<animateTransform attributeName='transform' type='scale' begin='-0.2941176470588235s' values='1.5 1.5;1 1' keyTimes='0;1' dur='1.176470588235294s' repeatCount='indefinite'></animateTransform>
|
||||
<animate attributeName='fill-opacity' keyTimes='0;1' dur='1.176470588235294s' repeatCount='indefinite' values='1;0' begin='-0.2941176470588235s'></animate>
|
||||
</circle>
|
||||
|
@ -61,7 +61,7 @@ const LoadingIcon = ({
|
|||
</g>
|
||||
<g transform='translate(50,18)'>
|
||||
<g transform='rotate(270)'>
|
||||
<circle cx='0' cy='0' r='6' className={_s.fillColorSecondary} fillOpacity='0.25' transform='scale(1.40905 1.40905)'>
|
||||
<circle cx='0' cy='0' r='6' className={_s.fillSecondary} fillOpacity='0.25' transform='scale(1.40905 1.40905)'>
|
||||
<animateTransform attributeName='transform' type='scale' begin='-0.14705882352941174s' values='1.5 1.5;1 1' keyTimes='0;1' dur='1.176470588235294s' repeatCount='indefinite'></animateTransform>
|
||||
<animate attributeName='fill-opacity' keyTimes='0;1' dur='1.176470588235294s' repeatCount='indefinite' values='1;0' begin='-0.14705882352941174s'></animate>
|
||||
</circle>
|
||||
|
@ -69,7 +69,7 @@ const LoadingIcon = ({
|
|||
</g>
|
||||
<g transform='translate(72.62741699796952,27.372583002030474)'>
|
||||
<g transform='rotate(315)'>
|
||||
<circle cx='0' cy='0' r='6' className={_s.fillColorSecondary} fillOpacity='0.125' transform='scale(1.47155 1.47155)'>
|
||||
<circle cx='0' cy='0' r='6' className={_s.fillSecondary} fillOpacity='0.125' transform='scale(1.47155 1.47155)'>
|
||||
<animateTransform attributeName='transform' type='scale' begin='0s' values='1.5 1.5;1 1' keyTimes='0;1' dur='1.176470588235294s' repeatCount='indefinite'></animateTransform>
|
||||
<animate attributeName='fill-opacity' keyTimes='0;1' dur='1.176470588235294s' repeatCount='indefinite' values='1;0' begin='0s'></animate>
|
||||
</circle>
|
||||
|
|
|
@ -115,6 +115,7 @@ class Account extends ImmutablePureComponent {
|
|||
expanded,
|
||||
dismissAction,
|
||||
showDismiss,
|
||||
withBio,
|
||||
} = this.props
|
||||
|
||||
if (!account) return null
|
||||
|
@ -148,13 +149,15 @@ class Account extends ImmutablePureComponent {
|
|||
onClick={dismissAction}
|
||||
icon='close'
|
||||
iconSize='8px'
|
||||
iconClassName={_s.fillColorSecondary}
|
||||
iconClassName={_s.fillSecondary}
|
||||
/>
|
||||
)
|
||||
|
||||
const content = { __html: account.get('note_emojified') }
|
||||
|
||||
return (
|
||||
<div className={[_s.default, _s.px15, _s.py5, _s.backgroundColorSubtle_onHover, _s.mb5].join(' ')}>
|
||||
<div className={[_s.default, _s.flexRow, _s.alignItemsCenter].join(' ')}>
|
||||
<div className={[_s.default, _s.px15, _s.py10, _s.borderBottom1PX, _s.borderColorSecondary, _s.bgSubtle_onHover].join(' ')}>
|
||||
<div className={[_s.default, _s.flexRow, _s.alignItemsStart].join(' ')}>
|
||||
|
||||
<NavLink
|
||||
className={[_s.default, _s.noUnderline].join(' ')}
|
||||
|
@ -164,20 +167,28 @@ class Account extends ImmutablePureComponent {
|
|||
<Avatar account={account} size={avatarSize} />
|
||||
</NavLink>
|
||||
|
||||
<NavLink
|
||||
title={account.get('acct')}
|
||||
to={`/${account.get('acct')}`}
|
||||
className={[_s.default, _s.alignItemsStart, _s.noUnderline, _s.px10, _s.overflowHidden, _s.flexNormal].join(' ')}
|
||||
>
|
||||
<DisplayName account={account} isMultiline={compact} />
|
||||
{!compact && actionButton}
|
||||
</NavLink>
|
||||
<div className={[_s.default, _s.px10, _s.overflowHidden, _s.flexNormal].join(' ')}>
|
||||
<div className={[_s.default, _s.flexRow].join(' ')}>
|
||||
<NavLink
|
||||
title={account.get('acct')}
|
||||
to={`/${account.get('acct')}`}
|
||||
className={[_s.default, _s.alignItemsStart, _s.noUnderline, _s.overflowHidden, _s.flexNormal].join(' ')}
|
||||
>
|
||||
<DisplayName account={account} isMultiline={compact} />
|
||||
{!compact && actionButton}
|
||||
</NavLink>
|
||||
|
||||
<div className={[_s.default].join(' ')}>
|
||||
{dismissBtn}
|
||||
{compact && actionButton}
|
||||
<div className={[_s.default].join(' ')}>
|
||||
{dismissBtn}
|
||||
{compact && actionButton}
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{
|
||||
withBio &&
|
||||
<div className={[_s.py5, _s.dangerousContent].join(' ')} dangerouslySetInnerHTML={content} />
|
||||
}
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
|
|
|
@ -233,12 +233,12 @@ export default class AutosuggestTextbox extends ImmutablePureComponent {
|
|||
text: 1,
|
||||
displayBlock: 1,
|
||||
outlineNone: 1,
|
||||
backgroundColorPrimary: !small,
|
||||
backgroundColorSubtle: small,
|
||||
bgPrimary: !small,
|
||||
bgSubtle: small,
|
||||
py15: !small,
|
||||
py10: small,
|
||||
fontSize16PX: !small,
|
||||
fontSize14PX: small,
|
||||
fs16PX: !small,
|
||||
fs14PX: small,
|
||||
mr5: small,
|
||||
})
|
||||
|
||||
|
|
|
@ -11,7 +11,7 @@ export default class Block extends PureComponent {
|
|||
const { children } = this.props
|
||||
|
||||
return (
|
||||
<div className={[_s.default, _s.boxShadowBlock, _s.backgroundColorPrimary, _s.overflowHidden, _s.radiusSmall].join(' ')}>
|
||||
<div className={[_s.default, _s.boxShadowBlock, _s.bgPrimary, _s.overflowHidden, _s.radiusSmall].join(' ')}>
|
||||
{children}
|
||||
</div>
|
||||
)
|
||||
|
|
|
@ -37,6 +37,8 @@ const COLORS = {
|
|||
* @param {func} [props.onMouseEnter] - function to call on button mouse enter
|
||||
* @param {func} [props.onMouseLeave] - function to call on button mouse leave
|
||||
* @param {bool} [props.radiusSmall] - if the button has small radius
|
||||
* @param {bool} [props.rel] - rel for the button
|
||||
* @param {bool} [props.target] - target for the button
|
||||
* @param {bool} [props.text] - if the button is just text (i.e. link)
|
||||
* @param {bool} [props.title] - `title` attribute for button
|
||||
* @param {bool} [props.to] - `to` to send to on click
|
||||
|
@ -68,6 +70,8 @@ export default class Button extends PureComponent {
|
|||
onMouseLeave: PropTypes.func,
|
||||
isOutline: PropTypes.bool,
|
||||
radiusSmall: PropTypes.bool,
|
||||
rel: PropTypes.string,
|
||||
target: PropTypes.string,
|
||||
title: PropTypes.string,
|
||||
to: PropTypes.string,
|
||||
type: PropTypes.string,
|
||||
|
@ -118,6 +122,8 @@ export default class Button extends PureComponent {
|
|||
onMouseEnter,
|
||||
onMouseLeave,
|
||||
radiusSmall,
|
||||
rel,
|
||||
target,
|
||||
title,
|
||||
to,
|
||||
type,
|
||||
|
@ -136,13 +142,13 @@ export default class Button extends PureComponent {
|
|||
cursorNotAllowed: isDisabled,
|
||||
opacity05: isDisabled,
|
||||
|
||||
backgroundColorPrimary: backgroundColor === COLORS.white,
|
||||
backgroundColorBlack: backgroundColor === COLORS.black,
|
||||
backgroundColorBrand: backgroundColor === COLORS.brand,
|
||||
backgroundTransparent: backgroundColor === COLORS.none,
|
||||
backgroundColorSubtle2: backgroundColor === COLORS.tertiary,
|
||||
backgroundColorSubtle: backgroundColor === COLORS.secondary,
|
||||
backgroundColorDanger: backgroundColor === COLORS.danger,
|
||||
bgPrimary: backgroundColor === COLORS.white,
|
||||
bgBlack: backgroundColor === COLORS.black,
|
||||
bgBrand: backgroundColor === COLORS.brand,
|
||||
bgTransparent: backgroundColor === COLORS.none,
|
||||
bgSecondary: backgroundColor === COLORS.tertiary,
|
||||
bgSubtle: backgroundColor === COLORS.secondary,
|
||||
bgDanger: backgroundColor === COLORS.danger,
|
||||
|
||||
colorPrimary: !!children && color === COLORS.primary,
|
||||
colorSecondary: !!children && color === COLORS.secondary,
|
||||
|
@ -164,18 +170,18 @@ export default class Button extends PureComponent {
|
|||
|
||||
underline_onHover: underlineOnHover,
|
||||
|
||||
backgroundColorSubtle2Dark_onHover: backgroundColor === COLORS.tertiary || backgroundColor === COLORS.secondary && !isDisabled,
|
||||
backgroundColorBlackOpaque_onHover: backgroundColor === COLORS.black && !isDisabled,
|
||||
backgroundColorBrandDark_onHover: backgroundColor === COLORS.brand && !isDisabled,
|
||||
backgroundColorDangerDark_onHover: backgroundColor === COLORS.danger && !isDisabled,
|
||||
bgSecondaryDark_onHover: backgroundColor === COLORS.tertiary || backgroundColor === COLORS.secondary && !isDisabled,
|
||||
bgBlackOpaque_onHover: backgroundColor === COLORS.black && !isDisabled,
|
||||
bgBrandDark_onHover: backgroundColor === COLORS.brand && !isDisabled,
|
||||
bgDangerDark_onHover: backgroundColor === COLORS.danger && !isDisabled,
|
||||
|
||||
backgroundColorBrand_onHover: color === COLORS.brand && isOutline && !isDisabled,
|
||||
bgBrand_onHover: color === COLORS.brand && isOutline && !isDisabled,
|
||||
colorWhite_onHover: !!children && color === COLORS.brand && isOutline && !isDisabled,
|
||||
|
||||
fillColorSecondary: !!icon && color === COLORS.secondary,
|
||||
fillColorWhite: !!icon && color === COLORS.white,
|
||||
fillColorBrand: !!icon && color === COLORS.brand,
|
||||
fillColorWhite_onHover: !!icon && color === COLORS.brand && isOutline,
|
||||
fillSecondary: !!icon && color === COLORS.secondary,
|
||||
fillWhite: !!icon && color === COLORS.white,
|
||||
fillBrand: !!icon && color === COLORS.brand,
|
||||
fillWhite_onHover: !!icon && color === COLORS.brand && isOutline,
|
||||
})
|
||||
|
||||
const tagName = !!href ? 'a' : !!to ? 'NavLink' : 'button'
|
||||
|
@ -216,6 +222,8 @@ export default class Button extends PureComponent {
|
|||
}
|
||||
|
||||
const options = {
|
||||
rel,
|
||||
target,
|
||||
title,
|
||||
type,
|
||||
disabled: isDisabled,
|
||||
|
|
|
@ -45,14 +45,14 @@ export default class ColumnHeader extends PureComponent {
|
|||
className={[_s.alignItemsCenter, _s.pl0, _s.justifyContentCenter].join(' ')}
|
||||
icon='back'
|
||||
iconSize='20px'
|
||||
iconClassName={[_s.mr5, _s.fillColorPrimary].join(' ')}
|
||||
iconClassName={[_s.mr5, _s.fillPrimary].join(' ')}
|
||||
onClick={this.handleBackClick}
|
||||
/>
|
||||
}
|
||||
|
||||
<div className={[_s.default, _s.height100PC, _s.justifyContentCenter, _s.mr10].join(' ')}>
|
||||
<Heading size='h1'>
|
||||
{title}
|
||||
|
||||
</Heading>
|
||||
</div>
|
||||
|
||||
|
@ -63,7 +63,7 @@ export default class ColumnHeader extends PureComponent {
|
|||
|
||||
{
|
||||
!!actions &&
|
||||
<div className={[_s.default, _s.backgroundTransparent, _s.flexRow, _s.alignItemsCenter, _s.justifyContentCenter, _s.mlAuto].join(' ')}>
|
||||
<div className={[_s.default, _s.bgTransparent, _s.flexRow, _s.alignItemsCenter, _s.justifyContentCenter, _s.mlAuto].join(' ')}>
|
||||
{
|
||||
actions.map((action, i) => (
|
||||
<Button
|
||||
|
|
|
@ -61,7 +61,7 @@ class Comment extends ImmutablePureComponent {
|
|||
</NavLink>
|
||||
|
||||
<div className={[_s.default, _s.flexNormal].join(' ')}>
|
||||
<div className={[_s.default, _s.px10, _s.pt5, _s.pb10, _s.radiusSmall, _s.backgroundColorSubtle].join(' ')}>
|
||||
<div className={[_s.default, _s.px10, _s.pt5, _s.pb10, _s.radiusSmall, _s.bgSubtle].join(' ')}>
|
||||
<CommentHeader status={status} />
|
||||
<StatusContent
|
||||
status={status}
|
||||
|
@ -103,7 +103,7 @@ class CommentButton extends PureComponent {
|
|||
radiusSmall
|
||||
backgroundColor='none'
|
||||
color='tertiary'
|
||||
className={[_s.px5, _s.backgroundColorSubtle_onHover, _s.py2, _s.mr5].join(' ')}
|
||||
className={[_s.px5, _s.bgSubtle_onHover, _s.py2, _s.mr5].join(' ')}
|
||||
onClick={onClick}
|
||||
>
|
||||
<Text size='extraSmall' color='inherit' weight='bold'>
|
||||
|
|
|
@ -183,8 +183,8 @@ class Composer extends PureComponent {
|
|||
default: 1,
|
||||
cursorText: 1,
|
||||
text: 1,
|
||||
fontSize16PX: !small,
|
||||
fontSize14PX: small,
|
||||
fs16PX: !small,
|
||||
fs14PX: small,
|
||||
pt15: !small,
|
||||
px15: !small,
|
||||
px10: small,
|
||||
|
|
|
@ -98,9 +98,9 @@ class DisplayName extends ImmutablePureComponent {
|
|||
colorPrimary: 1,
|
||||
mr2: 1,
|
||||
lineHeight125: !isSmall,
|
||||
fontSize14PX: isSmall,
|
||||
fontSize15PX: !isLarge,
|
||||
fontSize24PX: isLarge && !isSmall,
|
||||
fs14PX: isSmall,
|
||||
fs15PX: !isLarge,
|
||||
fs24PX: isLarge && !isSmall,
|
||||
})
|
||||
|
||||
const usernameClasses = CX({
|
||||
|
@ -115,9 +115,9 @@ class DisplayName extends ImmutablePureComponent {
|
|||
lineHeight15: isMultiline,
|
||||
lineHeight125: !isMultiline,
|
||||
ml5: !isMultiline,
|
||||
fontSize14PX: isSmall,
|
||||
fontSize15PX: !isLarge,
|
||||
fontSize16PX: isLarge && !isSmall,
|
||||
fs14PX: isSmall,
|
||||
fs15PX: !isLarge,
|
||||
fs16PX: isLarge && !isSmall,
|
||||
})
|
||||
|
||||
const iconSize =
|
||||
|
@ -161,7 +161,7 @@ class DisplayName extends ImmutablePureComponent {
|
|||
/>
|
||||
{
|
||||
!noRelationship && account.get('locked') &&
|
||||
<Icon id='lock-filled' size={iconSize} className={[_s.fillColorPrimary, _s.ml5].join(' ')} />
|
||||
<Icon id='lock-filled' size={iconSize} className={[_s.fillPrimary, _s.ml5].join(' ')} />
|
||||
}
|
||||
</bdi>
|
||||
{
|
||||
|
@ -180,7 +180,7 @@ class DisplayName extends ImmutablePureComponent {
|
|||
size='extraSmall'
|
||||
isBadge
|
||||
color='tertiary'
|
||||
className={[_s.backgroundColorSubtle2, _s.py2].join(' ')}
|
||||
className={[_s.bgSecondary, _s.py2].join(' ')}
|
||||
>
|
||||
{relationshipLabel}
|
||||
</Text>
|
||||
|
|
|
@ -86,8 +86,8 @@ class GroupCollectionItem extends ImmutablePureComponent {
|
|||
mb10: 1,
|
||||
ml5: 1,
|
||||
mr5: 1,
|
||||
backgroundColorPrimary: 1,
|
||||
backgroundColorSubtle_onHover: isMember,
|
||||
bgPrimary: 1,
|
||||
bgSubtle_onHover: isMember,
|
||||
})
|
||||
|
||||
return (
|
||||
|
@ -107,7 +107,7 @@ class GroupCollectionItem extends ImmutablePureComponent {
|
|||
|
||||
{
|
||||
(!coverSrc || coverMissing) && (isMember || isAdmin) &&
|
||||
<div className={[_s.default, _s.height40PX, _s.backgroundColorSubtle, _s.borderColorSecondary, _s.borderBottom1PX].join(' ')} />
|
||||
<div className={[_s.default, _s.height40PX, _s.bgSubtle, _s.borderColorSecondary, _s.borderBottom1PX].join(' ')} />
|
||||
}
|
||||
|
||||
{
|
||||
|
@ -117,7 +117,7 @@ class GroupCollectionItem extends ImmutablePureComponent {
|
|||
isMember &&
|
||||
<Text
|
||||
isBadge
|
||||
className={_s.backgroundColorWhite}
|
||||
className={_s.bgWhite}
|
||||
size='extraSmall'
|
||||
color='brand'
|
||||
>
|
||||
|
@ -128,7 +128,7 @@ class GroupCollectionItem extends ImmutablePureComponent {
|
|||
isAdmin &&
|
||||
<Text
|
||||
isBadge
|
||||
className={[_s.backgroundColorBlack, _s.ml5].join(' ')}
|
||||
className={[_s.bgBlack, _s.ml5].join(' ')}
|
||||
size='extraSmall'
|
||||
color='white'
|
||||
>
|
||||
|
|
|
@ -3,7 +3,7 @@ import ImmutablePureComponent from 'react-immutable-pure-component'
|
|||
import { Fragment } from 'react'
|
||||
import { NavLink } from 'react-router-dom'
|
||||
import { defineMessages, injectIntl } from 'react-intl'
|
||||
import classNames from 'classnames/bind'
|
||||
import { CX } from '../constants'
|
||||
import { PLACEHOLDER_MISSING_HEADER_SRC } from '../constants'
|
||||
import { shortNumberFormat } from '../utils/numbers'
|
||||
import Image from './image'
|
||||
|
@ -17,11 +17,9 @@ const messages = defineMessages({
|
|||
|
||||
const mapStateToProps = (state, { id }) => ({
|
||||
group: state.getIn(['groups', id]),
|
||||
relationships: state.getIn(['group_relationships', id]),
|
||||
relatioships: state.getIn(['group_relationships', id]),
|
||||
})
|
||||
|
||||
const cx = classNames.bind(_s)
|
||||
|
||||
export default
|
||||
@connect(mapStateToProps)
|
||||
@injectIntl
|
||||
|
@ -50,17 +48,21 @@ class GroupListItem extends ImmutablePureComponent {
|
|||
isHidden,
|
||||
} = this.props
|
||||
|
||||
if (!relationships || !group) return null
|
||||
if (!group) return null
|
||||
|
||||
const unreadCount = relationships.get('unread_count')
|
||||
let unreadCount, subtitle
|
||||
|
||||
const subtitle = unreadCount > 0 ? (
|
||||
<Fragment>
|
||||
{shortNumberFormat(unreadCount)}
|
||||
|
||||
{intl.formatMessage(messages.new_statuses)}
|
||||
</Fragment>
|
||||
) : intl.formatMessage(messages.no_recent_activity)
|
||||
if (relationships) {
|
||||
unreadCount = relationships.get('unread_count')
|
||||
|
||||
subtitle = unreadCount > 0 ? (
|
||||
<Fragment>
|
||||
{shortNumberFormat(unreadCount)}
|
||||
|
||||
{intl.formatMessage(messages.new_statuses)}
|
||||
</Fragment>
|
||||
) : intl.formatMessage(messages.no_recent_activity)
|
||||
}
|
||||
|
||||
if (isHidden) {
|
||||
return (
|
||||
|
@ -71,22 +73,21 @@ class GroupListItem extends ImmutablePureComponent {
|
|||
)
|
||||
}
|
||||
|
||||
const containerClasses = cx({
|
||||
const containerClasses = CX({
|
||||
default: 1,
|
||||
noUnderline: 1,
|
||||
overflowHidden: 1,
|
||||
backgroundColorSubtle_onHover: 1,
|
||||
bgSubtle_onHover: 1,
|
||||
borderColorSecondary: 1,
|
||||
radiusSmall: !slim,
|
||||
mt5: !slim,
|
||||
mb10: !slim,
|
||||
mb10: !slim && !isLast,
|
||||
border1PX: !slim,
|
||||
borderBottom1PX: slim && !isLast,
|
||||
flexRow: slim,
|
||||
py5: slim,
|
||||
})
|
||||
|
||||
const imageClasses = cx({
|
||||
const imageClasses = CX({
|
||||
height122PX: !slim,
|
||||
radiusSmall: slim,
|
||||
height72PX: slim,
|
||||
|
@ -94,7 +95,7 @@ class GroupListItem extends ImmutablePureComponent {
|
|||
ml15: slim,
|
||||
})
|
||||
|
||||
const textContainerClasses = cx({
|
||||
const textContainerClasses = CX({
|
||||
default: 1,
|
||||
px10: 1,
|
||||
mt5: 1,
|
||||
|
@ -134,9 +135,12 @@ class GroupListItem extends ImmutablePureComponent {
|
|||
</Text>
|
||||
}
|
||||
|
||||
<Text color='secondary' size='small' className={_s.mt5}>
|
||||
{subtitle}
|
||||
</Text>
|
||||
{
|
||||
subtitle &&
|
||||
<Text color='secondary' size='small' className={_s.mt5}>
|
||||
{subtitle}
|
||||
</Text>
|
||||
}
|
||||
|
||||
</div>
|
||||
</NavLink>
|
||||
|
|
|
@ -24,12 +24,12 @@ export default class HashtagItem extends ImmutablePureComponent {
|
|||
return (
|
||||
<NavLink
|
||||
to={`/tags/${hashtag.get('name')}`}
|
||||
className={[_s.default, _s.noUnderline, _s.backgroundColorSubtle_onHover, _s.px15, _s.py5].join(' ')}
|
||||
className={[_s.default, _s.noUnderline, _s.bgSubtle_onHover, _s.px15, _s.py5].join(' ')}
|
||||
>
|
||||
<div className={[_s.default, _s.flexRow, _s.alignItemsCenter].join(' ')}>
|
||||
<div>
|
||||
<Text color='brand' size='medium' weight='bold' className={[_s.py2, _s.lineHeight15].join(' ')}>
|
||||
{hashtag.get('name')}
|
||||
#{hashtag.get('name')}
|
||||
</Text>
|
||||
</div>
|
||||
{
|
||||
|
@ -41,7 +41,7 @@ export default class HashtagItem extends ImmutablePureComponent {
|
|||
title='Remove'
|
||||
icon='close'
|
||||
iconSize='8px'
|
||||
iconClassName={_s.fillColorSecondary}
|
||||
iconClassName={_s.fillSecondary}
|
||||
className={_s.mlAuto}
|
||||
/>
|
||||
}
|
||||
|
|
|
@ -42,11 +42,11 @@ export default class Heading extends PureComponent {
|
|||
colorPrimary: [SIZES.h1, SIZES.h2].indexOf(size) > -1,
|
||||
colorSecondary: [SIZES.h3, SIZES.h4, SIZES.h5].indexOf(size) > -1,
|
||||
|
||||
fontSize24PX: size === SIZES.h1,
|
||||
fontSize19PX: size === SIZES.h2,
|
||||
fontSize16PX: size === SIZES.h3,
|
||||
fontSize13PX: size === SIZES.h4,
|
||||
fontSize12PX: size === SIZES.h5,
|
||||
fs24PX: size === SIZES.h1,
|
||||
fs19PX: size === SIZES.h2,
|
||||
fs16PX: size === SIZES.h3,
|
||||
fs13PX: size === SIZES.h4,
|
||||
fs12PX: size === SIZES.h5,
|
||||
|
||||
mt5: [SIZES.h4].indexOf(size) > -1,
|
||||
|
||||
|
|
|
@ -19,6 +19,7 @@ import DonorIcon from '../assets/donor_icon'
|
|||
import EllipsisIcon from '../assets/ellipsis_icon'
|
||||
import EmailIcon from '../assets/email_icon'
|
||||
import ErrorIcon from '../assets/error_icon'
|
||||
import ExploreIcon from '../assets/explore_icon'
|
||||
import FullscreenIcon from '../assets/fullscreen_icon'
|
||||
import GabLogoIcon from '../assets/gab_logo'
|
||||
import GifIcon from '../assets/gif_icon'
|
||||
|
@ -89,6 +90,7 @@ const ICONS = {
|
|||
'ellipsis': EllipsisIcon,
|
||||
'email': EmailIcon,
|
||||
'error': ErrorIcon,
|
||||
'explore': ExploreIcon,
|
||||
'fullscreen': FullscreenIcon,
|
||||
'gab-logo': GabLogoIcon,
|
||||
'gif': GifIcon,
|
||||
|
|
|
@ -50,7 +50,7 @@ export default class Image extends PureComponent {
|
|||
const classes = cx(className, {
|
||||
default: 1,
|
||||
objectFitCover: !!src && fit === 'cover',
|
||||
backgroundColorSubtle2: 1,
|
||||
bgSecondary: 1,
|
||||
})
|
||||
|
||||
//If error and not our own image
|
||||
|
|
|
@ -58,12 +58,12 @@ export default class Input extends PureComponent {
|
|||
displayBlock: 1,
|
||||
py10: !small,
|
||||
py5: small,
|
||||
backgroundTransparent: !readOnly,
|
||||
backgroundColorSubtle2: readOnly,
|
||||
bgTransparent: !readOnly,
|
||||
bgSecondary: readOnly,
|
||||
colorPrimary: !readOnly,
|
||||
colorSecondary: readOnly,
|
||||
fontSize15PX: !small,
|
||||
fontSize13PX: small,
|
||||
fs15PX: !small,
|
||||
fs13PX: small,
|
||||
flexGrow1: 1,
|
||||
circle: 1,
|
||||
px5: !!prependIcon,
|
||||
|
@ -87,10 +87,10 @@ export default class Input extends PureComponent {
|
|||
</Text>
|
||||
</div>
|
||||
}
|
||||
<div className={[_s.default, _s.backgroundColorPrimary, _s.border1PX, _s.borderColorSecondary, _s.flexRow, _s.circle, _s.alignItemsCenter].join(' ')}>
|
||||
<div className={[_s.default, _s.bgPrimary, _s.border1PX, _s.borderColorSecondary, _s.flexRow, _s.circle, _s.alignItemsCenter].join(' ')}>
|
||||
{
|
||||
!!prependIcon &&
|
||||
<Icon id={prependIcon} size='16px' className={[_s.fillColorPrimary, _s.ml15, _s.mr5].join(' ')} />
|
||||
<Icon id={prependIcon} size='16px' className={[_s.fillPrimary, _s.ml15, _s.mr5].join(' ')} />
|
||||
}
|
||||
|
||||
{
|
||||
|
|
|
@ -51,7 +51,7 @@ export default class List extends ImmutablePureComponent {
|
|||
))
|
||||
}
|
||||
</ScrollableList>
|
||||
</Block>
|
||||
</Block>
|
||||
)
|
||||
}
|
||||
|
||||
|
|
|
@ -56,7 +56,7 @@ export default class ListItem extends PureComponent {
|
|||
flexRow: 1,
|
||||
alignItemsCenter: 1,
|
||||
width100PC: 1,
|
||||
backgroundColorSubtle_onHover: 1,
|
||||
bgSubtle_onHover: 1,
|
||||
borderColorSecondary: !isLast,
|
||||
borderBottom1PX: !isLast,
|
||||
})
|
||||
|
@ -64,7 +64,7 @@ export default class ListItem extends PureComponent {
|
|||
const iconClasses = cx({
|
||||
mr10: !large,
|
||||
mr15: large,
|
||||
fillColorPrimary: 1,
|
||||
fillPrimary: 1,
|
||||
})
|
||||
|
||||
const textSize = small ? 'small' : large ? 'medium' : 'normal'
|
||||
|
@ -97,7 +97,7 @@ export default class ListItem extends PureComponent {
|
|||
<Icon
|
||||
id='angle-right'
|
||||
size='10px'
|
||||
className={[_s.mlAuto, _s.fillColorSecondary, _s.flexShrink1].join(' ')}
|
||||
className={[_s.mlAuto, _s.fillSecondary, _s.flexShrink1].join(' ')}
|
||||
/>
|
||||
}
|
||||
</Button>
|
||||
|
|
|
@ -216,7 +216,7 @@ class Item extends ImmutablePureComponent {
|
|||
playsInline
|
||||
/>
|
||||
|
||||
<div className={[_s.default, _s.posAbs, _s.z2, _s.radiusSmall, _s.backgroundColorBlackOpaque, _s.px5, _s.py5, _s.mr10, _s.mb10, _s.bottom0, _s.right0].join(' ')}>
|
||||
<div className={[_s.default, _s.posAbs, _s.z2, _s.radiusSmall, _s.bgBlackOpaque, _s.px5, _s.py5, _s.mr10, _s.mb10, _s.bottom0, _s.right0].join(' ')}>
|
||||
<Text size='extraSmall' color='white' weight='medium'>GIF</Text>
|
||||
</div>
|
||||
</div>
|
||||
|
@ -574,7 +574,7 @@ class MediaGallery extends PureComponent {
|
|||
title={intl.formatMessage(messages.toggle_visible)}
|
||||
icon='hidden'
|
||||
backgroundColor='none'
|
||||
className={[_s.px10, _s.backgroundColorBlackOpaque_onHover].join(' ')}
|
||||
className={[_s.px10, _s.bgBlackOpaque_onHover].join(' ')}
|
||||
onClick={this.handleOpen}
|
||||
/>
|
||||
</div>
|
||||
|
|
|
@ -137,13 +137,13 @@ export default class MediaItem extends ImmutablePureComponent {
|
|||
<Icon
|
||||
id='hidden'
|
||||
size='22px'
|
||||
className={[_s.fillColorWhite].join('')}
|
||||
className={[_s.fillWhite].join('')}
|
||||
/>
|
||||
}
|
||||
|
||||
{
|
||||
!!badge &&
|
||||
<div className={[_s.default, _s.posAbs, _s.radiusSmall, _s.backgroundColorBlackOpaque, _s.px5, _s.py5, _s.mr5, _s.mt5, _s.mb5, _s.bottom0, _s.right0].join(' ')}>
|
||||
<div className={[_s.default, _s.posAbs, _s.radiusSmall, _s.bgBlackOpaque, _s.px5, _s.py5, _s.mr5, _s.mt5, _s.mb5, _s.bottom0, _s.right0].join(' ')}>
|
||||
<Text size='extraSmall' color='white'>
|
||||
{badge}
|
||||
</Text>
|
||||
|
|
|
@ -89,7 +89,7 @@ class EmbedModal extends ImmutablePureComponent {
|
|||
{intl.formatMessage(messages.preview)}
|
||||
</Text>
|
||||
|
||||
<div className={[_s.default, _s.width100PC, _s.backgroundColorSubtle, _s.height220PX, _s.alignItemsCenter, _s.justifyContentCenter].join(' ')}>
|
||||
<div className={[_s.default, _s.width100PC, _s.bgSubtle, _s.height220PX, _s.alignItemsCenter, _s.justifyContentCenter].join(' ')}>
|
||||
<iframe
|
||||
className={[_s.default, _s.width100PC, _s.height100PC, _s.z2].join(' ')}
|
||||
frameBorder='0'
|
||||
|
|
|
@ -45,7 +45,7 @@ class HomeTimelineSettingsModal extends ImmutablePureComponent {
|
|||
icon='pro'
|
||||
href='https://pro.gab.com'
|
||||
className={_s.justifyContentCenter}
|
||||
iconClassName={[_s.mr5, _s.fillColorWhite].join(' ')}
|
||||
iconClassName={[_s.mr5, _s.fillWhite].join(' ')}
|
||||
>
|
||||
<Text color='inherit' weight='bold' align='center'>
|
||||
{intl.formatMessage(messages.title)}
|
||||
|
|
|
@ -137,7 +137,7 @@ class ModalBase extends PureComponent {
|
|||
<Fragment>
|
||||
<div
|
||||
role='presentation'
|
||||
className={[_s.default, _s.backgroundColorBlackOpaque, _s.posFixed, _s.z3, _s.top0, _s.right0, _s.bottom0, _s.left0].join(' ')}
|
||||
className={[_s.default, _s.bgBlackOpaque, _s.posFixed, _s.z3, _s.top0, _s.right0, _s.bottom0, _s.left0].join(' ')}
|
||||
/>
|
||||
<div
|
||||
ref={this.setDialog}
|
||||
|
|
|
@ -50,7 +50,7 @@ class ProUpgradeModal extends ImmutablePureComponent {
|
|||
icon='pro'
|
||||
href='https://pro.gab.com'
|
||||
className={_s.justifyContentCenter}
|
||||
iconClassName={[_s.mr5, _s.fillColorWhite].join(' ')}
|
||||
iconClassName={[_s.mr5, _s.fillWhite].join(' ')}
|
||||
>
|
||||
<Text color='inherit' weight='bold' align='center'>
|
||||
{intl.formatMessage(messages.title)}
|
||||
|
|
|
@ -5,8 +5,9 @@ import { BREAKPOINT_EXTRA_SMALL } from '../constants'
|
|||
import { me } from '../initial_state'
|
||||
import { makeGetAccount } from '../selectors'
|
||||
import Responsive from '../features/ui/util/responsive_component'
|
||||
import ColumnHeader from './column_header'
|
||||
import { CX } from '../constants'
|
||||
import Search from './search'
|
||||
import Avatar from './avatar'
|
||||
import Icon from './icon'
|
||||
|
||||
const mapStateToProps = (state) => ({
|
||||
|
@ -25,6 +26,10 @@ class NavigationBar extends ImmutablePureComponent {
|
|||
showBackBtn: PropTypes.bool,
|
||||
}
|
||||
|
||||
handleProfileClick = () => {
|
||||
|
||||
}
|
||||
|
||||
render() {
|
||||
const {
|
||||
title,
|
||||
|
@ -34,40 +39,118 @@ class NavigationBar extends ImmutablePureComponent {
|
|||
account,
|
||||
} = this.props
|
||||
|
||||
const isPro = account.get('is_pro')
|
||||
|
||||
return (
|
||||
<div className={[_s.default, _s.height53PX, _s.flexRow, _s.backgroundColorPrimary, _s.borderBottom1PX, _s.borderColorSecondary, _s.alignItemsCenter, _s.z3, _s.top0, _s.right0, _s.left0, _s.posFixed].join(' ')} >
|
||||
<div className={[_s.default, _s.flexGrow1, _s.z3, _s.alignItemsEnd].join(' ')}>
|
||||
<div className={[_s.default, _s.width240PX].join(' ')}>
|
||||
<div className={[_s.default, _s.height100PC, _s.alignItemsStart, _s.width240PX].join(' ')}>
|
||||
<h1 className={[_s.default].join(' ')}>
|
||||
<NavLink to='/' aria-label='Gab' className={[_s.default, _s.flexRow, _s.noSelect, _s.noUnderline, _s.height50PX, _s.cursorPointer, _s.px10].join(' ')}>
|
||||
<Icon id='gab-logo' />
|
||||
<div className={[_s.default, _s.z4, _s.height53PX, _s.width100PC].join(' ')}>
|
||||
<div className={[_s.default, _s.height53PX, _s.bgBrand, _s.alignItemsCenter, _s.z3, _s.top0, _s.right0, _s.left0, _s.posFixed].join(' ')} >
|
||||
|
||||
<div className={[_s.default, _s.flexRow, _s.width1255PX].join(' ')}>
|
||||
|
||||
<div className={[_s.default, _s.flexRow].join(' ')}>
|
||||
|
||||
<h1 className={[_s.default, _s.mr15].join(' ')}>
|
||||
<NavLink to='/' aria-label='Gab' className={[_s.default, _s.justifyContentCenter, _s.noSelect, _s.noUnderline, _s.height53PX, _s.cursorPointer, _s.px10, _s.mr15].join(' ')}>
|
||||
<Icon id='gab-logo' className={_s.fillWhite} />
|
||||
</NavLink>
|
||||
</h1>
|
||||
|
||||
<Responsive min={BREAKPOINT_EXTRA_SMALL}>
|
||||
<div className={[_s.default, _s.width340PX].join(' ')}>
|
||||
<Search />
|
||||
</div>
|
||||
</Responsive>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
<div className={[_s.default, _s.flexShrink1, _s.flexGrow1].join(' ')}>
|
||||
<div className={[_s.default, _s.height53PX, _s.pl15, _s.width1015PX, _s.flexRow, _s.justifyContentSpaceBetween].join(' ')}>
|
||||
<div className={[_s.default, _s.width645PX].join(' ')}>
|
||||
<ColumnHeader
|
||||
title={title}
|
||||
showBackBtn={showBackBtn}
|
||||
actions={actions}
|
||||
tabs={tabs}
|
||||
/>
|
||||
</div>
|
||||
<Responsive min={BREAKPOINT_EXTRA_SMALL}>
|
||||
<div className={[_s.default, _s.width340PX].join(' ')}>
|
||||
<Search />
|
||||
|
||||
<div className={[_s.default, _s.mlAuto].join(' ')}>
|
||||
<div className={[_s.default, _s.height53PX, _s.pl15, _s.flexRow, _s.alignItemsCenter, _s.justifyContentSpaceBetween].join(' ')}>
|
||||
<NavigationBarButton title='Home' icon='home' to='/home' />
|
||||
|
||||
<NavigationBarButtonDivider />
|
||||
|
||||
<NavigationBarButton icon='notifications' to='/notifications' />
|
||||
<NavigationBarButton icon='cog' to='/notifications' />
|
||||
|
||||
<NavigationBarButtonDivider />
|
||||
|
||||
<button onClick={this.handleProfileClick} className={[_s.height53PX, _s.bgTransparent, _s.outlineNone, _s.cursorPointer, _s.default, _s.justifyContentCenter, _s.ml15].join(' ')}>
|
||||
<Avatar account={account} size={32} />
|
||||
</button>
|
||||
</div>
|
||||
</Responsive>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
class NavigationBarButtonDivider extends PureComponent {
|
||||
|
||||
render() {
|
||||
return (
|
||||
<div className={[_s.default, _s.height20PX, _s.width1PX, _s.mr10, _s.ml10, _s.bgBrandDark].join(' ')} />
|
||||
)
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
class NavigationBarButton extends PureComponent {
|
||||
|
||||
static propTypes = {
|
||||
title: PropTypes.string,
|
||||
icon: PropTypes.string,
|
||||
to: PropTypes.string,
|
||||
onClick: PropTypes.func,
|
||||
}
|
||||
|
||||
render() {
|
||||
const {
|
||||
title,
|
||||
icon,
|
||||
to,
|
||||
onClick,
|
||||
} = this.props
|
||||
|
||||
const active = false
|
||||
|
||||
const classes = CX({
|
||||
default: 1,
|
||||
height53PX: 1,
|
||||
flexRow: 1,
|
||||
alignItemsCenter: 1,
|
||||
justifyContentCenter: 1,
|
||||
outlineNone: 1,
|
||||
px10: !!title,
|
||||
px5: !title,
|
||||
cursorPointer: 1,
|
||||
bgTransparent: 1,
|
||||
colorWhite: !!title,
|
||||
fs13PX: !!title,
|
||||
fontWeightNormal: !!title,
|
||||
textUppercase: !!title,
|
||||
})
|
||||
|
||||
const iconClasses = CX({
|
||||
fillWhite: !!title || active,
|
||||
fillBrandDark: !title,
|
||||
mr10: !!title,
|
||||
})
|
||||
|
||||
const iconSize = !!title ? 16 : 18
|
||||
|
||||
return (
|
||||
<button
|
||||
noClasses
|
||||
color='white'
|
||||
className={classes}
|
||||
>
|
||||
<Icon className={iconClasses} id={icon} size={iconSize} />
|
||||
{title}
|
||||
</button>
|
||||
)
|
||||
}
|
||||
|
||||
}
|
|
@ -96,11 +96,11 @@ class Notification extends ImmutablePureComponent {
|
|||
}
|
||||
|
||||
return (
|
||||
<div className={[_s.default, _s.px10, _s.cursorPointer, _s.backgroundColorSubtle_onHover].join(' ')}>
|
||||
<div className={[_s.default, _s.px10, _s.cursorPointer, _s.bgSubtle_onHover].join(' ')}>
|
||||
<div className={[_s.default, _s.borderBottom1PX, _s.borderColorSecondary].join(' ')}>
|
||||
<div className={[_s.default, _s.flexRow, _s.my10, _s.py10, _s.px10].join(' ')}>
|
||||
|
||||
<Icon id={icon} size='20px' className={[_s.fillColorPrimary, _s.mt5].join(' ')} />
|
||||
<Icon id={icon} size='20px' className={[_s.fillPrimary, _s.mt5].join(' ')} />
|
||||
|
||||
<div className={[_s.default, _s.ml15, _s.flexNormal].join(' ')}>
|
||||
<div className={[_s.default, _s.flexRow].join(' ')}>
|
||||
|
|
|
@ -69,7 +69,7 @@ class GroupInfoPanel extends ImmutablePureComponent {
|
|||
<Divider isSmall />
|
||||
|
||||
<div className={[_s.default, _s.flexRow, _s.alignItemsCenter].join(' ')}>
|
||||
<Icon id='calendar' size='12px' className={_s.fillColorSecondary} />
|
||||
<Icon id='calendar' size='12px' className={_s.fillSecondary} />
|
||||
<Text
|
||||
size='small'
|
||||
color='secondary'
|
||||
|
|
|
@ -17,15 +17,14 @@ const mapStateToProps = (state) => ({
|
|||
})
|
||||
|
||||
const mapDispatchToProps = (dispatch) => ({
|
||||
onFetchGroups: (type) => {
|
||||
dispatch(fetchGroups(type))
|
||||
}
|
||||
onFetchGroups: (type) => dispatch(fetchGroups(type))
|
||||
})
|
||||
|
||||
export default
|
||||
@connect(mapStateToProps, mapDispatchToProps)
|
||||
@injectIntl
|
||||
class GroupSidebarPanel extends ImmutablePureComponent {
|
||||
|
||||
static propTypes = {
|
||||
groupIds: ImmutablePropTypes.list,
|
||||
isLazy: PropTypes.bool,
|
||||
|
@ -37,6 +36,12 @@ class GroupSidebarPanel extends ImmutablePureComponent {
|
|||
fetched: false,
|
||||
}
|
||||
|
||||
updateOnProps = [
|
||||
'groupIds',
|
||||
'isLazy',
|
||||
'isSlim',
|
||||
]
|
||||
|
||||
componentDidMount() {
|
||||
if (!this.props.isLazy) {
|
||||
this.props.onFetchGroups('member')
|
||||
|
@ -76,23 +81,20 @@ class GroupSidebarPanel extends ImmutablePureComponent {
|
|||
footerButtonTo={count > maxCount ? '/groups/browse/member' : undefined}
|
||||
noPadding={slim}
|
||||
>
|
||||
<div className={_s.default}>
|
||||
<ScrollableList
|
||||
scrollKey='groups-panel'
|
||||
>
|
||||
{
|
||||
groupIds.slice(0, maxCount).map((groupId, i) => (
|
||||
<GroupListItem
|
||||
key={`group-panel-item-${groupId}`}
|
||||
id={groupId}
|
||||
slim={slim}
|
||||
isLast={groupIds.length - 1 === i}
|
||||
/>
|
||||
))
|
||||
}
|
||||
</ScrollableList>
|
||||
</div>
|
||||
<ScrollableList scrollKey='groups_panel'>
|
||||
{
|
||||
groupIds.slice(0, maxCount).map((groupId, i) => (
|
||||
<GroupListItem
|
||||
key={`group-panel-item-${groupId}`}
|
||||
id={groupId}
|
||||
slim={slim}
|
||||
isLast={groupIds.count() - 1 === i}
|
||||
/>
|
||||
))
|
||||
}
|
||||
</ScrollableList>
|
||||
</PanelLayout>
|
||||
)
|
||||
}
|
||||
|
||||
}
|
|
@ -49,7 +49,7 @@ class ListDetailsPanel extends ImmutablePureComponent {
|
|||
<Divider isSmall />
|
||||
|
||||
<div className={[_s.default, _s.flexRow, _s.alignItemsCenter].join(' ')}>
|
||||
<Icon id='calendar' size='12px' className={_s.fillColorSecondary} />
|
||||
<Icon id='calendar' size='12px' className={_s.fillSecondary} />
|
||||
<Text
|
||||
size='small'
|
||||
color='secondary'
|
||||
|
|
|
@ -17,9 +17,7 @@ const mapStateToProps = (state) => ({
|
|||
})
|
||||
|
||||
const mapDispatchToProps = (dispatch) => ({
|
||||
onFetchLists() {
|
||||
return dispatch(fetchLists())
|
||||
},
|
||||
onFetchLists: () => dispatch(fetchLists()),
|
||||
})
|
||||
|
||||
export default
|
||||
|
@ -64,7 +62,7 @@ class ListsPanel extends ImmutablePureComponent {
|
|||
|
||||
const maxCount = 6
|
||||
|
||||
const listItems = lists.slice(0, maxCount).map(list => ({
|
||||
const listItems = lists.slice(0, maxCount).map((list) => ({
|
||||
to: `/lists/${list.get('id')}`,
|
||||
title: list.get('title'),
|
||||
}))
|
||||
|
@ -79,10 +77,7 @@ class ListsPanel extends ImmutablePureComponent {
|
|||
noPadding
|
||||
>
|
||||
<div className={[_s.default, _s.boxShadowNone].join(' ')}>
|
||||
<List
|
||||
scrollKey='lists_sidebar_panel'
|
||||
items={listItems}
|
||||
/>
|
||||
<List scrollKey='lists_sidebar_panel' items={listItems} />
|
||||
</div>
|
||||
</PanelLayout>
|
||||
)
|
||||
|
|
|
@ -55,7 +55,6 @@ class MediaGalleryPanel extends ImmutablePureComponent {
|
|||
} = this.props
|
||||
|
||||
if (!account || !attachments) return null
|
||||
if (attachments.size === 0) return null
|
||||
|
||||
return (
|
||||
<PanelLayout
|
||||
|
@ -63,19 +62,22 @@ class MediaGalleryPanel extends ImmutablePureComponent {
|
|||
title={intl.formatMessage(messages.title)}
|
||||
headerButtonTitle={intl.formatMessage(messages.show_all)}
|
||||
headerButtonTo={`/${account.get('acct')}/media`}
|
||||
>
|
||||
<div className={[_s.default, _s.flexRow, _s.flexWrap, _s.px10, _s.py10].join(' ')}>
|
||||
{
|
||||
attachments.slice(0, 16).map((attachment, i) => (
|
||||
<MediaItem
|
||||
isSmall
|
||||
key={attachment.get('id')}
|
||||
attachment={attachment}
|
||||
account={account}
|
||||
/>
|
||||
))
|
||||
}
|
||||
</div>
|
||||
>
|
||||
{
|
||||
attachments.size > 0 &&
|
||||
<div className={[_s.default, _s.flexRow, _s.flexWrap, _s.px10, _s.py10].join(' ')}>
|
||||
{
|
||||
attachments.slice(0, 16).map((attachment, i) => (
|
||||
<MediaItem
|
||||
isSmall
|
||||
key={attachment.get('id')}
|
||||
attachment={attachment}
|
||||
account={account}
|
||||
/>
|
||||
))
|
||||
}
|
||||
</div>
|
||||
}
|
||||
</PanelLayout>
|
||||
)
|
||||
}
|
||||
|
|
|
@ -87,7 +87,7 @@ export default class PanelLayout extends PureComponent {
|
|||
backgroundColor='none'
|
||||
to={footerButtonTo}
|
||||
onClick={footerButtonAction}
|
||||
className={[_s.px15, _s.py15, _s.backgroundColorSubtle_onHover].join(' ')}
|
||||
className={[_s.px15, _s.py15, _s.bgSubtle_onHover].join(' ')}
|
||||
>
|
||||
<Text color='brand' size='medium'>
|
||||
{footerButtonTitle}
|
||||
|
|
|
@ -71,7 +71,7 @@ class ProfileInfoPanel extends ImmutablePureComponent {
|
|||
}
|
||||
|
||||
<div className={[_s.default, _s.flexRow, _s.alignItemsCenter].join(' ')}>
|
||||
<Icon id='calendar' size='12px' className={_s.fillColorSecondary} />
|
||||
<Icon id='calendar' size='12px' className={_s.fillSecondary} />
|
||||
<Text
|
||||
size='small'
|
||||
color='secondary'
|
||||
|
|
|
@ -1,23 +1,42 @@
|
|||
import { me, monthlyExpensesComplete } from '../../initial_state'
|
||||
import { injectIntl, defineMessages } from 'react-intl'
|
||||
import { monthlyExpensesComplete } from '../../initial_state'
|
||||
import { URL_DISSENTER_SHOP } from '../../constants'
|
||||
import PanelLayout from './panel_layout';
|
||||
import ProgressBar from '../progress_bar'
|
||||
|
||||
export default class ProgressPanel extends PureComponent {
|
||||
const messages = defineMessages({
|
||||
progressTitle: { id: 'progress_title', defaultMessage: '{value}% covered this month' },
|
||||
operationsTitle: { id: 'operations_title', defaultMessage: "Gab's Operational Expenses" },
|
||||
operationsSubtitle: { id: 'operations_subtitle', defaultMessage: 'We are 100% funded by you' },
|
||||
})
|
||||
|
||||
export default
|
||||
@injectIntl
|
||||
class ProgressPanel extends PureComponent {
|
||||
|
||||
static propTypes = {
|
||||
intl: PropTypes.object.isRequired,
|
||||
}
|
||||
|
||||
render() {
|
||||
if (!monthlyExpensesComplete || !me) return null
|
||||
const { intl } = this.props
|
||||
|
||||
if (!monthlyExpensesComplete) return null
|
||||
|
||||
const value = Math.min(parseFloat(monthlyExpensesComplete), 100)
|
||||
|
||||
return (
|
||||
<PanelLayout
|
||||
title="Gab's Operational Expenses"
|
||||
subtitle="We are 100% funded by you"
|
||||
hasBackground
|
||||
title={intl.formatMessage(messages.operationsTitle)}
|
||||
subtitle={intl.formatMessage(messages.operationsSubtitle)}
|
||||
>
|
||||
<ProgressBar
|
||||
progress={monthlyExpensesComplete}
|
||||
title={`${Math.min(parseFloat(monthlyExpensesComplete), 100)}% covered this month`}
|
||||
href='https://shop.dissenter.com/category/donations'
|
||||
title={intl.formatMessage(messages.progressTitle, { value })}
|
||||
href={URL_DISSENTER_SHOP}
|
||||
/>
|
||||
</PanelLayout>
|
||||
)
|
||||
}
|
||||
|
||||
}
|
|
@ -3,9 +3,8 @@ import ImmutablePureComponent from 'react-immutable-pure-component'
|
|||
import ImmutablePropTypes from 'react-immutable-proptypes'
|
||||
import { fetchGabTrends } from '../../actions/gab_trends'
|
||||
import PanelLayout from './panel_layout'
|
||||
import ColumnIndicator from '../column_indicator'
|
||||
import ScrollableList from '../scrollable_list'
|
||||
import TrendingItem from '../trends_item'
|
||||
import TrendsItem from '../trends_item'
|
||||
|
||||
const messages = defineMessages({
|
||||
title: { id: 'trends.title', defaultMessage: 'Trending right now' },
|
||||
|
@ -30,6 +29,10 @@ class TrendsPanel extends ImmutablePureComponent {
|
|||
onFetchGabTrends: PropTypes.func.isRequired,
|
||||
}
|
||||
|
||||
updateOnProps = [
|
||||
'gabtrends',
|
||||
]
|
||||
|
||||
componentDidMount() {
|
||||
this.props.onFetchGabTrends()
|
||||
}
|
||||
|
@ -42,34 +45,21 @@ class TrendsPanel extends ImmutablePureComponent {
|
|||
noPadding
|
||||
title={intl.formatMessage(messages.title)}
|
||||
>
|
||||
<div className={_s.default}>
|
||||
<ScrollableList
|
||||
showLoading={gabtrends.size == 0}
|
||||
scrollKey='trending-items'
|
||||
>
|
||||
{
|
||||
gabtrends.isEmpty() &&
|
||||
<ColumnIndicator type='loading' />
|
||||
gabtrends.slice(0, 8).map((trend, i) => (
|
||||
<TrendsItem
|
||||
key={`gab-trend-${i}`}
|
||||
index={i + 1}
|
||||
isLast={i === 7}
|
||||
trend={trend}
|
||||
/>
|
||||
))
|
||||
}
|
||||
{
|
||||
!gabtrends.isEmpty() &&
|
||||
<ScrollableList
|
||||
scrollKey='trending-items'
|
||||
>
|
||||
{
|
||||
gabtrends.slice(0, 8).map((trend, i) => (
|
||||
<TrendingItem
|
||||
key={`gab-trend-${i}`}
|
||||
index={i + 1}
|
||||
isLast={i === 7}
|
||||
url={trend.get('url')}
|
||||
title={trend.get('title')}
|
||||
description={trend.get('description')}
|
||||
imageUrl={trend.get('image')}
|
||||
publishDate={trend.get('date_published')}
|
||||
author={trend.getIn(['author', 'name'], '')}
|
||||
/>
|
||||
))
|
||||
}
|
||||
</ScrollableList>
|
||||
}
|
||||
</div>
|
||||
</ScrollableList>
|
||||
</PanelLayout>
|
||||
)
|
||||
}
|
||||
|
|
|
@ -2,19 +2,20 @@ import { NavLink } from 'react-router-dom'
|
|||
import { injectIntl, defineMessages } from 'react-intl'
|
||||
import ImmutablePropTypes from 'react-immutable-proptypes'
|
||||
import ImmutablePureComponent from 'react-immutable-pure-component'
|
||||
import classNames from 'classnames/bind'
|
||||
import { me } from '../../initial_state'
|
||||
import { makeGetAccount } from '../../selectors'
|
||||
import { shortNumberFormat } from '../../utils/numbers'
|
||||
import { openModal } from '../../actions/modal'
|
||||
import {
|
||||
CX,
|
||||
MODAL_EDIT_PROFILE,
|
||||
} from '../../constants'
|
||||
import PanelLayout from './panel_layout'
|
||||
import Avatar from '../avatar'
|
||||
import Button from '../button'
|
||||
import DisplayName from '../display_name'
|
||||
import Avatar from '../avatar'
|
||||
import Image from '../image'
|
||||
import UserStat from '../user_stat'
|
||||
import PanelLayout from './panel_layout'
|
||||
|
||||
const cx = classNames.bind(_s)
|
||||
|
||||
const messages = defineMessages({
|
||||
gabs: { id: 'account.posts', defaultMessage: 'Gabs' },
|
||||
|
@ -30,7 +31,7 @@ const mapStateToProps = (state) => ({
|
|||
|
||||
const mapDispatchToProps = (dispatch) => ({
|
||||
onOpenEditProfile() {
|
||||
dispatch(openModal('EDIT_PROFILE'))
|
||||
dispatch(openModal(MODAL_EDIT_PROFILE))
|
||||
},
|
||||
})
|
||||
|
||||
|
@ -38,6 +39,7 @@ export default
|
|||
@connect(mapStateToProps, mapDispatchToProps)
|
||||
@injectIntl
|
||||
class UserPanel extends ImmutablePureComponent {
|
||||
|
||||
static propTypes = {
|
||||
account: ImmutablePropTypes.map.isRequired,
|
||||
intl: PropTypes.object.isRequired,
|
||||
|
@ -60,15 +62,15 @@ class UserPanel extends ImmutablePureComponent {
|
|||
this.setState({ hovering: false })
|
||||
}
|
||||
|
||||
handleOnOpenEditProfile = () => {
|
||||
this.props.onOpenEditProfile()
|
||||
}
|
||||
|
||||
render() {
|
||||
const { account, intl } = this.props
|
||||
const {
|
||||
account,
|
||||
intl,
|
||||
onOpenEditProfile,
|
||||
} = this.props
|
||||
const { hovering } = this.state
|
||||
|
||||
const buttonClasses = cx({
|
||||
const buttonClasses = CX({
|
||||
posAbs: 1,
|
||||
mt10: 1,
|
||||
mr10: 1,
|
||||
|
@ -96,7 +98,7 @@ class UserPanel extends ImmutablePureComponent {
|
|||
backgroundColor='secondary'
|
||||
radiusSmall
|
||||
className={buttonClasses}
|
||||
onClick={this.handleOnOpenEditProfile}
|
||||
onClick={onOpenEditProfile}
|
||||
>
|
||||
{intl.formatMessage(messages.edit_profile)}
|
||||
</Button>
|
||||
|
@ -134,4 +136,5 @@ class UserPanel extends ImmutablePureComponent {
|
|||
</PanelLayout>
|
||||
)
|
||||
}
|
||||
|
||||
}
|
|
@ -0,0 +1,96 @@
|
|||
import { withRouter } from 'react-router-dom'
|
||||
import { CX } from '../constants'
|
||||
import Button from './button'
|
||||
import Text from './text'
|
||||
|
||||
export default
|
||||
@withRouter
|
||||
class PillItem extends PureComponent {
|
||||
|
||||
static propTypes = {
|
||||
icon: PropTypes.string,
|
||||
isActive: PropTypes.bool,
|
||||
onClick: PropTypes.func,
|
||||
title: PropTypes.string,
|
||||
to: PropTypes.string,
|
||||
}
|
||||
|
||||
state = {
|
||||
isCurrent: -1,
|
||||
}
|
||||
|
||||
componentDidUpdate(prevProps) {
|
||||
// If user navigates to different page, ensure tab bar item
|
||||
// with this.props.to that is on location is set to active.
|
||||
if (this.props.location !== prevProps.location) {
|
||||
const isCurrent = this.props.to === this.props.location.pathname
|
||||
|
||||
if (this.state.isCurrent !== isCurrent) {
|
||||
this.setState({ isCurrent })
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
render() {
|
||||
const {
|
||||
title,
|
||||
to,
|
||||
onClick,
|
||||
location,
|
||||
isActive,
|
||||
} = this.props
|
||||
const { isCurrent } = this.state
|
||||
|
||||
// Combine state, props, location to make absolutely
|
||||
// sure of active status.
|
||||
const active = isActive ||
|
||||
(isCurrent === -1 ? to === location.pathname : false)
|
||||
|
||||
const containerClasses = CX({
|
||||
default: 1,
|
||||
noUnderline: 1,
|
||||
text: 1,
|
||||
alignItemsCenter: 1,
|
||||
justifyContentCenter: 1,
|
||||
py5: 1,
|
||||
outlineNone: 1,
|
||||
cursorPointer: 1,
|
||||
circle: 1,
|
||||
bgSecondary: !active,
|
||||
bgSecondaryDark_onHover: !active,
|
||||
bgBrand: active,
|
||||
mr5: 1,
|
||||
mb5: 1,
|
||||
})
|
||||
|
||||
const textParentClasses = CX({
|
||||
default: 1,
|
||||
height100PC: 1,
|
||||
alignItemsCenter: 1,
|
||||
justifyContentCenter: 1,
|
||||
py2: 1,
|
||||
px15: 1,
|
||||
})
|
||||
|
||||
const textOptions = {
|
||||
size: 'small',
|
||||
color: active ? 'white' : 'secondary',
|
||||
weight: active ? 'bold' : 'medium',
|
||||
}
|
||||
|
||||
return (
|
||||
<Button
|
||||
onClick={onClick}
|
||||
className={containerClasses}
|
||||
to={to || undefined}
|
||||
noClasses
|
||||
>
|
||||
<span className={textParentClasses}>
|
||||
<Text {...textOptions}>
|
||||
{title}
|
||||
</Text>
|
||||
</span>
|
||||
</Button>
|
||||
)
|
||||
}
|
||||
}
|
|
@ -0,0 +1,34 @@
|
|||
import PillItem from './pill_item'
|
||||
|
||||
/**
|
||||
* Renders pills components
|
||||
* @param {array} [props.pills] - tab bar data for creating `TabBarItem`
|
||||
*/
|
||||
export default class Pills extends PureComponent {
|
||||
|
||||
static propTypes = {
|
||||
pills: PropTypes.array,
|
||||
}
|
||||
|
||||
render() {
|
||||
const { pills } = this.props
|
||||
|
||||
return (
|
||||
<div className={[_s.default, _s.flexWrap, _s.px5, _s.flexRow].join(' ')}>
|
||||
{
|
||||
!!pills &&
|
||||
pills.map((tab, i) => (
|
||||
<PillItem
|
||||
key={`pill-item-${i}`}
|
||||
title={tab.title}
|
||||
onClick={tab.onClick}
|
||||
to={tab.to}
|
||||
isActive={tab.active}
|
||||
/>
|
||||
))
|
||||
}
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
}
|
|
@ -92,8 +92,8 @@ class Poll extends ImmutablePureComponent {
|
|||
left0: 1,
|
||||
radiusSmall: 1,
|
||||
height100PC: 1,
|
||||
backgroundColorSubtle2: !leading,
|
||||
backgroundColorBrandLight: leading,
|
||||
bgSecondary: !leading,
|
||||
bgBrandLight: leading,
|
||||
})
|
||||
|
||||
const inputClasses = cx('poll__input', {
|
||||
|
@ -107,11 +107,11 @@ class Poll extends ImmutablePureComponent {
|
|||
py10: showResults,
|
||||
mb10: 1,
|
||||
border1PX: !showResults,
|
||||
fillColorSecondary: !showResults,
|
||||
fillSecondary: !showResults,
|
||||
circle: !showResults,
|
||||
cursorPointer: !showResults,
|
||||
backgroundColorSubtle_onHover: !showResults,
|
||||
backgroundColorSubtle: !showResults && active,
|
||||
bgSubtle_onHover: !showResults,
|
||||
bgSubtle: !showResults && active,
|
||||
})
|
||||
|
||||
const textContainerClasses = cx({
|
||||
|
|
|
@ -90,14 +90,14 @@ class StatusVisibilityDropdown extends PureComponent {
|
|||
cursorPointer: 1,
|
||||
borderBottom1PX: !isLast,
|
||||
borderColorSecondary: !isLast,
|
||||
backgroundColorSubtle_onHover: !isActive,
|
||||
backgroundColorBrand: isActive,
|
||||
bgSubtle_onHover: !isActive,
|
||||
bgBrand: isActive,
|
||||
})
|
||||
|
||||
const iconClasses = cx({
|
||||
ml10: 1,
|
||||
mt2: 1,
|
||||
fillColorWhite: isActive,
|
||||
fillWhite: isActive,
|
||||
})
|
||||
|
||||
return (
|
||||
|
|
|
@ -108,6 +108,7 @@ class ProfileHeader extends ImmutablePureComponent {
|
|||
const headerSrc = !!account ? account.get('header') : ''
|
||||
const headerMissing = headerSrc.indexOf(PLACEHOLDER_MISSING_HEADER_SRC) > -1 || !headerSrc
|
||||
const avatarSize = headerMissing ? 75 : 150
|
||||
const top = headerMissing ? -30 : -380
|
||||
|
||||
const avatarContainerClasses = CX({
|
||||
default: 1,
|
||||
|
@ -131,96 +132,101 @@ class ProfileHeader extends ImmutablePureComponent {
|
|||
|
||||
return (
|
||||
<div className={[_s.default, _s.z1, _s.width100PC].join(' ')}>
|
||||
<Sticky top={top} enabled onStateChange={this.onStickyStateChange}>
|
||||
<div className={[_s.default, _s.z1, _s.width100PC, _s.alignItemsCenter, _s.boxShadowBlock, _s.bgPrimary].join(' ')}>
|
||||
|
||||
{
|
||||
!headerMissing &&
|
||||
<div className={[_s.default, _s.height350PX, _s.width100PC, _s.radiusSmall, _s.overflowHidden].join(' ')}>
|
||||
<Image
|
||||
alt={intl.formatMessage(messages.headerPhoto)}
|
||||
className={_s.height350PX}
|
||||
src={headerSrc}
|
||||
/>
|
||||
</div>
|
||||
}
|
||||
|
||||
<div className={[_s.default, _s.width100PC].join(' ')}>
|
||||
|
||||
<div className={[_s.default, _s.flexRow, _s.pr15, _s.pl25, _s.mb5].join(' ')}>
|
||||
<div className={avatarContainerClasses}>
|
||||
<Avatar size={avatarSize} account={account} noHover />
|
||||
</div>
|
||||
|
||||
<div className={[_s.default, _s.flexRow, _s.px15, _s.flexNormal, _s.py10].join(' ')}>
|
||||
<DisplayName account={account} isMultiline noRelationship isLarge noHover />
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<Sticky enabled onStateChange={this.onStickyStateChange}>
|
||||
<div className={[_s.default, _s.flexRow, _s.backgroundColorSecondary3, _s.borderBottom1PX, _s.borderColorSecondary, _s.height53PX].join(' ')}>
|
||||
<div className={tabBarContainerClasses}>
|
||||
<TabBar tabs={tabs} isLarge />
|
||||
</div>
|
||||
|
||||
<div className={stickyBarContainerClasses}>
|
||||
<Avatar size={36} account={account} noHover />
|
||||
<div className={[_s.default, _s.ml10].join(' ')}>
|
||||
<DisplayName account={account} noUsername noRelationship noHover isLarge />
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div className={[_s.default, _s.width1015PX].join(' ')}>
|
||||
{
|
||||
account && account.get('id') === me &&
|
||||
<div className={[_s.default, _s.flexRow, _s.mlAuto, _s.py5].join(' ')}>
|
||||
<Button
|
||||
isOutline
|
||||
backgroundColor='none'
|
||||
color='brand'
|
||||
className={[_s.justifyContentCenter, _s.alignItemsCenter].join(' ')}
|
||||
onClick={this.handleOnEditProfile}
|
||||
>
|
||||
<Text color='inherit' weight='bold' size='medium' className={_s.px15}>
|
||||
{intl.formatMessage(messages.editProfile)}
|
||||
</Text>
|
||||
</Button>
|
||||
</div>
|
||||
}
|
||||
|
||||
{
|
||||
account && account.get('id') !== me &&
|
||||
<div className={[_s.default, _s.flexRow, _s.mlAuto, _s.py5].join(' ')}>
|
||||
<Button
|
||||
isOutline
|
||||
icon='ellipsis'
|
||||
iconSize='18px'
|
||||
iconClassName={_s.inheritFill}
|
||||
color='brand'
|
||||
backgroundColor='none'
|
||||
className={[_s.justifyContentCenter, _s.alignItemsCenter, _s.mr10, _s.px10].join(' ')}
|
||||
onClick={this.handleOpenMore}
|
||||
buttonRef={this.setOpenMoreNodeRef}
|
||||
!headerMissing &&
|
||||
<div className={[_s.default, _s.height350PX, _s.width100PC, _s.bottomRightRadiusSmall, _s.bottomLeftRadiusSmall, _s.overflowHidden].join(' ')}>
|
||||
<Image
|
||||
alt={intl.formatMessage(messages.headerPhoto)}
|
||||
className={_s.height350PX}
|
||||
src={headerSrc}
|
||||
/>
|
||||
|
||||
<form action='https://chat.gab.com/private-message' method='POST'>
|
||||
<Button
|
||||
isOutline
|
||||
type='submit'
|
||||
icon='chat'
|
||||
iconSize='18px'
|
||||
iconClassName={_s.inheritFill}
|
||||
color='brand'
|
||||
backgroundColor='none'
|
||||
className={[_s.justifyContentCenter, _s.alignItemsCenter, _s.mr10, _s.px10].join(' ')}
|
||||
/>
|
||||
<input type='hidden' value={account.get('username')} name='username' />
|
||||
</form>
|
||||
|
||||
<AccountActionButton account={account} />
|
||||
|
||||
</div>
|
||||
}
|
||||
|
||||
<div className={[_s.default, _s.width100PC].join(' ')}>
|
||||
|
||||
<div className={[_s.default, _s.flexRow, _s.pr15, _s.pl25, _s.mb5].join(' ')}>
|
||||
<div className={avatarContainerClasses}>
|
||||
<Avatar size={avatarSize} account={account} noHover />
|
||||
</div>
|
||||
|
||||
<div className={[_s.default, _s.flexRow, _s.px15, _s.flexNormal, _s.py10].join(' ')}>
|
||||
<DisplayName account={account} isMultiline noRelationship isLarge noHover />
|
||||
</div>
|
||||
</div>
|
||||
|
||||
|
||||
<div className={[_s.default, _s.flexRow, _s.bgPrimary, _s.height53PX].join(' ')}>
|
||||
<div className={tabBarContainerClasses}>
|
||||
<TabBar tabs={tabs} isLarge />
|
||||
</div>
|
||||
|
||||
<div className={stickyBarContainerClasses}>
|
||||
<Avatar size={36} account={account} noHover />
|
||||
<div className={[_s.default, _s.ml10].join(' ')}>
|
||||
<DisplayName account={account} noUsername noRelationship noHover isLarge />
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{
|
||||
account && account.get('id') === me &&
|
||||
<div className={[_s.default, _s.flexRow, _s.mlAuto, _s.py5].join(' ')}>
|
||||
<Button
|
||||
isOutline
|
||||
backgroundColor='none'
|
||||
color='brand'
|
||||
className={[_s.justifyContentCenter, _s.alignItemsCenter].join(' ')}
|
||||
onClick={this.handleOnEditProfile}
|
||||
>
|
||||
<Text color='inherit' weight='bold' size='medium' className={_s.px15}>
|
||||
{intl.formatMessage(messages.editProfile)}
|
||||
</Text>
|
||||
</Button>
|
||||
</div>
|
||||
}
|
||||
|
||||
{
|
||||
account && account.get('id') !== me &&
|
||||
<div className={[_s.default, _s.flexRow, _s.mlAuto, _s.py5].join(' ')}>
|
||||
<Button
|
||||
isOutline
|
||||
icon='ellipsis'
|
||||
iconSize='18px'
|
||||
iconClassName={_s.inheritFill}
|
||||
color='brand'
|
||||
backgroundColor='none'
|
||||
className={[_s.justifyContentCenter, _s.alignItemsCenter, _s.mr10, _s.px10].join(' ')}
|
||||
onClick={this.handleOpenMore}
|
||||
buttonRef={this.setOpenMoreNodeRef}
|
||||
/>
|
||||
|
||||
<form action='https://chat.gab.com/private-message' method='POST'>
|
||||
<Button
|
||||
isOutline
|
||||
type='submit'
|
||||
icon='chat'
|
||||
iconSize='18px'
|
||||
iconClassName={_s.inheritFill}
|
||||
color='brand'
|
||||
backgroundColor='none'
|
||||
className={[_s.justifyContentCenter, _s.alignItemsCenter, _s.mr10, _s.px10].join(' ')}
|
||||
/>
|
||||
<input type='hidden' value={account.get('username')} name='username' />
|
||||
</form>
|
||||
|
||||
<AccountActionButton account={account} />
|
||||
|
||||
</div>
|
||||
}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</Sticky>
|
||||
</div>
|
||||
</div>
|
||||
</Sticky>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
|
|
@ -1,14 +1,14 @@
|
|||
import classNames from 'classnames/bind'
|
||||
import { CX } from '../constants'
|
||||
import Button from './button'
|
||||
import Text from './text'
|
||||
|
||||
const cx = classNames.bind(_s)
|
||||
|
||||
export default class ProgressBar extends PureComponent {
|
||||
|
||||
static propTypes = {
|
||||
progress: PropTypes.number,
|
||||
small: PropTypes.bool,
|
||||
title: PropTypes.string,
|
||||
href: PropTypes.string,
|
||||
}
|
||||
|
||||
render() {
|
||||
|
@ -16,7 +16,7 @@ export default class ProgressBar extends PureComponent {
|
|||
progress,
|
||||
small,
|
||||
title,
|
||||
href
|
||||
href,
|
||||
} = this.props
|
||||
|
||||
const completed = Math.min(parseFloat(progress), 100)
|
||||
|
@ -24,10 +24,10 @@ export default class ProgressBar extends PureComponent {
|
|||
width: `${completed}%`,
|
||||
}
|
||||
|
||||
const containerClassName = cx({
|
||||
const containerClassName = CX({
|
||||
default: 1,
|
||||
backgroundColorLoading: !small,
|
||||
backgroundColorSubtle2: small,
|
||||
bgLoading: !small,
|
||||
bgSecondary: small,
|
||||
noUnderline: 1,
|
||||
circle: 1,
|
||||
overflowHidden: 1,
|
||||
|
@ -42,7 +42,7 @@ export default class ProgressBar extends PureComponent {
|
|||
noClasses
|
||||
className={containerClassName}
|
||||
>
|
||||
<div className={[_s.default, _s.backgroundColorBrand, _s.circle, _s.height100PC, _s.backgroundCandy].join(' ')} style={style} />
|
||||
<div className={[_s.default, _s.bgBrand, _s.circle, _s.height100PC, _s.backgroundCandy].join(' ')} style={style} />
|
||||
<div className={[_s.default, _s.posAbs, _s.width100PC, _s.height100PC, _s.alignItemsCenter, _s.justifyContentCenter].join(' ')}>
|
||||
{
|
||||
!!title &&
|
||||
|
|
|
@ -116,7 +116,7 @@ class RichTextEditorBar extends PureComponent {
|
|||
if (!rteControlsVisible || !isPro) return null
|
||||
|
||||
return (
|
||||
<div className={[_s.default, _s.backgroundColorPrimary, _s.borderBottom1PX, _s.borderColorSecondary, _s.py5, _s.px15, _s.alignItemsCenter, _s.flexRow].join(' ')}>
|
||||
<div className={[_s.default, _s.bgPrimary, _s.borderBottom1PX, _s.borderColorSecondary, _s.py5, _s.px15, _s.alignItemsCenter, _s.flexRow].join(' ')}>
|
||||
{
|
||||
RTE_ITEMS.map((item, i) => (
|
||||
<StyleButton
|
||||
|
@ -179,8 +179,8 @@ class StyleButton extends PureComponent {
|
|||
px10: 1,
|
||||
mr5: 1,
|
||||
noSelect: 1,
|
||||
backgroundColorSubtle2Dark_onHover: 1,
|
||||
backgroundColorBrandLight: active,
|
||||
bgSecondaryDark_onHover: 1,
|
||||
bgBrandLight: active,
|
||||
// py10: !small,
|
||||
// py5: small,
|
||||
// px5: small,
|
||||
|
|
|
@ -1,12 +1,13 @@
|
|||
import { withRouter } from 'react-router-dom'
|
||||
import queryString from 'query-string'
|
||||
import { CX } from '../constants'
|
||||
import {
|
||||
changeSearch,
|
||||
clearSearch,
|
||||
submitSearch,
|
||||
showSearch,
|
||||
} from '../actions/search'
|
||||
import Input from './input'
|
||||
import Button from './button'
|
||||
|
||||
const mapStateToProps = (state) => ({
|
||||
value: state.getIn(['search', 'value']),
|
||||
|
@ -40,7 +41,7 @@ class Search extends PureComponent {
|
|||
}
|
||||
|
||||
state = {
|
||||
expanded: false,
|
||||
focused: false,
|
||||
}
|
||||
|
||||
textbox = React.createRef()
|
||||
|
@ -57,17 +58,17 @@ class Search extends PureComponent {
|
|||
}
|
||||
}
|
||||
|
||||
handleChange = (value) => {
|
||||
this.props.onChange(value)
|
||||
handleOnChange = (e) => {
|
||||
this.props.onChange(e.target.value)
|
||||
}
|
||||
|
||||
handleFocus = () => {
|
||||
this.setState({ expanded: true })
|
||||
handleOnFocus = () => {
|
||||
this.setState({ focused: true })
|
||||
this.props.onShow()
|
||||
}
|
||||
|
||||
handleBlur = () => {
|
||||
this.setState({ expanded: false })
|
||||
handleOnBlur = () => {
|
||||
this.setState({ focused: false })
|
||||
}
|
||||
|
||||
handleKeyUp = (e) => {
|
||||
|
@ -88,44 +89,80 @@ class Search extends PureComponent {
|
|||
this.textbox = n
|
||||
}
|
||||
|
||||
handleSubmit = () => {
|
||||
this.props.onSubmit()
|
||||
}
|
||||
|
||||
render() {
|
||||
const {
|
||||
value,
|
||||
submitted,
|
||||
onClear,
|
||||
withOverlay
|
||||
} = this.props
|
||||
const { expanded } = this.state
|
||||
const { focused } = this.state
|
||||
const highlighted = focused || `${value}`.length > 0
|
||||
|
||||
const hasValue = value ? value.length > 0 || submitted : 0
|
||||
const inputClasses = CX({
|
||||
default: 1,
|
||||
text: 1,
|
||||
outlineNone: 1,
|
||||
lineHeight125: 1,
|
||||
displayBlock: 1,
|
||||
py7: 1,
|
||||
bgTransparent: !highlighted,
|
||||
colorPrimary: 1,
|
||||
fs14PX: 1,
|
||||
flexGrow1: 1,
|
||||
radiusSmall: 1,
|
||||
pl15: 1,
|
||||
searchInput: 1,
|
||||
})
|
||||
|
||||
const containerClasses = CX({
|
||||
default: 1,
|
||||
bgBrandLight: !highlighted,
|
||||
bgWhite: highlighted,
|
||||
flexRow: 1,
|
||||
radiusSmall: 1,
|
||||
alignItemsCenter: 1,
|
||||
})
|
||||
|
||||
const prependIconColor = highlighted ? 'brand' : 'white'
|
||||
|
||||
const id = 'nav-search'
|
||||
|
||||
return (
|
||||
<div className={[_s.default, _s.justifyContentCenter, _s.height53PX].join(' ')}>
|
||||
<Input
|
||||
hasClear
|
||||
value={value}
|
||||
inputRef={this.setTextbox}
|
||||
id='search'
|
||||
prependIcon='search'
|
||||
placeholder='Search Gab'
|
||||
onChange={this.handleChange}
|
||||
onKeyUp={this.handleKeyUp}
|
||||
onFocus={this.handleFocus}
|
||||
onBlur={this.handleBlur}
|
||||
onClear={onClear}
|
||||
hideLabel
|
||||
title='Search'
|
||||
/>
|
||||
<div className={containerClasses}>
|
||||
<label className={_s.visiblyHidden} htmlFor={id}>Search</label>
|
||||
|
||||
{
|
||||
withOverlay &&
|
||||
{/*<Overlay show={expanded && !hasValue} placement='bottom' target={this}>
|
||||
<SearchPopout />
|
||||
</Overlay>*/}
|
||||
}
|
||||
<input
|
||||
id={id}
|
||||
className={inputClasses}
|
||||
type='text'
|
||||
placeholder='Search for people, groups or news'
|
||||
ref={this.setTextbox}
|
||||
value={value}
|
||||
onKeyUp={this.handleKeyUp}
|
||||
onChange={this.handleOnChange}
|
||||
onFocus={this.handleOnFocus}
|
||||
onBlur={this.handleOnBlur}
|
||||
/>
|
||||
|
||||
<Button
|
||||
className={[_s.px10, _s.mr5].join(' ')}
|
||||
tabIndex='0'
|
||||
title='...'
|
||||
backgroundColor='none'
|
||||
color={prependIconColor}
|
||||
onClick={this.handleSubmit}
|
||||
icon='search'
|
||||
iconClassName={_s.inheritFill}
|
||||
iconSize='16px'
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
}
|
||||
}
|
|
@ -49,7 +49,7 @@ export default class Select extends ImmutablePureComponent {
|
|||
<Icon
|
||||
id='select'
|
||||
size='14px'
|
||||
className={[_s.fillColorSecondary, _s.posAbs, _s.right0, _s.mr10, _s.bottom0, _s.mb15].join(' ')}
|
||||
className={[_s.fillSecondary, _s.posAbs, _s.right0, _s.mr10, _s.bottom0, _s.mb15].join(' ')}
|
||||
/>
|
||||
</div>
|
||||
)
|
||||
|
|
|
@ -24,7 +24,7 @@ class SensitiveMediaItem extends PureComponent {
|
|||
|
||||
return (
|
||||
<div className={[_s.default, _s.px15, _s.pt5].join(' ')}>
|
||||
<div className={[_s.default, _s.flexRow, _s.radiusSmall, _s.backgroundColorSecondary3, _s.py10, _s.px15, _s.height100PC, _s.width100PC].join(' ')}>
|
||||
<div className={[_s.default, _s.flexRow, _s.radiusSmall, _s.bgTertiary, _s.py10, _s.px15, _s.height100PC, _s.width100PC].join(' ')}>
|
||||
<div className={[_s.default, _s.justifyContentCenter, _s.flexNormal].join(' ')}>
|
||||
<Text color='secondary'>
|
||||
{intl.formatMessage(messages.warning)}
|
||||
|
@ -35,7 +35,7 @@ class SensitiveMediaItem extends PureComponent {
|
|||
onClick={onClick}
|
||||
color='tertiary'
|
||||
backgroundColor='none'
|
||||
className={_s.backgroundColorSubtle2Dark_onHover}
|
||||
className={_s.bgSecondaryDark_onHover}
|
||||
>
|
||||
<Text color='inherit' weight='bold' size='medium'>
|
||||
{intl.formatMessage(messages.view)}
|
||||
|
|
|
@ -11,7 +11,9 @@ import { makeGetAccount } from '../selectors'
|
|||
import Responsive from '../features/ui/util/responsive_component'
|
||||
import SidebarSectionTitle from './sidebar_section_title'
|
||||
import SidebarSectionItem from './sidebar_section_item'
|
||||
import SidebarHeader from './sidebar_header'
|
||||
import Heading from './heading'
|
||||
import Pills from './pills'
|
||||
import Divider from './divider'
|
||||
|
||||
const messages = defineMessages({
|
||||
followers: { id: 'account.followers', defaultMessage: 'Followers' },
|
||||
|
@ -27,6 +29,8 @@ const messages = defineMessages({
|
|||
lists: { id: 'column.lists', defaultMessage: 'Lists' },
|
||||
apps: { id: 'tabs_bar.apps', defaultMessage: 'Apps' },
|
||||
more: { id: 'sidebar.more', defaultMessage: 'More' },
|
||||
explore: { id: 'explore', defaultMessage: 'Explore' },
|
||||
menu: { id: 'menu', defaultMessage: 'Menu' },
|
||||
pro: { id: 'promo.gab_pro', defaultMessage: 'Upgrade to GabPRO' },
|
||||
trends: { id: 'promo.trends', defaultMessage: 'Trends' },
|
||||
search: { id: 'tabs_bar.search', defaultMessage: 'Search' },
|
||||
|
@ -73,6 +77,10 @@ class Sidebar extends ImmutablePureComponent {
|
|||
openSidebarMorePopover: PropTypes.func.isRequired,
|
||||
notificationCount: PropTypes.number.isRequired,
|
||||
homeItemsQueueCount: PropTypes.number.isRequired,
|
||||
actions: PropTypes.array,
|
||||
tabs: PropTypes.array,
|
||||
title: PropTypes.string,
|
||||
showBackBtn: PropTypes.bool,
|
||||
}
|
||||
|
||||
handleOpenComposeModal = () => {
|
||||
|
@ -98,6 +106,10 @@ class Sidebar extends ImmutablePureComponent {
|
|||
homeItemsQueueCount,
|
||||
showCommunityTimeline,
|
||||
moreOpen,
|
||||
actions,
|
||||
tabs,
|
||||
title,
|
||||
showBackBtn,
|
||||
} = this.props
|
||||
|
||||
// : todo :
|
||||
|
@ -196,13 +208,23 @@ class Sidebar extends ImmutablePureComponent {
|
|||
return (
|
||||
<header role='banner' className={[_s.default, _s.flexGrow1, _s.z3, _s.alignItemsEnd].join(' ')}>
|
||||
<div className={[_s.default, _s.width240PX].join(' ')}>
|
||||
<div className={[_s.default, _s.posFixed, _s.top0, _s.height100PC].join(' ')}>
|
||||
<div className={[_s.default, _s.posFixed, _s.heightCalc53PX, _s.bottom0].join(' ')}>
|
||||
<div className={[_s.default, _s.height100PC, _s.alignItemsStart, _s.width240PX, _s.pr15, _s.py10, _s.overflowYScroll].join(' ')}>
|
||||
|
||||
<SidebarHeader />
|
||||
|
||||
<div className={_s.default}>
|
||||
<div className={[_s.default, _s.px5, _s.py10].join(' ')}>
|
||||
<Heading size='h1'>
|
||||
{title}
|
||||
</Heading>
|
||||
</div>
|
||||
{
|
||||
!!tabs &&
|
||||
<div className={[_s.default, _s.mt10, _s.pb15, _s.borderBottom1PX, _s.borderColorSecondary].join(' ')}>
|
||||
<Pills pills={tabs} />
|
||||
</div>
|
||||
}
|
||||
</div>
|
||||
<nav aria-label='Primary' role='navigation' className={[_s.default, _s.width100PC, _s.mb15].join(' ')}>
|
||||
<SidebarSectionTitle>Menu</SidebarSectionTitle>
|
||||
<SidebarSectionTitle>{intl.formatMessage(messages.menu)}</SidebarSectionTitle>
|
||||
{
|
||||
menuItems.map((menuItem, i) => {
|
||||
if (menuItem.hidden) return null
|
||||
|
@ -212,13 +234,7 @@ class Sidebar extends ImmutablePureComponent {
|
|||
)
|
||||
})
|
||||
}
|
||||
{ /* <SidebarSectionTitle>Shortcuts</SidebarSectionTitle> */ }
|
||||
{
|
||||
shortcutItems.map((shortcutItem, i) => (
|
||||
<SidebarSectionItem {...shortcutItem} key={`sidebar-item-shortcut-${i}`} />
|
||||
))
|
||||
}
|
||||
<SidebarSectionTitle>Explore</SidebarSectionTitle>
|
||||
<SidebarSectionTitle>{intl.formatMessage(messages.explore)}</SidebarSectionTitle>
|
||||
{
|
||||
exploreItems.map((exploreItem, i) => (
|
||||
<SidebarSectionItem {...exploreItem} key={`sidebar-item-explore-${i}`} />
|
||||
|
@ -230,7 +246,7 @@ class Sidebar extends ImmutablePureComponent {
|
|||
<Button
|
||||
isBlock
|
||||
onClick={this.handleOpenComposeModal}
|
||||
className={[_s.py15, _s.fontSize15PX, _s.fontWeightBold].join(' ')}
|
||||
className={[_s.py15, _s.fs15PX, _s.fontWeightBold].join(' ')}
|
||||
>
|
||||
Gab
|
||||
</Button>
|
||||
|
|
|
@ -1,57 +0,0 @@
|
|||
import { Fragment } from 'react'
|
||||
import { NavLink } from 'react-router-dom'
|
||||
import ImmutablePropTypes from 'react-immutable-proptypes'
|
||||
import ImmutablePureComponent from 'react-immutable-pure-component'
|
||||
import { me } from '../initial_state'
|
||||
import { makeGetAccount } from '../selectors'
|
||||
import Icon from './icon'
|
||||
import SidebarSectionItem from './sidebar_section_item'
|
||||
import Text from './text'
|
||||
|
||||
const mapStateToProps = (state) => {
|
||||
const getAccount = makeGetAccount()
|
||||
|
||||
return {
|
||||
account: getAccount(state, me),
|
||||
}
|
||||
}
|
||||
|
||||
export default
|
||||
@connect(mapStateToProps)
|
||||
class SidebarHeader extends ImmutablePureComponent {
|
||||
|
||||
static propTypes = {
|
||||
account: ImmutablePropTypes.map,
|
||||
}
|
||||
|
||||
render() {
|
||||
const { account } = this.props
|
||||
|
||||
const isPro = account.get('is_pro')
|
||||
|
||||
return (
|
||||
<Fragment>
|
||||
<h1 className={[_s.default].join(' ')}>
|
||||
<NavLink to='/' aria-label='Gab' className={[_s.default, _s.flexRow, _s.noSelect, _s.noUnderline, _s.height50PX, _s.cursorPointer, _s.px10].join(' ')}>
|
||||
<Icon id='gab-logo' className={_s.fillColorBrand} />
|
||||
{
|
||||
isPro &&
|
||||
<Text weight='bold' color='brand' size='extraSmall' className={[_s.pb5].join(' ')}>
|
||||
PRO
|
||||
</Text>
|
||||
}
|
||||
</NavLink>
|
||||
</h1>
|
||||
|
||||
{
|
||||
(!!me && !!account) &&
|
||||
<SidebarSectionItem
|
||||
image={account.get('avatar')}
|
||||
title={account.get('acct')}
|
||||
to={`/${account.get('acct')}`}
|
||||
/>
|
||||
}
|
||||
</Fragment>
|
||||
)
|
||||
}
|
||||
}
|
|
@ -69,35 +69,35 @@ export default class SidebarSectionItem extends PureComponent {
|
|||
outlineNone: 1,
|
||||
borderColorTransparent: !shouldShowActive,
|
||||
borderColorSecondary: shouldShowActive,
|
||||
backgroundTransparent: !shouldShowActive,
|
||||
backgroundColorPrimary: shouldShowActive,
|
||||
bgTransparent: !shouldShowActive,
|
||||
bgPrimary: shouldShowActive,
|
||||
})
|
||||
|
||||
const textClasses = cx({
|
||||
default: 1,
|
||||
fontWeightNormal: 1,
|
||||
fontSize15PX: 1,
|
||||
fs15PX: 1,
|
||||
text: 1,
|
||||
textOverflowEllipsis: 1,
|
||||
colorPrimary: 1,
|
||||
})
|
||||
|
||||
const iconClasses = cx({
|
||||
fillColorPrimary: 1,
|
||||
fillPrimary: 1,
|
||||
})
|
||||
|
||||
const countClasses = cx({
|
||||
default: 1,
|
||||
text: 1,
|
||||
mlAuto: 1,
|
||||
fontSize12PX: 1,
|
||||
fs12PX: 1,
|
||||
px5: 1,
|
||||
mr2: 1,
|
||||
lineHeight15: 1,
|
||||
ml5: 1,
|
||||
colorSecondary: !isNotifications,
|
||||
colorWhite: isNotifications,
|
||||
backgroundColorBrand: isNotifications,
|
||||
bgBrand: isNotifications,
|
||||
radiusSmall: isNotifications,
|
||||
})
|
||||
|
||||
|
@ -110,7 +110,7 @@ export default class SidebarSectionItem extends PureComponent {
|
|||
buttonRef={buttonRef}
|
||||
onMouseEnter={() => this.handleOnMouseEnter()}
|
||||
onMouseLeave={() => this.handleOnMouseLeave()}
|
||||
className={[_s.default, _s.noUnderline, _s.outlineNone, _s.cursorPointer, _s.width100PC, _s.backgroundTransparent].join(' ')}
|
||||
className={[_s.default, _s.noUnderline, _s.outlineNone, _s.cursorPointer, _s.width100PC, _s.bgTransparent].join(' ')}
|
||||
>
|
||||
<div className={containerClasses}>
|
||||
{
|
||||
|
|
|
@ -11,7 +11,7 @@ export default class SidebarSectionTitle extends PureComponent {
|
|||
|
||||
return (
|
||||
<div className={[_s.default, _s.py5, _s.px10, _s.mt10].join(' ')}>
|
||||
<Text size='small' weight='bold' color='tertiary'>
|
||||
<Text color='tertiary'>
|
||||
{children}
|
||||
</Text>
|
||||
</div>
|
||||
|
|
|
@ -444,10 +444,9 @@ class Status extends ImmutablePureComponent {
|
|||
|
||||
const containerClasses = cx({
|
||||
default: 1,
|
||||
radiusSmall: !isChild,
|
||||
pb15: isFeatured,
|
||||
radiusSmall: !isChild,
|
||||
backgroundColorPrimary: !isChild,
|
||||
bgPrimary: !isChild,
|
||||
boxShadowBlock: !isChild,
|
||||
outlineNone: 1,
|
||||
mb15: !isChild,
|
||||
|
@ -465,7 +464,7 @@ class Status extends ImmutablePureComponent {
|
|||
pb10: isChild && status.get('media_attachments').size === 0,
|
||||
pb5: isChild && status.get('media_attachments').size > 1,
|
||||
cursorPointer: isChild,
|
||||
backgroundColorSubtle_onHover: isChild,
|
||||
bgSubtle_onHover: isChild,
|
||||
})
|
||||
|
||||
return (
|
||||
|
|
|
@ -2,9 +2,13 @@ import ImmutablePropTypes from 'react-immutable-proptypes'
|
|||
import ImmutablePureComponent from 'react-immutable-pure-component'
|
||||
import { defineMessages, injectIntl } from 'react-intl'
|
||||
import { NavLink } from 'react-router-dom'
|
||||
import classNames from 'classnames/bind'
|
||||
import Text from './text'
|
||||
import StatusActionBarItem from './status_action_bar_item'
|
||||
import {
|
||||
CX,
|
||||
BREAKPOINT_EXTRA_SMALL,
|
||||
} from '../constants'
|
||||
import Responsive from '../features/ui/util/responsive_component'
|
||||
|
||||
const messages = defineMessages({
|
||||
comment: { id: 'status.comment', defaultMessage: 'Comment' },
|
||||
|
@ -17,8 +21,6 @@ const messages = defineMessages({
|
|||
commentsLabel: { id: 'comments.label', defaultMessage: '{number, plural, one {# comment} other {# comments}}' },
|
||||
})
|
||||
|
||||
const cx = classNames.bind(_s)
|
||||
|
||||
export default
|
||||
@injectIntl
|
||||
class StatusActionBar extends ImmutablePureComponent {
|
||||
|
@ -88,14 +90,14 @@ class StatusActionBar extends ImmutablePureComponent {
|
|||
|
||||
const statusUrl = `/${status.getIn(['account', 'acct'])}/posts/${status.get('id')}`
|
||||
|
||||
const containerClasses = cx({
|
||||
const containerClasses = CX({
|
||||
default: 1,
|
||||
px10: 1,
|
||||
mt10: !shouldCondense,
|
||||
mt5: shouldCondense,
|
||||
})
|
||||
|
||||
const innerContainerClasses = cx({
|
||||
const innerContainerClasses = CX({
|
||||
default: 1,
|
||||
py2: 1,
|
||||
flexRow: 1,
|
||||
|
@ -105,14 +107,14 @@ class StatusActionBar extends ImmutablePureComponent {
|
|||
mt5: hasInteractions,
|
||||
})
|
||||
|
||||
const interactionBtnClasses = cx({
|
||||
const interactionBtnClasses = CX({
|
||||
default: 1,
|
||||
text: 1,
|
||||
cursorPointer: 1,
|
||||
fontWeightNormal: 1,
|
||||
noUnderline: 1,
|
||||
underline_onHover: 1,
|
||||
backgroundTransparent: 1,
|
||||
bgTransparent: 1,
|
||||
mr10: 1,
|
||||
py5: 1,
|
||||
})
|
||||
|
@ -179,12 +181,14 @@ class StatusActionBar extends ImmutablePureComponent {
|
|||
buttonRef={this.setRepostButton}
|
||||
onClick={this.handleRepostClick}
|
||||
/>
|
||||
<StatusActionBarItem
|
||||
buttonRef={this.setShareButton}
|
||||
title={intl.formatMessage(messages.share)}
|
||||
icon='share'
|
||||
onClick={this.handleShareClick}
|
||||
/>
|
||||
<Responsive min={BREAKPOINT_EXTRA_SMALL}>
|
||||
<StatusActionBarItem
|
||||
buttonRef={this.setShareButton}
|
||||
title={intl.formatMessage(messages.share)}
|
||||
icon='share'
|
||||
onClick={this.handleShareClick}
|
||||
/>
|
||||
</Responsive>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
|
|
@ -34,7 +34,7 @@ export default class StatusActionBarItem extends PureComponent {
|
|||
justifyContentCenter: 1,
|
||||
alignItemsCenter: 1,
|
||||
px10: 1,
|
||||
backgroundColorSubtle_onHover: !disabled,
|
||||
bgSubtle_onHover: !disabled,
|
||||
})
|
||||
|
||||
const color = active ? 'brand' : 'secondary'
|
||||
|
|
|
@ -120,7 +120,7 @@ export default class Card extends ImmutablePureComponent {
|
|||
return (
|
||||
<div
|
||||
ref={this.setRef}
|
||||
className={[_s.default, _s.backgroundColorSecondary3, _s.posAbs, _s.top0, _s.right0, _s.bottom0, _s.left0, _s.statusCardVideo].join(' ')}
|
||||
className={[_s.default, _s.bgTertiary, _s.posAbs, _s.top0, _s.right0, _s.bottom0, _s.left0, _s.statusCardVideo].join(' ')}
|
||||
dangerouslySetInnerHTML={content}
|
||||
/>
|
||||
)
|
||||
|
@ -141,7 +141,7 @@ export default class Card extends ImmutablePureComponent {
|
|||
const title = interactive ?
|
||||
(
|
||||
<a
|
||||
className={[_s.default, _s.displayFlex, _s.text, _s.noUnderline, _s.overflowWrapBreakWord, _s.colorPrimary, _s.fontSize15PX, _s.fontWeightMedium].join(' ')}
|
||||
className={[_s.default, _s.displayFlex, _s.text, _s.noUnderline, _s.overflowWrapBreakWord, _s.colorPrimary, _s.fs15PX, _s.fontWeightMedium].join(' ')}
|
||||
href={card.get('url')}
|
||||
title={card.get('title')}
|
||||
rel='noopener noreferrer'
|
||||
|
@ -151,7 +151,7 @@ export default class Card extends ImmutablePureComponent {
|
|||
</a>
|
||||
)
|
||||
: (
|
||||
<span className={[_s.default, _s.displayFlex, _s.text, _s.overflowWrapBreakWord, _s.colorPrimary, _s.fontSize15PX, _s.fontWeightMedium].join(' ')}>
|
||||
<span className={[_s.default, _s.displayFlex, _s.text, _s.overflowWrapBreakWord, _s.colorPrimary, _s.fs15PX, _s.fontWeightMedium].join(' ')}>
|
||||
{card.get('title')}
|
||||
</span>
|
||||
)
|
||||
|
@ -159,11 +159,11 @@ export default class Card extends ImmutablePureComponent {
|
|||
const description = (
|
||||
<div className={[_s.default, _s.flexNormal, _s.px10, _s.py10, _s.borderColorSecondary, _s.borderLeft1PX].join(' ')}>
|
||||
{title}
|
||||
<p className={[_s.default, _s.displayFlex, _s.text, _s.mt5, _s.mb5, _s.overflowWrapBreakWord, _s.colorSecondary, _s.fontSize13PX, _s.fontWeightNormal].join(' ')}>
|
||||
<p className={[_s.default, _s.displayFlex, _s.text, _s.mt5, _s.mb5, _s.overflowWrapBreakWord, _s.colorSecondary, _s.fs13PX, _s.fontWeightNormal].join(' ')}>
|
||||
{trim(card.get('description') || '', maxDescription)}
|
||||
</p>
|
||||
<span className={[_s.default, _s.mtAuto, _s.flexRow, _s.alignItemsCenter, _s.colorSecondary, _s.text, _s.displayFlex, _s.textOverflowEllipsis, _s.fontSize13PX].join(' ')}>
|
||||
<Icon id='link' size='10px' className={[_s.fillColorSecondary, _s.mr5].join(' ')} fixedWidth />
|
||||
<span className={[_s.default, _s.mtAuto, _s.flexRow, _s.alignItemsCenter, _s.colorSecondary, _s.text, _s.displayFlex, _s.textOverflowEllipsis, _s.fs13PX].join(' ')}>
|
||||
<Icon id='link' size='10px' className={[_s.fillSecondary, _s.mr5].join(' ')} fixedWidth />
|
||||
{provider}
|
||||
</span>
|
||||
</div>
|
||||
|
@ -197,10 +197,10 @@ export default class Card extends ImmutablePureComponent {
|
|||
{ !embed &&
|
||||
<div className={[_s.default, _s.posAbs, _s.top0, _s.right0, _s.left0, _s.bottom0, _s.alignItemsCenter, _s.justifyContentCenter].join(' ')}>
|
||||
<button
|
||||
className={[_s.default, _s.cursorPointer, _s.backgroundColorBlackOpaque, _s.radiusSmall, _s.py15, _s.px15].join(' ')}
|
||||
className={[_s.default, _s.cursorPointer, _s.bgBlackOpaque, _s.radiusSmall, _s.py15, _s.px15].join(' ')}
|
||||
onClick={this.handleEmbedClick}
|
||||
>
|
||||
<Icon id={iconVariant} size='22px' className={[_s.fillColorWhite].join(' ')} />
|
||||
<Icon id={iconVariant} size='22px' className={[_s.fillWhite].join(' ')} />
|
||||
</button>
|
||||
</div>
|
||||
}
|
||||
|
@ -219,7 +219,7 @@ export default class Card extends ImmutablePureComponent {
|
|||
} else {
|
||||
embed = (
|
||||
<div className={[_s.default, _s.py15, _s.px15, _s.width72PX, _s.alignItemsCenter, _s.justifyContentCenter].join(' ')}>
|
||||
<Icon id='website' size='22px' className={_s.fillColorSecondary} />
|
||||
<Icon id='website' size='22px' className={_s.fillSecondary} />
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
@ -228,7 +228,7 @@ export default class Card extends ImmutablePureComponent {
|
|||
<div className={[_s.default, _s.width100PC, _s.px10].join(' ')}>
|
||||
<a
|
||||
href={card.get('url')}
|
||||
className={[_s.default, _s.cursorPointer, _s.flexRow, _s.overflowHidden, _s.noUnderline, _s.width100PC, _s.backgroundColorSubtle_onHover, _s.borderColorSecondary, _s.border1PX, _s.radiusSmall].join(' ')}
|
||||
className={[_s.default, _s.cursorPointer, _s.flexRow, _s.overflowHidden, _s.noUnderline, _s.width100PC, _s.bgSubtle_onHover, _s.borderColorSecondary, _s.border1PX, _s.radiusSmall].join(' ')}
|
||||
rel='noopener noreferrer'
|
||||
ref={this.setRef}
|
||||
>
|
||||
|
|
|
@ -85,7 +85,7 @@ class StatusContent extends ImmutablePureComponent {
|
|||
|
||||
if (descendent.classList.contains('invisible')) {
|
||||
descendent.classList.remove('invisible')
|
||||
descendent.classList.add(_s.fontSize0, _s.text, _s.inherit)
|
||||
descendent.classList.add(_s.fs0, _s.text, _s.inherit)
|
||||
}
|
||||
if (descendent.classList.contains('ellipsis')) {
|
||||
descendent.classList.remove('ellipsis')
|
||||
|
@ -254,7 +254,7 @@ class StatusContent extends ImmutablePureComponent {
|
|||
|
||||
<div className={spoilerContainerClasses}>
|
||||
<div className={[_s.default, _s.flexRow, _s.mr5].join(' ')}>
|
||||
<Icon id='warning' size='14px' className={[_s.fillColorPrimary, _s.mt2, _s.mr5].join(' ')}/>
|
||||
<Icon id='warning' size='14px' className={[_s.fillPrimary, _s.mt2, _s.mr5].join(' ')}/>
|
||||
<div
|
||||
className={_s.statusContent}
|
||||
dangerouslySetInnerHTML={spoilerContent}
|
||||
|
|
|
@ -104,7 +104,7 @@ class StatusHeader extends ImmutablePureComponent {
|
|||
color='none'
|
||||
icon='ellipsis'
|
||||
iconSize='20px'
|
||||
iconClassName={_s.fillColorSecondary}
|
||||
iconClassName={_s.fillSecondary}
|
||||
className={_s.mlAuto}
|
||||
onClick={this.handleOpenStatusOptionsPopover}
|
||||
buttonRef={this.setStatusOptionsButton}
|
||||
|
@ -127,7 +127,7 @@ class StatusHeader extends ImmutablePureComponent {
|
|||
|
||||
<DotTextSeperator />
|
||||
|
||||
<Icon id={visibilityIcon} size='12px' className={[_s.default, _s.displayInline, _s.ml5, _s.fillColorSecondary].join(' ')} />
|
||||
<Icon id={visibilityIcon} size='12px' className={[_s.default, _s.displayInline, _s.ml5, _s.fillSecondary].join(' ')} />
|
||||
|
||||
{
|
||||
!!status.get('group') &&
|
||||
|
|
|
@ -42,7 +42,7 @@ class StatusPrepend extends ImmutablePureComponent {
|
|||
return (
|
||||
<div className={[_s.default, _s.width100PC, _s.alignItemsStart, _s.borderBottom1PX, _s.borderColorSecondary].join(' ')}>
|
||||
<div className={[_s.default, _s.width100PC, _s.flexRow, _s.alignItemsCenter, _s.py5, _s.px15].join(' ')}>
|
||||
<Icon id={iconId} size='12px' className={[_s.fillColorSecondary, _s.mr5].join(' ')} />
|
||||
<Icon id={iconId} size='12px' className={[_s.fillSecondary, _s.mr5].join(' ')} />
|
||||
{
|
||||
isRepost &&
|
||||
<div className={[_s.default, _s.flexRow].join(' ')}>
|
||||
|
|
|
@ -36,18 +36,18 @@ export default class Switch extends PureComponent {
|
|||
border1PX: 1,
|
||||
mlAuto: 1,
|
||||
borderColorSecondary: 1,
|
||||
backgroundColorBrand: checked,
|
||||
bgBrand: checked,
|
||||
})
|
||||
|
||||
const checkboxLabelClasses = cx({
|
||||
default: 1,
|
||||
margin1PX: 1,
|
||||
m1PX: 1,
|
||||
height20PX: 1,
|
||||
width20PX: 1,
|
||||
circle: 1,
|
||||
posAbs: 1,
|
||||
backgroundColorSubtle2: !checked,
|
||||
backgroundColorPrimary: checked,
|
||||
bgSecondary: !checked,
|
||||
bgPrimary: checked,
|
||||
left0: !checked,
|
||||
right0: checked,
|
||||
})
|
||||
|
|
|
@ -26,7 +26,6 @@ export default class TabBar extends PureComponent {
|
|||
key={`tab-bar-item-${i}`}
|
||||
title={tab.title}
|
||||
onClick={tab.onClick}
|
||||
icon={tab.icon}
|
||||
to={tab.to}
|
||||
isActive={tab.active}
|
||||
isLarge={isLarge}
|
||||
|
|
|
@ -1,7 +1,6 @@
|
|||
import { withRouter } from 'react-router-dom'
|
||||
import classNames from 'classnames/bind'
|
||||
import Button from './button'
|
||||
import Icon from './icon'
|
||||
import Text from './text'
|
||||
|
||||
// Bind CSS Modules global variable `_s` to classNames module
|
||||
|
@ -9,7 +8,6 @@ const cx = classNames.bind(_s)
|
|||
|
||||
/**
|
||||
* Renders a tab bar item component
|
||||
* @param {string} [props.icon] - icon to use
|
||||
* @param {bool} [props.isLarge] - to style the tab bar larger
|
||||
* @param {bool} [props.isActive] - if item is active
|
||||
* @param {func} [props.onClick] - function to call on click
|
||||
|
@ -21,7 +19,6 @@ export default
|
|||
class TabBarItem extends PureComponent {
|
||||
|
||||
static propTypes = {
|
||||
icon: PropTypes.string,
|
||||
isLarge: PropTypes.bool,
|
||||
isActive: PropTypes.bool,
|
||||
onClick: PropTypes.func,
|
||||
|
@ -52,7 +49,6 @@ class TabBarItem extends PureComponent {
|
|||
onClick,
|
||||
location,
|
||||
isLarge,
|
||||
icon,
|
||||
isActive,
|
||||
} = this.props
|
||||
const { isCurrent } = this.state
|
||||
|
@ -74,7 +70,7 @@ class TabBarItem extends PureComponent {
|
|||
py5: 1,
|
||||
outlineNone: 1,
|
||||
cursorPointer: 1,
|
||||
backgroundTransparent: 1,
|
||||
bgTransparent: 1,
|
||||
borderColorTransparent: !active,
|
||||
borderColorBrand: active,
|
||||
mr5: isLarge,
|
||||
|
@ -89,7 +85,7 @@ class TabBarItem extends PureComponent {
|
|||
radiusSmall: 1,
|
||||
px10: !isLarge,
|
||||
px15: isLarge,
|
||||
backgroundColorSubtle2Dark_onHover: !active,
|
||||
bgSecondaryDark_onHover: !active,
|
||||
})
|
||||
|
||||
const textOptions = {
|
||||
|
@ -98,12 +94,6 @@ class TabBarItem extends PureComponent {
|
|||
weight: active ? 'bold' : isLarge ? 'medium' : 'normal',
|
||||
}
|
||||
|
||||
const iconOptions = {
|
||||
id: icon,
|
||||
width: !!isLarge ? 20 : 14,
|
||||
height: !!isLarge ? 20 : 14,
|
||||
}
|
||||
|
||||
return (
|
||||
<Button
|
||||
onClick={onClick}
|
||||
|
@ -112,17 +102,9 @@ class TabBarItem extends PureComponent {
|
|||
noClasses
|
||||
>
|
||||
<span className={textParentClasses}>
|
||||
{
|
||||
!!title &&
|
||||
<Text {...textOptions}>
|
||||
{title}
|
||||
</Text>
|
||||
}
|
||||
|
||||
{
|
||||
!!icon &&
|
||||
<Icon {...iconOptions} />
|
||||
}
|
||||
<Text {...textOptions}>
|
||||
{title}
|
||||
</Text>
|
||||
</span>
|
||||
</Button>
|
||||
)
|
||||
|
|
|
@ -103,11 +103,11 @@ export default class Text extends PureComponent {
|
|||
colorWhite: color === COLORS.white,
|
||||
inherit: color === COLORS.inherit,
|
||||
|
||||
fontSize19PX: size === SIZES.large,
|
||||
fontSize15PX: size === SIZES.medium,
|
||||
fontSize14PX: size === SIZES.normal,
|
||||
fontSize13PX: size === SIZES.small,
|
||||
fontSize12PX: size === SIZES.extraSmall,
|
||||
fs19PX: size === SIZES.large,
|
||||
fs15PX: size === SIZES.medium,
|
||||
fs14PX: size === SIZES.normal,
|
||||
fs13PX: size === SIZES.small,
|
||||
fs12PX: size === SIZES.extraSmall,
|
||||
|
||||
fontWeightNormal: weight === WEIGHTS.normal,
|
||||
fontWeightMedium: weight === WEIGHTS.medium,
|
||||
|
|
|
@ -8,7 +8,6 @@ export default class Textarea extends PureComponent {
|
|||
placeholder: PropTypes.string,
|
||||
prependIcon: PropTypes.string,
|
||||
value: PropTypes.string,
|
||||
hasClear: PropTypes.bool,
|
||||
onChange: PropTypes.func,
|
||||
onKeyUp: PropTypes.func,
|
||||
onFocus: PropTypes.func,
|
||||
|
@ -25,7 +24,6 @@ export default class Textarea extends PureComponent {
|
|||
placeholder,
|
||||
prependIcon,
|
||||
value,
|
||||
hasClear,
|
||||
onKeyUp,
|
||||
onFocus,
|
||||
onBlur,
|
||||
|
@ -39,14 +37,13 @@ export default class Textarea extends PureComponent {
|
|||
lineHeight125: 1,
|
||||
displayBlock: 1,
|
||||
py10: 1,
|
||||
backgroundTransparent: 1,
|
||||
fontSize15PX: 1,
|
||||
bgTransparent: 1,
|
||||
fs15PX: 1,
|
||||
flexGrow1: 1,
|
||||
heightMax100VH: 1,
|
||||
resizeVertical: 1,
|
||||
px5: !!prependIcon,
|
||||
pl15: !prependIcon,
|
||||
pr15: !hasClear,
|
||||
})
|
||||
|
||||
return (
|
||||
|
@ -59,7 +56,7 @@ export default class Textarea extends PureComponent {
|
|||
</Text>
|
||||
</div>
|
||||
}
|
||||
<div className={[_s.default, _s.backgroundColorPrimary, _s.border1PX, _s.borderColorSecondary, _s.flexRow, _s.radiusSmall, _s.alignItemsCenter].join(' ')}>
|
||||
<div className={[_s.default, _s.bgPrimary, _s.border1PX, _s.borderColorSecondary, _s.flexRow, _s.radiusSmall, _s.alignItemsCenter].join(' ')}>
|
||||
<textarea
|
||||
className={inputClasses}
|
||||
type='text'
|
||||
|
|
|
@ -53,7 +53,7 @@ class TimelineComposeBlock extends ImmutablePureComponent {
|
|||
return (
|
||||
<section className={[_s.default, _s.mb15].join(' ')}>
|
||||
<Block>
|
||||
<div className={[_s.default, _s.backgroundColorSubtle, _s.borderTop1PX, _s.borderBottom1PX, _s.borderColorSecondary, _s.px15, _s.py2, _s.alignItemsCenter, _s.flexRow].join(' ')}>
|
||||
<div className={[_s.default, _s.bgSubtle, _s.borderTop1PX, _s.borderBottom1PX, _s.borderColorSecondary, _s.px15, _s.py2, _s.alignItemsCenter, _s.flexRow].join(' ')}>
|
||||
<div className={_s.mr10}>
|
||||
<Avatar account={account} size={20} noHover />
|
||||
</div>
|
||||
|
|
|
@ -1,27 +1,24 @@
|
|||
import { Fragment } from 'react'
|
||||
import classNames from 'classnames/bind'
|
||||
import ImmutablePureComponent from 'react-immutable-pure-component'
|
||||
import ImmutablePropTypes from 'react-immutable-proptypes'
|
||||
import { urlRegex } from '../features/ui/util/url_regex'
|
||||
import {
|
||||
CX,
|
||||
DEFAULT_REL,
|
||||
} from '../constants'
|
||||
import Button from './button'
|
||||
import DotTextSeperator from './dot_text_seperator'
|
||||
import Image from './image'
|
||||
import RelativeTimestamp from './relative_timestamp'
|
||||
import Text from './text'
|
||||
|
||||
const cx = classNames.bind(_s)
|
||||
|
||||
export default class TrendingItem extends PureComponent {
|
||||
export default class TrendingItem extends ImmutablePureComponent {
|
||||
|
||||
static propTypes = {
|
||||
index: PropTypes.number,
|
||||
url: PropTypes.string.isRequired,
|
||||
title: PropTypes.string.isRequired,
|
||||
description: PropTypes.string,
|
||||
imageUrl: PropTypes.string,
|
||||
author: PropTypes.string,
|
||||
publishDate: PropTypes.string,
|
||||
trend: ImmutablePropTypes.map.isRequired,
|
||||
isLast: PropTypes.bool,
|
||||
isHidden: PropTypes.bool,
|
||||
wide: PropTypes.bool,
|
||||
}
|
||||
|
||||
static defaultProps = {
|
||||
|
@ -45,19 +42,18 @@ export default class TrendingItem extends PureComponent {
|
|||
render() {
|
||||
const {
|
||||
index,
|
||||
url,
|
||||
title,
|
||||
description,
|
||||
imageUrl,
|
||||
author,
|
||||
publishDate,
|
||||
trend,
|
||||
isLast,
|
||||
wide,
|
||||
isHidden,
|
||||
} = this.props
|
||||
const { hovering } = this.state
|
||||
|
||||
const correctedAuthor = author.replace('www.', '')
|
||||
if (!trend) return null
|
||||
|
||||
const title = trend.get('title')
|
||||
const description = trend.get('description')
|
||||
|
||||
const correctedAuthor = trend.getIn(['author', 'name'], '').replace('www.', '')
|
||||
const correctedDescription = description.length >= 120 ? `${description.substring(0, 120).trim()}...` : description
|
||||
const descriptionHasLink = correctedDescription.match(urlRegex)
|
||||
|
||||
|
@ -71,7 +67,7 @@ export default class TrendingItem extends PureComponent {
|
|||
)
|
||||
}
|
||||
|
||||
const containerClasses = cx({
|
||||
const containerClasses = CX({
|
||||
default: 1,
|
||||
noUnderline: 1,
|
||||
px15: 1,
|
||||
|
@ -82,35 +78,29 @@ export default class TrendingItem extends PureComponent {
|
|||
backgroundColorSubtle_onHover: 1,
|
||||
})
|
||||
|
||||
const subtitleClasses = cx({
|
||||
const subtitleClasses = CX({
|
||||
ml5: 1,
|
||||
underline: hovering,
|
||||
})
|
||||
|
||||
const image = (
|
||||
<Image
|
||||
nullable
|
||||
width='116px'
|
||||
height='78px'
|
||||
alt={title}
|
||||
src={imageUrl}
|
||||
className={[_s.radiusSmall, _s.overflowHidden, _s.mb10].join(' ')}
|
||||
/>
|
||||
)
|
||||
|
||||
return (
|
||||
<Button
|
||||
noClasses
|
||||
href={url}
|
||||
href={trend.get('url')}
|
||||
target='_blank'
|
||||
rel='noopener noreferrer'
|
||||
rel={DEFAULT_REL}
|
||||
className={containerClasses}
|
||||
onMouseEnter={() => this.handleOnMouseEnter()}
|
||||
onMouseLeave={() => this.handleOnMouseLeave()}
|
||||
>
|
||||
{
|
||||
!wide && image
|
||||
}
|
||||
<Image
|
||||
nullable
|
||||
width='116px'
|
||||
height='78px'
|
||||
alt={title}
|
||||
src={trend.get('image')}
|
||||
className={[_s.radiusSmall, _s.overflowHidden, _s.mb10].join(' ')}
|
||||
/>
|
||||
|
||||
<div className={[_s.default, _s.flexNormal, _s.pb5].join(' ')}>
|
||||
<div className={_s.default}>
|
||||
|
@ -127,6 +117,7 @@ export default class TrendingItem extends PureComponent {
|
|||
</Text>
|
||||
</div>
|
||||
}
|
||||
|
||||
<div className={[_s.default, _s.flexRow].join(' ')}>
|
||||
<Text color='secondary' size='small'>
|
||||
{index}
|
||||
|
@ -137,13 +128,14 @@ export default class TrendingItem extends PureComponent {
|
|||
</Text>
|
||||
<DotTextSeperator />
|
||||
<Text color='secondary' size='small' className={subtitleClasses}>
|
||||
<RelativeTimestamp timestamp={publishDate} />
|
||||
<RelativeTimestamp timestamp={trend.get('date_published')} />
|
||||
</Text>
|
||||
{
|
||||
hovering &&
|
||||
<Text color='secondary' size='small' className={_s.ml10}>→</Text>
|
||||
}
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</Button>
|
||||
)
|
||||
|
|
|
@ -54,7 +54,7 @@ class UploadArea extends PureComponent {
|
|||
>
|
||||
{({ backgroundOpacity, backgroundScale }) => (
|
||||
<div
|
||||
className={[_s.default, _s.alignItemsCenter, _s.justifyContentCenter, _s.backgroundColorPrimaryOpaque, _s.width100PC, _s.height100PC, _s.posAbs, _s.top0, _s.rightAuto, _s.bottomAuto, _s.left0].join(' ')}
|
||||
className={[_s.default, _s.alignItemsCenter, _s.justifyContentCenter, _s.bgPrimaryOpaque, _s.width100PC, _s.height100PC, _s.posAbs, _s.top0, _s.rightAuto, _s.bottomAuto, _s.left0].join(' ')}
|
||||
style={{
|
||||
visibility: active ? 'visible' : 'hidden',
|
||||
opacity: backgroundOpacity
|
||||
|
@ -62,7 +62,7 @@ class UploadArea extends PureComponent {
|
|||
>
|
||||
<div className={[_s.default, _s.width340PX, _s.height260PX, _s.px10, _s.py10].join(' ')}>
|
||||
<div
|
||||
className={[_s.default, _s.posAbs, _s.backgroundColorPrimary, _s.height100PC, _s.width100PC, _s.radiusSmall].join(' ')}
|
||||
className={[_s.default, _s.posAbs, _s.bgPrimary, _s.height100PC, _s.width100PC, _s.radiusSmall].join(' ')}
|
||||
style={{
|
||||
transform: `scale(${backgroundScale})`
|
||||
}}
|
||||
|
|
|
@ -460,7 +460,7 @@ class Video extends PureComponent {
|
|||
circle: 1,
|
||||
px10: 1,
|
||||
py10: 1,
|
||||
backgroundColorBrand: 1,
|
||||
bgBrand: 1,
|
||||
mlNeg5PX: 1,
|
||||
z3: 1,
|
||||
boxShadow1: 1,
|
||||
|
@ -479,7 +479,7 @@ class Video extends PureComponent {
|
|||
const volumeControlClasses = cx({
|
||||
default: 1,
|
||||
posAbs: 1,
|
||||
backgroundColorBlackOpaque: 1,
|
||||
bgBlackOpaque: 1,
|
||||
videoPlayerVolume: 1,
|
||||
height122PX: 1,
|
||||
circle: 1,
|
||||
|
@ -550,19 +550,19 @@ class Video extends PureComponent {
|
|||
ref={this.setVolumeRef}
|
||||
>
|
||||
<div
|
||||
className={[_s.default, _s.radiusSmall, _s.my10, _s.posAbs, _s.width4PX, _s.ml10, _s.backgroundColorPrimaryOpaque].join(' ')}
|
||||
className={[_s.default, _s.radiusSmall, _s.my10, _s.posAbs, _s.width4PX, _s.ml10, _s.bgPrimaryOpaque].join(' ')}
|
||||
style={{
|
||||
height: '102px',
|
||||
}}
|
||||
/>
|
||||
<div
|
||||
className={[_s.default, _s.radiusSmall, _s.my10, _s.bottom0, _s.posAbs, _s.width4PX, _s.ml10, _s.backgroundColorPrimary].join(' ')}
|
||||
className={[_s.default, _s.radiusSmall, _s.my10, _s.bottom0, _s.posAbs, _s.width4PX, _s.ml10, _s.bgPrimary].join(' ')}
|
||||
style={{
|
||||
height: `${volumeHeight}px`
|
||||
}}
|
||||
/>
|
||||
<span
|
||||
className={[_s.default, _s.cursorPointer, _s.posAbs, _s.circle, _s.px5, _s.boxShadow1, _s.mbNeg5PX, _s.py5, _s.backgroundColorPrimary, _s.z3].join(' ')}
|
||||
className={[_s.default, _s.cursorPointer, _s.posAbs, _s.circle, _s.px5, _s.boxShadow1, _s.mbNeg5PX, _s.py5, _s.bgPrimary, _s.z3].join(' ')}
|
||||
tabIndex='0'
|
||||
style={{
|
||||
marginLeft: '7px',
|
||||
|
@ -579,9 +579,9 @@ class Video extends PureComponent {
|
|||
ref={this.setSeekRef}
|
||||
>
|
||||
|
||||
<div className={[progressClasses, _s.backgroundColorLoading, _s.width100PC].join(' ')} />
|
||||
<div className={[progressClasses, _s.backgroundColorSubtle].join(' ')} style={{ width: `${buffer}%` }} />
|
||||
<div className={[progressClasses, _s.backgroundColorBrand].join(' ')} style={{ width: `${progress}%` }} />
|
||||
<div className={[progressClasses, _s.bgLoading, _s.width100PC].join(' ')} />
|
||||
<div className={[progressClasses, _s.bgSubtle].join(' ')} style={{ width: `${buffer}%` }} />
|
||||
<div className={[progressClasses, _s.bgBrand].join(' ')} style={{ width: `${progress}%` }} />
|
||||
|
||||
<span
|
||||
className={seekHandleClasses}
|
||||
|
@ -600,7 +600,7 @@ class Video extends PureComponent {
|
|||
onClick={this.togglePlay}
|
||||
icon={paused ? 'play' : 'pause'}
|
||||
iconSize='16px'
|
||||
iconClassName={_s.fillColorWhite}
|
||||
iconClassName={_s.fillWhite}
|
||||
className={_s.pl0}
|
||||
/>
|
||||
|
||||
|
@ -619,7 +619,7 @@ class Video extends PureComponent {
|
|||
onClick={this.toggleMute}
|
||||
icon={muted ? 'audio-mute' : 'audio'}
|
||||
iconSize='24px'
|
||||
iconClassName={_s.fillColorWhite}
|
||||
iconClassName={_s.fillWhite}
|
||||
className={[_s.px10, _s.ml10].join(' ')}
|
||||
onMouseEnter={this.handleMouseEnterAudio}
|
||||
onMouseLeave={this.handleMouseLeaveAudio}
|
||||
|
@ -632,7 +632,7 @@ class Video extends PureComponent {
|
|||
onClick={this.toggleFullscreen}
|
||||
icon={fullscreen ? 'minimize-fullscreen' : 'fullscreen'}
|
||||
iconSize='20px'
|
||||
iconClassName={_s.fillColorWhite}
|
||||
iconClassName={_s.fillWhite}
|
||||
className={[_s.px10, _s.pr0].join(' ')}
|
||||
/>
|
||||
</div>
|
||||
|
|
|
@ -3,6 +3,8 @@ export const CX = classNames.bind(_s)
|
|||
|
||||
export const APP_NAME = 'Gab'
|
||||
|
||||
export const DEFAULT_REL = 'noopener noreferrer'
|
||||
|
||||
export const BREAKPOINT_EXTRA_LARGE = 1480
|
||||
export const BREAKPOINT_LARGE = 1280
|
||||
export const BREAKPOINT_MEDIUM = 1160
|
||||
|
@ -12,6 +14,8 @@ export const BREAKPOINT_EXTRA_SMALL = 992
|
|||
export const ALLOWED_AROUND_SHORT_CODE = '><\u0085\u0020\u00a0\u1680\u2000\u2001\u2002\u2003\u2004\u2005\u2006\u2007\u2008\u2009\u200a\u202f\u205f\u3000\u2028\u2029\u0009\u000a\u000b\u000c\u000d'
|
||||
export const MAX_POST_CHARACTER_COUNT = 3000
|
||||
|
||||
export const URL_DISSENTER_SHOP = 'https://shop.dissenter.com'
|
||||
|
||||
export const PLACEHOLDER_MISSING_HEADER_SRC = '/original/missing.png'
|
||||
|
||||
export const POPOVER_CONTENT_WARNING = 'CONTENT_WARNING'
|
||||
|
|
|
@ -48,7 +48,13 @@ const makeMapStateToProps = () => {
|
|||
const getStatus = makeGetStatus();
|
||||
|
||||
const mapStateToProps = (state, props) => {
|
||||
const status = getStatus(state, props)
|
||||
const statusId = props.id || props.params.statusId
|
||||
const username = props.params ? props.params.username : undefined
|
||||
|
||||
const status = getStatus(state, {
|
||||
id: statusId,
|
||||
username: username,
|
||||
})
|
||||
|
||||
// : todo : if is comment (i.e. if any ancestorsIds) use comment not status
|
||||
|
||||
|
|
|
@ -27,8 +27,8 @@ export default class ComposeExtraButton extends PureComponent {
|
|||
} = this.props
|
||||
|
||||
const btnClasses = cx({
|
||||
backgroundColorSubtle_onHover: !active,
|
||||
backgroundColorBrandLight: active,
|
||||
bgSubtle_onHover: !active,
|
||||
bgBrandLight: active,
|
||||
py10: !small,
|
||||
px10: !small,
|
||||
py5: small,
|
||||
|
@ -37,8 +37,8 @@ export default class ComposeExtraButton extends PureComponent {
|
|||
})
|
||||
|
||||
const iconClasses = cx({
|
||||
fillColorSecondary: !active,
|
||||
fillColorWhite: active,
|
||||
fillSecondary: !active,
|
||||
fillWhite: active,
|
||||
})
|
||||
|
||||
const iconSize = !!small ? '14px' : '16px'
|
||||
|
|
|
@ -257,7 +257,7 @@ class ComposeForm extends ImmutablePureComponent {
|
|||
alignItemsEnd: shouldCondense,
|
||||
flexRow: shouldCondense,
|
||||
radiusSmall: shouldCondense,
|
||||
backgroundColorSubtle: shouldCondense,
|
||||
bgSubtle: shouldCondense,
|
||||
px5: shouldCondense,
|
||||
})
|
||||
|
||||
|
@ -427,7 +427,7 @@ class ComposeForm extends ImmutablePureComponent {
|
|||
isDisabled={disabledButton}
|
||||
backgroundColor='none'
|
||||
color='brand'
|
||||
className={[_s.fontSize15PX, _s.px15].join(' ')}
|
||||
className={[_s.fs15PX, _s.px15].join(' ')}
|
||||
onClick={this.handleSubmit}
|
||||
>
|
||||
{intl.formatMessage(scheduledAt ? messages.schedulePost : messages.publish)}
|
||||
|
|
|
@ -278,7 +278,7 @@ class PollFormOption extends ImmutablePureComponent {
|
|||
className={[_s.ml5, _s.justifyContentCenter].join(' ')}
|
||||
icon='close'
|
||||
iconSize='8px'
|
||||
iconClassName={_s.fillColorSecondary}
|
||||
iconClassName={_s.fillSecondary}
|
||||
disabled={index <= 1}
|
||||
title={intl.formatMessage(messages.remove_option)}
|
||||
onClick={this.handleOptionRemove}
|
||||
|
|
|
@ -88,7 +88,7 @@ class Followers extends ImmutablePureComponent {
|
|||
>
|
||||
{
|
||||
!!accountIds && accountIds.map((id) => (
|
||||
<Account key={`follower-${id}`} id={id} compact />
|
||||
<Account key={`follower-${id}`} id={id} compact withBio />
|
||||
))
|
||||
}
|
||||
</ScrollableList>
|
||||
|
|
|
@ -88,7 +88,7 @@ class Following extends ImmutablePureComponent {
|
|||
>
|
||||
{
|
||||
!!accountIds && accountIds.map((id) => (
|
||||
<Account key={`following-${id}`} id={id} compact />
|
||||
<Account key={`following-${id}`} id={id} compact withBio />
|
||||
))
|
||||
}
|
||||
</ScrollableList>
|
||||
|
|
|
@ -10,6 +10,7 @@ import StatusList from '../components/status_list'
|
|||
import ColumnIndicator from '../components/column_indicator'
|
||||
import Button from '../components/button'
|
||||
import Text from '../components/text'
|
||||
import Block from '../components/block'
|
||||
|
||||
const mapStateToProps = (state, props) => ({
|
||||
list: state.getIn(['lists', props.params.id]),
|
||||
|
@ -85,7 +86,7 @@ class ListTimeline extends ImmutablePureComponent {
|
|||
}
|
||||
|
||||
const emptyMessage = (
|
||||
<div className={[_s.default].join(' ')}>
|
||||
<div className={[_s.default, _s.py15, _s.px15].join(' ')}>
|
||||
<FormattedMessage
|
||||
id='empty_column.list'
|
||||
defaultMessage='There is nothing in this list yet. When members of this list post new statuses, they will appear here.'
|
||||
|
@ -95,7 +96,7 @@ class ListTimeline extends ImmutablePureComponent {
|
|||
onClick={this.handleEditClick}
|
||||
className={[_s.mt10]}
|
||||
>
|
||||
<Text color='inherit'>
|
||||
<Text color='inherit' align='center'>
|
||||
<FormattedMessage id='list.click_to_add' defaultMessage='Click here to add people' />
|
||||
</Text>
|
||||
</Button>
|
||||
|
|
|
@ -16,9 +16,7 @@ const mapStateToProps = (state) => ({
|
|||
})
|
||||
|
||||
const mapDispatchToProps = (dispatch) => ({
|
||||
onFetchLists() {
|
||||
return dispatch(fetchLists())
|
||||
},
|
||||
onFetchLists: () => dispatch(fetchLists()),
|
||||
})
|
||||
|
||||
export default
|
||||
|
@ -37,7 +35,7 @@ class ListsDirectory extends ImmutablePureComponent {
|
|||
}
|
||||
|
||||
updateOnProps = [
|
||||
'lists'
|
||||
'lists',
|
||||
]
|
||||
|
||||
componentDidMount() {
|
||||
|
|
|
@ -13,6 +13,7 @@ import Heading from '../components/heading'
|
|||
import Button from '../components/button'
|
||||
import Text from '../components/text'
|
||||
import Account from '../components/account'
|
||||
import PanelLayout from '../components/panel/panel_layout'
|
||||
|
||||
const mapStateToProps = (state) => ({
|
||||
results: state.getIn(['search', 'results']),
|
||||
|
@ -38,14 +39,14 @@ class Search extends ImmutablePureComponent {
|
|||
isSmallScreen: (window.innerWidth <= 895),
|
||||
}
|
||||
|
||||
render () {
|
||||
render() {
|
||||
const { results, location } = this.props
|
||||
const { isSmallScreen } = this.state
|
||||
|
||||
console.log("results:", results)
|
||||
|
||||
if (results.isEmpty() && isSmallScreen) {
|
||||
return (
|
||||
<div />
|
||||
)
|
||||
return null
|
||||
}
|
||||
|
||||
const pathname = location.pathname || ''
|
||||
|
@ -53,58 +54,94 @@ class Search extends ImmutablePureComponent {
|
|||
const showHashtags = pathname === '/search/hashtags'
|
||||
const showGroups = pathname === '/search/groups'
|
||||
const isTop = !showPeople && !showHashtags && !showGroups
|
||||
const theLimit = 10
|
||||
|
||||
let accounts, statuses, hashtags, groups
|
||||
|
||||
// : todo : statuses
|
||||
|
||||
if (results.get('accounts') && results.get('accounts').size > 0 && (isTop || showPeople)) {
|
||||
const size = isTop ? Math.min(results.get('accounts').size, 5) : results.get('accounts').size;
|
||||
const size = isTop ? Math.min(results.get('accounts').size, theLimit) : results.get('accounts').size;
|
||||
const isMax = size === results.get('accounts').size
|
||||
accounts = (
|
||||
<Block>
|
||||
<div className={[_s.default, _s.py15].join(' ')}>
|
||||
<div className={[_s.default, _s.flexRow, _s.mb15, _s.px15].join(' ')}>
|
||||
<Heading size='h2'>
|
||||
People
|
||||
</Heading>
|
||||
<div className={[_s.default, _s.mlAuto].join(' ')}>
|
||||
<Button
|
||||
isText
|
||||
backgroundColor='none'
|
||||
color='brand'
|
||||
to='/search/people'
|
||||
>
|
||||
<Text size='small' color='inherit' weight='bold'>
|
||||
See All
|
||||
</Text>
|
||||
</Button>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
{
|
||||
results.get('accounts').slice(0, size).map(accountId => <Account compact key={accountId} id={accountId} />)
|
||||
}
|
||||
<PanelLayout
|
||||
title='People'
|
||||
headerButtonTo={isMax ? undefined : '/search/people'}
|
||||
headerButtonTitle={isMax ? undefined : 'See more'}
|
||||
footerButtonTo={isMax ? undefined : '/search/people'}
|
||||
footerButtonTitle={isMax ? undefined : 'See more'}
|
||||
noPadding
|
||||
>
|
||||
<div className={[_s.default, _s.pb10, _s.px15, _s.borderBottom1PX, _s.borderColorSecondary].join(' ')}>
|
||||
<Text color='tertiary' size='small'>
|
||||
Showing {size} of {results.get('accounts').size} results
|
||||
</Text>
|
||||
</div>
|
||||
</Block>
|
||||
{
|
||||
results.get('accounts').slice(0, size).map(accountId => (
|
||||
<Account
|
||||
compact
|
||||
withBio
|
||||
key={accountId}
|
||||
id={accountId}
|
||||
/>
|
||||
))
|
||||
}
|
||||
</PanelLayout>
|
||||
)
|
||||
}
|
||||
|
||||
if (results.get('groups') && results.get('groups').size > 0 && (isTop || showGroups)) {
|
||||
const size = isTop ? Math.min(results.get('groups').size, 5) : results.get('groups').size;
|
||||
const size = isTop ? Math.min(results.get('groups').size, theLimit) : results.get('groups').size;
|
||||
const isMax = size === results.get('groups').size
|
||||
|
||||
groups = (
|
||||
<div className='search-results__section'>
|
||||
<h5><Icon id='users' fixedWidth /><FormattedMessage id='search_results.groups' defaultMessage='Groups' /></h5>
|
||||
{results.get('groups').slice(0, size).map(group => <GroupListItem key={`search-${group.get('name')}`} group={group} />)}
|
||||
</div>
|
||||
);
|
||||
<PanelLayout
|
||||
title='Groups'
|
||||
headerButtonTo={isMax ? undefined : '/search/groups'}
|
||||
headerButtonTitle={isMax ? undefined : 'See more'}
|
||||
footerButtonTo={isMax ? undefined : '/search/groups'}
|
||||
footerButtonTitle={isMax ? undefined : 'See more'}
|
||||
noPadding
|
||||
>
|
||||
<div className={[_s.default, _s.pb10, _s.px15, _s.borderBottom1PX, _s.borderColorSecondary].join(' ')}>
|
||||
<Text color='tertiary' size='small'>
|
||||
Showing {size} of {results.get('groups').size} results
|
||||
</Text>
|
||||
</div>
|
||||
{
|
||||
results.get('groups').slice(0, size).map(group => (
|
||||
<GroupListItem
|
||||
key={`search-${group.get('name')}`}
|
||||
id={group.get('id')}
|
||||
/>
|
||||
))
|
||||
}
|
||||
</PanelLayout>
|
||||
)
|
||||
}
|
||||
|
||||
if (results.get('hashtags') && results.get('hashtags').size > 0 && (isTop || showHashtags)) {
|
||||
const size = isTop ? Math.min(results.get('hashtags').size, 5) : results.get('hashtags').size;
|
||||
const size = isTop ? Math.min(results.get('hashtags').size, theLimit) : results.get('hashtags').size;
|
||||
const isMax = size === results.get('hashtags').size
|
||||
|
||||
hashtags = (
|
||||
<div className='search-results__section'>
|
||||
<h5><Icon id='hashtag' fixedWidth /><FormattedMessage id='search_results.hashtags' defaultMessage='Hashtags' /></h5>
|
||||
<PanelLayout
|
||||
title='Hashtags'
|
||||
headerButtonTo={isMax ? undefined : '/search/hashtags'}
|
||||
headerButtonTitle={isMax ? undefined : 'See more'}
|
||||
footerButtonTo={isMax ? undefined : '/search/hashtags'}
|
||||
footerButtonTitle={isMax ? undefined : 'See more'}
|
||||
noPadding
|
||||
>
|
||||
<div className={[_s.default, _s.pb10, _s.px15, _s.borderBottom1PX, _s.borderColorSecondary].join(' ')}>
|
||||
<Text color='tertiary' size='small'>
|
||||
Showing {size} of {results.get('hashtags').size} results
|
||||
</Text>
|
||||
</div>
|
||||
{results.get('hashtags').slice(0, size).map(hashtag => <HashtagItem isCompact key={hashtag.get('name')} hashtag={hashtag} />)}
|
||||
</div>
|
||||
);
|
||||
</PanelLayout>
|
||||
)
|
||||
}
|
||||
|
||||
return (
|
||||
|
|
|
@ -0,0 +1,12 @@
|
|||
import StatusContainer from '../containers/status_container'
|
||||
|
||||
export default class Status extends PureComponent {
|
||||
render() {
|
||||
console.log("this.props:", this.props)
|
||||
|
||||
return (
|
||||
<StatusContainer {...this.props} />
|
||||
)
|
||||
}
|
||||
|
||||
}
|
|
@ -63,7 +63,7 @@ import {
|
|||
Notifications,
|
||||
Search,
|
||||
// Shortcuts,
|
||||
Status,
|
||||
StatusFeature,
|
||||
StatusLikes,
|
||||
StatusReposts,
|
||||
} from './util/async_components'
|
||||
|
@ -206,7 +206,7 @@ class SwitchingArea extends PureComponent {
|
|||
<WrappedRoute path='/:username/likes' page={ProfilePage} component={LikedStatuses} content={children} />
|
||||
|
||||
<Redirect from='/@:username/posts/:statusId' to='/:username/posts/:statusId' exact />
|
||||
<WrappedRoute path='/:username/posts/:statusId' publicRoute exact page={BasicPage} component={Status} content={children} componentParams={{ title: 'Status' }} />
|
||||
<WrappedRoute path='/:username/posts/:statusId' publicRoute exact page={BasicPage} component={StatusFeature} content={children} componentParams={{ title: 'Status' }} />
|
||||
|
||||
<Redirect from='/@:username/posts/:statusId/reposts' to='/:username/posts/:statusId/reposts' />
|
||||
<WrappedRoute path='/:username/posts/:statusId/reposts' page={BasicPage} component={StatusReposts} content={children} componentParams={{ title: 'Reposts' }} />
|
||||
|
@ -497,7 +497,7 @@ class UI extends PureComponent {
|
|||
|
||||
return (
|
||||
<div ref={this.setRef}>
|
||||
<LoadingBar className={[_s.height1PX, _s.z3, _s.backgroundColorBrandLight].join(' ')} />
|
||||
<LoadingBar className={[_s.height1PX, _s.z3, _s.bgBrandLight].join(' ')} />
|
||||
|
||||
<SwitchingArea location={location} onLayoutChange={this.handleLayoutChange}>
|
||||
{children}
|
||||
|
|
|
@ -59,6 +59,7 @@ export function ReportModal() { return import(/* webpackChunkName: "modals/repor
|
|||
export function RepostOptionsPopover() { return import(/* webpackChunkName: "components/repost_options_popover" */'../../../components/popover/repost_options_popover') }
|
||||
export function Search() { return import(/*webpackChunkName: "features/search" */'../../search') }
|
||||
export function Status() { return import(/* webpackChunkName: "components/status" */'../../../components/status') }
|
||||
export function StatusFeature() { return import(/* webpackChunkName: "features/status" */'../../status') }
|
||||
export function SearchPopover() { return import(/* webpackChunkName: "components/search_popover" */'../../../components/popover/search_popover') }
|
||||
export function SidebarMorePopover() { return import(/* webpackChunkName: "components/sidebar_more_popover" */'../../../components/popover/sidebar_more_popover') }
|
||||
export function StatusLikes() { return import(/* webpackChunkName: "features/status_likes" */'../../status_likes') }
|
||||
|
|
|
@ -1,9 +1,9 @@
|
|||
import Sticky from 'react-stickynode'
|
||||
import * as Constants from '../constants'
|
||||
import Search from '../components/search'
|
||||
import ColumnHeader from '../components/column_header'
|
||||
import Sidebar from '../components/sidebar'
|
||||
// import Header from '../components/header'
|
||||
import { BREAKPOINT_EXTRA_SMALL } from '../constants'
|
||||
import NavigationBar from '../components/navigation_bar'
|
||||
// import Footer from '../components/footer'
|
||||
import FloatingActionButton from '../components/floating_action_button'
|
||||
import Responsive from '../features/ui/util/responsive_component'
|
||||
|
@ -36,82 +36,63 @@ export default class Layout extends PureComponent {
|
|||
} = this.props
|
||||
|
||||
return (
|
||||
<div className={[_s.default, _s.flexRow, _s.width100PC, _s.heightMin100VH, _s.backgroundColorSecondary3].join(' ')}>
|
||||
<div className={[_s.default, _s.width100PC, _s.heightMin100VH, _s.bgTertiary].join(' ')}>
|
||||
|
||||
{
|
||||
!noSidebar &&
|
||||
<Responsive min={Constants.BREAKPOINT_EXTRA_SMALL}>
|
||||
<Sidebar />
|
||||
</Responsive>
|
||||
}
|
||||
|
||||
<main role='main' className={[_s.default, _s.flexShrink1, _s.flexGrow1, _s.borderColorSecondary, _s.borderLeft1PX].join(' ')}>
|
||||
<NavigationBar
|
||||
title={title}
|
||||
tabs={tabs}
|
||||
actions={actions}
|
||||
/>
|
||||
|
||||
<div className={[_s.default, _s.flexRow, _s.width100PC].join(' ')}>
|
||||
{
|
||||
!noHeader &&
|
||||
<div className={[_s.default, _s.height53PX, _s.borderBottom1PX, _s.borderColorSecondary, _s.backgroundColorSecondary3, _s.z3, _s.top0, _s.posFixed].join(' ')}>
|
||||
<div className={[_s.default, _s.height53PX, _s.pl15, _s.width1015PX, _s.flexRow, _s.justifyContentSpaceBetween].join(' ')}>
|
||||
<div className={[_s.default, _s.width645PX].join(' ')}>
|
||||
<ColumnHeader
|
||||
title={title}
|
||||
showBackBtn={showBackBtn}
|
||||
actions={actions}
|
||||
tabs={tabs}
|
||||
/>
|
||||
!noSidebar &&
|
||||
<Responsive min={BREAKPOINT_EXTRA_SMALL}>
|
||||
<Sidebar title={title} tabs={tabs} actions={actions} />
|
||||
</Responsive>
|
||||
}
|
||||
|
||||
<main role='main' className={[_s.default, _s.flexShrink1, _s.flexGrow1].join(' ')}>
|
||||
|
||||
<div className={[_s.default, _s.width1015PX, _s.flexRow, _s.justifyContentEnd, _s.py15].join(' ')}>
|
||||
|
||||
{
|
||||
noRightSidebar && children
|
||||
}
|
||||
|
||||
{
|
||||
!noRightSidebar &&
|
||||
<div className={[_s.default, _s.width645PX, _s.z1].join(' ')}>
|
||||
<div className={_s.default}>
|
||||
{children}
|
||||
</div>
|
||||
</div>
|
||||
<Responsive min={Constants.BREAKPOINT_EXTRA_SMALL}>
|
||||
<div className={[_s.default, _s.width340PX].join(' ')}>
|
||||
<Search />
|
||||
}
|
||||
|
||||
{
|
||||
!noRightSidebar &&
|
||||
<Responsive min={BREAKPOINT_EXTRA_SMALL}>
|
||||
<div className={[_s.default, _s.width340PX, _s.ml15].join(' ')}>
|
||||
<Sticky top={73} enabled>
|
||||
<div className={[_s.default, _s.width340PX].join(' ')}>
|
||||
{layout}
|
||||
</div>
|
||||
</Sticky>
|
||||
</div>
|
||||
</Responsive>
|
||||
</div>
|
||||
}
|
||||
|
||||
{
|
||||
!noComposeButton &&
|
||||
<Responsive max={BREAKPOINT_EXTRA_SMALL}>
|
||||
<FloatingActionButton />
|
||||
</Responsive>
|
||||
}
|
||||
|
||||
</div>
|
||||
}
|
||||
|
||||
{
|
||||
!noHeader &&
|
||||
<div className={[_s.default, _s.height53PX].join(' ')}></div>
|
||||
}
|
||||
|
||||
<div className={[_s.default, _s.width1015PX, _s.flexRow, _s.justifyContentSpaceBetween, _s.pl15, _s.py15].join(' ')}>
|
||||
|
||||
{
|
||||
noRightSidebar && children
|
||||
}
|
||||
|
||||
{
|
||||
!noRightSidebar &&
|
||||
<div className={[_s.default, _s.width645PX, _s.z1].join(' ')}>
|
||||
<div className={_s.default}>
|
||||
{children}
|
||||
</div>
|
||||
</div>
|
||||
}
|
||||
|
||||
{
|
||||
!noRightSidebar &&
|
||||
<Responsive min={Constants.BREAKPOINT_EXTRA_SMALL}>
|
||||
<div className={[_s.default, _s.width340PX].join(' ')}>
|
||||
<Sticky top={73} enabled>
|
||||
<div className={[_s.default, _s.width340PX].join(' ')}>
|
||||
{layout}
|
||||
</div>
|
||||
</Sticky>
|
||||
</div>
|
||||
</Responsive>
|
||||
}
|
||||
|
||||
{
|
||||
!noComposeButton &&
|
||||
<Responsive max={Constants.BREAKPOINT_EXTRA_SMALL}>
|
||||
<FloatingActionButton />
|
||||
</Responsive>
|
||||
}
|
||||
|
||||
</div>
|
||||
|
||||
</main>
|
||||
|
||||
</main>
|
||||
</div>
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
|
|
@ -1,8 +1,8 @@
|
|||
import ImmutablePropTypes from 'react-immutable-proptypes'
|
||||
import ImmutablePureComponent from 'react-immutable-pure-component'
|
||||
import Sticky from 'react-stickynode'
|
||||
import Layout from './layout'
|
||||
import ProfileHeader from '../components/profile_header'
|
||||
import NavigationBar from '../components/navigation_bar'
|
||||
|
||||
export default class ProfileLayout extends ImmutablePureComponent {
|
||||
static propTypes = {
|
||||
|
@ -18,38 +18,48 @@ export default class ProfileLayout extends ImmutablePureComponent {
|
|||
account,
|
||||
children,
|
||||
layout,
|
||||
title,
|
||||
showBackBtn,
|
||||
} = this.props
|
||||
|
||||
return (
|
||||
<Layout
|
||||
noRightSidebar
|
||||
noComposeButton
|
||||
>
|
||||
<div className={[_s.default, _s.width1015PX, _s.flexRow, _s.justifyContentSpaceBetween, _s.pr15].join(' ')}>
|
||||
<div className={[_s.default, _s.z1, _s.width100PC].join(' ')}>
|
||||
<div className={[_s.default, _s.width100PC, _s.heightMin100VH, _s.bgTertiary].join(' ')}>
|
||||
|
||||
<ProfileHeader account={account} />
|
||||
<NavigationBar />
|
||||
|
||||
<div className={[_s.default, _s.width100PC, _s.flexRow, _s.justifyContentSpaceBetween, _s.py15].join(' ')}>
|
||||
<div className={[_s.default, _s.width645PX, _s.z1].join(' ')}>
|
||||
<div className={_s.default}>
|
||||
{children}
|
||||
</div>
|
||||
</div>
|
||||
<main role='main' className={[_s.default, _s.width100PC].join(' ')}>
|
||||
|
||||
<div className={[_s.default, _s.width340PX].join(' ')}>
|
||||
<Sticky top={63} enabled>
|
||||
<div className={[_s.default, _s.width340PX].join(' ')}>
|
||||
{layout}
|
||||
<div className={[_s.default, _s.width100PC, _s.flexRow, _s.pb15].join(' ')}>
|
||||
|
||||
<div className={[_s.default, _s.width100PC, _s.flexRow, _s.justifyContentSpaceBetween].join(' ')}>
|
||||
<div className={[_s.default, _s.z1, _s.width100PC, _s.alignItemsCenter].join(' ')}>
|
||||
|
||||
<ProfileHeader account={account} />
|
||||
|
||||
<div className={[_s.default, _s.width1015PX,, _s.flexRow, _s.justifyContentEnd, _s.py15].join(' ')}>
|
||||
<div className={[_s.default, _s.width340PX, _s.mr15].join(' ')}>
|
||||
<Sticky top={63} enabled>
|
||||
<div className={[_s.default, _s.width340PX].join(' ')}>
|
||||
{layout}
|
||||
</div>
|
||||
</Sticky>
|
||||
</div>
|
||||
</Sticky>
|
||||
<div className={[_s.default, _s.width645PX, _s.z1].join(' ')}>
|
||||
<div className={_s.default}>
|
||||
{children}
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
</div>
|
||||
|
||||
</Layout>
|
||||
</div>
|
||||
|
||||
</main>
|
||||
|
||||
</div>
|
||||
)
|
||||
}
|
||||
|
||||
|
|
|
@ -14,13 +14,13 @@ export default class SettingsLayout extends PureComponent {
|
|||
const { children, actions, tabs, title } = this.props
|
||||
|
||||
return (
|
||||
<div className={[_s.default, _s.flexRow, _s.width100PC, _s.heightMin100VH, _s.backgroundColorSecondary3].join(' ')}>
|
||||
<div className={[_s.default, _s.flexRow, _s.width100PC, _s.heightMin100VH, _s.bgTertiary].join(' ')}>
|
||||
|
||||
<Sidebar />
|
||||
|
||||
<main role='main' className={[_s.default, _s.flexShrink1, _s.flexGrow1, _s.borderColorSecondary, _s.borderLeft1PX].join(' ')}>
|
||||
|
||||
<div className={[_s.default, _s.height53PX, _s.borderBottom1PX, _s.borderColorSecondary, _s.backgroundColorSecondary3, _s.z3, _s.top0, _s.posFixed].join(' ')}>
|
||||
<div className={[_s.default, _s.height53PX, _s.borderBottom1PX, _s.borderColorSecondary, _s.bgTertiary, _s.z3, _s.top0, _s.posFixed].join(' ')}>
|
||||
<div className={[_s.default, _s.height53PX, _s.pl15, _s.width1015PX, _s.flexRow, _s.justifyContentSpaceBetween].join(' ')}>
|
||||
<div className={[_s.default, _s.width100PC].join(' ')}>
|
||||
<ColumnHeader
|
||||
|
|
|
@ -12,7 +12,7 @@ import DefaultLayout from '../layouts/default_layout'
|
|||
const messages = defineMessages({
|
||||
groups: { id: 'groups', defaultMessage: 'Groups' },
|
||||
featured: { id: 'featured', defaultMessage: 'Featured' },
|
||||
new: { id: 'new', defaultMessage: 'New' },
|
||||
new: { id: 'new', defaultMessage: 'Just Added' },
|
||||
myGroups: { id: 'my_groups', defaultMessage: 'My Groups' },
|
||||
admin: { id: 'admin', defaultMessage: 'Admin' },
|
||||
})
|
||||
|
@ -50,7 +50,7 @@ class GroupsPage extends PureComponent {
|
|||
const actions = []
|
||||
const tabs = [
|
||||
{
|
||||
title: intl.formatMessage(messages.groups),
|
||||
title: intl.formatMessage(messages.featured),
|
||||
to: '/groups',
|
||||
},
|
||||
{
|
||||
|
|
|
@ -38,10 +38,6 @@ class SearchPage extends PureComponent {
|
|||
title: 'Groups',
|
||||
to: '/search/groups'
|
||||
},
|
||||
{
|
||||
title: 'Gabs',
|
||||
to: '/search/gabs'
|
||||
},
|
||||
{
|
||||
title: 'Trends',
|
||||
to: '/search/trends'
|
||||
|
|
|
@ -2,6 +2,7 @@ import { Map as ImmutableMap, List as ImmutableList } from 'immutable';
|
|||
import { GROUPS_FETCH_SUCCESS } from '../actions/groups';
|
||||
|
||||
const initialState = ImmutableMap({
|
||||
new: ImmutableList(),
|
||||
featured: ImmutableList(),
|
||||
member: ImmutableList(),
|
||||
admin: ImmutableList(),
|
||||
|
|
|
@ -12,8 +12,8 @@
|
|||
--font_size_extra_large: 19px;
|
||||
--font_size_extra_extra_large: 24px;
|
||||
|
||||
--color_brand-dark: #38a16b;
|
||||
--color_brand-light: #36e991;
|
||||
--color_brand-dark: #378e61;
|
||||
--color_brand-light: #63DA9D;
|
||||
--color_brand-light-opaque: rgb(54, 233, 145, .125);
|
||||
--color_brand: #21cf7a;
|
||||
|
||||
|
@ -30,7 +30,7 @@
|
|||
--solid_color_primary-opaque:rgba(255, 255, 255,.6);
|
||||
--solid_color_secondary: #e2e8ec;
|
||||
--solid_color_secondary-dark: #d9e0e5;
|
||||
--solid_color_tertiary: #f6f6f9;
|
||||
--solid_color_tertiary: #f5f5f7;
|
||||
--solid_color_block: #f5f8fa;
|
||||
|
||||
--text_color_primary: #2d3436;
|
||||
|
@ -214,6 +214,7 @@ body {
|
|||
|
||||
.justifyContentSpaceBetween { justify-content: space-between; }
|
||||
.justifyContentCenter { justify-content: center; }
|
||||
.justifyContentEnd { justify-content: flex-end; }
|
||||
|
||||
.overflowHidden {
|
||||
overflow-x: hidden;
|
||||
|
@ -230,6 +231,8 @@ body {
|
|||
white-space: nowrap;
|
||||
}
|
||||
|
||||
.textUppercase { text-transform: uppercase; }
|
||||
|
||||
.whiteSpaceNoWrap { white-space: nowrap; }
|
||||
|
||||
.outlineNone { outline: none; }
|
||||
|
@ -295,39 +298,39 @@ body {
|
|||
);
|
||||
}
|
||||
|
||||
.backgroundTransparent { background-color: transparent; }
|
||||
.bgTransparent { background-color: transparent; }
|
||||
|
||||
.backgroundColorLoading { background-color: #ccc; }
|
||||
.bgLoading { background-color: #ccc; }
|
||||
|
||||
.backgroundColorSubtle { background-color: var(--solid_color_block); }
|
||||
.backgroundColorSubtle_onHover:hover { background-color: var(--solid_color_block); }
|
||||
.bgSubtle { background-color: var(--solid_color_block); }
|
||||
.bgSubtle_onHover:hover { background-color: var(--solid_color_block); }
|
||||
|
||||
.backgroundColorSubtle2 { background-color: var(--solid_color_secondary); }
|
||||
.backgroundColorSubtle2Dark_onHover:hover { background-color: var(--solid_color_secondary-dark); }
|
||||
.bgSecondary { background-color: var(--solid_color_secondary); }
|
||||
.bgSecondaryDark_onHover:hover { background-color: var(--solid_color_secondary-dark); }
|
||||
|
||||
.backgroundColorSecondary3 { background-color: var(--solid_color_tertiary); }
|
||||
.bgTertiary { background-color: var(--solid_color_tertiary); }
|
||||
|
||||
.backgroundColorPrimary { background-color: var(--solid_color_primary); }
|
||||
.backgroundColorPrimaryOpaque { background-color: var(--solid_color_primary-opaque) }
|
||||
.bgPrimary { background-color: var(--solid_color_primary); }
|
||||
.bgPrimaryOpaque { background-color: var(--solid_color_primary-opaque) }
|
||||
|
||||
.backgroundColorWhite { background-color: var(--color_white); }
|
||||
.bgWhite { background-color: var(--color_white); }
|
||||
|
||||
.backgroundColorBlack { background-color: var(--color_black); }
|
||||
.backgroundColorBlackOpaque { background-color: var(--color_black-opaquer); }
|
||||
.backgroundColorBlackOpaque_onHover:hover { background-color: var(--color_black-opaque); }
|
||||
.bgBlack { background-color: var(--color_black); }
|
||||
.bgBlackOpaque { background-color: var(--color_black-opaquer); }
|
||||
.bgBlackOpaque_onHover:hover { background-color: var(--color_black-opaque); }
|
||||
|
||||
.backgroundColorBrand { background-color: var(--color_brand); }
|
||||
.backgroundColorBrand_onHover:hover { background-color: var(--color_brand); }
|
||||
.bgBrand { background-color: var(--color_brand); }
|
||||
.bgBrand_onHover:hover { background-color: var(--color_brand); }
|
||||
|
||||
.backgroundColorBrandLight { background-color: var(--color_brand-light); }
|
||||
.backgroundColorBrandLightOpaque { background-color: var(--color_brand-light-opaque); }
|
||||
.backgroundColorBrandLightOpaque_onHover:hover { background-color: var(--color_brand-light-opaque); }
|
||||
.bgBrandLight { background-color: var(--color_brand-light); }
|
||||
.bgBrandLightOpaque { background-color: var(--color_brand-light-opaque); }
|
||||
.bgBrandLightOpaque_onHover:hover { background-color: var(--color_brand-light-opaque); }
|
||||
|
||||
.backgroundColorBrandDark { background-color: var(--color_brand-dark); }
|
||||
.backgroundColorBrandDark_onHover:hover { background-color: var(--color_brand-dark); }
|
||||
.bgBrandDark { background-color: var(--color_brand-dark); }
|
||||
.bgBrandDark_onHover:hover { background-color: var(--color_brand-dark); }
|
||||
|
||||
.backgroundColorDanger { background-color: var(--color_red); }
|
||||
.backgroundColorDangerDark_onHover:hover { background-color: var(--color_red-dark); }
|
||||
.bgDanger { background-color: var(--color_red); }
|
||||
.bgDangerDark_onHover:hover { background-color: var(--color_red-dark); }
|
||||
|
||||
/* */
|
||||
|
||||
|
@ -344,14 +347,15 @@ body {
|
|||
|
||||
/* */
|
||||
|
||||
.fillColorPrimary { fill: var(--text_color_primary); }
|
||||
.fillColorSecondary { fill: var(--text_color_secondary); }
|
||||
.fillPrimary { fill: var(--text_color_primary); }
|
||||
.fillSecondary { fill: var(--text_color_secondary); }
|
||||
|
||||
.fillColorWhite { fill: var(--color_white); }
|
||||
.fillColorWhite_onHover:hover { fill: var(--color_white); }
|
||||
.fillWhite { fill: var(--color_white); }
|
||||
.fillWhite_onHover:hover { fill: var(--color_white); }
|
||||
|
||||
.fillColorBrand { fill: var(--color_brand); }
|
||||
.fillColorBrand_onHover:hover { fill: var(--color_brand);}
|
||||
.fillBrand { fill: var(--color_brand); }
|
||||
.fillBrandDark { fill: var(--color_brand-dark); }
|
||||
.fillBrand_onHover:hover { fill: var(--color_brand);}
|
||||
|
||||
.fillColorGabPro { fill: var(--color_gold); }
|
||||
|
||||
|
@ -391,12 +395,12 @@ body {
|
|||
.heightMax100VH { max-height: 100vh; }
|
||||
.heightMax80VH { max-height: 80vh; }
|
||||
.heightMax56PX { max-height: 56px; }
|
||||
.heightCalc53PX { height: calc(100vh - 53px); }
|
||||
|
||||
.heightMin100VH { min-height: 100vh; }
|
||||
.heightMin50VH { min-height: 50vh; }
|
||||
.heightMin50PX { min-height: 50px; }
|
||||
|
||||
.height100VH { height: 100vh; }
|
||||
.height100PC { height: 100%; }
|
||||
.height350PX { height: 350px; }
|
||||
.height260PX { height: 260px; }
|
||||
|
@ -405,7 +409,6 @@ body {
|
|||
.height122PX { height: 122px; }
|
||||
.height72PX { height: 72px; }
|
||||
.height53PX { height: 53px; }
|
||||
.height50PX { height: 50px; }
|
||||
.height40PX { height: 40px; }
|
||||
.height24PX { height: 24px; }
|
||||
.height22PX { height: 22px; }
|
||||
|
@ -418,6 +421,7 @@ body {
|
|||
.width100PC { width: 100%; }
|
||||
.width50PC { width: 50%; }
|
||||
.width25PC { width: 25%; }
|
||||
.width1255PX { width: 1255px; }
|
||||
.width1015PX { width: 1015px; }
|
||||
.width645PX { width: 645px; }
|
||||
.width340PX { width: 340px; }
|
||||
|
@ -429,6 +433,7 @@ body {
|
|||
.width50PX { width: 50px; }
|
||||
.width20PX { width: 20px; }
|
||||
.width4PX { width: 4px; }
|
||||
.width1PX { width: 1px; }
|
||||
|
||||
|
||||
@media (min-width: 1480px) {
|
||||
|
@ -507,6 +512,8 @@ body {
|
|||
.width1015PX {
|
||||
max-width: 600px;
|
||||
width: 100%;
|
||||
margin-left: auto;
|
||||
margin-right: auto;
|
||||
}
|
||||
|
||||
.width645PX {
|
||||
|
@ -526,14 +533,14 @@ body {
|
|||
.textAlignLeft { text-align: left; }
|
||||
.textAlignCenter { text-align: center; }
|
||||
|
||||
.fontSize24PX { font-size: var(--font_size_extra_extra_large); }
|
||||
.fontSize19PX { font-size: var(--font_size_extra_large); }
|
||||
.fontSize16PX { font-size: var(--font_size_large); }
|
||||
.fontSize15PX { font-size: var(--font_size_medium); }
|
||||
.fontSize14PX { font-size: var(--font_size_normal); }
|
||||
.fontSize13PX { font-size: var(--font_size_small); }
|
||||
.fontSize12PX { font-size: var(--font_size_extra_small); }
|
||||
.fontSize0 { font-size: 0; }
|
||||
.fs24PX { font-size: var(--font_size_extra_extra_large); }
|
||||
.fs19PX { font-size: var(--font_size_extra_large); }
|
||||
.fs16PX { font-size: var(--font_size_large); }
|
||||
.fs15PX { font-size: var(--font_size_medium); }
|
||||
.fs14PX { font-size: var(--font_size_normal); }
|
||||
.fs13PX { font-size: var(--font_size_small); }
|
||||
.fs12PX { font-size: var(--font_size_extra_small); }
|
||||
.fs0 { font-size: 0; }
|
||||
|
||||
.fontWeightNormal { font-weight: 400; }
|
||||
.fontWeightMedium { font-weight: 500; }
|
||||
|
@ -562,7 +569,7 @@ body {
|
|||
margin-bottom: 10px;
|
||||
}
|
||||
|
||||
.margin1PX { margin: 1px; }
|
||||
.m1PX { margin: 1px; }
|
||||
|
||||
.mr15 { margin-right: 15px; }
|
||||
.mr10 { margin-right: 10px; }
|
||||
|
@ -602,9 +609,12 @@ body {
|
|||
|
||||
.pl25 { padding-left: 25px; }
|
||||
.pl15 { padding-left: 15px; }
|
||||
.pl10 { padding-left: 10px; }
|
||||
.pl5 { padding-left: 5px; }
|
||||
.pl0 { padding-left: 0; }
|
||||
|
||||
.pr15 { padding-right: 15px; }
|
||||
.pr10 { padding-right: 10px; }
|
||||
.pr5 { padding-right: 5px; }
|
||||
.pr0 { padding-right: 0; }
|
||||
|
||||
|
@ -618,6 +628,11 @@ body {
|
|||
padding-bottom: 5px;
|
||||
}
|
||||
|
||||
.py7 {
|
||||
padding-top: 7px;
|
||||
padding-bottom: 7px;
|
||||
}
|
||||
|
||||
.py10 {
|
||||
padding-top: 10px;
|
||||
padding-bottom: 10px;
|
||||
|
@ -658,6 +673,7 @@ body {
|
|||
|
||||
.boxShadowNone .boxShadowBlock {
|
||||
box-shadow: none !important;
|
||||
border-radius: 0 !important;
|
||||
}
|
||||
|
||||
.boxShadowAvatarPro {
|
||||
|
@ -727,6 +743,19 @@ body {
|
|||
visibility: hidden;
|
||||
}
|
||||
|
||||
.searchInput::placeholder {
|
||||
color: rgba(255,255,255,0.65);
|
||||
opacity: 1;
|
||||
}
|
||||
|
||||
.searchInput:-ms-input-placeholder {
|
||||
color: rgba(255,255,255,0.65);
|
||||
}
|
||||
|
||||
.searchInput::-ms-input-placeholder {
|
||||
color: rgba(255,255,255,0.65);
|
||||
}
|
||||
|
||||
/**
|
||||
* Rich Text Editor
|
||||
*/
|
||||
|
|
|
@ -2,7 +2,7 @@
|
|||
|
||||
class SearchService < BaseService
|
||||
def call(query, account, limit, options = {})
|
||||
@query = query.strip
|
||||
@query = query&.strip
|
||||
@account = account
|
||||
@options = options
|
||||
@limit = limit.to_i
|
||||
|
@ -10,8 +10,10 @@ class SearchService < BaseService
|
|||
@resolve = options[:resolve] || false
|
||||
|
||||
default_results.tap do |results|
|
||||
next if @query.blank? || @limit.zero?
|
||||
|
||||
if url_query?
|
||||
results.merge!(url_resource_results) unless url_resource.nil?
|
||||
results.merge!(url_resource_results) unless url_resource.nil? || @offset.positive? || (@options[:type].present? && url_resource_symbol != @options[:type].to_sym)
|
||||
elsif @query.present?
|
||||
results[:accounts] = perform_accounts_search! if account_searchable?
|
||||
results[:statuses] = perform_statuses_search! if full_text_searchable?
|
||||
|
@ -79,7 +81,7 @@ class SearchService < BaseService
|
|||
end
|
||||
|
||||
def url_query?
|
||||
@options[:type].blank? && @query =~ /\Ahttps?:\/\//
|
||||
@resolve && @query =~ /\Ahttps?:\/\//
|
||||
end
|
||||
|
||||
def url_resource_results
|
||||
|
|
Loading…
Reference in New Issue