import React from 'react'; import { SessionIconButton, SessionIconSize, SessionIconType } from './icon'; import { Avatar } from '../Avatar'; import { SessionButton, SessionButtonColor, SessionButtonType } from './SessionButton'; import { MediaGallery } from '../conversation/media-gallery/MediaGallery'; import _ from 'lodash'; interface Props { id: string; name: string; memberCount: number; description: string; avatarPath: string; onGoBack: () => void; onInviteFriends: () => void; onLeaveGroup: () => void; } export class SessionChannelSettings extends React.Component { public constructor(props: Props) { super(props); this.state = { documents: Array(), media: Array(), onItemClick: undefined, }; } public componentWillMount() { this.getMediaGalleryProps().then(({ documents, media, onItemClick }) => { this.setState({ documents, media, onItemClick, }); }).ignore(); } public async getMediaGalleryProps() { // We fetch more documents than media as they don’t require to be loaded // into memory right away. Revisit this once we have infinite scrolling: const DEFAULT_MEDIA_FETCH_COUNT = 50; const DEFAULT_DOCUMENTS_FETCH_COUNT = 150; const conversationId = this.props.id; const rawMedia = await window.Signal.Data.getMessagesWithVisualMediaAttachments( conversationId, { limit: DEFAULT_MEDIA_FETCH_COUNT, MessageCollection: window.Whisper.MessageCollection, } ); const rawDocuments = await window.Signal.Data.getMessagesWithFileAttachments( conversationId, { limit: DEFAULT_DOCUMENTS_FETCH_COUNT, MessageCollection: window.Whisper.MessageCollection, } ); // First we upgrade these messages to ensure that they have thumbnails const max = rawMedia.length; for (let i = 0; i < max; i += 1) { const message = rawMedia[i]; const { schemaVersion } = message; if (schemaVersion < message.VERSION_NEEDED_FOR_DISPLAY) { // Yep, we really do want to wait for each of these // eslint-disable-next-line no-await-in-loop rawMedia[i] = await window.Signal.Migrations.upgradeMessageSchema(message); // eslint-disable-next-line no-await-in-loop await window.Signal.Data.saveMessage(rawMedia[i], { Message: window.Whisper.Message, }); } } // tslint:disable-next-line: underscore-consistent-invocation const media = _.flatten( rawMedia.map((message: { attachments: any }) => { const { attachments } = message; return (attachments || []) .filter( (attachment: { thumbnail: any; pending: any; error: any }) => attachment.thumbnail && !attachment.pending && !attachment.error ) .map((attachment: { path?: any; contentType?: any; thumbnail?: any }, index: any) => { const { thumbnail } = attachment; return { objectURL: window.Signal.Migrations.getAbsoluteAttachmentPath(attachment.path), thumbnailObjectUrl: thumbnail ? window.Signal.Migrations.getAbsoluteAttachmentPath(thumbnail.path) : null, contentType: attachment.contentType, index, attachment, message, }; }); }) ); // Unlike visual media, only one non-image attachment is supported const documents = rawDocuments.map((message: { attachments: Array }) => { const attachments = message.attachments || []; const attachment = attachments[0]; return { contentType: attachment.contentType, index: 0, attachment, message, }; }); const saveAttachment = async ({ attachment, message }: any = {}) => { const timestamp = message.received_at; window.Signal.Types.Attachment.save({ attachment, document, getAbsolutePath: window.Signal.Migrations.getAbsoluteAttachmentPath, timestamp, }); }; const onItemClick = async ({ message, attachment, type } : any) => { switch (type) { case 'documents': case 'media': { saveAttachment({ message, attachment }).ignore(); break; } /*case 'media': { const selectedIndex = media.findIndex( mediaMessage => mediaMessage.attachment.path === attachment.path ); this.lightboxGalleryView = new Whisper.ReactWrapperView({ className: 'lightbox-wrapper', Component: Signal.Components.LightboxGallery, props: { media, onSave: saveAttachment, selectedIndex, }, onClose: () => Signal.Backbone.Views.Lightbox.hide(), }); Signal.Backbone.Views.Lightbox.show(this.lightboxGalleryView.el); break; }*/ default: throw new TypeError(`Unknown attachment type: '${type}'`); } }; return { documents, media, onItemClick, }; } public render() { const { memberCount, name, onLeaveGroup } = this.props; const { documents, media, onItemClick } = this.state; return (
{this.renderHeader()}

{name}

{memberCount &&
{window.i18n('members', memberCount)}
}
{window.i18n('notifications')}
{window.i18n('disappearingMessages')}
); } private renderHeader() { const { id, onGoBack, onInviteFriends, avatarPath } = this.props; return (
); } }