From 38c7fa3da6bcecbf1fa666fc585c8e9e301ca50d Mon Sep 17 00:00:00 2001 From: Ken Powers Date: Fri, 7 Feb 2020 14:07:22 -0500 Subject: [PATCH] Storybook: Basic messages and messages with reactions --- .babelrc.js | 9 +- .storybook/config.js | 75 +- .storybook/preview-head.html | 2 +- .storybook/styles.scss | 11 +- .storybook/webpack.config.js | 3 +- package.json | 3 +- styleguide.config.js | 7 + stylesheets/_modules.scss | 4 +- ts/components/PopperRootContext.tsx | 18 +- .../conversation/Message.stories.tsx | 1302 +++++++++++++++++ ts/components/conversation/Message.tsx | 14 +- ts/components/conversation/ReactionViewer.tsx | 2 +- tsconfig.json | 1 + yarn.lock | 31 + 14 files changed, 1449 insertions(+), 33 deletions(-) create mode 100644 ts/components/conversation/Message.stories.tsx diff --git a/.babelrc.js b/.babelrc.js index 0bf885695..315ad1ac0 100644 --- a/.babelrc.js +++ b/.babelrc.js @@ -1,8 +1,15 @@ module.exports = { presets: ['@babel/preset-react', '@babel/preset-typescript'], + // Detects the type of file being babel'd (either esmodule or commonjs) + sourceType: 'unambiguous', plugins: [ 'react-hot-loader/babel', 'lodash', '@babel/plugin-proposal-class-properties', - ], + // This plugin converts commonjs to esmodules which is required for + // importing commonjs modules from esmodules in storybook. As a part of + // converting to TypeScript we should use esmodules and can eventually + // remove this plugin + process.env.SIGNAL_ENV === 'storybook' && '@babel/transform-runtime', + ].filter(Boolean), }; diff --git a/.storybook/config.js b/.storybook/config.js index 9bd434504..05965ae38 100644 --- a/.storybook/config.js +++ b/.storybook/config.js @@ -1,27 +1,83 @@ import * as React from 'react'; import { addDecorator, configure } from '@storybook/react'; -import { withKnobs } from '@storybook/addon-knobs'; +import { withKnobs, boolean, optionsKnob } from '@storybook/addon-knobs'; import classnames from 'classnames'; import * as styles from './styles.scss'; import messages from '../_locales/en/messages.json'; import { I18n } from '../sticker-creator/util/i18n'; -import { ThemedProvider } from '../ts/components/PopperRootContext'; +import { ClassyProvider } from '../ts/components/PopperRootContext'; + +const optionsConfig = { + display: 'inline-radio', +}; + +const makeThemeKnob = pane => + optionsKnob( + `${pane} Pane Theme`, + { Light: '', Dark: classnames('dark-theme', styles.darkTheme) }, + '', + optionsConfig, + `${pane} Pane` + ); + +const makeDeviceThemeKnob = pane => + optionsKnob( + `${pane} Pane Device Theme`, + { Android: '', iOS: 'ios-theme' }, + '', + optionsConfig, + `${pane} Pane` + ); + +const makeModeKnob = pane => + optionsKnob( + `${pane} Pane Mode`, + { Mouse: 'mouse-mode', Keyboard: 'keyboard-mode' }, + 'mouse-mode', + optionsConfig, + `${pane} Pane` + ); addDecorator(withKnobs); addDecorator((storyFn /* , context */) => { const contents = storyFn(); + const firstPaneTheme = makeThemeKnob('First'); + const firstPaneDeviceTheme = makeDeviceThemeKnob('First'); + const firstPaneMode = makeModeKnob('First'); + + const secondPane = boolean('Second Pane Active', false, 'Second Pane'); + + const secondPaneTheme = makeThemeKnob('Second'); + const secondPaneDeviceTheme = makeDeviceThemeKnob('Second'); + const secondPaneMode = makeModeKnob('Second'); return (
-
{contents}
- +
{contents}
-
+ + {secondPane ? ( +
+ {contents} +
+ ) : null}
); }); @@ -39,4 +95,11 @@ configure(() => { /\.stories\.tsx?$/ ); stickerCreatorContext.keys().forEach(f => stickerCreatorContext(f)); + // Load main app stories + const tsComponentsContext = require.context( + '../ts/components', + true, + /\.stories.tsx?$/ + ); + tsComponentsContext.keys().forEach(f => tsComponentsContext(f)); }, module); diff --git a/.storybook/preview-head.html b/.storybook/preview-head.html index 76e0bd779..cb7b5c1bd 100644 --- a/.storybook/preview-head.html +++ b/.storybook/preview-head.html @@ -1,2 +1,2 @@ - + diff --git a/.storybook/styles.scss b/.storybook/styles.scss index 3fc8c681e..58481dfcb 100644 --- a/.storybook/styles.scss +++ b/.storybook/styles.scss @@ -1,3 +1,5 @@ +@import '../stylesheets/variables'; + .container { display: flex; flex-direction: row; @@ -9,13 +11,12 @@ .panel { flex: 1; - display: flex; - flex-direction: column; - justify-content: space-around; - align-items: center; padding: 16px; + height: 100%; + overflow: auto; } .dark-theme { - background-color: #17191d; + background-color: $color-gray-95; + color: $color-gray-05; } diff --git a/.storybook/webpack.config.js b/.storybook/webpack.config.js index e4465f9da..268602c5e 100644 --- a/.storybook/webpack.config.js +++ b/.storybook/webpack.config.js @@ -6,8 +6,9 @@ module.exports = ({ config }) => { config.module.rules.unshift( { - test: /\.tsx?$/, + test: /\.[jt]sx?$/, loader: 'babel-loader', + exclude: /node_modules/, }, { test: /\.scss$/, diff --git a/package.json b/package.json index 8d1b20f1e..beec2bd2a 100644 --- a/package.json +++ b/package.json @@ -46,7 +46,7 @@ "dev:grunt": "yarn grunt dev", "dev:webpack": "NODE_ENV=development webpack-dev-server --hot", "dev:typed-scss": "yarn build:typed-scss -w", - "dev:storybook": "start-storybook -p 6006 -s ./", + "dev:storybook": "SIGNAL_ENV=storybook start-storybook -p 6006 -s ./", "build": "run-s --print-label build:grunt build:typed-scss build:webpack build:release", "build:dev": "run-s --print-label build:grunt build:typed-scss build:webpack", "build:grunt": "yarn grunt", @@ -148,6 +148,7 @@ "devDependencies": { "@babel/core": "7.7.7", "@babel/plugin-proposal-class-properties": "7.7.4", + "@babel/plugin-transform-runtime": "^7.8.3", "@babel/preset-react": "7.7.4", "@babel/preset-typescript": "7.7.7", "@storybook/addon-actions": "5.1.11", diff --git a/styleguide.config.js b/styleguide.config.js index 7185f36fc..4d670f5f1 100644 --- a/styleguide.config.js +++ b/styleguide.config.js @@ -10,36 +10,43 @@ module.exports = { name: 'Components', description: '', components: 'ts/components/[^_]*.tsx', + ignore: ['**/*.stories.*'], }, { name: 'Conversation', description: 'Everything necessary to render a conversation', components: 'ts/components/conversation/[^_]*.tsx', + ignore: ['**/*.stories.*'], }, { name: 'Emoji', description: 'All components related to emojis', components: 'ts/components/emoji/[^_]*.tsx', + ignore: ['**/*.stories.*'], }, { name: 'Media Gallery', description: 'Display media and documents in a conversation', components: 'ts/components/conversation/media-gallery/[^_]*.tsx', + ignore: ['**/*.stories.*'], }, { name: 'Stickers', description: 'All components related to stickers', components: 'ts/components/stickers/[^_]*.tsx', + ignore: ['**/*.stories.*'], }, { name: 'Utility', description: 'Utility components used across the application', components: 'ts/components/utility/[^_]*.tsx', + ignore: ['**/*.stories.*'], }, { name: 'Test', description: 'Components only used for testing', components: 'ts/styleguide/**/*.tsx', + ignore: ['**/*.stories.*'], }, ], context: { diff --git a/stylesheets/_modules.scss b/stylesheets/_modules.scss index 825a0ca96..12d958628 100644 --- a/stylesheets/_modules.scss +++ b/stylesheets/_modules.scss @@ -6724,7 +6724,9 @@ button.module-image__border-overlay:focus { } .module-emoji { - display: block; + display: flex; + justify-content: center; + align-items: center; color: transparent; font-family: auto; diff --git a/ts/components/PopperRootContext.tsx b/ts/components/PopperRootContext.tsx index 2a58014cf..4eb0d75c4 100644 --- a/ts/components/PopperRootContext.tsx +++ b/ts/components/PopperRootContext.tsx @@ -1,12 +1,12 @@ import * as React from 'react'; -const makeApi = (themes?: Array) => ({ +const makeApi = (classes?: Array) => ({ createRoot: () => { const div = document.createElement('div'); - if (themes) { - themes.forEach(theme => { - div.classList.add(`${theme}-theme`); + if (classes) { + classes.forEach(theme => { + div.classList.add(theme); }); } @@ -21,16 +21,16 @@ const makeApi = (themes?: Array) => ({ export const PopperRootContext = React.createContext(makeApi()); -export type ThemedProviderProps = { - themes?: Array; +export type ClassyProviderProps = { + classes?: Array; children?: React.ReactChildren; }; -export const ThemedProvider: React.FunctionComponent = ({ - themes, +export const ClassyProvider: React.FunctionComponent = ({ + classes, children, }) => { - const api = React.useMemo(() => makeApi(themes), [themes]); + const api = React.useMemo(() => makeApi(classes), [classes]); return ( diff --git a/ts/components/conversation/Message.stories.tsx b/ts/components/conversation/Message.stories.tsx new file mode 100644 index 000000000..f94e33abf --- /dev/null +++ b/ts/components/conversation/Message.stories.tsx @@ -0,0 +1,1302 @@ +import * as React from 'react'; + +import { storiesOf } from '@storybook/react'; +import { action } from '@storybook/addon-actions'; + +// @ts-ignore +import { setup as setupI18n } from '../../../js/modules/i18n'; +// @ts-ignore +import enMessages from '../../../_locales/en/messages.json'; + +import { Message, PropsActions, PropsData, PropsHousekeeping } from './Message'; + +const book = storiesOf('Components/Conversation/Message', module); + +const baseDataProps: Pick< + PropsData, + | 'id' + | 'conversationId' + | 'interactionMode' + | 'conversationType' + | 'previews' + | 'timestamp' + | 'authorPhoneNumber' +> = { + id: 'asdf', + conversationId: 'asdf', + interactionMode: 'mouse', + conversationType: 'direct', + previews: [], + timestamp: Date.now(), + authorPhoneNumber: '(202) 555-2001', +}; + +type MessageStory = [ + string, + Array<{ + makeDataProps: () => PropsData; + makeActionProps?: () => PropsActions; + makeHouseKeepingProps?: () => PropsHousekeeping; + title?: string; + }> +]; + +const makeDefaultActionProps = (): PropsActions => ({ + clearSelectedMessage: action('clearSelectedMessage'), + reactToMessage: action('reactToMessage'), + replyToMessage: action('replyToMessage'), + retrySend: action('retrySend'), + deleteMessage: action('deleteMessage'), + showMessageDetail: action('showMessageDetail'), + openConversation: action('openConversation'), + showContactDetail: action('showContactDetail'), + showVisualAttachment: action('showVisualAttachment'), + downloadAttachment: action('downloadAttachment'), + displayTapToViewMessage: action('displayTapToViewMessage'), + openLink: action('openLink'), + scrollToQuotedMessage: action('scrollToQuotedMessage'), + selectMessage: action('selectMessage'), + showExpiredIncomingTapToViewToast: action( + 'showExpiredIncomingTapToViewToast' + ), + showExpiredOutgoingTapToViewToast: action( + 'showExpiredOutgoingTapToViewToast' + ), +}); + +const makeDefaultHousekeepingProps = (): PropsHousekeeping => ({ + i18n: setupI18n('en', enMessages), +}); + +const stories: Array = [ + [ + 'Plain Message', + [ + { + makeDataProps: () => ({ + ...baseDataProps, + direction: 'incoming', + authorColor: 'green', + text: '🔥', + }), + }, + { + makeDataProps: () => ({ + ...baseDataProps, + direction: 'incoming', + authorColor: 'green', + text: 'Hello there from the new world! http://somewhere.com', + }), + }, + { + makeDataProps: () => ({ + ...baseDataProps, + direction: 'incoming', + authorColor: 'red', + text: 'Hello there from the new world!', + }), + makeHouseKeepingProps: () => ({ + ...makeDefaultHousekeepingProps(), + collapseMetadata: true, + }), + }, + { + makeDataProps: () => ({ + ...baseDataProps, + direction: 'incoming', + authorColor: 'gray', + text: + 'Hello there from the new world! And this is multiple lines of text. Lines and lines and lines.', + }), + }, + { + makeDataProps: () => ({ + ...baseDataProps, + direction: 'incoming', + authorColor: 'deep_orange', + text: + 'Hello there from the new world! And this is multiple lines of text. Lines and lines and lines.', + }), + makeHouseKeepingProps: () => ({ + ...makeDefaultHousekeepingProps(), + collapseMetadata: true, + }), + }, + { + makeDataProps: () => ({ + ...baseDataProps, + direction: 'outgoing', + status: 'sent', + authorColor: 'pink', + text: '🔥', + }), + }, + { + makeDataProps: () => ({ + ...baseDataProps, + direction: 'outgoing', + status: 'read', + authorColor: 'pink', + text: 'Hello there from the new world! http://somewhere.com', + }), + }, + { + makeDataProps: () => ({ + ...baseDataProps, + direction: 'outgoing', + status: 'sent', + text: 'Hello there from the new world! 🔥', + }), + makeHouseKeepingProps: () => ({ + ...makeDefaultHousekeepingProps(), + collapseMetadata: true, + }), + }, + { + makeDataProps: () => ({ + ...baseDataProps, + direction: 'outgoing', + status: 'sent', + authorColor: 'blue', + text: + 'Hello there from the new world! And this is multiple lines of text. Lines and lines and lines.', + }), + makeHouseKeepingProps: () => ({ + ...makeDefaultHousekeepingProps(), + collapseMetadata: true, + }), + }, + ], + ], + [ + 'Reactions', + [ + ...([ + { + title: 'Single Reaction (not me)', + reactions: [ + { + emoji: '👍', + from: { + id: '+14155552671', + phoneNumber: '+14155552671', + name: 'Jack Sparrow', + }, + }, + ], + }, + { + title: 'Two Reactions (neither me)', + reactions: [ + { + emoji: '👍', + from: { + id: '+14155552671', + phoneNumber: '+14155552671', + name: 'Jack Sparrow', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552672', + phoneNumber: '+14155552672', + profileName: 'Davy Jones', + }, + }, + ], + }, + { + title: 'Three Reactions (none me)', + reactions: [ + { + emoji: '👍', + from: { + id: '+14155552671', + phoneNumber: '+14155552671', + name: 'Jack Sparrow', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552672', + phoneNumber: '+14155552672', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😮', + from: { + id: '+14155552673', + phoneNumber: '+14155552673', + profileName: 'Joel Ferrari', + }, + }, + ], + }, + { + title: 'Six Reactions (none me)', + reactions: [ + { + emoji: '👍', + from: { + id: '+14155552671', + phoneNumber: '+14155552671', + name: 'Jack Sparrow', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552672', + phoneNumber: '+14155552672', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😮', + from: { + id: '+14155552673', + phoneNumber: '+14155552673', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😡', + from: { + id: '+14155552674', + phoneNumber: '+14155552674', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👎', + from: { + id: '+14155552675', + phoneNumber: '+14155552675', + name: 'Amelia Briggs', + }, + }, + { + emoji: '❤️', + from: { + id: '+14155552676', + phoneNumber: '+14155552676', + name: 'Amelia Briggs', + }, + }, + ], + }, + { + title: 'Four Reactions, Three Same (none me)', + reactions: [ + { + emoji: '👍', + from: { + id: '+14155552671', + phoneNumber: '+14155552671', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552672', + phoneNumber: '+14155552672', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552673', + phoneNumber: '+14155552673', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552674', + phoneNumber: '+14155552674', + name: 'Amelia Briggs', + }, + }, + ], + }, + { + title: 'Seven Reactions, Three Same, One Different (none me)', + reactions: [ + { + emoji: '👍', + from: { + id: '+14155552671', + phoneNumber: '+14155552671', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552672', + phoneNumber: '+14155552672', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552673', + phoneNumber: '+14155552673', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552674', + phoneNumber: '+14155552674', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😡', + from: { + id: '+14155552675', + phoneNumber: '+14155552675', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👎', + from: { + id: '+14155552676', + phoneNumber: '+14155552676', + name: 'Amelia Briggs', + }, + }, + { + emoji: '❤️', + from: { + id: '+14155552678', + phoneNumber: '+14155552678', + name: 'Amelia Briggs', + }, + }, + ], + }, + { + title: 'Three Reations, All Same (none me)', + reactions: [ + { + emoji: '👍', + from: { + id: '+14155552671', + phoneNumber: '+14155552671', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552672', + phoneNumber: '+14155552672', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552673', + phoneNumber: '+14155552673', + name: 'Amelia Briggs', + }, + }, + ], + }, + { + title: 'Six Reactions, Two Kinds (none me)', + reactions: [ + { + emoji: '👍', + from: { + id: '+14155552671', + phoneNumber: '+14155552671', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552672', + phoneNumber: '+14155552672', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552673', + phoneNumber: '+14155552673', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552674', + phoneNumber: '+14155552674', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552675', + phoneNumber: '+14155552675', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552676', + phoneNumber: '+14155552676', + name: 'Amelia Briggs', + }, + }, + ], + }, + { + title: 'Nine Reactions, Three Kinds (none me)', + reactions: [ + { + emoji: '👍', + from: { + id: '+14155552671', + phoneNumber: '+14155552671', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552672', + phoneNumber: '+14155552672', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552673', + phoneNumber: '+14155552673', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552674', + phoneNumber: '+14155552674', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552675', + phoneNumber: '+14155552675', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552676', + phoneNumber: '+14155552676', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😮', + from: { + id: '+14155552677', + phoneNumber: '+14155552677', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😮', + from: { + id: '+14155552678', + phoneNumber: '+14155552678', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😮', + from: { + id: '+14155552679', + phoneNumber: '+14155552679', + name: 'Amelia Briggs', + }, + }, + ], + }, + { + title: 'Short Message, Seven Reactions (none me)', + short: true, + reactions: [ + { + emoji: '👍', + from: { + id: '+14155552671', + phoneNumber: '+14155552671', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552672', + phoneNumber: '+14155552672', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552673', + phoneNumber: '+14155552673', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552674', + phoneNumber: '+14155552674', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😡', + from: { + id: '+14155552675', + phoneNumber: '+14155552675', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👎', + from: { + id: '+14155552676', + phoneNumber: '+14155552676', + name: 'Amelia Briggs', + }, + }, + { + emoji: '❤️', + from: { + id: '+14155552677', + phoneNumber: '+14155552677', + name: 'Amelia Briggs', + }, + }, + ], + }, + { + title: 'Short Message, Six Reactions (none me)', + short: true, + reactions: [ + { + emoji: '👍', + from: { + id: '+14155552671', + phoneNumber: '+14155552671', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552672', + phoneNumber: '+14155552672', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552673', + phoneNumber: '+14155552673', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552674', + phoneNumber: '+14155552674', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552675', + phoneNumber: '+14155552675', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552676', + phoneNumber: '+14155552676', + name: 'Amelia Briggs', + }, + }, + ], + }, + { + title: 'Short Message, No Reactions', + short: true, + reactions: [], + }, + { + title: 'Nine Reactions (me in second group)', + reactions: [ + { + emoji: '👍', + from: { + isMe: true, + id: '+14155552671', + phoneNumber: '+14155552671', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552672', + phoneNumber: '+14155552672', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552673', + phoneNumber: '+14155552673', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552674', + phoneNumber: '+14155552674', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552675', + phoneNumber: '+14155552675', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552676', + phoneNumber: '+14155552676', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😡', + from: { + id: '+14155552677', + phoneNumber: '+14155552677', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👎', + from: { + id: '+14155552678', + phoneNumber: '+14155552678', + name: 'Amelia Briggs', + }, + }, + { + emoji: '❤️', + from: { + id: '+14155552679', + phoneNumber: '+14155552679', + name: 'Amelia Briggs', + }, + }, + ], + }, + { + title: 'Nine Reactions (me in first group)', + reactions: [ + { + emoji: '👍', + from: { + id: '+14155552671', + phoneNumber: '+14155552671', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552672', + phoneNumber: '+14155552672', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552673', + phoneNumber: '+14155552673', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + isMe: true, + id: '+14155552674', + phoneNumber: '+14155552674', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552675', + phoneNumber: '+14155552675', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552676', + phoneNumber: '+14155552676', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😡', + from: { + id: '+14155552677', + phoneNumber: '+14155552677', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👎', + from: { + id: '+14155552678', + phoneNumber: '+14155552678', + name: 'Amelia Briggs', + }, + }, + { + emoji: '❤️', + from: { + id: '+14155552679', + phoneNumber: '+14155552679', + name: 'Amelia Briggs', + }, + }, + ], + }, + { + title: 'Nine Reactions (me in third group)', + reactions: [ + { + emoji: '👍', + from: { + id: '+14155552671', + phoneNumber: '+14155552671', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552672', + phoneNumber: '+14155552672', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552673', + phoneNumber: '+14155552673', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552674', + phoneNumber: '+14155552674', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552675', + phoneNumber: '+14155552675', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552676', + phoneNumber: '+14155552676', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😡', + from: { + isMe: true, + id: '+14155552677', + phoneNumber: '+14155552677', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👎', + from: { + id: '+14155552678', + phoneNumber: '+14155552678', + name: 'Amelia Briggs', + }, + }, + { + emoji: '❤️', + from: { + id: '+14155552679', + phoneNumber: '+14155552679', + name: 'Amelia Briggs', + }, + }, + ], + }, + { + title: 'Outgoing Message, One Reaction (not me)', + outgoing: true, + reactions: [ + { + emoji: '😂', + from: { + id: '+14155552671', + phoneNumber: '+14155552671', + name: 'Amelia Briggs', + }, + }, + ], + }, + { + title: 'Outgoing Message, Nine Reactions (none me)', + outgoing: true, + reactions: [ + { + emoji: '👍', + from: { + id: '+14155552671', + phoneNumber: '+14155552671', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552672', + phoneNumber: '+14155552672', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552673', + phoneNumber: '+14155552673', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552674', + phoneNumber: '+14155552674', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552675', + phoneNumber: '+14155552675', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552676', + phoneNumber: '+14155552676', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😡', + from: { + id: '+14155552677', + phoneNumber: '+14155552677', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👎', + from: { + id: '+14155552678', + phoneNumber: '+14155552678', + name: 'Amelia Briggs', + }, + }, + { + emoji: '❤️', + from: { + id: '+14155552679', + phoneNumber: '+14155552679', + name: 'Amelia Briggs', + }, + }, + ], + }, + { + title: 'Outgoing Message, Nine Reactions (me in first group)', + outgoing: true, + reactions: [ + { + emoji: '👍', + from: { + id: '+14155552671', + phoneNumber: '+14155552671', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552672', + phoneNumber: '+14155552672', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552673', + phoneNumber: '+14155552673', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + isMe: true, + id: '+14155552674', + phoneNumber: '+14155552674', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552675', + phoneNumber: '+14155552675', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552676', + phoneNumber: '+14155552676', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😡', + from: { + id: '+14155552677', + phoneNumber: '+14155552677', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👎', + from: { + id: '+14155552678', + phoneNumber: '+14155552678', + name: 'Amelia Briggs', + }, + }, + { + emoji: '❤️', + from: { + id: '+14155552679', + phoneNumber: '+14155552679', + name: 'Amelia Briggs', + }, + }, + ], + }, + { + title: 'Outgoing Short Message, Nine Reactions (none me)', + outgoing: true, + short: true, + reactions: [ + { + emoji: '👍', + from: { + id: '+14155552671', + phoneNumber: '+14155552671', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552672', + phoneNumber: '+14155552672', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552673', + phoneNumber: '+14155552673', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552674', + phoneNumber: '+14155552674', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552675', + phoneNumber: '+14155552675', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552676', + phoneNumber: '+14155552676', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😡', + from: { + id: '+14155552677', + phoneNumber: '+14155552677', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👎', + from: { + id: '+14155552678', + phoneNumber: '+14155552678', + name: 'Amelia Briggs', + }, + }, + { + emoji: '❤️', + from: { + id: '+14155552679', + phoneNumber: '+14155552679', + name: 'Amelia Briggs', + }, + }, + ], + }, + { + title: 'Outgoing Short Message, Six Reactions, Two Groups (none me)', + outgoing: true, + short: true, + reactions: [ + { + emoji: '👍', + from: { + id: '+14155552671', + phoneNumber: '+14155552671', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552672', + phoneNumber: '+14155552672', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552673', + phoneNumber: '+14155552673', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552674', + phoneNumber: '+14155552674', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552675', + phoneNumber: '+14155552675', + name: 'Amelia Briggs', + }, + }, + { + emoji: '😂', + from: { + id: '+14155552676', + phoneNumber: '+14155552676', + name: 'Amelia Briggs', + }, + }, + ], + }, + { + title: 'Outgoing Short Message, Three Reactions, All Same (none me)', + outgoing: true, + short: true, + reactions: [ + { + emoji: '👍', + from: { + id: '+14155552671', + phoneNumber: '+14155552671', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552672', + phoneNumber: '+14155552672', + name: 'Amelia Briggs', + }, + }, + { + emoji: '👍', + from: { + id: '+14155552673', + phoneNumber: '+14155552673', + name: 'Amelia Briggs', + }, + }, + ], + }, + ] as Array<{ + outgoing: boolean; + short: boolean; + reactions: PropsData['reactions']; + title?: string; + }>).map(spec => ({ + title: spec.title, + makeDataProps: () => ({ + ...baseDataProps, + // tsc disagrees with tslint, I favor safety (tsc) + // tslint:disable-next-line no-unnecessary-type-assertion + direction: (spec.outgoing + ? 'outgoing' + : 'incoming') as PropsData['direction'], + text: spec.short + ? 'hahaha' + : "I'd like to order one large phone with extra phones please. cell phone, no no no rotary... and payphone on half.", + reactions: spec.reactions + ? spec.reactions.map((re, i) => ({ + ...re, + timestamp: i, + })) + : [], + }), + })), + ], + ], +]; + +stories.forEach(([chapterTitle, propsArr]) => + book.add(chapterTitle, () => + propsArr.map( + ( + { + title, + makeDataProps, + makeActionProps = makeDefaultActionProps, + makeHouseKeepingProps = makeDefaultHousekeepingProps, + }, + i + ) => { + const dataProps = makeDataProps(); + const outgoing = dataProps.direction === 'outgoing'; + + return ( + <> + {title ? ( +

+ {title} +

+ ) : null} +
+ +
+ + ); + } + ) + ) +); diff --git a/ts/components/conversation/Message.tsx b/ts/components/conversation/Message.tsx index 24768c081..702848010 100644 --- a/ts/components/conversation/Message.tsx +++ b/ts/components/conversation/Message.tsx @@ -65,9 +65,9 @@ export type PropsData = { conversationId: string; text?: string; textPending?: boolean; - isSticker: boolean; - isSelected: boolean; - isSelectedCounter: number; + isSticker?: boolean; + isSelected?: boolean; + isSelectedCounter?: number; interactionMode: 'mouse' | 'keyboard'; direction: 'incoming' | 'outgoing'; timestamp: number; @@ -94,7 +94,7 @@ export type PropsData = { }; previews: Array; authorAvatarPath?: string; - isExpired: boolean; + isExpired?: boolean; isTapToView?: boolean; isTapToViewExpired?: boolean; @@ -107,7 +107,7 @@ export type PropsData = { selectedReaction?: string; }; -type PropsHousekeeping = { +export type PropsHousekeeping = { i18n: LocalizerType; disableMenu?: boolean; disableScroll?: boolean; @@ -158,8 +158,8 @@ interface State { expired: boolean; imageBroken: boolean; - isSelected: boolean; - prevSelectedCounter: number; + isSelected?: boolean; + prevSelectedCounter?: number; pickedReaction?: string; reactionViewerRoot: HTMLDivElement | null; diff --git a/ts/components/conversation/ReactionViewer.tsx b/ts/components/conversation/ReactionViewer.tsx index 80e93152f..52c61b01b 100644 --- a/ts/components/conversation/ReactionViewer.tsx +++ b/ts/components/conversation/ReactionViewer.tsx @@ -101,7 +101,7 @@ export const ReactionViewer = React.forwardRef( return (
- {...renderedEmojis + {renderedEmojis .filter(e => e === 'all' || Boolean(grouped[e])) .map((cat, index) => { const re = grouped[cat] || reactions; diff --git a/tsconfig.json b/tsconfig.json index d9680f2be..471083a62 100644 --- a/tsconfig.json +++ b/tsconfig.json @@ -33,6 +33,7 @@ // Module Resolution Options "moduleResolution": "node", // Specify module resolution strategy: 'node' (Node.js) or 'classic' (TypeScript pre-1.6). + "resolveJsonModule": true, // "baseUrl": "./", // Base directory to resolve non-absolute module names. // "paths": {}, // A series of entries which re-map imports to lookup locations relative to the 'baseUrl'. // "rootDirs": [], // List of root folders whose combined content represents the structure of the project at runtime. diff --git a/yarn.lock b/yarn.lock index 288d92c55..9f71d638d 100644 --- a/yarn.lock +++ b/yarn.lock @@ -226,6 +226,13 @@ dependencies: "@babel/types" "^7.0.0" +"@babel/helper-module-imports@^7.8.3": + version "7.8.3" + resolved "https://registry.yarnpkg.com/@babel/helper-module-imports/-/helper-module-imports-7.8.3.tgz#7fe39589b39c016331b6b8c3f441e8f0b1419498" + integrity sha512-R0Bx3jippsbAEtzkpZ/6FIiuzOURPcMjHp+Z6xPe6DtApDJx+w7UYyOLanZqO8+wKR9G10s/FmHXvxaMd9s6Kg== + dependencies: + "@babel/types" "^7.8.3" + "@babel/helper-module-transforms@^7.1.0", "@babel/helper-module-transforms@^7.4.4": version "7.5.5" resolved "https://registry.yarnpkg.com/@babel/helper-module-transforms/-/helper-module-transforms-7.5.5.tgz#f84ff8a09038dcbca1fd4355661a500937165b4a" @@ -257,6 +264,11 @@ resolved "https://registry.yarnpkg.com/@babel/helper-plugin-utils/-/helper-plugin-utils-7.0.0.tgz#bbb3fbee98661c569034237cc03967ba99b4f250" integrity sha512-CYAOUCARwExnEixLdB6sDm2dIJ/YgEAKDM1MOeMeZu9Ld/bDgVo8aiWrXwcY7OBh+1Ea2uUcVRcxKk0GJvW7QA== +"@babel/helper-plugin-utils@^7.8.3": + version "7.8.3" + resolved "https://registry.yarnpkg.com/@babel/helper-plugin-utils/-/helper-plugin-utils-7.8.3.tgz#9ea293be19babc0f52ff8ca88b34c3611b208670" + integrity sha512-j+fq49Xds2smCUNYmEHF9kGNkhbet6yVIBp4e6oeQpH1RUs/Ir06xUKzDjDkGcaaokPiTNs2JBWHjaE4csUkZQ== + "@babel/helper-regex@^7.0.0", "@babel/helper-regex@^7.4.4": version "7.5.5" resolved "https://registry.yarnpkg.com/@babel/helper-regex/-/helper-regex-7.5.5.tgz#0aa6824f7100a2e0e89c1527c23936c152cab351" @@ -811,6 +823,16 @@ resolve "^1.8.1" semver "^5.5.1" +"@babel/plugin-transform-runtime@^7.8.3": + version "7.8.3" + resolved "https://registry.yarnpkg.com/@babel/plugin-transform-runtime/-/plugin-transform-runtime-7.8.3.tgz#c0153bc0a5375ebc1f1591cb7eea223adea9f169" + integrity sha512-/vqUt5Yh+cgPZXXjmaG9NT8aVfThKk7G4OqkVhrXqwsC5soMn/qTCxs36rZ2QFhpfTJcjw4SNDIZ4RUb8OL4jQ== + dependencies: + "@babel/helper-module-imports" "^7.8.3" + "@babel/helper-plugin-utils" "^7.8.3" + resolve "^1.8.1" + semver "^5.5.1" + "@babel/plugin-transform-shorthand-properties@^7.2.0": version "7.2.0" resolved "https://registry.yarnpkg.com/@babel/plugin-transform-shorthand-properties/-/plugin-transform-shorthand-properties-7.2.0.tgz#6333aee2f8d6ee7e28615457298934a3b46198f0" @@ -1071,6 +1093,15 @@ lodash "^4.17.13" to-fast-properties "^2.0.0" +"@babel/types@^7.8.3": + version "7.8.3" + resolved "https://registry.yarnpkg.com/@babel/types/-/types-7.8.3.tgz#5a383dffa5416db1b73dedffd311ffd0788fb31c" + integrity sha512-jBD+G8+LWpMBBWvVcdr4QysjUE4mU/syrhN17o1u3gx0/WzJB1kwiVZAXRtWbsIPOwW8pF/YJV5+nmetPzepXg== + dependencies: + esutils "^2.0.2" + lodash "^4.17.13" + to-fast-properties "^2.0.0" + "@develar/schema-utils@~2.1.0": version "2.1.0" resolved "https://registry.yarnpkg.com/@develar/schema-utils/-/schema-utils-2.1.0.tgz#eceb1695bfbed6f6bb84666d5d3abe5e1fd54e17"