signal-desktop/ts/components/conversation/media-gallery/MediaGallery.tsx

148 lines
3.1 KiB
TypeScript
Raw Normal View History

2018-04-13 20:25:52 +00:00
/**
* @prettier
*/
2018-04-11 15:57:31 +00:00
import React from 'react';
2018-04-13 00:56:05 +00:00
import moment from 'moment';
import { map } from 'lodash';
2018-04-12 20:23:26 +00:00
import { AttachmentListSection } from './AttachmentListSection';
2018-04-13 00:56:05 +00:00
import { groupMessagesByDate } from './groupMessagesByDate';
2018-04-12 20:23:26 +00:00
import { Message } from './propTypes/Message';
type AttachmentType = 'media' | 'documents';
2018-04-11 15:57:31 +00:00
interface Props {
2018-04-13 00:56:05 +00:00
documents: Array<Message>;
2018-04-12 20:23:26 +00:00
i18n: (key: string, values?: Array<string>) => string;
2018-04-13 00:56:05 +00:00
media: Array<Message>;
2018-04-12 20:23:26 +00:00
}
interface State {
selectedTab: AttachmentType;
2018-04-11 15:57:31 +00:00
}
2018-04-13 00:56:05 +00:00
const MONTH_FORMAT = 'MMMM YYYY';
2018-04-12 20:23:26 +00:00
const COLOR_GREY = '#f3f3f3';
const tabStyle = {
width: '100%',
backgroundColor: COLOR_GREY,
padding: 20,
textAlign: 'center',
};
const styles = {
tabContainer: {
cursor: 'pointer',
display: 'flex',
width: '100%',
},
tab: {
default: tabStyle,
active: {
...tabStyle,
borderBottom: '2px solid #08f',
},
},
attachmentsContainer: {
padding: 20,
},
};
interface TabSelectEvent {
type: AttachmentType;
}
const Tab = ({
isSelected,
label,
onSelect,
type,
}: {
2018-04-13 20:25:52 +00:00
isSelected: boolean;
label: string;
onSelect?: (event: TabSelectEvent) => void;
type: AttachmentType;
2018-04-12 20:23:26 +00:00
}) => {
2018-04-13 20:25:52 +00:00
const handleClick = onSelect ? () => onSelect({ type }) : undefined;
2018-04-12 20:23:26 +00:00
return (
<div
style={isSelected ? styles.tab.active : styles.tab.default}
onClick={handleClick}
>
{label}
</div>
);
};
export class MediaGallery extends React.Component<Props, State> {
public state: State = {
selectedTab: 'media',
};
2018-04-11 15:57:31 +00:00
public render() {
2018-04-12 20:23:26 +00:00
const { selectedTab } = this.state;
2018-04-11 15:57:31 +00:00
return (
2018-04-12 20:23:26 +00:00
<div>
<div style={styles.tabContainer}>
<Tab
label="Media"
type="media"
isSelected={selectedTab === 'media'}
onSelect={this.handleTabSelect}
/>
<Tab
label="Documents"
type="documents"
isSelected={selectedTab === 'documents'}
onSelect={this.handleTabSelect}
/>
</div>
2018-04-13 20:25:52 +00:00
<div style={styles.attachmentsContainer}>{this.renderSections()}</div>
2018-04-12 20:23:26 +00:00
</div>
2018-04-11 15:57:31 +00:00
);
}
2018-04-12 20:23:26 +00:00
private handleTabSelect = (event: TabSelectEvent): void => {
2018-04-13 20:25:52 +00:00
this.setState({ selectedTab: event.type });
};
2018-04-13 00:56:05 +00:00
private renderSections() {
const { i18n, media, documents } = this.props;
const { selectedTab } = this.state;
const messages = selectedTab === 'media' ? media : documents;
const type = selectedTab;
if (!messages || messages.length === 0) {
// return <LoadingIndicator />;
return null;
}
const now = Date.now();
const groups = groupMessagesByDate(now, messages);
return map(groups, (annotations) => {
const first = annotations[0];
const date = moment(first.message.received_at);
const header = first.label === 'yearMonth'
? date.format(MONTH_FORMAT)
: i18n(first.label);
const groupMessages = map(annotations, 'message');
return (
<AttachmentListSection
key={header}
header={header}
i18n={i18n}
type={type}
messages={groupMessages}
/>
);
});
2018-04-12 20:23:26 +00:00
}
2018-04-11 15:57:31 +00:00
}