@azure/communication-react 1.4.2-alpha-202211240014.0 → 1.4.2-alpha-202211260013.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -2,5 +2,5 @@
2
2
  // Copyright (c) Microsoft Corporation.
3
3
  // Licensed under the MIT license.
4
4
  // GENERATED FILE. DO NOT EDIT MANUALLY.
5
- module.exports = '1.4.2-alpha-202211240014.0';
5
+ module.exports = '1.4.2-alpha-202211260013.0';
6
6
  //# sourceMappingURL=telemetryVersion.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"telemetryVersion.js","sourceRoot":"","sources":["../../../../../acs-ui-common/src/telemetryVersion.js"],"names":[],"mappings":";AAAA,uCAAuC;AACvC,kCAAkC;AAElC,wCAAwC;AAExC,MAAM,CAAC,OAAO,GAAG,4BAA4B,CAAC","sourcesContent":["// Copyright (c) Microsoft Corporation.\n// Licensed under the MIT license.\n\n// GENERATED FILE. DO NOT EDIT MANUALLY.\n\nmodule.exports = '1.4.2-alpha-202211240014.0';\n"]}
1
+ {"version":3,"file":"telemetryVersion.js","sourceRoot":"","sources":["../../../../../acs-ui-common/src/telemetryVersion.js"],"names":[],"mappings":";AAAA,uCAAuC;AACvC,kCAAkC;AAElC,wCAAwC;AAExC,MAAM,CAAC,OAAO,GAAG,4BAA4B,CAAC","sourcesContent":["// Copyright (c) Microsoft Corporation.\n// Licensed under the MIT license.\n\n// GENERATED FILE. DO NOT EDIT MANUALLY.\n\nmodule.exports = '1.4.2-alpha-202211260013.0';\n"]}
@@ -9,7 +9,7 @@ var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, ge
9
9
  step((generator = generator.apply(thisArg, _arguments || [])).next());
10
10
  });
11
11
  };
12
- import React, { useEffect, useCallback } from 'react';
12
+ import React, { useEffect } from 'react';
13
13
  import { IconButton } from '@fluentui/react';
14
14
  import { concatStyleSets, DefaultButton, FocusZone, mergeStyles, Stack, Text, TextField, useTheme } from '@fluentui/react';
15
15
  import { useState } from 'react';
@@ -50,14 +50,17 @@ const DialpadButton = (props) => {
50
50
  var _a, _b, _c, _d;
51
51
  const theme = useTheme();
52
52
  const { digit, index, onClick, onLongPress, isMobile = false } = props;
53
- const clickFunction = useCallback(() => __awaiter(void 0, void 0, void 0, function* () {
54
- onClick(digit, index);
55
- }), [digit, index, onClick]);
56
- const longPressFunction = useCallback(() => __awaiter(void 0, void 0, void 0, function* () {
57
- onLongPress(digit, index);
58
- }), [digit, index, onLongPress]);
59
- const { handlers } = useLongPress(clickFunction, longPressFunction, isMobile);
60
- return (React.createElement(DefaultButton, Object.assign({ "data-test-id": `dialpad-button-${props.index}`, styles: concatStyleSets(buttonStyles(theme), (_a = props.styles) === null || _a === void 0 ? void 0 : _a.button) }, handlers),
53
+ const useLongPressProps = React.useMemo(() => ({
54
+ onClick: () => __awaiter(void 0, void 0, void 0, function* () {
55
+ onClick(digit, index);
56
+ }),
57
+ onLongPress: () => __awaiter(void 0, void 0, void 0, function* () {
58
+ onLongPress(digit, index);
59
+ }),
60
+ touchEventsOnly: isMobile
61
+ }), [digit, index, isMobile, onClick, onLongPress]);
62
+ const longPressHandlers = useLongPress(useLongPressProps);
63
+ return (React.createElement(DefaultButton, Object.assign({ "data-test-id": `dialpad-button-${props.index}`, styles: concatStyleSets(buttonStyles(theme), (_a = props.styles) === null || _a === void 0 ? void 0 : _a.button) }, longPressHandlers),
61
64
  React.createElement(Stack, null,
62
65
  React.createElement(Text, { className: mergeStyles(digitStyles(theme), (_b = props.styles) === null || _b === void 0 ? void 0 : _b.digit) }, props.digit),
63
66
  React.createElement(Text, { className: mergeStyles(letterStyles(theme), (_c = props.styles) === null || _c === void 0 ? void 0 : _c.letter) }, (_d = props.letter) !== null && _d !== void 0 ? _d : ' '))));
@@ -1 +1 @@
1
- {"version":3,"file":"Dialpad.js","sourceRoot":"","sources":["../../../../../../../react-components/src/components/Dialpad/Dialpad.tsx"],"names":[],"mappings":"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","sourcesContent":["// Copyright (c) Microsoft Corporation.\n// Licensed under the MIT license.\n\nimport React, { useEffect, useCallback } from 'react';\nimport { IStyle, IButtonStyles, ITextFieldStyles } from '@fluentui/react';\n\nimport { IconButton } from '@fluentui/react';\nimport {\n concatStyleSets,\n DefaultButton,\n FocusZone,\n mergeStyles,\n Stack,\n Text,\n TextField,\n useTheme\n} from '@fluentui/react';\nimport { _formatString } from '@internal/acs-ui-common';\nimport { useState } from 'react';\n/* @conditional-compile-remove(dialpad) */\nimport { useLocale } from '../../localization';\nimport {\n buttonStyles,\n containerStyles,\n iconButtonStyles,\n digitStyles,\n letterStyles,\n textFieldStyles\n} from '../styles/Dialpad.styles';\nimport { formatPhoneNumber } from '../utils/formatPhoneNumber';\nimport useLongPress from '../utils/useLongPress';\n\n/**\n * Strings of {@link Dialpad} that can be overridden.\n *\n * @beta\n */\nexport interface DialpadStrings {\n placeholderText: string;\n deleteButtonAriaLabel?: string;\n}\n\n/**\n * Styles for {@link Dialpad} component.\n *\n * @beta\n */\nexport interface DialpadStyles {\n root?: IStyle;\n button?: IButtonStyles;\n textField?: Partial<ITextFieldStyles>;\n digit?: IStyle;\n letter?: IStyle;\n deleteIcon?: IButtonStyles;\n}\n\n/**\n * DTMF tone for PSTN calls.\n *\n * @beta\n */\nexport type DtmfTone =\n | 'A'\n | 'B'\n | 'C'\n | 'D'\n | 'Flash'\n | 'Num0'\n | 'Num1'\n | 'Num2'\n | 'Num3'\n | 'Num4'\n | 'Num5'\n | 'Num6'\n | 'Num7'\n | 'Num8'\n | 'Num9'\n | 'Pound'\n | 'Star';\n\n/**\n * Props for {@link Dialpad} component.\n *\n * @beta\n */\nexport interface DialpadProps {\n strings?: DialpadStrings;\n /** function to send dtmf tones on button click */\n onSendDtmfTone?: (dtmfTone: DtmfTone) => Promise<void>;\n /** Callback for dialpad button behavior*/\n onClickDialpadButton?: (buttonValue: string, buttonIndex: number) => void;\n /** set dialpad textfield content */\n textFieldValue?: string;\n /** on change function for text field, provides an unformatted plain text*/\n onChange?: (input: string) => void;\n /** boolean input to determine when to show/hide delete button, default true */\n showDeleteButton?: boolean;\n /** boolean input to determine if dialpad is in mobile view, default false */\n isMobile?: boolean;\n styles?: DialpadStyles;\n}\n\ntype DialpadButtonContent = {\n /** Number displayed on each dialpad button */\n digit: string;\n /** Letters displayed on each dialpad button */\n letter?: string;\n};\n\nconst dialPadButtonsDefault: DialpadButtonContent[][] = [\n [{ digit: '1' }, { digit: '2', letter: 'ABC' }, { digit: '3', letter: 'DEF' }],\n [\n { digit: '4', letter: 'GHI' },\n { digit: '5', letter: 'JKL' },\n { digit: '6', letter: 'MNO' }\n ],\n [\n { digit: '7', letter: 'PQRS' },\n { digit: '8', letter: 'TUV' },\n { digit: '9', letter: 'WXYZ' }\n ],\n [{ digit: '*' }, { digit: '0', letter: '+' }, { digit: '#' }]\n];\n\nconst DtmfTones: DtmfTone[] = [\n 'Num1',\n 'Num2',\n 'Num3',\n 'Num4',\n 'Num5',\n 'Num6',\n 'Num7',\n 'Num8',\n 'Num9',\n 'Star',\n 'Num0',\n 'Pound'\n];\n\nconst DialpadButton = (props: {\n digit: string;\n letter?: string;\n styles?: DialpadStyles;\n index: number;\n onClick: (input: string, index: number) => void;\n onLongPress: (input: string, index: number) => void;\n isMobile?: boolean;\n}): JSX.Element => {\n const theme = useTheme();\n\n const { digit, index, onClick, onLongPress, isMobile = false } = props;\n\n const clickFunction = useCallback(async () => {\n onClick(digit, index);\n }, [digit, index, onClick]);\n\n const longPressFunction = useCallback(async () => {\n onLongPress(digit, index);\n }, [digit, index, onLongPress]);\n\n const { handlers } = useLongPress(clickFunction, longPressFunction, isMobile);\n return (\n <DefaultButton\n data-test-id={`dialpad-button-${props.index}`}\n styles={concatStyleSets(buttonStyles(theme), props.styles?.button)}\n {...handlers}\n >\n <Stack>\n <Text className={mergeStyles(digitStyles(theme), props.styles?.digit)}>{props.digit}</Text>\n\n <Text className={mergeStyles(letterStyles(theme), props.styles?.letter)}>{props.letter ?? ' '}</Text>\n </Stack>\n </DefaultButton>\n );\n};\n\nconst DialpadContainer = (props: {\n strings: DialpadStrings;\n onSendDtmfTone?: (dtmfTone: DtmfTone) => Promise<void>;\n /** Callback for dialpad button behavior */\n onClickDialpadButton?: (buttonValue: string, buttonIndex: number) => void;\n /** Pass in custom content to dialpad textfield */\n textFieldValue?: string;\n /** on change function for text field, provides an unformatted plain text */\n onChange?: (input: string) => void;\n /** boolean input to determine when to show/hide delete button, default true */\n showDeleteButton?: boolean;\n /** boolean input to determine if dialpad is in mobile view, default false */\n isMobile?: boolean;\n styles?: DialpadStyles;\n}): JSX.Element => {\n const theme = useTheme();\n\n const {\n onSendDtmfTone,\n onClickDialpadButton,\n textFieldValue,\n onChange,\n showDeleteButton = true,\n isMobile = false\n } = props;\n\n const [plainTextValue, setPlainTextValue] = useState(textFieldValue ?? '');\n\n useEffect(() => {\n if (onChange) {\n onChange(plainTextValue);\n }\n }, [plainTextValue, onChange]);\n\n useEffect(() => {\n setText(textFieldValue ?? '');\n }, [textFieldValue]);\n\n const onClickDialpad = (input: string, index: number): void => {\n setText(plainTextValue + input);\n if (onSendDtmfTone) {\n onSendDtmfTone(DtmfTones[index]);\n }\n if (onClickDialpadButton) {\n onClickDialpadButton(input, index);\n }\n };\n\n const onLongPressDialpad = (input: string, index: number): void => {\n if (input === '0' && index === 10) {\n setText(plainTextValue + '+');\n } else {\n setText(plainTextValue + input);\n }\n if (onSendDtmfTone) {\n onSendDtmfTone(DtmfTones[index]);\n }\n if (onClickDialpadButton) {\n onClickDialpadButton(input, index);\n }\n };\n\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n const setText = (input: string): void => {\n // remove non-valid characters from input: letters,special characters excluding +, *,#\n const plainInput = sanitizeInput(input);\n setPlainTextValue(plainInput);\n };\n\n const deleteNumbers = (): void => {\n const modifiedInput = plainTextValue.substring(0, plainTextValue.length - 1);\n setText(modifiedInput);\n };\n\n return (\n <div\n className={mergeStyles(containerStyles(theme), props.styles?.root)}\n data-test-id=\"dialpadContainer\"\n data-ui-id=\"dialpadContainer\"\n >\n <TextField\n styles={concatStyleSets(textFieldStyles(theme), props.styles?.textField)}\n value={textFieldValue ? textFieldValue : formatPhoneNumber(plainTextValue)}\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n onChange={(e: any) => {\n setText(e.target.value);\n }}\n placeholder={props.strings.placeholderText}\n data-test-id=\"dialpad-input\"\n onRenderSuffix={(): JSX.Element => (\n <>\n {showDeleteButton && plainTextValue.length !== 0 && (\n <IconButton\n ariaLabel={props.strings.deleteButtonAriaLabel}\n onClick={deleteNumbers}\n styles={concatStyleSets(iconButtonStyles(theme), props.styles?.deleteIcon)}\n iconProps={{ iconName: 'DialpadBackspace' }}\n />\n )}\n </>\n )}\n />\n <FocusZone>\n {dialPadButtonsDefault.map((rows, rowIndex) => {\n return (\n <Stack horizontal key={`row_${rowIndex}`} horizontalAlign=\"stretch\">\n {rows.map((button, columnIndex) => (\n <DialpadButton\n key={`button_${columnIndex}`}\n /* row index = 0\n columnIndex: (0,1,2) => (0,1,2)\n row index = 1\n columnIndex: (0,1,2)=> (3,4,5)\n row index = 2\n columnIndex: (0,1,2)=> (6,7,8)\n row index = 3\n columnIndex: (0,1,2)=> (9,10,11)\n columnIndex + rowIndex*rows.length calculates the corresponding index for each button\n dialpad index:\n 0 1 2\n 3 4 5\n 6 7 8\n 9 10 11\n then use this index to locate the corresponding dtmf tones\n DtmfTones[index]\n */\n index={columnIndex + rowIndex * rows.length}\n digit={button.digit}\n letter={button.letter}\n styles={props.styles}\n onClick={onClickDialpad}\n onLongPress={onLongPressDialpad}\n isMobile={isMobile}\n />\n ))}\n </Stack>\n );\n })}\n </FocusZone>\n </div>\n );\n};\n\n/**\n * A component to allow users to enter phone number through clicking on dialpad/using keyboard\n * It will return empty component for stable builds\n *\n * @beta\n */\nexport const Dialpad = (props: DialpadProps): JSX.Element => {\n /* @conditional-compile-remove(dialpad) */ /* @conditional-compile-remove(PSTN-calls) */\n const localeStrings = useLocale().strings.dialpad;\n\n const dialpadLocaleStringsTrampoline = (): DialpadStrings => {\n /* @conditional-compile-remove(dialpad) */ /* @conditional-compile-remove(PSTN-calls) */\n return localeStrings;\n // Even though the component strings type doesn't have `DialpadStrings` in stable build,\n // the string values exist. So unsafe cast for stable build.\n return '' as unknown as DialpadStrings;\n };\n const strings = { ...dialpadLocaleStringsTrampoline(), ...props.strings };\n return <DialpadContainer strings={strings} {...props} />;\n};\n\nconst sanitizeInput = (input: string): string => {\n // remove non-valid characters from input: letters,special characters excluding +, *,#\n return input.replace(/[^\\d*#+]/g, '');\n};\n\"../../../../acs-ui-common/src\""]}
1
+ {"version":3,"file":"Dialpad.js","sourceRoot":"","sources":["../../../../../../../react-components/src/components/Dialpad/Dialpad.tsx"],"names":[],"mappings":"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","sourcesContent":["// Copyright (c) Microsoft Corporation.\n// Licensed under the MIT license.\n\nimport React, { useEffect } from 'react';\nimport { IStyle, IButtonStyles, ITextFieldStyles } from '@fluentui/react';\n\nimport { IconButton } from '@fluentui/react';\nimport {\n concatStyleSets,\n DefaultButton,\n FocusZone,\n mergeStyles,\n Stack,\n Text,\n TextField,\n useTheme\n} from '@fluentui/react';\nimport { _formatString } from '@internal/acs-ui-common';\nimport { useState } from 'react';\n/* @conditional-compile-remove(dialpad) */\nimport { useLocale } from '../../localization';\nimport {\n buttonStyles,\n containerStyles,\n iconButtonStyles,\n digitStyles,\n letterStyles,\n textFieldStyles\n} from '../styles/Dialpad.styles';\nimport { formatPhoneNumber } from '../utils/formatPhoneNumber';\nimport useLongPress from '../utils/useLongPress';\n\n/**\n * Strings of {@link Dialpad} that can be overridden.\n *\n * @beta\n */\nexport interface DialpadStrings {\n placeholderText: string;\n deleteButtonAriaLabel?: string;\n}\n\n/**\n * Styles for {@link Dialpad} component.\n *\n * @beta\n */\nexport interface DialpadStyles {\n root?: IStyle;\n button?: IButtonStyles;\n textField?: Partial<ITextFieldStyles>;\n digit?: IStyle;\n letter?: IStyle;\n deleteIcon?: IButtonStyles;\n}\n\n/**\n * DTMF tone for PSTN calls.\n *\n * @beta\n */\nexport type DtmfTone =\n | 'A'\n | 'B'\n | 'C'\n | 'D'\n | 'Flash'\n | 'Num0'\n | 'Num1'\n | 'Num2'\n | 'Num3'\n | 'Num4'\n | 'Num5'\n | 'Num6'\n | 'Num7'\n | 'Num8'\n | 'Num9'\n | 'Pound'\n | 'Star';\n\n/**\n * Props for {@link Dialpad} component.\n *\n * @beta\n */\nexport interface DialpadProps {\n strings?: DialpadStrings;\n /** function to send dtmf tones on button click */\n onSendDtmfTone?: (dtmfTone: DtmfTone) => Promise<void>;\n /** Callback for dialpad button behavior*/\n onClickDialpadButton?: (buttonValue: string, buttonIndex: number) => void;\n /** set dialpad textfield content */\n textFieldValue?: string;\n /** on change function for text field, provides an unformatted plain text*/\n onChange?: (input: string) => void;\n /** boolean input to determine when to show/hide delete button, default true */\n showDeleteButton?: boolean;\n /** boolean input to determine if dialpad is in mobile view, default false */\n isMobile?: boolean;\n styles?: DialpadStyles;\n}\n\ntype DialpadButtonContent = {\n /** Number displayed on each dialpad button */\n digit: string;\n /** Letters displayed on each dialpad button */\n letter?: string;\n};\n\nconst dialPadButtonsDefault: DialpadButtonContent[][] = [\n [{ digit: '1' }, { digit: '2', letter: 'ABC' }, { digit: '3', letter: 'DEF' }],\n [\n { digit: '4', letter: 'GHI' },\n { digit: '5', letter: 'JKL' },\n { digit: '6', letter: 'MNO' }\n ],\n [\n { digit: '7', letter: 'PQRS' },\n { digit: '8', letter: 'TUV' },\n { digit: '9', letter: 'WXYZ' }\n ],\n [{ digit: '*' }, { digit: '0', letter: '+' }, { digit: '#' }]\n];\n\nconst DtmfTones: DtmfTone[] = [\n 'Num1',\n 'Num2',\n 'Num3',\n 'Num4',\n 'Num5',\n 'Num6',\n 'Num7',\n 'Num8',\n 'Num9',\n 'Star',\n 'Num0',\n 'Pound'\n];\n\nconst DialpadButton = (props: {\n digit: string;\n letter?: string;\n styles?: DialpadStyles;\n index: number;\n onClick: (input: string, index: number) => void;\n onLongPress: (input: string, index: number) => void;\n isMobile?: boolean;\n}): JSX.Element => {\n const theme = useTheme();\n\n const { digit, index, onClick, onLongPress, isMobile = false } = props;\n\n const useLongPressProps = React.useMemo(\n () => ({\n onClick: async () => {\n onClick(digit, index);\n },\n onLongPress: async () => {\n onLongPress(digit, index);\n },\n touchEventsOnly: isMobile\n }),\n [digit, index, isMobile, onClick, onLongPress]\n );\n\n const longPressHandlers = useLongPress(useLongPressProps);\n\n return (\n <DefaultButton\n data-test-id={`dialpad-button-${props.index}`}\n styles={concatStyleSets(buttonStyles(theme), props.styles?.button)}\n {...longPressHandlers}\n >\n <Stack>\n <Text className={mergeStyles(digitStyles(theme), props.styles?.digit)}>{props.digit}</Text>\n\n <Text className={mergeStyles(letterStyles(theme), props.styles?.letter)}>{props.letter ?? ' '}</Text>\n </Stack>\n </DefaultButton>\n );\n};\n\nconst DialpadContainer = (props: {\n strings: DialpadStrings;\n onSendDtmfTone?: (dtmfTone: DtmfTone) => Promise<void>;\n /** Callback for dialpad button behavior */\n onClickDialpadButton?: (buttonValue: string, buttonIndex: number) => void;\n /** Pass in custom content to dialpad textfield */\n textFieldValue?: string;\n /** on change function for text field, provides an unformatted plain text */\n onChange?: (input: string) => void;\n /** boolean input to determine when to show/hide delete button, default true */\n showDeleteButton?: boolean;\n /** boolean input to determine if dialpad is in mobile view, default false */\n isMobile?: boolean;\n styles?: DialpadStyles;\n}): JSX.Element => {\n const theme = useTheme();\n\n const {\n onSendDtmfTone,\n onClickDialpadButton,\n textFieldValue,\n onChange,\n showDeleteButton = true,\n isMobile = false\n } = props;\n\n const [plainTextValue, setPlainTextValue] = useState(textFieldValue ?? '');\n\n useEffect(() => {\n if (onChange) {\n onChange(plainTextValue);\n }\n }, [plainTextValue, onChange]);\n\n useEffect(() => {\n setText(textFieldValue ?? '');\n }, [textFieldValue]);\n\n const onClickDialpad = (input: string, index: number): void => {\n setText(plainTextValue + input);\n if (onSendDtmfTone) {\n onSendDtmfTone(DtmfTones[index]);\n }\n if (onClickDialpadButton) {\n onClickDialpadButton(input, index);\n }\n };\n\n const onLongPressDialpad = (input: string, index: number): void => {\n if (input === '0' && index === 10) {\n setText(plainTextValue + '+');\n } else {\n setText(plainTextValue + input);\n }\n if (onSendDtmfTone) {\n onSendDtmfTone(DtmfTones[index]);\n }\n if (onClickDialpadButton) {\n onClickDialpadButton(input, index);\n }\n };\n\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n const setText = (input: string): void => {\n // remove non-valid characters from input: letters,special characters excluding +, *,#\n const plainInput = sanitizeInput(input);\n setPlainTextValue(plainInput);\n };\n\n const deleteNumbers = (): void => {\n const modifiedInput = plainTextValue.substring(0, plainTextValue.length - 1);\n setText(modifiedInput);\n };\n\n return (\n <div\n className={mergeStyles(containerStyles(theme), props.styles?.root)}\n data-test-id=\"dialpadContainer\"\n data-ui-id=\"dialpadContainer\"\n >\n <TextField\n styles={concatStyleSets(textFieldStyles(theme), props.styles?.textField)}\n value={textFieldValue ? textFieldValue : formatPhoneNumber(plainTextValue)}\n // eslint-disable-next-line @typescript-eslint/no-explicit-any\n onChange={(e: any) => {\n setText(e.target.value);\n }}\n placeholder={props.strings.placeholderText}\n data-test-id=\"dialpad-input\"\n onRenderSuffix={(): JSX.Element => (\n <>\n {showDeleteButton && plainTextValue.length !== 0 && (\n <IconButton\n ariaLabel={props.strings.deleteButtonAriaLabel}\n onClick={deleteNumbers}\n styles={concatStyleSets(iconButtonStyles(theme), props.styles?.deleteIcon)}\n iconProps={{ iconName: 'DialpadBackspace' }}\n />\n )}\n </>\n )}\n />\n <FocusZone>\n {dialPadButtonsDefault.map((rows, rowIndex) => {\n return (\n <Stack horizontal key={`row_${rowIndex}`} horizontalAlign=\"stretch\">\n {rows.map((button, columnIndex) => (\n <DialpadButton\n key={`button_${columnIndex}`}\n /* row index = 0\n columnIndex: (0,1,2) => (0,1,2)\n row index = 1\n columnIndex: (0,1,2)=> (3,4,5)\n row index = 2\n columnIndex: (0,1,2)=> (6,7,8)\n row index = 3\n columnIndex: (0,1,2)=> (9,10,11)\n columnIndex + rowIndex*rows.length calculates the corresponding index for each button\n dialpad index:\n 0 1 2\n 3 4 5\n 6 7 8\n 9 10 11\n then use this index to locate the corresponding dtmf tones\n DtmfTones[index]\n */\n index={columnIndex + rowIndex * rows.length}\n digit={button.digit}\n letter={button.letter}\n styles={props.styles}\n onClick={onClickDialpad}\n onLongPress={onLongPressDialpad}\n isMobile={isMobile}\n />\n ))}\n </Stack>\n );\n })}\n </FocusZone>\n </div>\n );\n};\n\n/**\n * A component to allow users to enter phone number through clicking on dialpad/using keyboard\n * It will return empty component for stable builds\n *\n * @beta\n */\nexport const Dialpad = (props: DialpadProps): JSX.Element => {\n /* @conditional-compile-remove(dialpad) */ /* @conditional-compile-remove(PSTN-calls) */\n const localeStrings = useLocale().strings.dialpad;\n\n const dialpadLocaleStringsTrampoline = (): DialpadStrings => {\n /* @conditional-compile-remove(dialpad) */ /* @conditional-compile-remove(PSTN-calls) */\n return localeStrings;\n // Even though the component strings type doesn't have `DialpadStrings` in stable build,\n // the string values exist. So unsafe cast for stable build.\n return '' as unknown as DialpadStrings;\n };\n const strings = { ...dialpadLocaleStringsTrampoline(), ...props.strings };\n return <DialpadContainer strings={strings} {...props} />;\n};\n\nconst sanitizeInput = (input: string): string => {\n // remove non-valid characters from input: letters,special characters excluding +, *,#\n return input.replace(/[^\\d*#+]/g, '');\n};\n\"../../../../acs-ui-common/src\""]}
@@ -104,6 +104,10 @@ export interface VideoTileProps {
104
104
  */
105
105
  participantState?: ParticipantState;
106
106
  strings?: VideoTileStrings;
107
+ /**
108
+ * Callback triggered by video tile on touch and hold.
109
+ */
110
+ onLongTouch?: () => void;
107
111
  }
108
112
  /**
109
113
  * @beta
@@ -16,6 +16,8 @@ import { getVideoTileOverrideColor } from './utils/videoTileStylesUtils';
16
16
  import { DefaultButton, concatStyleSets, DirectionalHint } from '@fluentui/react';
17
17
  /* @conditional-compile-remove(pinned-participants) */
18
18
  import { mapMenuItemsToContextualMenuItems } from './utils';
19
+ /* @conditional-compile-remove(pinned-participants) */
20
+ import useLongPress from './utils/useLongPress';
19
21
  // Coin max size is set to PersonaSize.size100
20
22
  const DEFAULT_PERSONA_MAX_SIZE_PX = 100;
21
23
  // Coin min size is set PersonaSize.size32
@@ -67,6 +69,27 @@ export const VideoTile = (props) => {
67
69
  const currentObserver = observer.current;
68
70
  return () => currentObserver.disconnect();
69
71
  }, [observer, videoTileRef]);
72
+ /* @conditional-compile-remove(pinned-participants) */
73
+ const useLongPressProps = useMemo(() => {
74
+ return {
75
+ onLongPress: () => {
76
+ var _a;
77
+ (_a = props.onLongTouch) === null || _a === void 0 ? void 0 : _a.call(props);
78
+ },
79
+ touchEventsOnly: true
80
+ };
81
+ // eslint-disable-next-line react-hooks/exhaustive-deps
82
+ }, [props.onLongTouch]);
83
+ /* @conditional-compile-remove(pinned-participants) */
84
+ const longPressHandlers = useLongPress(useLongPressProps);
85
+ const longPressHandlersTrampoline = useMemo(() => {
86
+ /* @conditional-compile-remove(pinned-participants) */
87
+ return longPressHandlers;
88
+ return {};
89
+ }, [
90
+ /* @conditional-compile-remove(pinned-participants) */
91
+ longPressHandlers
92
+ ]);
70
93
  const placeholderOptions = {
71
94
  userId,
72
95
  text: initialsName || displayName,
@@ -81,7 +104,7 @@ export const VideoTile = (props) => {
81
104
  const canShowLabel = showLabel && (displayName || (showMuteIndicator && isMuted));
82
105
  const participantStateString = participantStateStringTrampoline(props, locale);
83
106
  return (React.createElement(Ref, { innerRef: videoTileRef },
84
- React.createElement(Stack, { "data-ui-id": ids.videoTile, className: mergeStyles(rootStyles, {
107
+ React.createElement(Stack, Object.assign({ "data-ui-id": ids.videoTile, className: mergeStyles(rootStyles, {
85
108
  background: theme.palette.neutralLighter,
86
109
  borderRadius: theme.effects.roundedCorner4
87
110
  }, isSpeaking && {
@@ -94,7 +117,7 @@ export const VideoTile = (props) => {
94
117
  width: '100%',
95
118
  height: '100%'
96
119
  }
97
- }, styles === null || styles === void 0 ? void 0 : styles.root) },
120
+ }, styles === null || styles === void 0 ? void 0 : styles.root) }, longPressHandlersTrampoline),
98
121
  isVideoRendered ? (React.createElement(Stack, { className: mergeStyles(videoContainerStyles, isMirrored && { transform: 'scaleX(-1)' }, styles === null || styles === void 0 ? void 0 : styles.videoContainer) }, renderElement)) : (React.createElement(Stack, { className: mergeStyles(videoContainerStyles), style: { opacity: participantStateString ? 0.4 : 1 } }, onRenderPlaceholder ? (onRenderPlaceholder(userId !== null && userId !== void 0 ? userId : '', placeholderOptions, DefaultPlaceholder)) : (React.createElement(DefaultPlaceholder, Object.assign({}, placeholderOptions))))),
99
122
  (canShowLabel || participantStateString) && (React.createElement(Stack, { horizontal: true, className: tileInfoContainerStyle, tokens: tileInfoContainerTokens },
100
123
  React.createElement(Stack, { horizontal: true, className: tileInfoStyle },
@@ -1 +1 @@
1
- {"version":3,"file":"VideoTile.js","sourceRoot":"","sources":["../../../../../../react-components/src/components/VideoTile.tsx"],"names":[],"mappings":"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","sourcesContent":["// Copyright (c) Microsoft Corporation.\n// Licensed under the MIT license.\n\nimport { Icon, IStyle, mergeStyles, Persona, Stack, Text, IIconProps } from '@fluentui/react';\n/* @conditional-compile-remove(pinned-participants) */\nimport { MoreHorizontal20Filled } from '@fluentui/react-icons';\nimport { Ref } from '@fluentui/react-northstar';\nimport React, { useLayoutEffect, useMemo, useRef, useState } from 'react';\nimport { useIdentifiers } from '../identifiers';\nimport { ComponentLocale, useLocale } from '../localization';\nimport { useTheme } from '../theming';\nimport { BaseCustomStyles, CustomAvatarOptions, OnRenderAvatarCallback } from '../types';\n/* @conditional-compile-remove(one-to-n-calling) */\n/* @conditional-compile-remove(PSTN-calls) */\nimport { ParticipantState } from '../types';\nimport {\n disabledVideoHint,\n displayNameStyle,\n iconContainerStyle,\n overlayContainerStyles,\n rootStyles,\n videoContainerStyles,\n videoHint,\n tileInfoContainerStyle,\n participantStateStringStyles\n} from './styles/VideoTile.styles';\n/* @conditional-compile-remove(pinned-participants) */\nimport { pinIconStyle, menuButtonStyles } from './styles/VideoTile.styles';\nimport { getVideoTileOverrideColor } from './utils/videoTileStylesUtils';\n/* @conditional-compile-remove(pinned-participants) */\nimport { DefaultButton, concatStyleSets, DirectionalHint } from '@fluentui/react';\n/* @conditional-compile-remove(pinned-participants) */\nimport { mapMenuItemsToContextualMenuItems } from './utils';\n\n/**\n * Strings of {@link VideoTile} that can be overridden.\n * @beta\n */\nexport interface VideoTileStrings {\n participantStateConnecting: string;\n participantStateRinging: string;\n participantStateHold: string;\n}\n\n/**\n * Fluent styles for {@link VideoTile}.\n *\n * @public\n */\nexport interface VideoTileStylesProps extends BaseCustomStyles {\n /** Styles for video container. */\n videoContainer?: IStyle;\n /** Styles for container overlayed on the video container. */\n overlayContainer?: IStyle;\n /** Styles for displayName on the video container. */\n displayNameContainer?: IStyle;\n}\n\n/**\n * Props for {@link VideoTile}.\n *\n * @public\n */\nexport interface VideoTileProps {\n /** React Child components. Child Components will show as overlay component in the VideoTile. */\n children?: React.ReactNode;\n /**\n * Allows users to pass in an object contains custom CSS styles.\n * @Example\n * ```\n * <VideoTile styles={{ root: { background: 'blue' } }} />\n * ```\n */\n styles?: VideoTileStylesProps;\n /** user id for the VideoTile placeholder. */\n userId?: string;\n /** Component with the video stream. */\n renderElement?: JSX.Element | null;\n /** Determines if the video is mirrored or not. */\n isMirrored?: boolean;\n /** Custom render Component function for no video is available. Render a Persona Icon if undefined. */\n onRenderPlaceholder?: OnRenderAvatarCallback;\n /**\n * Show label on the VideoTile\n * @defaultValue true\n */\n showLabel?: boolean;\n /**\n * Whether to display a mute icon beside the user's display name.\n * @defaultValue true\n */\n showMuteIndicator?: boolean;\n /**\n * Whether the video is muted or not.\n */\n isMuted?: boolean;\n /* @conditional-compile-remove(pinned-participants) */\n /**\n * Display custom menu items in the VideoTile's contextual menu.\n */\n menuItems?: VideoTileMenuItems;\n /* @conditional-compile-remove(pinned-participants) */\n /**\n * If true, the video tile will show the pin icon.\n */\n isPinned?: boolean;\n /**\n * Display Name of the Participant to be shown in the label.\n * @remarks `displayName` is used to generate avatar initials if `initialsName` is not provided.\n */\n displayName?: string;\n /**\n * Name of the participant used to generate initials. For example, a name `John Doe` will display `JD` as initials.\n * @remarks `displayName` is used if this property is not specified.\n */\n initialsName?: string;\n /**\n * Minimum size of the persona avatar in px.\n * The persona avatar is the default placeholder shown when no video stream is available.\n * For more information see https://developer.microsoft.com/en-us/fluentui#/controls/web/persona\n * @defaultValue 32px\n */\n personaMinSize?: number;\n /**\n * Maximum size of the personal avatar in px.\n * The persona avatar is the default placeholder shown when no video stream is available.\n * For more information see https://developer.microsoft.com/en-us/fluentui#/controls/web/persona\n * @defaultValue 100px\n */\n personaMaxSize?: number;\n /** Optional property to set the aria label of the video tile if there is no available stream. */\n noVideoAvailableAriaLabel?: string;\n /** Whether the participant in the videoTile is speaking. Shows a speaking indicator (border). */\n isSpeaking?: boolean;\n\n /* @conditional-compile-remove(one-to-n-calling) */\n /* @conditional-compile-remove(PSTN-calls) */\n /**\n * The call connection state of the participant.\n * For example, `Hold` means the participant is on hold.\n */\n participantState?: ParticipantState;\n /* @conditional-compile-remove(one-to-n-calling) */\n /* @conditional-compile-remove(PSTN-calls) */\n strings?: VideoTileStrings;\n}\n\n// Coin max size is set to PersonaSize.size100\nconst DEFAULT_PERSONA_MAX_SIZE_PX = 100;\n// Coin min size is set PersonaSize.size32\nconst DEFAULT_PERSONA_MIN_SIZE_PX = 32;\n\nconst DefaultPlaceholder = (props: CustomAvatarOptions): JSX.Element => {\n const { text, noVideoAvailableAriaLabel, coinSize, hidePersonaDetails } = props;\n\n return (\n <Stack className={mergeStyles({ position: 'absolute', height: '100%', width: '100%' })}>\n <Stack styles={defaultPersonaStyles}>\n <Persona\n coinSize={coinSize}\n hidePersonaDetails={hidePersonaDetails}\n text={text ?? ''}\n initialsTextColor=\"white\"\n aria-label={noVideoAvailableAriaLabel ?? ''}\n showOverflowTooltip={false}\n />\n </Stack>\n </Stack>\n );\n};\n\n/**\n * @beta\n * MenuItems to be diplayed in video tile in the contextual/drawer menu\n */\nexport type VideoTileMenuItems = Array<{\n key: string;\n ariaLabel?: string;\n text: string;\n onClick: () => void;\n iconProps: IIconProps;\n}>;\n\n/* @conditional-compile-remove(pinned-participants) */\nconst menuIcon = (): JSX.Element => <MoreHorizontal20Filled primaryFill=\"currentColor\" />;\n\nconst defaultPersonaStyles = { root: { margin: 'auto', maxHeight: '100%' } };\n\n/* @conditional-compile-remove(pinned-participants) */\nconst VideoTileMoreOptionsButton = (props: { menuItems?: VideoTileMenuItems; menuStyles?: IStyle }): JSX.Element => {\n const { menuItems, menuStyles } = props;\n if (!menuItems || menuItems.length === 0) {\n return <></>;\n }\n return (\n <DefaultButton\n styles={concatStyleSets(menuButtonStyles, menuStyles ?? {})}\n onRenderIcon={menuIcon}\n menuIconProps={{ hidden: true }}\n menuProps={{ items: mapMenuItemsToContextualMenuItems(menuItems), directionalHint: DirectionalHint.topRightEdge }}\n />\n );\n};\n\n/**\n * A component to render the video stream for a single call participant.\n *\n * Use with {@link GridLayout} in a {@link VideoGallery}.\n *\n * @public\n */\nexport const VideoTile = (props: VideoTileProps): JSX.Element => {\n const {\n children,\n displayName,\n initialsName,\n isMirrored,\n isMuted,\n /* @conditional-compile-remove(pinned-participants) */\n isPinned,\n onRenderPlaceholder,\n renderElement,\n showLabel = true,\n showMuteIndicator = true,\n styles,\n userId,\n noVideoAvailableAriaLabel,\n isSpeaking,\n /* @conditional-compile-remove(pinned-participants) */\n menuItems,\n personaMinSize = DEFAULT_PERSONA_MIN_SIZE_PX,\n personaMaxSize = DEFAULT_PERSONA_MAX_SIZE_PX\n } = props;\n\n const [personaSize, setPersonaSize] = useState(100);\n const videoTileRef = useRef<HTMLElement>(null);\n\n const locale = useLocale();\n const theme = useTheme();\n\n const isVideoRendered = !!renderElement;\n\n const observer = useRef(\n new ResizeObserver((entries): void => {\n const { width, height } = entries[0].contentRect;\n const personaSize = Math.min(width, height) / 3;\n setPersonaSize(Math.max(Math.min(personaSize, personaMaxSize), personaMinSize));\n })\n );\n\n useLayoutEffect(() => {\n if (videoTileRef.current) {\n observer.current.observe(videoTileRef.current);\n }\n const currentObserver = observer.current;\n return () => currentObserver.disconnect();\n }, [observer, videoTileRef]);\n\n const placeholderOptions = {\n userId,\n text: initialsName || displayName,\n noVideoAvailableAriaLabel,\n coinSize: personaSize,\n styles: defaultPersonaStyles,\n hidePersonaDetails: true\n };\n\n const videoHintWithBorderRadius = mergeStyles(videoHint, { borderRadius: theme.effects.roundedCorner4 });\n\n const tileInfoStyle = useMemo(\n () =>\n mergeStyles(\n isVideoRendered ? videoHintWithBorderRadius : disabledVideoHint,\n getVideoTileOverrideColor(isVideoRendered, theme, 'neutralPrimary'),\n styles?.displayNameContainer\n ),\n [isVideoRendered, videoHintWithBorderRadius, theme, styles?.displayNameContainer]\n );\n\n const ids = useIdentifiers();\n\n const canShowLabel = showLabel && (displayName || (showMuteIndicator && isMuted));\n const participantStateString = participantStateStringTrampoline(props, locale);\n return (\n <Ref innerRef={videoTileRef}>\n <Stack\n data-ui-id={ids.videoTile}\n className={mergeStyles(\n rootStyles,\n {\n background: theme.palette.neutralLighter,\n borderRadius: theme.effects.roundedCorner4\n },\n isSpeaking && {\n '&::before': {\n content: `''`,\n position: 'absolute',\n zIndex: 1,\n border: `0.25rem solid ${theme.palette.themePrimary}`,\n borderRadius: theme.effects.roundedCorner4,\n width: '100%',\n height: '100%'\n }\n },\n styles?.root\n )}\n >\n {isVideoRendered ? (\n <Stack\n className={mergeStyles(\n videoContainerStyles,\n isMirrored && { transform: 'scaleX(-1)' },\n styles?.videoContainer\n )}\n >\n {renderElement}\n </Stack>\n ) : (\n <Stack className={mergeStyles(videoContainerStyles)} style={{ opacity: participantStateString ? 0.4 : 1 }}>\n {onRenderPlaceholder ? (\n onRenderPlaceholder(userId ?? '', placeholderOptions, DefaultPlaceholder)\n ) : (\n <DefaultPlaceholder {...placeholderOptions} />\n )}\n </Stack>\n )}\n\n {(canShowLabel || participantStateString) && (\n <Stack horizontal className={tileInfoContainerStyle} tokens={tileInfoContainerTokens}>\n <Stack horizontal className={tileInfoStyle}>\n {canShowLabel && (\n <Text\n className={mergeStyles(displayNameStyle)}\n title={displayName}\n style={{ color: participantStateString ? theme.palette.neutralSecondary : 'inherit' }}\n >\n {displayName}\n </Text>\n )}\n {participantStateString && (\n <Text className={mergeStyles(participantStateStringStyles(theme))}>\n {bracketedParticipantString(participantStateString, !!canShowLabel)}\n </Text>\n )}\n {showMuteIndicator && isMuted && (\n <Stack className={mergeStyles(iconContainerStyle)}>\n <Icon iconName=\"VideoTileMicOff\" />\n </Stack>\n )}\n {\n /* @conditional-compile-remove(pinned-participants) */\n <VideoTileMoreOptionsButton menuItems={menuItems} menuStyles={props.styles} />\n }\n {\n /* @conditional-compile-remove(pinned-participants) */\n isPinned && (\n <Stack className={mergeStyles(iconContainerStyle)}>\n <Icon iconName=\"VideoTilePinned\" className={mergeStyles(pinIconStyle)} />\n </Stack>\n )\n }\n </Stack>\n </Stack>\n )}\n\n {children && (\n <Stack className={mergeStyles(overlayContainerStyles, styles?.overlayContainer)}>{children}</Stack>\n )}\n </Stack>\n </Ref>\n );\n};\n\nconst participantStateStringTrampoline = (props: VideoTileProps, locale: ComponentLocale): string | undefined => {\n /* @conditional-compile-remove(one-to-n-calling) */\n /* @conditional-compile-remove(PSTN-calls) */\n const strings = { ...locale.strings.videoTile, ...props.strings };\n /* @conditional-compile-remove(one-to-n-calling) */\n /* @conditional-compile-remove(PSTN-calls) */\n return props.participantState === 'Idle' || props.participantState === 'Connecting'\n ? strings?.participantStateConnecting\n : props.participantState === 'EarlyMedia' || props.participantState === 'Ringing'\n ? strings?.participantStateRinging\n : props.participantState === 'Hold'\n ? strings?.participantStateHold\n : undefined;\n\n return undefined;\n};\n\nconst tileInfoContainerTokens = {\n // A horizontal Stack sets the left margin to 0 for all it's children.\n // We need to allow the children to set their own margins\n childrenGap: 'none'\n};\n\nconst bracketedParticipantString = (participantString: string, withBrackets: boolean): string => {\n return withBrackets ? `(${participantString})` : participantString;\n};\n"]}
1
+ {"version":3,"file":"VideoTile.js","sourceRoot":"","sources":["../../../../../../react-components/src/components/VideoTile.tsx"],"names":[],"mappings":"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","sourcesContent":["// Copyright (c) Microsoft Corporation.\n// Licensed under the MIT license.\n\nimport { Icon, IStyle, mergeStyles, Persona, Stack, Text, IIconProps } from '@fluentui/react';\n/* @conditional-compile-remove(pinned-participants) */\nimport { MoreHorizontal20Filled } from '@fluentui/react-icons';\nimport { Ref } from '@fluentui/react-northstar';\nimport React, { useLayoutEffect, useMemo, useRef, useState } from 'react';\nimport { useIdentifiers } from '../identifiers';\nimport { ComponentLocale, useLocale } from '../localization';\nimport { useTheme } from '../theming';\nimport { BaseCustomStyles, CustomAvatarOptions, OnRenderAvatarCallback } from '../types';\n/* @conditional-compile-remove(one-to-n-calling) */\n/* @conditional-compile-remove(PSTN-calls) */\nimport { ParticipantState } from '../types';\nimport {\n disabledVideoHint,\n displayNameStyle,\n iconContainerStyle,\n overlayContainerStyles,\n rootStyles,\n videoContainerStyles,\n videoHint,\n tileInfoContainerStyle,\n participantStateStringStyles\n} from './styles/VideoTile.styles';\n/* @conditional-compile-remove(pinned-participants) */\nimport { pinIconStyle, menuButtonStyles } from './styles/VideoTile.styles';\nimport { getVideoTileOverrideColor } from './utils/videoTileStylesUtils';\n/* @conditional-compile-remove(pinned-participants) */\nimport { DefaultButton, concatStyleSets, DirectionalHint } from '@fluentui/react';\n/* @conditional-compile-remove(pinned-participants) */\nimport { mapMenuItemsToContextualMenuItems } from './utils';\n/* @conditional-compile-remove(pinned-participants) */\nimport useLongPress from './utils/useLongPress';\n\n/**\n * Strings of {@link VideoTile} that can be overridden.\n * @beta\n */\nexport interface VideoTileStrings {\n participantStateConnecting: string;\n participantStateRinging: string;\n participantStateHold: string;\n}\n\n/**\n * Fluent styles for {@link VideoTile}.\n *\n * @public\n */\nexport interface VideoTileStylesProps extends BaseCustomStyles {\n /** Styles for video container. */\n videoContainer?: IStyle;\n /** Styles for container overlayed on the video container. */\n overlayContainer?: IStyle;\n /** Styles for displayName on the video container. */\n displayNameContainer?: IStyle;\n}\n\n/**\n * Props for {@link VideoTile}.\n *\n * @public\n */\nexport interface VideoTileProps {\n /** React Child components. Child Components will show as overlay component in the VideoTile. */\n children?: React.ReactNode;\n /**\n * Allows users to pass in an object contains custom CSS styles.\n * @Example\n * ```\n * <VideoTile styles={{ root: { background: 'blue' } }} />\n * ```\n */\n styles?: VideoTileStylesProps;\n /** user id for the VideoTile placeholder. */\n userId?: string;\n /** Component with the video stream. */\n renderElement?: JSX.Element | null;\n /** Determines if the video is mirrored or not. */\n isMirrored?: boolean;\n /** Custom render Component function for no video is available. Render a Persona Icon if undefined. */\n onRenderPlaceholder?: OnRenderAvatarCallback;\n /**\n * Show label on the VideoTile\n * @defaultValue true\n */\n showLabel?: boolean;\n /**\n * Whether to display a mute icon beside the user's display name.\n * @defaultValue true\n */\n showMuteIndicator?: boolean;\n /**\n * Whether the video is muted or not.\n */\n isMuted?: boolean;\n /* @conditional-compile-remove(pinned-participants) */\n /**\n * Display custom menu items in the VideoTile's contextual menu.\n */\n menuItems?: VideoTileMenuItems;\n /* @conditional-compile-remove(pinned-participants) */\n /**\n * If true, the video tile will show the pin icon.\n */\n isPinned?: boolean;\n /**\n * Display Name of the Participant to be shown in the label.\n * @remarks `displayName` is used to generate avatar initials if `initialsName` is not provided.\n */\n displayName?: string;\n /**\n * Name of the participant used to generate initials. For example, a name `John Doe` will display `JD` as initials.\n * @remarks `displayName` is used if this property is not specified.\n */\n initialsName?: string;\n /**\n * Minimum size of the persona avatar in px.\n * The persona avatar is the default placeholder shown when no video stream is available.\n * For more information see https://developer.microsoft.com/en-us/fluentui#/controls/web/persona\n * @defaultValue 32px\n */\n personaMinSize?: number;\n /**\n * Maximum size of the personal avatar in px.\n * The persona avatar is the default placeholder shown when no video stream is available.\n * For more information see https://developer.microsoft.com/en-us/fluentui#/controls/web/persona\n * @defaultValue 100px\n */\n personaMaxSize?: number;\n /** Optional property to set the aria label of the video tile if there is no available stream. */\n noVideoAvailableAriaLabel?: string;\n /** Whether the participant in the videoTile is speaking. Shows a speaking indicator (border). */\n isSpeaking?: boolean;\n\n /* @conditional-compile-remove(one-to-n-calling) */\n /* @conditional-compile-remove(PSTN-calls) */\n /**\n * The call connection state of the participant.\n * For example, `Hold` means the participant is on hold.\n */\n participantState?: ParticipantState;\n /* @conditional-compile-remove(one-to-n-calling) */\n /* @conditional-compile-remove(PSTN-calls) */\n strings?: VideoTileStrings;\n\n /* @conditional-compile-remove(pinned-participants) */\n /**\n * Callback triggered by video tile on touch and hold.\n */\n onLongTouch?: () => void;\n}\n\n// Coin max size is set to PersonaSize.size100\nconst DEFAULT_PERSONA_MAX_SIZE_PX = 100;\n// Coin min size is set PersonaSize.size32\nconst DEFAULT_PERSONA_MIN_SIZE_PX = 32;\n\nconst DefaultPlaceholder = (props: CustomAvatarOptions): JSX.Element => {\n const { text, noVideoAvailableAriaLabel, coinSize, hidePersonaDetails } = props;\n\n return (\n <Stack className={mergeStyles({ position: 'absolute', height: '100%', width: '100%' })}>\n <Stack styles={defaultPersonaStyles}>\n <Persona\n coinSize={coinSize}\n hidePersonaDetails={hidePersonaDetails}\n text={text ?? ''}\n initialsTextColor=\"white\"\n aria-label={noVideoAvailableAriaLabel ?? ''}\n showOverflowTooltip={false}\n />\n </Stack>\n </Stack>\n );\n};\n\n/**\n * @beta\n * MenuItems to be diplayed in video tile in the contextual/drawer menu\n */\nexport type VideoTileMenuItems = Array<{\n key: string;\n ariaLabel?: string;\n text: string;\n onClick: () => void;\n iconProps: IIconProps;\n}>;\n\n/* @conditional-compile-remove(pinned-participants) */\nconst menuIcon = (): JSX.Element => <MoreHorizontal20Filled primaryFill=\"currentColor\" />;\n\nconst defaultPersonaStyles = { root: { margin: 'auto', maxHeight: '100%' } };\n\n/* @conditional-compile-remove(pinned-participants) */\nconst VideoTileMoreOptionsButton = (props: { menuItems?: VideoTileMenuItems; menuStyles?: IStyle }): JSX.Element => {\n const { menuItems, menuStyles } = props;\n if (!menuItems || menuItems.length === 0) {\n return <></>;\n }\n return (\n <DefaultButton\n styles={concatStyleSets(menuButtonStyles, menuStyles ?? {})}\n onRenderIcon={menuIcon}\n menuIconProps={{ hidden: true }}\n menuProps={{ items: mapMenuItemsToContextualMenuItems(menuItems), directionalHint: DirectionalHint.topRightEdge }}\n />\n );\n};\n\n/**\n * A component to render the video stream for a single call participant.\n *\n * Use with {@link GridLayout} in a {@link VideoGallery}.\n *\n * @public\n */\nexport const VideoTile = (props: VideoTileProps): JSX.Element => {\n const {\n children,\n displayName,\n initialsName,\n isMirrored,\n isMuted,\n /* @conditional-compile-remove(pinned-participants) */\n isPinned,\n onRenderPlaceholder,\n renderElement,\n showLabel = true,\n showMuteIndicator = true,\n styles,\n userId,\n noVideoAvailableAriaLabel,\n isSpeaking,\n /* @conditional-compile-remove(pinned-participants) */\n menuItems,\n personaMinSize = DEFAULT_PERSONA_MIN_SIZE_PX,\n personaMaxSize = DEFAULT_PERSONA_MAX_SIZE_PX\n } = props;\n\n const [personaSize, setPersonaSize] = useState(100);\n const videoTileRef = useRef<HTMLElement>(null);\n\n const locale = useLocale();\n const theme = useTheme();\n\n const isVideoRendered = !!renderElement;\n\n const observer = useRef(\n new ResizeObserver((entries): void => {\n const { width, height } = entries[0].contentRect;\n const personaSize = Math.min(width, height) / 3;\n setPersonaSize(Math.max(Math.min(personaSize, personaMaxSize), personaMinSize));\n })\n );\n\n useLayoutEffect(() => {\n if (videoTileRef.current) {\n observer.current.observe(videoTileRef.current);\n }\n const currentObserver = observer.current;\n return () => currentObserver.disconnect();\n }, [observer, videoTileRef]);\n\n /* @conditional-compile-remove(pinned-participants) */\n const useLongPressProps = useMemo(() => {\n return {\n onLongPress: () => {\n props.onLongTouch?.();\n },\n touchEventsOnly: true\n };\n // eslint-disable-next-line react-hooks/exhaustive-deps\n }, [props.onLongTouch]);\n /* @conditional-compile-remove(pinned-participants) */\n const longPressHandlers = useLongPress(useLongPressProps);\n const longPressHandlersTrampoline = useMemo(() => {\n /* @conditional-compile-remove(pinned-participants) */\n return longPressHandlers;\n return {};\n }, [\n /* @conditional-compile-remove(pinned-participants) */\n longPressHandlers\n ]);\n\n const placeholderOptions = {\n userId,\n text: initialsName || displayName,\n noVideoAvailableAriaLabel,\n coinSize: personaSize,\n styles: defaultPersonaStyles,\n hidePersonaDetails: true\n };\n\n const videoHintWithBorderRadius = mergeStyles(videoHint, { borderRadius: theme.effects.roundedCorner4 });\n\n const tileInfoStyle = useMemo(\n () =>\n mergeStyles(\n isVideoRendered ? videoHintWithBorderRadius : disabledVideoHint,\n getVideoTileOverrideColor(isVideoRendered, theme, 'neutralPrimary'),\n styles?.displayNameContainer\n ),\n [isVideoRendered, videoHintWithBorderRadius, theme, styles?.displayNameContainer]\n );\n\n const ids = useIdentifiers();\n\n const canShowLabel = showLabel && (displayName || (showMuteIndicator && isMuted));\n const participantStateString = participantStateStringTrampoline(props, locale);\n return (\n <Ref innerRef={videoTileRef}>\n <Stack\n data-ui-id={ids.videoTile}\n className={mergeStyles(\n rootStyles,\n {\n background: theme.palette.neutralLighter,\n borderRadius: theme.effects.roundedCorner4\n },\n isSpeaking && {\n '&::before': {\n content: `''`,\n position: 'absolute',\n zIndex: 1,\n border: `0.25rem solid ${theme.palette.themePrimary}`,\n borderRadius: theme.effects.roundedCorner4,\n width: '100%',\n height: '100%'\n }\n },\n styles?.root\n )}\n {...longPressHandlersTrampoline}\n >\n {isVideoRendered ? (\n <Stack\n className={mergeStyles(\n videoContainerStyles,\n isMirrored && { transform: 'scaleX(-1)' },\n styles?.videoContainer\n )}\n >\n {renderElement}\n </Stack>\n ) : (\n <Stack className={mergeStyles(videoContainerStyles)} style={{ opacity: participantStateString ? 0.4 : 1 }}>\n {onRenderPlaceholder ? (\n onRenderPlaceholder(userId ?? '', placeholderOptions, DefaultPlaceholder)\n ) : (\n <DefaultPlaceholder {...placeholderOptions} />\n )}\n </Stack>\n )}\n\n {(canShowLabel || participantStateString) && (\n <Stack horizontal className={tileInfoContainerStyle} tokens={tileInfoContainerTokens}>\n <Stack horizontal className={tileInfoStyle}>\n {canShowLabel && (\n <Text\n className={mergeStyles(displayNameStyle)}\n title={displayName}\n style={{ color: participantStateString ? theme.palette.neutralSecondary : 'inherit' }}\n >\n {displayName}\n </Text>\n )}\n {participantStateString && (\n <Text className={mergeStyles(participantStateStringStyles(theme))}>\n {bracketedParticipantString(participantStateString, !!canShowLabel)}\n </Text>\n )}\n {showMuteIndicator && isMuted && (\n <Stack className={mergeStyles(iconContainerStyle)}>\n <Icon iconName=\"VideoTileMicOff\" />\n </Stack>\n )}\n {\n /* @conditional-compile-remove(pinned-participants) */\n <VideoTileMoreOptionsButton menuItems={menuItems} menuStyles={props.styles} />\n }\n {\n /* @conditional-compile-remove(pinned-participants) */\n isPinned && (\n <Stack className={mergeStyles(iconContainerStyle)}>\n <Icon iconName=\"VideoTilePinned\" className={mergeStyles(pinIconStyle)} />\n </Stack>\n )\n }\n </Stack>\n </Stack>\n )}\n\n {children && (\n <Stack className={mergeStyles(overlayContainerStyles, styles?.overlayContainer)}>{children}</Stack>\n )}\n </Stack>\n </Ref>\n );\n};\n\nconst participantStateStringTrampoline = (props: VideoTileProps, locale: ComponentLocale): string | undefined => {\n /* @conditional-compile-remove(one-to-n-calling) */\n /* @conditional-compile-remove(PSTN-calls) */\n const strings = { ...locale.strings.videoTile, ...props.strings };\n /* @conditional-compile-remove(one-to-n-calling) */\n /* @conditional-compile-remove(PSTN-calls) */\n return props.participantState === 'Idle' || props.participantState === 'Connecting'\n ? strings?.participantStateConnecting\n : props.participantState === 'EarlyMedia' || props.participantState === 'Ringing'\n ? strings?.participantStateRinging\n : props.participantState === 'Hold'\n ? strings?.participantStateHold\n : undefined;\n\n return undefined;\n};\n\nconst tileInfoContainerTokens = {\n // A horizontal Stack sets the left margin to 0 for all it's children.\n // We need to allow the children to set their own margins\n childrenGap: 'none'\n};\n\nconst bracketedParticipantString = (participantString: string, withBrackets: boolean): string => {\n return withBrackets ? `(${participantString})` : participantString;\n};\n"]}
@@ -1,15 +1,17 @@
1
1
  /**
2
2
  * @private
3
3
  */
4
- export default function useLongPress(onClick: () => void, onLongPress: () => void, isMobile: boolean): {
5
- handlers: {
6
- onClick: () => void;
7
- onMouseDown: () => void;
8
- onMouseUp: () => void;
9
- onTouchStart: () => void;
10
- onTouchEnd: () => void;
11
- onKeyDown: () => void;
12
- onKeyUp: () => void;
13
- };
4
+ export default function useLongPress(props: {
5
+ onLongPress: () => void;
6
+ onClick?: () => void;
7
+ touchEventsOnly?: boolean;
8
+ }): {
9
+ onClick: () => void;
10
+ onMouseDown: () => void;
11
+ onMouseUp: () => void;
12
+ onTouchStart: () => void;
13
+ onTouchEnd: () => void;
14
+ onKeyDown: () => void;
15
+ onKeyUp: () => void;
14
16
  };
15
17
  //# sourceMappingURL=useLongPress.d.ts.map
@@ -1,65 +1,89 @@
1
1
  // Copyright (c) Microsoft Corporation.
2
2
  // Licensed under the MIT license.
3
- import { useRef, useState } from 'react';
3
+ import { useMemo, useRef, useState, useCallback, useEffect } from 'react';
4
4
  /**
5
5
  * @private
6
6
  */
7
- export default function useLongPress(onClick, onLongPress, isMobile) {
7
+ export default function useLongPress(props) {
8
+ const { onClick, onLongPress, touchEventsOnly = false } = props;
8
9
  const timerRef = useRef();
9
10
  const [isLongPress, setIsLongPress] = useState(false);
10
11
  const [action, setAction] = useState(false);
11
- function startPressTimer() {
12
+ useEffect(() => {
13
+ if (timerRef.current) {
14
+ clearTimeout(timerRef.current);
15
+ }
16
+ return () => {
17
+ if (timerRef.current) {
18
+ clearTimeout(timerRef.current);
19
+ }
20
+ };
21
+ }, [onClick, onLongPress, touchEventsOnly]);
22
+ const startPressTimer = useCallback(() => {
12
23
  setIsLongPress(false);
13
24
  timerRef.current = setTimeout(() => {
14
25
  setIsLongPress(true);
26
+ onLongPress();
15
27
  }, 500);
16
- }
17
- function handleOnClick() {
18
- // when it's mobile use ontouchstart and ontouchend to fire onclick and onlongpress event
19
- if (isMobile) {
28
+ }, [onLongPress]);
29
+ const handleOnClick = useCallback(() => {
30
+ if (touchEventsOnly || !onClick) {
20
31
  return;
21
32
  }
22
- onClick();
23
- if (isLongPress) {
24
- onLongPress();
33
+ if (!isLongPress) {
34
+ onClick();
35
+ }
36
+ }, [isLongPress, onClick, touchEventsOnly]);
37
+ const handleOnKeyDown = useCallback(() => {
38
+ if (touchEventsOnly) {
25
39
  return;
26
40
  }
27
- }
28
- function handleOnKeyDown() {
29
41
  if (action) {
30
42
  setAction(false);
31
43
  startPressTimer();
32
44
  }
33
- }
34
- function handleOnKeyUp() {
45
+ }, [action, startPressTimer, touchEventsOnly]);
46
+ const handleOnKeyUp = useCallback(() => {
47
+ if (touchEventsOnly) {
48
+ return;
49
+ }
35
50
  setAction(true);
36
51
  timerRef.current && clearTimeout(timerRef.current);
37
- }
38
- function handleOnMouseDown() {
52
+ }, [touchEventsOnly]);
53
+ const handleOnMouseDown = useCallback(() => {
54
+ if (touchEventsOnly) {
55
+ return;
56
+ }
39
57
  startPressTimer();
40
- }
41
- function handleOnMouseUp() {
58
+ }, [startPressTimer, touchEventsOnly]);
59
+ const handleOnMouseUp = useCallback(() => {
60
+ if (touchEventsOnly) {
61
+ return;
62
+ }
42
63
  timerRef.current && clearTimeout(timerRef.current);
43
- }
44
- function handleOnTouchStart() {
64
+ }, [touchEventsOnly]);
65
+ const handleOnTouchStart = useCallback(() => {
45
66
  startPressTimer();
46
- }
47
- function handleOnTouchEnd() {
48
- if (isMobile) {
49
- isLongPress ? onLongPress() : onClick();
50
- }
67
+ }, [startPressTimer]);
68
+ const handleOnTouchEnd = useCallback(() => {
51
69
  timerRef.current && clearTimeout(timerRef.current);
52
- }
53
- return {
54
- handlers: {
55
- onClick: handleOnClick,
56
- onMouseDown: handleOnMouseDown,
57
- onMouseUp: handleOnMouseUp,
58
- onTouchStart: handleOnTouchStart,
59
- onTouchEnd: handleOnTouchEnd,
60
- onKeyDown: handleOnKeyDown,
61
- onKeyUp: handleOnKeyUp
62
- }
63
- };
70
+ }, []);
71
+ return useMemo(() => ({
72
+ onClick: handleOnClick,
73
+ onMouseDown: handleOnMouseDown,
74
+ onMouseUp: handleOnMouseUp,
75
+ onTouchStart: handleOnTouchStart,
76
+ onTouchEnd: handleOnTouchEnd,
77
+ onKeyDown: handleOnKeyDown,
78
+ onKeyUp: handleOnKeyUp
79
+ }), [
80
+ handleOnClick,
81
+ handleOnKeyDown,
82
+ handleOnKeyUp,
83
+ handleOnMouseDown,
84
+ handleOnMouseUp,
85
+ handleOnTouchEnd,
86
+ handleOnTouchStart
87
+ ]);
64
88
  }
65
89
  //# sourceMappingURL=useLongPress.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"useLongPress.js","sourceRoot":"","sources":["../../../../../../../react-components/src/components/utils/useLongPress.ts"],"names":[],"mappings":"AAAA,uCAAuC;AACvC,kCAAkC;AAElC,OAAO,EAAE,MAAM,EAAE,QAAQ,EAAE,MAAM,OAAO,CAAC;AAEzC;;GAEG;AACH,MAAM,CAAC,OAAO,UAAU,YAAY,CAClC,OAAmB,EACnB,WAAuB,EACvB,QAAiB;IAYjB,MAAM,QAAQ,GAAG,MAAM,EAAiC,CAAC;IACzD,MAAM,CAAC,WAAW,EAAE,cAAc,CAAC,GAAG,QAAQ,CAAC,KAAK,CAAC,CAAC;IACtD,MAAM,CAAC,MAAM,EAAE,SAAS,CAAC,GAAG,QAAQ,CAAC,KAAK,CAAC,CAAC;IAE5C,SAAS,eAAe;QACtB,cAAc,CAAC,KAAK,CAAC,CAAC;QACtB,QAAQ,CAAC,OAAO,GAAG,UAAU,CAAC,GAAG,EAAE;YACjC,cAAc,CAAC,IAAI,CAAC,CAAC;QACvB,CAAC,EAAE,GAAG,CAAC,CAAC;IACV,CAAC;IAED,SAAS,aAAa;QACpB,yFAAyF;QACzF,IAAI,QAAQ,EAAE;YACZ,OAAO;SACR;QACD,OAAO,EAAE,CAAC;QACV,IAAI,WAAW,EAAE;YACf,WAAW,EAAE,CAAC;YACd,OAAO;SACR;IACH,CAAC;IAED,SAAS,eAAe;QACtB,IAAI,MAAM,EAAE;YACV,SAAS,CAAC,KAAK,CAAC,CAAC;YACjB,eAAe,EAAE,CAAC;SACnB;IACH,CAAC;IAED,SAAS,aAAa;QACpB,SAAS,CAAC,IAAI,CAAC,CAAC;QAChB,QAAQ,CAAC,OAAO,IAAI,YAAY,CAAC,QAAQ,CAAC,OAAO,CAAC,CAAC;IACrD,CAAC;IAED,SAAS,iBAAiB;QACxB,eAAe,EAAE,CAAC;IACpB,CAAC;IAED,SAAS,eAAe;QACtB,QAAQ,CAAC,OAAO,IAAI,YAAY,CAAC,QAAQ,CAAC,OAAO,CAAC,CAAC;IACrD,CAAC;IAED,SAAS,kBAAkB;QACzB,eAAe,EAAE,CAAC;IACpB,CAAC;IAED,SAAS,gBAAgB;QACvB,IAAI,QAAQ,EAAE;YACZ,WAAW,CAAC,CAAC,CAAC,WAAW,EAAE,CAAC,CAAC,CAAC,OAAO,EAAE,CAAC;SACzC;QAED,QAAQ,CAAC,OAAO,IAAI,YAAY,CAAC,QAAQ,CAAC,OAAO,CAAC,CAAC;IACrD,CAAC;IAED,OAAO;QACL,QAAQ,EAAE;YACR,OAAO,EAAE,aAAa;YACtB,WAAW,EAAE,iBAAiB;YAC9B,SAAS,EAAE,eAAe;YAC1B,YAAY,EAAE,kBAAkB;YAChC,UAAU,EAAE,gBAAgB;YAC5B,SAAS,EAAE,eAAe;YAC1B,OAAO,EAAE,aAAa;SACvB;KACF,CAAC;AACJ,CAAC","sourcesContent":["// Copyright (c) Microsoft Corporation.\n// Licensed under the MIT license.\n\nimport { useRef, useState } from 'react';\n\n/**\n * @private\n */\nexport default function useLongPress(\n onClick: () => void,\n onLongPress: () => void,\n isMobile: boolean\n): {\n handlers: {\n onClick: () => void;\n onMouseDown: () => void;\n onMouseUp: () => void;\n onTouchStart: () => void;\n onTouchEnd: () => void;\n onKeyDown: () => void;\n onKeyUp: () => void;\n };\n} {\n const timerRef = useRef<ReturnType<typeof setTimeout>>();\n const [isLongPress, setIsLongPress] = useState(false);\n const [action, setAction] = useState(false);\n\n function startPressTimer(): void {\n setIsLongPress(false);\n timerRef.current = setTimeout(() => {\n setIsLongPress(true);\n }, 500);\n }\n\n function handleOnClick(): void {\n // when it's mobile use ontouchstart and ontouchend to fire onclick and onlongpress event\n if (isMobile) {\n return;\n }\n onClick();\n if (isLongPress) {\n onLongPress();\n return;\n }\n }\n\n function handleOnKeyDown(): void {\n if (action) {\n setAction(false);\n startPressTimer();\n }\n }\n\n function handleOnKeyUp(): void {\n setAction(true);\n timerRef.current && clearTimeout(timerRef.current);\n }\n\n function handleOnMouseDown(): void {\n startPressTimer();\n }\n\n function handleOnMouseUp(): void {\n timerRef.current && clearTimeout(timerRef.current);\n }\n\n function handleOnTouchStart(): void {\n startPressTimer();\n }\n\n function handleOnTouchEnd(): void {\n if (isMobile) {\n isLongPress ? onLongPress() : onClick();\n }\n\n timerRef.current && clearTimeout(timerRef.current);\n }\n\n return {\n handlers: {\n onClick: handleOnClick,\n onMouseDown: handleOnMouseDown,\n onMouseUp: handleOnMouseUp,\n onTouchStart: handleOnTouchStart,\n onTouchEnd: handleOnTouchEnd,\n onKeyDown: handleOnKeyDown,\n onKeyUp: handleOnKeyUp\n }\n };\n}\n"]}
1
+ {"version":3,"file":"useLongPress.js","sourceRoot":"","sources":["../../../../../../../react-components/src/components/utils/useLongPress.ts"],"names":[],"mappings":"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","sourcesContent":["// Copyright (c) Microsoft Corporation.\n// Licensed under the MIT license.\n\nimport { useMemo, useRef, useState, useCallback, useEffect } from 'react';\n\n/**\n * @private\n */\nexport default function useLongPress(props: {\n onLongPress: () => void;\n onClick?: () => void;\n touchEventsOnly?: boolean;\n}): {\n onClick: () => void;\n onMouseDown: () => void;\n onMouseUp: () => void;\n onTouchStart: () => void;\n onTouchEnd: () => void;\n onKeyDown: () => void;\n onKeyUp: () => void;\n} {\n const { onClick, onLongPress, touchEventsOnly = false } = props;\n const timerRef = useRef<ReturnType<typeof setTimeout>>();\n const [isLongPress, setIsLongPress] = useState(false);\n const [action, setAction] = useState(false);\n\n useEffect(() => {\n if (timerRef.current) {\n clearTimeout(timerRef.current);\n }\n return () => {\n if (timerRef.current) {\n clearTimeout(timerRef.current);\n }\n };\n }, [onClick, onLongPress, touchEventsOnly]);\n\n const startPressTimer = useCallback(() => {\n setIsLongPress(false);\n timerRef.current = setTimeout(() => {\n setIsLongPress(true);\n onLongPress();\n }, 500);\n }, [onLongPress]);\n\n const handleOnClick = useCallback(() => {\n if (touchEventsOnly || !onClick) {\n return;\n }\n if (!isLongPress) {\n onClick();\n }\n }, [isLongPress, onClick, touchEventsOnly]);\n\n const handleOnKeyDown = useCallback(() => {\n if (touchEventsOnly) {\n return;\n }\n if (action) {\n setAction(false);\n startPressTimer();\n }\n }, [action, startPressTimer, touchEventsOnly]);\n\n const handleOnKeyUp = useCallback(() => {\n if (touchEventsOnly) {\n return;\n }\n setAction(true);\n timerRef.current && clearTimeout(timerRef.current);\n }, [touchEventsOnly]);\n\n const handleOnMouseDown = useCallback(() => {\n if (touchEventsOnly) {\n return;\n }\n startPressTimer();\n }, [startPressTimer, touchEventsOnly]);\n\n const handleOnMouseUp = useCallback(() => {\n if (touchEventsOnly) {\n return;\n }\n timerRef.current && clearTimeout(timerRef.current);\n }, [touchEventsOnly]);\n\n const handleOnTouchStart = useCallback(() => {\n startPressTimer();\n }, [startPressTimer]);\n\n const handleOnTouchEnd = useCallback(() => {\n timerRef.current && clearTimeout(timerRef.current);\n }, []);\n\n return useMemo(\n () => ({\n onClick: handleOnClick,\n onMouseDown: handleOnMouseDown,\n onMouseUp: handleOnMouseUp,\n onTouchStart: handleOnTouchStart,\n onTouchEnd: handleOnTouchEnd,\n onKeyDown: handleOnKeyDown,\n onKeyUp: handleOnKeyUp\n }),\n [\n handleOnClick,\n handleOnKeyDown,\n handleOnKeyUp,\n handleOnMouseDown,\n handleOnMouseUp,\n handleOnTouchEnd,\n handleOnTouchStart\n ]\n );\n}\n"]}
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@azure/communication-react",
3
- "version": "1.4.2-alpha-202211240014.0",
3
+ "version": "1.4.2-alpha-202211260013.0",
4
4
  "sideEffects": false,
5
5
  "description": "React library for building modern communication user experiences utilizing Azure Communication Services",
6
6
  "keywords": [
@@ -86,13 +86,13 @@
86
86
  "@azure/core-auth": "1.3.2",
87
87
  "@babel/cli": "~7.16.0",
88
88
  "@babel/core": "~7.16.0",
89
- "@internal/calling-component-bindings": "1.4.2-alpha-202211240014.0",
90
- "@internal/calling-stateful-client": "1.4.2-alpha-202211240014.0",
91
- "@internal/chat-component-bindings": "1.4.2-alpha-202211240014.0",
92
- "@internal/chat-stateful-client": "1.4.2-alpha-202211240014.0",
93
- "@internal/fake-backends": "1.4.2-alpha-202211240014.0",
94
- "@internal/react-components": "1.4.2-alpha-202211240014.0",
95
- "@internal/react-composites": "1.4.2-alpha-202211240014.0",
89
+ "@internal/calling-component-bindings": "1.4.2-alpha-202211260013.0",
90
+ "@internal/calling-stateful-client": "1.4.2-alpha-202211260013.0",
91
+ "@internal/chat-component-bindings": "1.4.2-alpha-202211260013.0",
92
+ "@internal/chat-stateful-client": "1.4.2-alpha-202211260013.0",
93
+ "@internal/fake-backends": "1.4.2-alpha-202211260013.0",
94
+ "@internal/react-components": "1.4.2-alpha-202211260013.0",
95
+ "@internal/react-composites": "1.4.2-alpha-202211260013.0",
96
96
  "@microsoft/api-documenter": "~7.12.11",
97
97
  "@microsoft/api-extractor": "~7.18.0",
98
98
  "@rollup/plugin-json": "~4.1.0",