update pan tool button after zoom changes
This commit is contained in:
parent
1de4b3f644
commit
eb7c3dcbc8
@ -4,6 +4,7 @@ import WhiteboardOverlayContainer from '/imports/ui/components/whiteboard/whiteb
|
||||
import WhiteboardContainer from '/imports/ui/components/whiteboard/container';
|
||||
import WhiteboardToolbarContainer from '/imports/ui/components/whiteboard/whiteboard-toolbar/container';
|
||||
import { HUNDRED_PERCENT, MAX_PERCENT } from '/imports/utils/slideCalcUtils';
|
||||
import { SPACE } from '/imports/utils/keyCodes';
|
||||
import { defineMessages, injectIntl } from 'react-intl';
|
||||
import { toast } from 'react-toastify';
|
||||
import { Session } from 'meteor/session';
|
||||
@ -76,6 +77,7 @@ class Presentation extends PureComponent {
|
||||
fitToWidth: false,
|
||||
isFullscreen: false,
|
||||
tldrawAPI: null,
|
||||
isPanning: false,
|
||||
};
|
||||
|
||||
this.currentPresentationToastId = null;
|
||||
@ -90,6 +92,8 @@ class Presentation extends PureComponent {
|
||||
this.getPresentationSizesAvailable = this.getPresentationSizesAvailable.bind(this);
|
||||
this.handleResize = this.handleResize.bind(this);
|
||||
this.setTldrawAPI = this.setTldrawAPI.bind(this);
|
||||
this.setIsPanning = this.setIsPanning.bind(this);
|
||||
this.handlePanShortcut = this.handlePanShortcut.bind(this);
|
||||
this.renderPresentationMenu = this.renderPresentationMenu.bind(this);
|
||||
|
||||
this.onResize = () => setTimeout(this.handleResize.bind(this), 0);
|
||||
@ -122,8 +126,28 @@ class Presentation extends PureComponent {
|
||||
return stateChange;
|
||||
}
|
||||
|
||||
setIsPanning() {
|
||||
this.setState({
|
||||
isPanning: !this.state.isPanning,
|
||||
});
|
||||
}
|
||||
|
||||
handlePanShortcut(e) {
|
||||
const { userIsPresenter } = this.props;
|
||||
if (e.keyCode === SPACE && userIsPresenter) {
|
||||
switch(e.type) {
|
||||
case 'keyup':
|
||||
return this.state.isPanning && this.setIsPanning();
|
||||
case 'keydown':
|
||||
return !this.state.isPanning && this.setIsPanning();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
this.getInitialPresentationSizes();
|
||||
this.refPresentationContainer.addEventListener('keydown', this.handlePanShortcut);
|
||||
this.refPresentationContainer.addEventListener('keyup', this.handlePanShortcut);
|
||||
this.refPresentationContainer
|
||||
.addEventListener(FULLSCREEN_CHANGE_EVENT, this.onFullscreenChange);
|
||||
window.addEventListener('resize', this.onResize, false);
|
||||
@ -267,6 +291,9 @@ class Presentation extends PureComponent {
|
||||
value: currentSlide.num,
|
||||
});
|
||||
}
|
||||
if (!userIsPresenter && prevProps.userIsPresenter) {
|
||||
this.setIsPanning();
|
||||
}
|
||||
}
|
||||
|
||||
componentWillUnmount() {
|
||||
@ -276,6 +303,8 @@ class Presentation extends PureComponent {
|
||||
window.removeEventListener('resize', this.onResize, false);
|
||||
this.refPresentationContainer
|
||||
.removeEventListener(FULLSCREEN_CHANGE_EVENT, this.onFullscreenChange);
|
||||
this.refPresentationContainer.removeEventListener('keydown', this.handlePanShortcut);
|
||||
this.refPresentationContainer.removeEventListener('keyup', this.handlePanShortcut);
|
||||
|
||||
if (fullscreenContext) {
|
||||
layoutContextDispatch({
|
||||
@ -738,7 +767,8 @@ class Presentation extends PureComponent {
|
||||
layoutContextDispatch,
|
||||
presentationIsOpen,
|
||||
}}
|
||||
isZoomed={this.state.isZoomed}
|
||||
setIsPanning={this.setIsPanning}
|
||||
isPanning={this.state.isPanning}
|
||||
curPageId={this.state.tldrawAPI?.getPage()?.id}
|
||||
currentSlideNum={currentSlide.num}
|
||||
presentationId={currentSlide.presentationId}
|
||||
@ -992,6 +1022,7 @@ class Presentation extends PureComponent {
|
||||
presentationWidth={svgWidth}
|
||||
presentationHeight={svgHeight}
|
||||
isViewersCursorLocked={isViewersCursorLocked}
|
||||
isPanning={this.state.isPanning}
|
||||
zoomChanger={this.zoomChanger}
|
||||
fitToWidth={fitToWidth}
|
||||
zoomValue={zoom}
|
||||
|
@ -84,6 +84,10 @@ const intlMessages = defineMessages({
|
||||
id: 'app.whiteboard.toolbar.multiUserOff',
|
||||
description: 'Whiteboard toolbar turn multi-user off menu',
|
||||
},
|
||||
pan: {
|
||||
id: 'app.whiteboard.toolbar.tools.hand',
|
||||
description: 'presentation toolbar pan label',
|
||||
}
|
||||
});
|
||||
|
||||
class PresentationToolbar extends PureComponent {
|
||||
@ -105,6 +109,11 @@ class PresentationToolbar extends PureComponent {
|
||||
document.addEventListener('keydown', this.switchSlide);
|
||||
}
|
||||
|
||||
componentDidUpdate(prevProps, prevState) {
|
||||
const { zoom, setIsPanning } = this.props;
|
||||
if (zoom <= HUNDRED_PERCENT && zoom !== prevProps.zoom) setIsPanning();
|
||||
}
|
||||
|
||||
componentWillUnmount() {
|
||||
document.removeEventListener('keydown', this.switchSlide);
|
||||
}
|
||||
@ -257,6 +266,8 @@ class PresentationToolbar extends PureComponent {
|
||||
toolbarWidth,
|
||||
multiUserSize,
|
||||
multiUser,
|
||||
setIsPanning,
|
||||
isPanning,
|
||||
} = this.props;
|
||||
|
||||
const { isMobile } = deviceInfo;
|
||||
@ -393,6 +404,20 @@ class PresentationToolbar extends PureComponent {
|
||||
/>
|
||||
</TooltipContainer>
|
||||
) : null}
|
||||
<Styled.FitToWidthButton
|
||||
role="button"
|
||||
data-test="panButton"
|
||||
aria-label={intl.formatMessage(intlMessages.pan)}
|
||||
color="light"
|
||||
disabled={(zoom <= HUNDRED_PERCENT)}
|
||||
icon="hand"
|
||||
size="md"
|
||||
circle
|
||||
onClick={setIsPanning}
|
||||
label={intl.formatMessage(intlMessages.pan)}
|
||||
hideLabel
|
||||
panning={isPanning}
|
||||
/>
|
||||
<Styled.FitToWidthButton
|
||||
role="button"
|
||||
data-test="fitToWidthButton"
|
||||
|
@ -204,6 +204,12 @@ const FitToWidthButton = styled(Button)`
|
||||
background-color: ${colorOffWhite};
|
||||
border: 0;
|
||||
}
|
||||
|
||||
${({ panning }) => panning && `
|
||||
> span {
|
||||
background-color: #DCE4EC;
|
||||
}
|
||||
`}
|
||||
`;
|
||||
|
||||
const MultiUserTool = styled.span`
|
||||
|
@ -50,6 +50,7 @@ export default function Whiteboard(props) {
|
||||
zoomValue,
|
||||
width,
|
||||
height,
|
||||
isPanning,
|
||||
} = props;
|
||||
|
||||
const { pages, pageStates } = initDefaultPages(curPres?.pages.length || 1);
|
||||
@ -63,6 +64,7 @@ export default function Whiteboard(props) {
|
||||
assets: {},
|
||||
});
|
||||
const [tldrawAPI, setTLDrawAPI] = React.useState(null);
|
||||
const [forcePanning, setForcePanning] = React.useState(false);
|
||||
const [zoom, setZoom] = React.useState(HUNDRED_PERCENT);
|
||||
const [isMounting, setIsMounting] = React.useState(true);
|
||||
const prevShapes = usePrevious(shapes);
|
||||
@ -221,8 +223,18 @@ export default function Whiteboard(props) {
|
||||
// removes image tool from the tldraw toolbar
|
||||
document.getElementById("TD-PrimaryTools-Image").style.display = 'none';
|
||||
}
|
||||
|
||||
if (tldrawAPI) {
|
||||
tldrawAPI.isForcePanning = isPanning;
|
||||
}
|
||||
});
|
||||
|
||||
React.useEffect(() => {
|
||||
if (tldrawAPI) {
|
||||
tldrawAPI.isForcePanning = isPanning;
|
||||
}
|
||||
}, [isPanning]);
|
||||
|
||||
const onMount = (app) => {
|
||||
app.setSetting('language', document.getElementsByTagName('html')[0]?.lang || 'en');
|
||||
app.setSetting('dockPosition', isRTL ? 'left' : 'right');
|
||||
@ -310,7 +322,7 @@ export default function Whiteboard(props) {
|
||||
const dockPos = webcams?.getAttribute("data-position");
|
||||
const editableWB = (
|
||||
<Tldraw
|
||||
key={`wb-${isRTL}-${width}-${height}-${dockPos}`}
|
||||
key={`wb-${isRTL}-${width}-${height}-${dockPos}-${forcePanning}`}
|
||||
document={doc}
|
||||
// disable the ability to drag and drop files onto the whiteboard
|
||||
// until we handle saving of assets in akka.
|
||||
@ -525,6 +537,7 @@ export default function Whiteboard(props) {
|
||||
whiteboardId={whiteboardId}
|
||||
isViewersCursorLocked={isViewersCursorLocked}
|
||||
isMultiUserActive={isMultiUserActive}
|
||||
isPanning={isPanning}
|
||||
>
|
||||
{hasWBAccess || isPresenter ? editableWB : readOnlyWB}
|
||||
</Cursors>
|
||||
|
@ -127,6 +127,7 @@ export default function Cursors(props) {
|
||||
hasMultiUserAccess,
|
||||
isMultiUserActive,
|
||||
application,
|
||||
isPanning,
|
||||
} = props;
|
||||
|
||||
const start = () => setActive(true);
|
||||
@ -282,10 +283,12 @@ export default function Cursors(props) {
|
||||
});
|
||||
|
||||
const multiUserAccess = hasMultiUserAccess(whiteboardId, currentUser?.userId);
|
||||
let cursorType = multiUserAccess || currentUser?.presenter ? "none" : "default";
|
||||
if (isPanning) cursorType = 'grab';
|
||||
|
||||
return (
|
||||
<span ref={(r) => (cursorWrapper = r)}>
|
||||
<div style={{ height: "100%", cursor: multiUserAccess || currentUser?.presenter ? "none" : "default" }}>
|
||||
<div style={{ height: "100%", cursor: cursorType }}>
|
||||
{(active && multiUserAccess || (active && currentUser?.presenter)) && (
|
||||
<PositionLabel
|
||||
pos={pos}
|
||||
|
Loading…
Reference in New Issue
Block a user