Merge branch 'develop' into feature/profile-active-sessions
This commit is contained in:
commit
43ea0aee3e
@ -61,8 +61,14 @@ const StyledContainer = styled.div`
|
||||
`;
|
||||
|
||||
const Layout = (props) => {
|
||||
const { children, isTabletView, setIsTabletView, setWindowWidth, isFrame } =
|
||||
props;
|
||||
const {
|
||||
children,
|
||||
isTabletView,
|
||||
setIsTabletView,
|
||||
setWindowWidth,
|
||||
setWindowAngle,
|
||||
isFrame,
|
||||
} = props;
|
||||
|
||||
const [contentHeight, setContentHeight] = useState();
|
||||
const [isPortrait, setIsPortrait] = useState();
|
||||
@ -97,12 +103,23 @@ const Layout = (props) => {
|
||||
window.addEventListener("resize", onResize);
|
||||
|
||||
if (isMobile || isTabletView || !isFrame) {
|
||||
if (window.screen?.orientation) {
|
||||
window.screen.orientation.addEventListener(
|
||||
"change",
|
||||
onOrientationChange,
|
||||
);
|
||||
} else {
|
||||
window.addEventListener("orientationchange", onOrientationChange);
|
||||
}
|
||||
}
|
||||
|
||||
return () => {
|
||||
window.removeEventListener("resize", onResize);
|
||||
window.removeEventListener("orientationchange", onOrientationChange);
|
||||
window.screen?.orientation?.removeEventListener(
|
||||
"change",
|
||||
onOrientationChange,
|
||||
);
|
||||
};
|
||||
}, [isTabletView]);
|
||||
|
||||
@ -128,6 +145,9 @@ const Layout = (props) => {
|
||||
e.preventDefault();
|
||||
e.stopPropagation();
|
||||
|
||||
const angle = window.screen?.orientation?.angle ?? window.orientation ?? 0;
|
||||
|
||||
setWindowAngle(angle);
|
||||
setWindowWidth(window.innerWidth);
|
||||
};
|
||||
|
||||
@ -149,12 +169,18 @@ Layout.propTypes = {
|
||||
};
|
||||
|
||||
export default inject(({ settingsStore }) => {
|
||||
const { isTabletView, setIsTabletView, setWindowWidth, isFrame } =
|
||||
settingsStore;
|
||||
return {
|
||||
const {
|
||||
isTabletView,
|
||||
setIsTabletView,
|
||||
setWindowWidth,
|
||||
isFrame,
|
||||
setWindowAngle,
|
||||
} = settingsStore;
|
||||
return {
|
||||
isTabletView,
|
||||
setIsTabletView,
|
||||
setWindowWidth,
|
||||
setWindowAngle,
|
||||
isFrame,
|
||||
};
|
||||
})(observer(Layout));
|
||||
|
@ -318,6 +318,8 @@ class FileRow extends Component {
|
||||
name,
|
||||
isMediaActive,
|
||||
downloadInCurrentTab,
|
||||
isPlugin,
|
||||
onPluginClick,
|
||||
} = this.props;
|
||||
|
||||
const { showPasswordInput, password, passwordValid } = this.state;
|
||||
@ -347,13 +349,13 @@ class FileRow extends Component {
|
||||
>
|
||||
<>
|
||||
{item.fileId ? (
|
||||
isMedia ? (
|
||||
isMedia || (isPlugin && onPluginClick) ? (
|
||||
<Link
|
||||
className="upload-panel_file-row-link"
|
||||
fontWeight="600"
|
||||
color={item.error && "#A3A9AE"}
|
||||
truncate
|
||||
onClick={onMediaClick}
|
||||
onClick={isMedia ? onMediaClick : onPluginClick}
|
||||
>
|
||||
{name}
|
||||
{fileExtension}
|
||||
@ -435,6 +437,7 @@ export default inject(
|
||||
uploadDataStore,
|
||||
mediaViewerDataStore,
|
||||
settingsStore,
|
||||
pluginStore,
|
||||
},
|
||||
{ item },
|
||||
) => {
|
||||
@ -458,6 +461,31 @@ export default inject(
|
||||
if (!!ext) splitted.splice(-1);
|
||||
}
|
||||
|
||||
const { fileItemsList } = pluginStore;
|
||||
const { enablePlugins, currentDeviceType } = settingsStore;
|
||||
|
||||
let isPlugin = false;
|
||||
let onPluginClick = null;
|
||||
|
||||
if (fileItemsList && enablePlugins) {
|
||||
let currPluginItem = null;
|
||||
|
||||
fileItemsList.forEach((i) => {
|
||||
if (i.key === item?.fileInfo?.fileExst) currPluginItem = i.value;
|
||||
});
|
||||
|
||||
if (currPluginItem) {
|
||||
const correctDevice = currPluginItem.devices
|
||||
? currPluginItem.devices.includes(currentDeviceType)
|
||||
: true;
|
||||
if (correctDevice) {
|
||||
isPlugin = true;
|
||||
onPluginClick = () =>
|
||||
currPluginItem.onClick({ ...item, ...item.fileInfo });
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
name = splitted.join(".");
|
||||
|
||||
const { theme } = settingsStore;
|
||||
@ -509,6 +537,9 @@ export default inject(
|
||||
|
||||
setCurrentItem,
|
||||
clearUploadedFilesHistory,
|
||||
|
||||
isPlugin,
|
||||
onPluginClick,
|
||||
};
|
||||
},
|
||||
)(withTranslation("UploadPanel")(observer(FileRow)));
|
||||
|
@ -55,6 +55,11 @@ const StyledModalDialog = styled(ModalDialog)`
|
||||
a {
|
||||
color: #4781d1;
|
||||
}
|
||||
|
||||
.debug-info-body,
|
||||
.debug-info-footer {
|
||||
user-select: text;
|
||||
}
|
||||
}
|
||||
|
||||
.markdown-wrapper {
|
||||
@ -130,7 +135,7 @@ const DebugInfoDialog = (props) => {
|
||||
)}
|
||||
<Text>{`# User Agent: ${navigator.userAgent}`}</Text>
|
||||
</ModalDialog.Body>
|
||||
<ModalDialog.Footer>
|
||||
<ModalDialog.Footer className="debug-info-footer">
|
||||
<Box
|
||||
className="markdown-wrapper"
|
||||
overflowProp="auto"
|
||||
|
@ -71,6 +71,7 @@ const WhiteLabel = (props) => {
|
||||
deviceType,
|
||||
|
||||
resetIsInit,
|
||||
standalone,
|
||||
} = props;
|
||||
const navigate = useNavigate();
|
||||
const location = useLocation();
|
||||
@ -82,7 +83,9 @@ const WhiteLabel = (props) => {
|
||||
const isMobileView = deviceType === DeviceType.mobile;
|
||||
|
||||
const init = async () => {
|
||||
const isWhiteLabelPage = location.pathname.includes("white-label");
|
||||
const isWhiteLabelPage = standalone
|
||||
? location.pathname.includes("white-label")
|
||||
: true;
|
||||
|
||||
if ((isMobileView && isWhiteLabelPage) || !isMobileView) {
|
||||
const page = isMobileView ? "white-label" : "branding";
|
||||
@ -555,8 +558,11 @@ export default inject(({ settingsStore, common, currentQuotaStore }) => {
|
||||
resetIsInit,
|
||||
} = common;
|
||||
|
||||
const { whiteLabelLogoUrls: defaultWhiteLabelLogoUrls, deviceType } =
|
||||
settingsStore;
|
||||
const {
|
||||
whiteLabelLogoUrls: defaultWhiteLabelLogoUrls,
|
||||
deviceType,
|
||||
standalone,
|
||||
} = settingsStore;
|
||||
const { isBrandingAndCustomizationAvailable } = currentQuotaStore;
|
||||
|
||||
return {
|
||||
@ -576,5 +582,6 @@ export default inject(({ settingsStore, common, currentQuotaStore }) => {
|
||||
|
||||
deviceType,
|
||||
resetIsInit,
|
||||
standalone,
|
||||
};
|
||||
})(withTranslation(["Settings", "Profile", "Common"])(observer(WhiteLabel)));
|
||||
|
@ -103,7 +103,7 @@ const Branding = ({
|
||||
};
|
||||
}, []);
|
||||
|
||||
if (isMobileView)
|
||||
if (isMobileView && standalone)
|
||||
return (
|
||||
<MobileView isSettingPaid={isSettingPaid} isManagement={isManagement()} />
|
||||
);
|
||||
|
@ -48,7 +48,7 @@ const SubmenuCommon = (props) => {
|
||||
loadBaseInfo,
|
||||
isLoadedSubmenu,
|
||||
getWhiteLabelLogoUrls,
|
||||
deviceType,
|
||||
currentDeviceType,
|
||||
isMobileView,
|
||||
} = props;
|
||||
const navigate = useNavigate();
|
||||
@ -118,9 +118,9 @@ const SubmenuCommon = (props) => {
|
||||
startSelect={currentTab}
|
||||
onSelect={(e) => onSelect(e)}
|
||||
topProps={
|
||||
deviceType === DeviceType.desktop
|
||||
currentDeviceType === DeviceType.desktop
|
||||
? 0
|
||||
: deviceType === DeviceType.mobile
|
||||
: currentDeviceType === DeviceType.mobile
|
||||
? "53px"
|
||||
: "61px"
|
||||
}
|
||||
@ -137,9 +137,9 @@ export default inject(({ settingsStore, common }) => {
|
||||
getWhiteLabelLogoUrls,
|
||||
} = common;
|
||||
|
||||
const deviceType = settingsStore.deviceType;
|
||||
const currentDeviceType = settingsStore.currentDeviceType;
|
||||
|
||||
const isMobileView = deviceType === DeviceType.mobile;
|
||||
const isMobileView = settingsStore.deviceType === DeviceType.mobile;
|
||||
return {
|
||||
loadBaseInfo: async (page) => {
|
||||
await initSettings(page);
|
||||
@ -148,7 +148,7 @@ export default inject(({ settingsStore, common }) => {
|
||||
setIsLoadedSubmenu,
|
||||
isLoadedSubmenu,
|
||||
getWhiteLabelLogoUrls,
|
||||
deviceType,
|
||||
currentDeviceType,
|
||||
isMobileView,
|
||||
};
|
||||
})(withLoading(withTranslation("Settings")(observer(SubmenuCommon))));
|
||||
|
@ -81,6 +81,8 @@ export interface PluginsProps {
|
||||
) => Promise<unknown>;
|
||||
addPlugin: (data: FormData) => Promise<void>;
|
||||
|
||||
updatePlugins: (fromList?: boolean) => Promise<void>;
|
||||
|
||||
currentColorScheme: TColorScheme;
|
||||
theme: TTheme;
|
||||
|
||||
|
@ -56,6 +56,8 @@ const PluginPage = ({
|
||||
updatePlugin,
|
||||
addPlugin,
|
||||
|
||||
updatePlugins,
|
||||
|
||||
theme,
|
||||
isLoading,
|
||||
isEmptyList,
|
||||
@ -73,6 +75,10 @@ const PluginPage = ({
|
||||
setDocumentTitle(t("Common:Plugins"));
|
||||
}, [t]);
|
||||
|
||||
React.useEffect(() => {
|
||||
updatePlugins(true);
|
||||
}, [updatePlugins]);
|
||||
|
||||
return isLoading || (!isEmptyList && pluginList.length === 0) ? (
|
||||
<StyledContainer>
|
||||
<ListLoader withUpload={withUpload} />
|
||||
@ -133,6 +139,7 @@ export default inject(
|
||||
const {
|
||||
pluginList,
|
||||
updatePlugin,
|
||||
updatePlugins,
|
||||
setCurrentSettingsDialogPlugin,
|
||||
setSettingsPluginDialogVisible,
|
||||
|
||||
@ -153,6 +160,7 @@ export default inject(
|
||||
pluginList,
|
||||
|
||||
updatePlugin,
|
||||
updatePlugins,
|
||||
|
||||
openSettingsDialog,
|
||||
|
||||
|
@ -239,7 +239,7 @@ class PluginStore {
|
||||
this.setIsInit(true);
|
||||
};
|
||||
|
||||
updatePlugins = async () => {
|
||||
updatePlugins = async (fromList?: boolean) => {
|
||||
if (!this.userStore || !this.userStore.user) return;
|
||||
|
||||
const { isAdmin, isOwner } = this.userStore.user;
|
||||
@ -254,7 +254,7 @@ class PluginStore {
|
||||
);
|
||||
|
||||
this.setIsEmptyList(plugins.length === 0);
|
||||
plugins.forEach((plugin) => this.initPlugin(plugin));
|
||||
plugins.forEach((plugin) => this.initPlugin(plugin, undefined, fromList));
|
||||
|
||||
setTimeout(() => {
|
||||
this.setIsLoading(false);
|
||||
@ -298,7 +298,12 @@ class PluginStore {
|
||||
}
|
||||
};
|
||||
|
||||
initPlugin = (plugin: TAPIPlugin, callback?: (plugin: TPlugin) => void) => {
|
||||
initPlugin = (
|
||||
plugin: TAPIPlugin,
|
||||
callback?: (plugin: TPlugin) => void,
|
||||
fromList?: boolean,
|
||||
) => {
|
||||
if (!plugin.enabled && !fromList) return;
|
||||
const onLoad = async () => {
|
||||
const iWindow = this.pluginFrame?.contentWindow as IframeWindow;
|
||||
|
||||
|
@ -359,6 +359,7 @@ const LoginForm: React.FC<ILoginFormProps> = ({
|
||||
onChange={onChangePassword}
|
||||
onKeyDown={onKeyDown}
|
||||
isAutoFocussed={!!emailFromInvitation}
|
||||
isDisableTooltip
|
||||
/>
|
||||
</FieldContainer>
|
||||
|
||||
|
@ -30,7 +30,7 @@ import { ReactSVG } from "react-svg";
|
||||
import TriangleNavigationDownReactSvgUrl from "PUBLIC_DIR/images/triangle.navigation.down.react.svg?url";
|
||||
|
||||
import { Text } from "../text";
|
||||
import { ContextMenu, ContextMenuTypeOnClick } from "../context-menu";
|
||||
import { ContextMenu } from "../context-menu";
|
||||
|
||||
import { GroupMainButton } from "./MainButton.styled";
|
||||
import { MainButtonProps } from "./MainButton.types";
|
||||
@ -47,7 +47,6 @@ const MainButton = (props: MainButtonProps) => {
|
||||
toggle: (e: React.MouseEvent) => boolean;
|
||||
getVisible: () => boolean;
|
||||
}>(null);
|
||||
const visibleRef = useRef(false);
|
||||
|
||||
const stopAction = (e: React.MouseEvent) => e.preventDefault();
|
||||
|
||||
@ -56,12 +55,7 @@ const MainButton = (props: MainButtonProps) => {
|
||||
|
||||
const menu = menuRef.current;
|
||||
|
||||
if (visibleRef.current) {
|
||||
menu.hide(e);
|
||||
visibleRef.current = false;
|
||||
} else {
|
||||
visibleRef.current = menu.toggle(e);
|
||||
}
|
||||
menu.toggle(e);
|
||||
};
|
||||
|
||||
const onMainButtonClick = (e: React.MouseEvent) => {
|
||||
@ -76,20 +70,6 @@ const MainButton = (props: MainButtonProps) => {
|
||||
}
|
||||
};
|
||||
|
||||
const newModel = React.useMemo(() => {
|
||||
return model.map((m) => {
|
||||
if ("onClick" in m && m.onClick) {
|
||||
const onClick: ContextMenuTypeOnClick = (e) => {
|
||||
visibleRef.current = false;
|
||||
m.onClick?.(e);
|
||||
};
|
||||
return { ...m, onClick };
|
||||
}
|
||||
|
||||
return m;
|
||||
});
|
||||
}, [model]);
|
||||
|
||||
return (
|
||||
<GroupMainButton {...rest} ref={ref} data-testid="main-button">
|
||||
<MainButtonTheme {...rest} id={id} onClick={onMainButtonClick}>
|
||||
@ -101,7 +81,7 @@ const MainButton = (props: MainButtonProps) => {
|
||||
src={TriangleNavigationDownReactSvgUrl}
|
||||
/>
|
||||
|
||||
<ContextMenu model={newModel} containerRef={ref} ref={menuRef} />
|
||||
<ContextMenu model={model} containerRef={ref} ref={menuRef} />
|
||||
</>
|
||||
)}
|
||||
</MainButtonTheme>
|
||||
|
@ -314,6 +314,8 @@ class SettingsStore {
|
||||
|
||||
windowWidth = window.innerWidth;
|
||||
|
||||
windowAngle = window.screen?.orientation?.angle ?? window.orientation ?? 0;
|
||||
|
||||
constructor() {
|
||||
makeAutoObservable(this);
|
||||
}
|
||||
@ -1083,6 +1085,10 @@ class SettingsStore {
|
||||
}
|
||||
};
|
||||
|
||||
setWindowAngle = (angle: number) => {
|
||||
this.windowAngle = angle;
|
||||
};
|
||||
|
||||
setWindowWidth = (width: number) => {
|
||||
if (width <= deviceSize.mobile && this.windowWidth <= deviceSize.mobile)
|
||||
return;
|
||||
@ -1100,7 +1106,8 @@ class SettingsStore {
|
||||
}
|
||||
|
||||
get deviceType() {
|
||||
const angleByRadians = (Math.PI / 180) * window.screen.orientation.angle;
|
||||
const angleByRadians = (Math.PI / 180) * this.windowAngle;
|
||||
|
||||
const width = Math.abs(
|
||||
Math.round(
|
||||
Math.sin(angleByRadians) * window.innerHeight +
|
||||
|
@ -53,7 +53,9 @@ export const isMobile = (width?: number) => {
|
||||
};
|
||||
|
||||
export const isMobileDevice = () => {
|
||||
const angleByRadians = (Math.PI / 180) * window.screen.orientation.angle;
|
||||
const angleByRadians =
|
||||
(Math.PI / 180) *
|
||||
(window.screen?.orientation?.angle ?? window.orientation ?? 0);
|
||||
const width = Math.abs(
|
||||
Math.round(
|
||||
Math.sin(angleByRadians) * window.innerHeight +
|
||||
|
Loading…
Reference in New Issue
Block a user