-
+
+ {showChat &&
+
+ }
{customLauncher ?
customLauncher(onToggleConversation) :
!fullScreenMode &&
@@ -85,6 +143,9 @@ function WidgetLayout({
closeLabel={launcherCloseLabel}
/>
}
+ {
+ imagePreview &&
+ }
);
}
diff --git a/src/components/Widget/style.scss b/src/components/Widget/style.scss
index e36ec2c96..565fea397 100644
--- a/src/components/Widget/style.scss
+++ b/src/components/Widget/style.scss
@@ -23,3 +23,7 @@
@include widget-container-fs;
}
}
+
+.rcw-previewer .rcw-message-img {
+ cursor: pointer;
+}
diff --git a/src/index.tsx b/src/index.tsx
index 2a54d2b64..4d742b506 100644
--- a/src/index.tsx
+++ b/src/index.tsx
@@ -25,6 +25,8 @@ type Props = {
launcherCloseLabel?: string,
sendButtonAlt?: string;
showTimeStamp?: boolean;
+ imagePreview?: boolean;
+ zoomStep?: number;
handleSubmit?: AnyFunction;
} & typeof defaultProps;
@@ -46,6 +48,8 @@ function ConnectedWidget({
launcherCloseLabel,
sendButtonAlt,
showTimeStamp,
+ imagePreview,
+ zoomStep,
handleSubmit
}: Props) {
return (
@@ -68,6 +72,8 @@ function ConnectedWidget({
launcherCloseLabel={launcherCloseLabel}
sendButtonAlt={sendButtonAlt}
showTimeStamp={showTimeStamp}
+ imagePreview={imagePreview}
+ zoomStep={zoomStep}
handleSubmit={handleSubmit}
/>
@@ -85,7 +91,9 @@ const defaultProps = {
launcherOpenLabel: 'Open chat',
launcherCloseLabel: 'Close chat',
sendButtonAlt: 'Send',
- showTimeStamp: true
+ showTimeStamp: true,
+ imagePreview: false,
+ zoomStep: 80,
};
ConnectedWidget.defaultProps = defaultProps;
diff --git a/src/store/actions/index.ts b/src/store/actions/index.ts
index e56d72dfe..8a12a646f 100644
--- a/src/store/actions/index.ts
+++ b/src/store/actions/index.ts
@@ -1,7 +1,7 @@
import { ElementType } from 'react';
import * as actionsTypes from './types';
-import { LinkParams } from '../types';
+import { LinkParams, ImageState } from '../types';
export function toggleChat(): actionsTypes.ToggleChat {
return {
@@ -100,3 +100,16 @@ export function markAllMessagesRead(): actionsTypes.MarkAllMessagesRead {
type: actionsTypes.MARK_ALL_READ
}
}
+
+export function openFullscreenPreview(payload: ImageState): actionsTypes.FullscreenPreviewActions {
+ return {
+ type: actionsTypes.OPEN_FULLSCREEN_PREVIEW,
+ payload
+ };
+}
+
+export function closeFullscreenPreview(): actionsTypes.FullscreenPreviewActions {
+ return {
+ type: actionsTypes.CLOSE_FULLSCREEN_PREVIEW
+ };
+}
diff --git a/src/store/actions/types.ts b/src/store/actions/types.ts
index 3358350f9..a3acc0a32 100644
--- a/src/store/actions/types.ts
+++ b/src/store/actions/types.ts
@@ -1,6 +1,6 @@
import { ElementType } from 'react';
-import { LinkParams } from '../types';
+import { LinkParams, FullscreenPreviewState } from '../types';
export const TOGGLE_CHAT = 'BEHAVIOR/TOGGLE_CHAT';
export const TOGGLE_INPUT_DISABLED = 'BEHAVIOR/TOGGLE_INPUT_DISABLED';
@@ -15,6 +15,8 @@ export const HIDE_AVATAR = 'MESSAGES/HIDE_AVATAR';
export const DELETE_MESSAGES = 'MESSAGES/DELETE_MESSAGES';
export const MARK_ALL_READ = 'MESSAGES/MARK_ALL_READ';
export const SET_QUICK_BUTTONS = 'SET_QUICK_BUTTONS';
+export const OPEN_FULLSCREEN_PREVIEW = 'FULLSCREEN/OPEN_PREVIEW';
+export const CLOSE_FULLSCREEN_PREVIEW = 'FULLSCREEN/CLOSE_PREVIEW';
export interface ToggleChat {
type: typeof TOGGLE_CHAT;
@@ -89,3 +91,14 @@ export type MessagesActions = AddUserMessage | AddResponseMessage | AddLinkSnipp
| DropMessages | HideAvatar | DeleteMessages | MarkAllMessagesRead | SetBadgeCount;
export type QuickButtonsActions = SetQuickButtons;
+
+export interface openFullscreenPreview {
+ type: typeof OPEN_FULLSCREEN_PREVIEW;
+ payload: FullscreenPreviewState
+}
+
+export interface closeFullscreenPreview {
+ type: typeof CLOSE_FULLSCREEN_PREVIEW;
+}
+
+export type FullscreenPreviewActions = openFullscreenPreview | closeFullscreenPreview;
\ No newline at end of file
diff --git a/src/store/dispatcher.ts b/src/store/dispatcher.ts
index 0d2ee5386..ca362adad 100644
--- a/src/store/dispatcher.ts
+++ b/src/store/dispatcher.ts
@@ -2,7 +2,7 @@ import { ElementType } from 'react';
import store from '.';
import * as actions from './actions';
-import { LinkParams } from './types';
+import { LinkParams, ImageState } from './types';
export function addUserMessage(text: string, id?: string) {
store.dispatch(actions.addUserMessage(text, id));
@@ -55,3 +55,11 @@ export function markAllAsRead() {
export function setBadgeCount(count: number) {
store.dispatch(actions.setBadgeCount(count));
}
+
+export function openFullscreenPreview(payload: ImageState) {
+ store.dispatch(actions.openFullscreenPreview(payload));
+}
+
+export function closeFullscreenPreview() {
+ store.dispatch(actions.closeFullscreenPreview());
+}
diff --git a/src/store/index.ts b/src/store/index.ts
index dca1fdd06..a70a40e90 100644
--- a/src/store/index.ts
+++ b/src/store/index.ts
@@ -3,6 +3,7 @@ import { createStore, combineReducers, compose } from 'redux';
import behavior from './reducers/behaviorReducer';
import messages from './reducers/messagesReducer';
import quickButtons from './reducers/quickButtonsReducer';
+import preview from './reducers/fullscreenPreviewReducer';
declare global {
interface Window {
@@ -11,6 +12,6 @@ declare global {
}
const composeEnhancers = (process.env.NODE_ENV !== 'production' && window.__REDUX_DEVTOOLS_EXTENSION_COMPOSE__) || compose;
-const reducer = combineReducers({ behavior, messages, quickButtons });
+const reducer = combineReducers({ behavior, messages, quickButtons, preview });
export default createStore(reducer, composeEnhancers());
diff --git a/src/store/reducers/fullscreenPreviewReducer.ts b/src/store/reducers/fullscreenPreviewReducer.ts
new file mode 100644
index 000000000..df8a50548
--- /dev/null
+++ b/src/store/reducers/fullscreenPreviewReducer.ts
@@ -0,0 +1,27 @@
+import { createReducer } from '../../utils/createReducer';
+import { FullscreenPreviewState, ImageState } from '../types';
+
+import {
+ OPEN_FULLSCREEN_PREVIEW,
+ CLOSE_FULLSCREEN_PREVIEW,
+ FullscreenPreviewActions
+} from '../actions/types';
+
+const initialState = {
+ src: '',
+ alt: '',
+ width: 0,
+ height: 0,
+ visible: false
+};
+
+const fullscreenPreviewReducer = {
+ [OPEN_FULLSCREEN_PREVIEW]: (state: FullscreenPreviewState, { payload }) => {
+ const { src, width, height } = payload
+ return { ...state, src, width, height, visible: true }
+ },
+
+ [CLOSE_FULLSCREEN_PREVIEW]: (state: FullscreenPreviewState) => ({ ...initialState }),
+};
+
+export default (state: FullscreenPreviewState = initialState, action: FullscreenPreviewActions) => createReducer(fullscreenPreviewReducer, state, action);
diff --git a/src/store/types.ts b/src/store/types.ts
index 71daf09ff..89ca058af 100644
--- a/src/store/types.ts
+++ b/src/store/types.ts
@@ -52,8 +52,20 @@ export interface QuickButtonsState {
quickButtons: QuickButton[];
}
+export interface ImageState {
+ src: string;
+ alt?: string;
+ width: number;
+ height: number;
+}
+
+export interface FullscreenPreviewState extends ImageState {
+ visible?: boolean;
+};
+
export interface GlobalState {
messages: MessagesState;
behavior: BehaviorState;
quickButtons: QuickButtonsState;
+ preview: FullscreenPreviewState;
}
diff --git a/src/utils/messages.ts b/src/utils/messages.ts
index f4f896bb3..65997180d 100644
--- a/src/utils/messages.ts
+++ b/src/utils/messages.ts
@@ -86,7 +86,7 @@ function scrollWithSlowMotion(target: any, scrollStart: any, scroll: number) {
raf(step);
}
-export function scrollToBottom(messagesDiv: HTMLDivElement) {
+export function scrollToBottom(messagesDiv: HTMLDivElement | null) {
if (!messagesDiv) return;
const screenHeight = messagesDiv.clientHeight;
const scrollTop = messagesDiv.scrollTop;