Actually hide NSFW content #1748
4 changed files with 50 additions and 85 deletions
|
@ -4,46 +4,20 @@ import classnames from 'classnames';
|
|||
|
||||
type Props = {
|
||||
thumbnail: ?string, // externally sourced image
|
||||
nsfw: ?boolean,
|
||||
};
|
||||
|
||||
const autoThumbColors = [
|
||||
'purple',
|
||||
'red',
|
||||
'pink',
|
||||
'indigo',
|
||||
'blue',
|
||||
'light-blue',
|
||||
'cyan',
|
||||
'teal',
|
||||
'green',
|
||||
'yellow',
|
||||
'orange',
|
||||
];
|
||||
|
||||
class CardMedia extends React.PureComponent<Props> {
|
||||
getAutoThumbClass = () => autoThumbColors[Math.floor(Math.random() * autoThumbColors.length)];
|
||||
|
||||
render() {
|
||||
const { thumbnail, nsfw } = this.props;
|
||||
|
||||
const generateAutothumb = !thumbnail && !nsfw;
|
||||
let autoThumbClass;
|
||||
if (generateAutothumb) {
|
||||
autoThumbClass = `card__media--autothumb.${this.getAutoThumbClass()}`;
|
||||
}
|
||||
const { thumbnail } = this.props;
|
||||
|
||||
return (
|
||||
<div
|
||||
style={thumbnail && !nsfw ? { backgroundImage: `url('${thumbnail}')` } : {}}
|
||||
className={classnames('card__media', autoThumbClass, {
|
||||
'card__media--no-img': !thumbnail || nsfw,
|
||||
'card__media--nsfw': nsfw,
|
||||
style={thumbnail ? { backgroundImage: `url('${thumbnail}')` } : {}}
|
||||
className={classnames('card__media', {
|
||||
'card__media--no-img': !thumbnail,
|
||||
})}
|
||||
>
|
||||
{(!thumbnail || nsfw) && (
|
||||
<span className="card__media-text">{nsfw ? __('NSFW') : 'LBRY'}</span>
|
||||
)}
|
||||
{!thumbnail && <span className="card__media-text">LBRY</span>}
|
||||
</div>
|
||||
);
|
||||
}
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
// @flow
|
||||
import * as React from 'react';
|
||||
import { normalizeURI, convertToShareLink } from 'lbry-redux';
|
||||
import Button from 'component/button';
|
||||
import type { Claim, Metadata } from 'types/claim';
|
||||
import CardMedia from 'component/cardMedia';
|
||||
import TruncatedText from 'component/common/truncated-text';
|
||||
import Icon from 'component/common/icon';
|
||||
|
@ -14,9 +14,9 @@ import { openCopyLinkMenu } from '../../util/contextMenu';
|
|||
// TODO: iron these out
|
||||
type Props = {
|
||||
uri: string,
|
||||
claim: ?{ claim_id: string },
|
||||
claim: ?Claim,
|
||||
fileInfo: ?{},
|
||||
metadata: ?{ nsfw: boolean, title: string, thumbnail: ?string },
|
||||
metadata: ?Metadata,
|
||||
navigate: (string, ?{}) => void,
|
||||
rewardedContentClaimIds: Array<string>,
|
||||
obscureNsfw: boolean,
|
||||
|
@ -62,10 +62,15 @@ class FileCard extends React.PureComponent<Props> {
|
|||
showPrice,
|
||||
pending,
|
||||
} = this.props;
|
||||
|
||||
const shouldHide = obscureNsfw && metadata && metadata.nsfw && !claimIsMine;
|
||||
if (shouldHide) {
|
||||
return null;
|
||||
}
|
||||
|
||||
const uri = !pending ? normalizeURI(this.props.uri) : this.props.uri;
|
||||
const title = metadata && metadata.title ? metadata.title : uri;
|
||||
const thumbnail = metadata && metadata.thumbnail ? metadata.thumbnail : null;
|
||||
const shouldObscureNsfw = obscureNsfw && metadata && metadata.nsfw && !claimIsMine;
|
||||
const isRewardContent = claim && rewardedContentClaimIds.includes(claim.claim_id);
|
||||
const handleContextMenu = event => {
|
||||
event.preventDefault();
|
||||
|
@ -86,27 +91,8 @@ class FileCard extends React.PureComponent<Props> {
|
|||
})}
|
||||
onContextMenu={handleContextMenu}
|
||||
>
|
||||
<CardMedia nsfw={shouldObscureNsfw} thumbnail={thumbnail} />
|
||||
<CardMedia thumbnail={thumbnail} />
|
||||
<div className="card-media__internal-links">{showPrice && <FilePrice uri={uri} />}</div>
|
||||
|
||||
{shouldObscureNsfw ? (
|
||||
<div className="card__title-identity">
|
||||
<div className="card__title--small">
|
||||
<TruncatedText lines={3}>
|
||||
{__('This content is obscured because it is NSFW. You can change this in ')}
|
||||
<Button
|
||||
button="link"
|
||||
label={__('Settings.')}
|
||||
onClick={e => {
|
||||
// Don't propagate to the onClick handler of parent element
|
||||
e.stopPropagation();
|
||||
navigate('/settings');
|
||||
}}
|
||||
/>
|
||||
</TruncatedText>
|
||||
</div>
|
||||
</div>
|
||||
) : (
|
||||
<div className="card__title-identity">
|
||||
<div className="card__title--small">
|
||||
<TruncatedText lines={3}>{title}</TruncatedText>
|
||||
|
@ -125,7 +111,6 @@ class FileCard extends React.PureComponent<Props> {
|
|||
)}
|
||||
</div>
|
||||
</div>
|
||||
)}
|
||||
</section>
|
||||
);
|
||||
/* eslint-enable jsx-a11y/click-events-have-key-events */
|
||||
|
|
|
@ -1,6 +1,7 @@
|
|||
// @flow
|
||||
import * as React from 'react';
|
||||
import * as icons from 'constants/icons';
|
||||
import type { Claim, Metadata } from 'types/claim';
|
||||
import { normalizeURI, parseURI } from 'lbry-redux';
|
||||
import CardMedia from 'component/cardMedia';
|
||||
import TruncatedText from 'component/common/truncated-text';
|
||||
|
@ -19,15 +20,8 @@ type Props = {
|
|||
uri: string,
|
||||
isResolvingUri: boolean,
|
||||
rewardedContentClaimIds: Array<string>,
|
||||
claim: ?{
|
||||
name: string,
|
||||
channel_name: string,
|
||||
claim_id: string,
|
||||
},
|
||||
metadata: ?{
|
||||
title: ?string,
|
||||
thumbnail: ?string,
|
||||
},
|
||||
claim: ?Claim,
|
||||
metadata: ?Metadata,
|
||||
resolveUri: string => void,
|
||||
navigate: (string, ?{}) => void,
|
||||
clearPublish: () => void,
|
||||
|
@ -70,6 +64,11 @@ class FileTile extends React.PureComponent<Props> {
|
|||
hideNoResult,
|
||||
} = this.props;
|
||||
|
||||
const shouldHide = obscureNsfw && metadata && metadata.nsfw && !claimIsMine;
|
||||
if (shouldHide) {
|
||||
return null;
|
||||
}
|
||||
|
||||
const uri = normalizeURI(this.props.uri);
|
||||
const isClaimed = !!claim;
|
||||
const description = isClaimed && metadata && metadata.description ? metadata.description : '';
|
||||
|
@ -77,8 +76,6 @@ class FileTile extends React.PureComponent<Props> {
|
|||
isClaimed && metadata && metadata.title ? metadata.title : parseURI(uri).contentName;
|
||||
const thumbnail = metadata && metadata.thumbnail ? metadata.thumbnail : null;
|
||||
const isRewardContent = claim && rewardedContentClaimIds.includes(claim.claim_id);
|
||||
const shouldObscureNsfw = obscureNsfw && metadata && metadata.nsfw && !claimIsMine;
|
||||
|
||||
const onClick = () => navigate('/show', { uri });
|
||||
|
||||
let name;
|
||||
|
@ -98,7 +95,7 @@ class FileTile extends React.PureComponent<Props> {
|
|||
role="button"
|
||||
tabIndex="0"
|
||||
>
|
||||
<CardMedia title={title || name} thumbnail={thumbnail} nsfw={shouldObscureNsfw} />
|
||||
<CardMedia title={title || name} thumbnail={thumbnail} />
|
||||
<div className="file-tile__info">
|
||||
{isResolvingUri && <div className="card__title--small">{__('Loading...')}</div>}
|
||||
{!isResolvingUri && (
|
||||
|
|
|
@ -1,5 +1,13 @@
|
|||
// @flow
|
||||
|
||||
// Currently incomplete
|
||||
export type Metadata = {
|
||||
nsfw: boolean,
|
||||
title: string,
|
||||
thumbnail: ?string,
|
||||
description: ?string,
|
||||
};
|
||||
|
||||
// Actual claim type has more values than this
|
||||
// Add them as they are used
|
||||
export type Claim = {
|
||||
|
@ -22,9 +30,10 @@ export type Claim = {
|
|||
nout: number,
|
||||
signature_is_valid: boolean,
|
||||
valid_at_height: number,
|
||||
value: {
|
||||
value: ?{
|
||||
publisherSignature: ?{
|
||||
certificateId: ?string,
|
||||
},
|
||||
stream: ?Metadata,
|
||||
},
|
||||
};
|
||||
|
|
Loading…
Reference in a new issue