Merge branch 'develop' into hotfix/documents-bugfix
# Conflicts: # web/ASC.Web.Common/src/components/PageLayout/index.js # web/ASC.Web.Components/package.json
This commit is contained in:
commit
5f6e0e60e8
@ -405,11 +405,11 @@ class FilesRowContent extends React.PureComponent {
|
||||
fileAction,
|
||||
isTrashFolder,
|
||||
folders,
|
||||
widthProp,
|
||||
isLoading,
|
||||
isMobile,
|
||||
canWebEdit,
|
||||
canConvert,
|
||||
sectionWidth,
|
||||
} = this.props;
|
||||
const {
|
||||
itemTitle,
|
||||
@ -473,7 +473,7 @@ class FilesRowContent extends React.PureComponent {
|
||||
/>
|
||||
)}
|
||||
<SimpleFilesRowContent
|
||||
widthProp={widthProp}
|
||||
sectionWidth={sectionWidth}
|
||||
isMobile={isMobile}
|
||||
sideColor={sideColor}
|
||||
isFile={fileExst}
|
||||
@ -505,7 +505,7 @@ class FilesRowContent extends React.PureComponent {
|
||||
>
|
||||
{fileExst}
|
||||
</Text>
|
||||
{canConvert && (
|
||||
{canConvert && !isTrashFolder && (
|
||||
<IconButton
|
||||
onClick={this.setConvertDialogVisible}
|
||||
iconName="FileActionsConvertIcon"
|
||||
@ -513,14 +513,18 @@ class FilesRowContent extends React.PureComponent {
|
||||
size="small"
|
||||
isfill={true}
|
||||
color="#A3A9AE"
|
||||
hoverColor="#3B72A7"
|
||||
/>
|
||||
)}
|
||||
{canWebEdit && (
|
||||
<Icons.AccessEditIcon
|
||||
{canWebEdit && !isTrashFolder && (
|
||||
<IconButton
|
||||
onClick={this.onFilesClick}
|
||||
iconName="AccessEditIcon"
|
||||
className="badge"
|
||||
size="small"
|
||||
isfill={true}
|
||||
color="#A3A9AE"
|
||||
hoverColor="#3B72A7"
|
||||
/>
|
||||
)}
|
||||
{fileStatus === 32 && !isTrashFolder && (
|
||||
|
@ -15,13 +15,13 @@ import {
|
||||
DragAndDrop,
|
||||
Box,
|
||||
Text,
|
||||
utils,
|
||||
} from "asc-web-components";
|
||||
import EmptyFolderContainer from "./EmptyFolderContainer";
|
||||
import FilesRowContent from "./FilesRowContent";
|
||||
import FilesTileContent from "./FilesTileContent";
|
||||
import TileContainer from "./TileContainer";
|
||||
import Tile from "./Tile";
|
||||
|
||||
import {
|
||||
api,
|
||||
constants,
|
||||
@ -103,6 +103,7 @@ const {
|
||||
|
||||
const { FilesFilter } = api;
|
||||
const { FileAction } = constants;
|
||||
const { Consumer } = utils.context;
|
||||
|
||||
const linkStyles = {
|
||||
isHovered: true,
|
||||
@ -745,6 +746,9 @@ class SectionBodyContent extends React.Component {
|
||||
if (currentProps.editing !== nextProps.editing) {
|
||||
return true;
|
||||
}
|
||||
if (currentProps.sectionWidth !== nextProps.sectionWidth) {
|
||||
return true;
|
||||
}
|
||||
if (!isEqual(currentProps.data, nextProps.data)) {
|
||||
return true;
|
||||
}
|
||||
@ -1500,7 +1504,6 @@ class SectionBodyContent extends React.Component {
|
||||
currentMediaFileId,
|
||||
viewAs,
|
||||
t,
|
||||
widthProp,
|
||||
isMobile,
|
||||
firstLoad,
|
||||
filesList,
|
||||
@ -1666,77 +1669,90 @@ class SectionBodyContent extends React.Component {
|
||||
})}
|
||||
</TileContainer>
|
||||
) : (
|
||||
<RowContainer draggable useReactWindow={false}>
|
||||
{items.map((item) => {
|
||||
const { checked, isFolder, value, contextOptions } = item;
|
||||
const isEdit =
|
||||
!!fileAction.type &&
|
||||
editingId === item.id &&
|
||||
item.fileExst === fileAction.extension;
|
||||
const contextOptionsProps =
|
||||
!isEdit && contextOptions && contextOptions.length > 0
|
||||
? {
|
||||
contextOptions: this.getFilesContextOptions(
|
||||
contextOptions,
|
||||
item
|
||||
),
|
||||
}
|
||||
: {};
|
||||
const checkedProps = isEdit || item.id <= 0 ? {} : { checked };
|
||||
const element = this.getItemIcon(item, isEdit || item.id <= 0);
|
||||
const sharedButton =
|
||||
isRecycleBin || isEdit || item.id <= 0
|
||||
? null
|
||||
: this.getSharedButton();
|
||||
const displayShareButton =
|
||||
widthProp < 500 ? "26px" : isRecycleBin ? "38px" : "96px";
|
||||
let classNameProp =
|
||||
isFolder && item.access < 2 && !isRecycleBin
|
||||
? { className: " dropable" }
|
||||
: { className: "" };
|
||||
<Consumer>
|
||||
{(context) => (
|
||||
<RowContainer draggable useReactWindow={false}>
|
||||
{items.map((item) => {
|
||||
const { checked, isFolder, value, contextOptions } = item;
|
||||
const sectionWidth = context.sectionWidth;
|
||||
const isEdit =
|
||||
!!fileAction.type &&
|
||||
editingId === item.id &&
|
||||
item.fileExst === fileAction.extension;
|
||||
const contextOptionsProps =
|
||||
!isEdit && contextOptions && contextOptions.length > 0
|
||||
? {
|
||||
contextOptions: this.getFilesContextOptions(
|
||||
contextOptions,
|
||||
item
|
||||
),
|
||||
}
|
||||
: {};
|
||||
const checkedProps =
|
||||
isEdit || item.id <= 0 ? {} : { checked };
|
||||
const element = this.getItemIcon(
|
||||
item,
|
||||
isEdit || item.id <= 0
|
||||
);
|
||||
const sharedButton =
|
||||
isRecycleBin || isEdit || item.id <= 0 || sectionWidth < 500
|
||||
? null
|
||||
: this.getSharedButton();
|
||||
const displayShareButton =
|
||||
sectionWidth < 500
|
||||
? "26px"
|
||||
: isRecycleBin
|
||||
? "38px"
|
||||
: "96px";
|
||||
let classNameProp =
|
||||
isFolder && item.access < 2 && !isRecycleBin
|
||||
? { className: " dropable" }
|
||||
: { className: "" };
|
||||
|
||||
if (item.draggable) classNameProp.className += " draggable";
|
||||
if (item.draggable) classNameProp.className += " draggable";
|
||||
|
||||
return (
|
||||
<DragAndDrop
|
||||
{...classNameProp}
|
||||
onDrop={this.onDrop.bind(this, item)}
|
||||
onMouseDown={this.onMouseDown}
|
||||
dragging={dragging && isFolder && item.access < 2}
|
||||
key={`dnd-key_${item.id}`}
|
||||
{...contextOptionsProps}
|
||||
value={value}
|
||||
>
|
||||
<SimpleFilesRow
|
||||
widthProp={widthProp}
|
||||
key={item.id}
|
||||
data={item}
|
||||
element={element}
|
||||
contentElement={sharedButton}
|
||||
onSelect={this.onContentRowSelect}
|
||||
editing={editingId}
|
||||
{...checkedProps}
|
||||
{...contextOptionsProps}
|
||||
needForUpdate={this.needForUpdate}
|
||||
selectItem={this.onSelectItem.bind(this, item)}
|
||||
contextButtonSpacerWidth={displayShareButton}
|
||||
>
|
||||
<FilesRowContent
|
||||
widthProp={widthProp}
|
||||
isMobile={isMobile}
|
||||
item={item}
|
||||
viewer={viewer}
|
||||
culture={settings.culture}
|
||||
onEditComplete={this.onEditComplete}
|
||||
onMediaFileClick={this.onMediaFileClick}
|
||||
onClickFavorite={this.onClickFavorite}
|
||||
openDocEditor={this.openDocEditor}
|
||||
/>
|
||||
</SimpleFilesRow>
|
||||
</DragAndDrop>
|
||||
);
|
||||
})}
|
||||
</RowContainer>
|
||||
return (
|
||||
<DragAndDrop
|
||||
{...classNameProp}
|
||||
onDrop={this.onDrop.bind(this, item)}
|
||||
onMouseDown={this.onMouseDown}
|
||||
dragging={dragging && isFolder && item.access < 2}
|
||||
key={`dnd-key_${item.id}`}
|
||||
{...contextOptionsProps}
|
||||
value={value}
|
||||
>
|
||||
<SimpleFilesRow
|
||||
sectionWidth={sectionWidth}
|
||||
key={item.id}
|
||||
data={item}
|
||||
element={element}
|
||||
contentElement={sharedButton}
|
||||
onSelect={this.onContentRowSelect}
|
||||
editing={editingId}
|
||||
{...checkedProps}
|
||||
{...contextOptionsProps}
|
||||
needForUpdate={this.needForUpdate}
|
||||
selectItem={this.onSelectItem.bind(this, item)}
|
||||
contextButtonSpacerWidth={displayShareButton}
|
||||
>
|
||||
<FilesRowContent
|
||||
sectionWidth={sectionWidth}
|
||||
isMobile={isMobile}
|
||||
item={item}
|
||||
viewer={viewer}
|
||||
culture={settings.culture}
|
||||
onEditComplete={this.onEditComplete}
|
||||
onMediaFileClick={this.onMediaFileClick}
|
||||
onClickFavorite={this.onClickFavorite}
|
||||
openDocEditor={this.openDocEditor}
|
||||
/>
|
||||
</SimpleFilesRow>
|
||||
</DragAndDrop>
|
||||
);
|
||||
})}
|
||||
</RowContainer>
|
||||
)}
|
||||
</Consumer>
|
||||
)}
|
||||
{playlist.length > 0 && mediaViewerVisible && (
|
||||
<MediaViewer
|
||||
|
@ -53,6 +53,7 @@ import {
|
||||
const { isAdmin } = store.auth.selectors;
|
||||
const { FilterType, FileAction } = constants;
|
||||
const { tablet, desktop } = utils.device;
|
||||
const { Consumer } = utils.context;
|
||||
|
||||
const StyledContainer = styled.div`
|
||||
@media ${desktop} {
|
||||
@ -126,9 +127,9 @@ const StyledContainer = styled.div`
|
||||
@media ${tablet} {
|
||||
& > div:first-child {
|
||||
${(props) =>
|
||||
props.isArticlePinned &&
|
||||
props.width &&
|
||||
css`
|
||||
width: calc(100% - 240px);
|
||||
width: ${props.width + 16 + "px"};
|
||||
`}
|
||||
position: absolute;
|
||||
top: 56px;
|
||||
@ -499,137 +500,145 @@ class SectionHeaderContent extends React.Component {
|
||||
const menuItems = this.getMenuItems();
|
||||
|
||||
return (
|
||||
<StyledContainer isHeaderVisible={isHeaderVisible}>
|
||||
{isHeaderVisible ? (
|
||||
<div className="group-button-menu-container">
|
||||
<GroupButtonsMenu
|
||||
checked={isHeaderChecked}
|
||||
isIndeterminate={isHeaderIndeterminate}
|
||||
onChange={this.onCheck}
|
||||
menuItems={menuItems}
|
||||
visible={isHeaderVisible}
|
||||
moreLabel={t("More")}
|
||||
closeTitle={t("CloseButton")}
|
||||
onClose={this.onClose}
|
||||
selected={menuItems[0].label}
|
||||
/>
|
||||
</div>
|
||||
) : (
|
||||
<div className="header-container">
|
||||
{!title ? (
|
||||
<Loaders.Headline />
|
||||
<Consumer>
|
||||
{(context) => (
|
||||
<StyledContainer
|
||||
isHeaderVisible={isHeaderVisible}
|
||||
width={context.sectionWidth}
|
||||
>
|
||||
{isHeaderVisible ? (
|
||||
<div className="group-button-menu-container">
|
||||
<GroupButtonsMenu
|
||||
checked={isHeaderChecked}
|
||||
isIndeterminate={isHeaderIndeterminate}
|
||||
onChange={this.onCheck}
|
||||
menuItems={menuItems}
|
||||
visible={isHeaderVisible}
|
||||
moreLabel={t("More")}
|
||||
closeTitle={t("CloseButton")}
|
||||
onClose={this.onClose}
|
||||
selected={menuItems[0].label}
|
||||
sectionWidth={context.sectionWidth}
|
||||
/>
|
||||
</div>
|
||||
) : (
|
||||
<>
|
||||
{!isRootFolder && (
|
||||
<IconButton
|
||||
iconName="ArrowPathIcon"
|
||||
size="17"
|
||||
color="#A3A9AE"
|
||||
hoverColor="#657077"
|
||||
isFill={true}
|
||||
onClick={this.onBackToParentFolder}
|
||||
className="arrow-button"
|
||||
/>
|
||||
)}
|
||||
<Headline
|
||||
className="headline-header"
|
||||
type="content"
|
||||
truncate={true}
|
||||
>
|
||||
{title}
|
||||
</Headline>
|
||||
{!isRootFolder && canCreate ? (
|
||||
<>
|
||||
<ContextMenuButton
|
||||
className="add-button"
|
||||
directionX="right"
|
||||
iconName="PlusIcon"
|
||||
size={17}
|
||||
color="#A3A9AE"
|
||||
hoverColor="#657077"
|
||||
isFill
|
||||
getData={this.getContextOptionsPlus}
|
||||
isDisabled={false}
|
||||
/>
|
||||
<ContextMenuButton
|
||||
className="option-button"
|
||||
directionX="right"
|
||||
iconName="VerticalDotsIcon"
|
||||
size={17}
|
||||
color="#A3A9AE"
|
||||
hoverColor="#657077"
|
||||
isFill
|
||||
getData={this.getContextOptionsFolder}
|
||||
isDisabled={false}
|
||||
/>
|
||||
</>
|
||||
<div className="header-container">
|
||||
{!title ? (
|
||||
<Loaders.Headline />
|
||||
) : (
|
||||
canCreate && (
|
||||
<ContextMenuButton
|
||||
className="add-button"
|
||||
directionX="right"
|
||||
iconName="PlusIcon"
|
||||
size={17}
|
||||
color="#A3A9AE"
|
||||
hoverColor="#657077"
|
||||
isFill
|
||||
getData={this.getContextOptionsPlus}
|
||||
isDisabled={false}
|
||||
/>
|
||||
)
|
||||
<>
|
||||
{!isRootFolder && (
|
||||
<IconButton
|
||||
iconName="ArrowPathIcon"
|
||||
size="17"
|
||||
color="#A3A9AE"
|
||||
hoverColor="#657077"
|
||||
isFill={true}
|
||||
onClick={this.onBackToParentFolder}
|
||||
className="arrow-button"
|
||||
/>
|
||||
)}
|
||||
<Headline
|
||||
className="headline-header"
|
||||
type="content"
|
||||
truncate={true}
|
||||
>
|
||||
{title}
|
||||
</Headline>
|
||||
{!isRootFolder && canCreate ? (
|
||||
<>
|
||||
<ContextMenuButton
|
||||
className="add-button"
|
||||
directionX="right"
|
||||
iconName="PlusIcon"
|
||||
size={17}
|
||||
color="#A3A9AE"
|
||||
hoverColor="#657077"
|
||||
isFill
|
||||
getData={this.getContextOptionsPlus}
|
||||
isDisabled={false}
|
||||
/>
|
||||
<ContextMenuButton
|
||||
className="option-button"
|
||||
directionX="right"
|
||||
iconName="VerticalDotsIcon"
|
||||
size={17}
|
||||
color="#A3A9AE"
|
||||
hoverColor="#657077"
|
||||
isFill
|
||||
getData={this.getContextOptionsFolder}
|
||||
isDisabled={false}
|
||||
/>
|
||||
</>
|
||||
) : (
|
||||
canCreate && (
|
||||
<ContextMenuButton
|
||||
className="add-button"
|
||||
directionX="right"
|
||||
iconName="PlusIcon"
|
||||
size={17}
|
||||
color="#A3A9AE"
|
||||
hoverColor="#657077"
|
||||
isFill
|
||||
getData={this.getContextOptionsPlus}
|
||||
isDisabled={false}
|
||||
/>
|
||||
)
|
||||
)}
|
||||
</>
|
||||
)}
|
||||
</>
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
)}
|
||||
|
||||
{showDeleteDialog && (
|
||||
<DeleteDialog
|
||||
isRecycleBin={isRecycleBin}
|
||||
visible={showDeleteDialog}
|
||||
onClose={this.onDeleteAction}
|
||||
selection={selection}
|
||||
/>
|
||||
)}
|
||||
{showDeleteDialog && (
|
||||
<DeleteDialog
|
||||
isRecycleBin={isRecycleBin}
|
||||
visible={showDeleteDialog}
|
||||
onClose={this.onDeleteAction}
|
||||
selection={selection}
|
||||
/>
|
||||
)}
|
||||
|
||||
{showEmptyTrashDialog && (
|
||||
<EmptyTrashDialog
|
||||
visible={showEmptyTrashDialog}
|
||||
onClose={this.onEmptyTrashAction}
|
||||
/>
|
||||
)}
|
||||
{showEmptyTrashDialog && (
|
||||
<EmptyTrashDialog
|
||||
visible={showEmptyTrashDialog}
|
||||
onClose={this.onEmptyTrashAction}
|
||||
/>
|
||||
)}
|
||||
|
||||
{showSharingPanel && (
|
||||
<SharingPanel
|
||||
onClose={this.onOpenSharingPanel}
|
||||
visible={showSharingPanel}
|
||||
/>
|
||||
)}
|
||||
{showSharingPanel && (
|
||||
<SharingPanel
|
||||
onClose={this.onOpenSharingPanel}
|
||||
visible={showSharingPanel}
|
||||
/>
|
||||
)}
|
||||
|
||||
{showMoveToPanel && (
|
||||
<OperationsPanel
|
||||
isCopy={false}
|
||||
visible={showMoveToPanel}
|
||||
onClose={this.onMoveAction}
|
||||
/>
|
||||
)}
|
||||
{showMoveToPanel && (
|
||||
<OperationsPanel
|
||||
isCopy={false}
|
||||
visible={showMoveToPanel}
|
||||
onClose={this.onMoveAction}
|
||||
/>
|
||||
)}
|
||||
|
||||
{showCopyPanel && (
|
||||
<OperationsPanel
|
||||
isCopy={true}
|
||||
visible={showCopyPanel}
|
||||
onClose={this.onCopyAction}
|
||||
/>
|
||||
)}
|
||||
{showCopyPanel && (
|
||||
<OperationsPanel
|
||||
isCopy={true}
|
||||
visible={showCopyPanel}
|
||||
onClose={this.onCopyAction}
|
||||
/>
|
||||
)}
|
||||
|
||||
{showDownloadDialog && (
|
||||
<DownloadDialog
|
||||
visible={showDownloadDialog}
|
||||
onClose={this.downloadAsAction}
|
||||
onDownloadProgress={this.loop}
|
||||
/>
|
||||
{showDownloadDialog && (
|
||||
<DownloadDialog
|
||||
visible={showDownloadDialog}
|
||||
onClose={this.downloadAsAction}
|
||||
onDownloadProgress={this.loop}
|
||||
/>
|
||||
)}
|
||||
</StyledContainer>
|
||||
)}
|
||||
</StyledContainer>
|
||||
</Consumer>
|
||||
);
|
||||
}
|
||||
}
|
||||
|
@ -47,19 +47,9 @@ const i18n = createI18N({
|
||||
});
|
||||
const { changeLanguage } = utils;
|
||||
const { FilesFilter } = api;
|
||||
const { getSettingsHomepage } = store.auth.selectors;
|
||||
const { getSettingsHomepage, getIsLoaded } = store.auth.selectors;
|
||||
|
||||
class PureHome extends React.Component {
|
||||
constructor(props) {
|
||||
super(props);
|
||||
|
||||
this.state = {
|
||||
overwriteSetting: false,
|
||||
uploadOriginalFormatSetting: false,
|
||||
hideWindowSetting: false,
|
||||
};
|
||||
}
|
||||
|
||||
componentDidMount() {
|
||||
const { fetchFiles, homepage, setIsLoading, setFirstLoad } = this.props;
|
||||
|
||||
@ -164,17 +154,6 @@ class PureHome extends React.Component {
|
||||
startUpload(files, folderId, t);
|
||||
};
|
||||
|
||||
onChangeOverwrite = () =>
|
||||
this.setState({ overwriteSetting: !this.state.overwriteSetting });
|
||||
|
||||
onChangeOriginalFormat = () =>
|
||||
this.setState({
|
||||
uploadOriginalFormatSetting: !this.state.uploadOriginalFormatSetting,
|
||||
});
|
||||
|
||||
onChangeWindowVisible = () =>
|
||||
this.setState({ hideWindowSetting: !this.state.hideWindowSetting });
|
||||
|
||||
componentDidUpdate(prevProps) {
|
||||
if (this.props.isLoading !== prevProps.isLoading) {
|
||||
if (this.props.isLoading) {
|
||||
@ -187,53 +166,20 @@ class PureHome extends React.Component {
|
||||
|
||||
render() {
|
||||
console.log("Home render");
|
||||
const {
|
||||
// overwriteSetting,
|
||||
// uploadOriginalFormatSetting,
|
||||
// hideWindowSetting
|
||||
} = this.state;
|
||||
const {
|
||||
progressData,
|
||||
viewAs,
|
||||
convertDialogVisible,
|
||||
fileActionId,
|
||||
isRecycleBin,
|
||||
isLoaded,
|
||||
} = this.props;
|
||||
|
||||
// const progressBarContent = (
|
||||
// <div>
|
||||
// <Checkbox
|
||||
// onChange={this.onChangeOverwrite}
|
||||
// isChecked={overwriteSetting}
|
||||
// label={t("OverwriteSetting")}
|
||||
// />
|
||||
// <Checkbox
|
||||
// onChange={this.onChangeOriginalFormat}
|
||||
// isChecked={uploadOriginalFormatSetting}
|
||||
// label={t("UploadOriginalFormatSetting")}
|
||||
// />
|
||||
// <Checkbox
|
||||
// onChange={this.onChangeWindowVisible}
|
||||
// isChecked={hideWindowSetting}
|
||||
// label={t("HideWindowSetting")}
|
||||
// />
|
||||
// </div>
|
||||
// );
|
||||
|
||||
return (
|
||||
<>
|
||||
{convertDialogVisible && (
|
||||
<ConvertDialog visible={convertDialogVisible} />
|
||||
)}
|
||||
{/* <RequestLoader
|
||||
visible={isLoading}
|
||||
zIndex={256}
|
||||
loaderSize="16px"
|
||||
loaderColor={"#999"}
|
||||
label={`${t("LoadingProcessing")} ${t("LoadingDescription")}`}
|
||||
fontSize="12px"
|
||||
fontColor={"#999"}
|
||||
/> */}
|
||||
<PageLayout
|
||||
withBodyScroll
|
||||
withBodyAutoFocus={!isMobile}
|
||||
@ -247,6 +193,7 @@ class PureHome extends React.Component {
|
||||
progressBarLabel={progressData.label}
|
||||
viewAs={viewAs}
|
||||
hideAside={!!fileActionId || progressData.visible}
|
||||
isLoaded={isLoaded}
|
||||
>
|
||||
<PageLayout.ArticleHeader>
|
||||
<ArticleHeaderContent />
|
||||
@ -314,6 +261,7 @@ function mapStateToProps(state) {
|
||||
isLoading: getIsLoading(state),
|
||||
homepage: getSettingsHomepage(state),
|
||||
dragging: getDragging(state),
|
||||
isLoaded: getIsLoaded(state),
|
||||
};
|
||||
}
|
||||
|
||||
|
@ -38,8 +38,8 @@ import {
|
||||
setTreeFolders,
|
||||
setUpdateTree,
|
||||
setNewRowItems,
|
||||
|
||||
addFileToRecentlyViewed
|
||||
setIsLoading,
|
||||
addFileToRecentlyViewed,
|
||||
} from "../../../store/files/actions";
|
||||
import { createI18N } from "../../../helpers/i18n";
|
||||
const i18n = createI18N({
|
||||
@ -136,7 +136,12 @@ class NewFilesPanelComponent extends React.Component {
|
||||
|
||||
onFilesClick = (item) => {
|
||||
const { id, fileExst, viewUrl, fileType } = item;
|
||||
const { filter, setMediaViewerData, fetchFiles, addFileToRecentlyViewed } = this.props;
|
||||
const {
|
||||
filter,
|
||||
setMediaViewerData,
|
||||
fetchFiles,
|
||||
addFileToRecentlyViewed,
|
||||
} = this.props;
|
||||
|
||||
if (!fileExst) {
|
||||
fetchFiles(id, filter).catch((err) => toastr.error(err));
|
||||
@ -146,9 +151,9 @@ class NewFilesPanelComponent extends React.Component {
|
||||
|
||||
if (canEdit) {
|
||||
return addFileToRecentlyViewed(id)
|
||||
.then(() => console.log("Pushed to recently viewed"))
|
||||
.catch(e => console.error(e))
|
||||
.finally(window.open(`./doceditor?fileId=${id}`, "_blank"));
|
||||
.then(() => console.log("Pushed to recently viewed"))
|
||||
.catch((e) => console.error(e))
|
||||
.finally(window.open(`./doceditor?fileId=${id}`, "_blank"));
|
||||
}
|
||||
|
||||
if (isMedia) {
|
||||
@ -317,5 +322,6 @@ export default connect(mapStateToProps, {
|
||||
setUpdateTree,
|
||||
setNewRowItems,
|
||||
fetchFiles,
|
||||
addFileToRecentlyViewed
|
||||
addFileToRecentlyViewed,
|
||||
setIsLoading,
|
||||
})(withRouter(NewFilesPanel));
|
||||
|
@ -227,6 +227,20 @@ namespace ASC.Api.Documents
|
||||
return result.Select(r => FilesControllerHelperInt.GetFolder(r, userIdOrGroupId, filterType, withsubfolders));
|
||||
}
|
||||
|
||||
|
||||
[Read("@privacy")]
|
||||
public FolderContentWrapper<int> GetPrivacyFolder(Guid userIdOrGroupId, FilterType filterType, bool withsubfolders)
|
||||
{
|
||||
if (!IsAvailablePrivacyRoomSettings()) throw new System.Security.SecurityException();
|
||||
return FilesControllerHelperInt.GetFolder(GlobalFolderHelper.FolderPrivacy, userIdOrGroupId, filterType, withsubfolders);
|
||||
}
|
||||
|
||||
[Read("@privacy/available")]
|
||||
public bool IsAvailablePrivacyRoomSettings()
|
||||
{
|
||||
return PrivacyRoomSettings.IsAvailable(TenantManager);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Returns the detailed list of files and folders located in the current user 'My Documents' section
|
||||
/// </summary>
|
||||
|
@ -39,6 +39,7 @@ const i18n = createI18N({
|
||||
page: "Home",
|
||||
localesPath: "pages/Home",
|
||||
});
|
||||
const { Consumer } = utils.context;
|
||||
const { isArrayEqual } = utils.array;
|
||||
const { getSettings } = store.auth.selectors;
|
||||
const { setIsLoaded } = store.auth.actions;
|
||||
@ -356,6 +357,9 @@ class SectionBodyContent extends React.PureComponent {
|
||||
if (currentProps.status !== nextProps.status) {
|
||||
return true;
|
||||
}
|
||||
if (currentProps.sectionWidth !== nextProps.sectionWidth) {
|
||||
return true;
|
||||
}
|
||||
if (!isEqual(currentProps.data, nextProps.data)) {
|
||||
return true;
|
||||
}
|
||||
@ -377,7 +381,7 @@ class SectionBodyContent extends React.PureComponent {
|
||||
widthProp,
|
||||
isMobile,
|
||||
selectGroup,
|
||||
isLoading
|
||||
isLoading,
|
||||
} = this.props;
|
||||
|
||||
const { dialogsVisible, user } = this.state;
|
||||
@ -386,58 +390,65 @@ class SectionBodyContent extends React.PureComponent {
|
||||
<Loaders.Rows />
|
||||
) : peopleList.length > 0 ? (
|
||||
<>
|
||||
<RowContainer useReactWindow={false}>
|
||||
{peopleList.map((man) => {
|
||||
const {
|
||||
checked,
|
||||
role,
|
||||
displayName,
|
||||
avatar,
|
||||
id,
|
||||
status,
|
||||
options,
|
||||
} = man;
|
||||
<Consumer>
|
||||
{(context) => (
|
||||
<RowContainer useReactWindow={false}>
|
||||
{peopleList.map((man) => {
|
||||
const {
|
||||
checked,
|
||||
role,
|
||||
displayName,
|
||||
avatar,
|
||||
id,
|
||||
status,
|
||||
options,
|
||||
} = man;
|
||||
const sectionWidth = context.sectionWidth;
|
||||
const contextOptionsProps =
|
||||
options && options.length > 0
|
||||
? {
|
||||
contextOptions: this.getUserContextOptions(options, id),
|
||||
}
|
||||
: {};
|
||||
|
||||
const contextOptionsProps =
|
||||
options && options.length > 0
|
||||
? { contextOptions: this.getUserContextOptions(options, id) }
|
||||
: {};
|
||||
const checkedProps = checked !== null ? { checked } : {};
|
||||
|
||||
const checkedProps = checked !== null ? { checked } : {};
|
||||
const element = (
|
||||
<Avatar
|
||||
size="small"
|
||||
role={role}
|
||||
userName={displayName}
|
||||
source={avatar}
|
||||
/>
|
||||
);
|
||||
|
||||
const element = (
|
||||
<Avatar
|
||||
size="small"
|
||||
role={role}
|
||||
userName={displayName}
|
||||
source={avatar}
|
||||
/>
|
||||
);
|
||||
|
||||
return (
|
||||
<Row
|
||||
key={id}
|
||||
status={status}
|
||||
data={man}
|
||||
element={element}
|
||||
onSelect={this.onContentRowSelect}
|
||||
{...checkedProps}
|
||||
{...contextOptionsProps}
|
||||
needForUpdate={this.needForUpdate}
|
||||
widthProp={widthProp}
|
||||
>
|
||||
<UserContent
|
||||
isMobile={isMobile}
|
||||
widthProp={widthProp}
|
||||
user={man}
|
||||
history={history}
|
||||
settings={settings}
|
||||
selectGroup={selectGroup}
|
||||
/>
|
||||
</Row>
|
||||
);
|
||||
})}
|
||||
</RowContainer>
|
||||
return (
|
||||
<Row
|
||||
key={id}
|
||||
status={status}
|
||||
data={man}
|
||||
element={element}
|
||||
onSelect={this.onContentRowSelect}
|
||||
{...checkedProps}
|
||||
{...contextOptionsProps}
|
||||
needForUpdate={this.needForUpdate}
|
||||
sectionWidth={sectionWidth}
|
||||
>
|
||||
<UserContent
|
||||
isMobile={isMobile}
|
||||
widthProp={widthProp}
|
||||
user={man}
|
||||
history={history}
|
||||
settings={settings}
|
||||
selectGroup={selectGroup}
|
||||
sectionWidth={sectionWidth}
|
||||
/>
|
||||
</Row>
|
||||
);
|
||||
})}
|
||||
</RowContainer>
|
||||
)}
|
||||
</Consumer>
|
||||
|
||||
{dialogsVisible.changeEmail && (
|
||||
<ChangeEmailDialog
|
||||
@ -492,15 +503,15 @@ class SectionBodyContent extends React.PureComponent {
|
||||
/>
|
||||
</Box>
|
||||
<Box displayProp="inline-block" marginProp="14px 0 0 0">
|
||||
<Link
|
||||
type="action"
|
||||
isHovered={true}
|
||||
fontWeight="600"
|
||||
color="#555f65"
|
||||
onClick={this.onResetFilter}
|
||||
>
|
||||
{t("ClearButton")}
|
||||
</Link>
|
||||
<Link
|
||||
type="action"
|
||||
isHovered={true}
|
||||
fontWeight="600"
|
||||
color="#555f65"
|
||||
onClick={this.onResetFilter}
|
||||
>
|
||||
{t("ClearButton")}
|
||||
</Link>
|
||||
</Box>
|
||||
</>
|
||||
}
|
||||
|
@ -13,7 +13,7 @@ import { connect } from "react-redux";
|
||||
const getFormattedGroups = (user, selectGroup) => {
|
||||
let temp = [];
|
||||
const groups = user.groups;
|
||||
const linkColor = "#A3A9AE";
|
||||
const linkColor = user.statusType === "pending" ? "#D0D5DA" : "#A3A9AE";
|
||||
|
||||
if (!groups) temp.push({ key: 0, label: "" });
|
||||
|
||||
@ -67,6 +67,7 @@ const UserContent = ({
|
||||
selectGroup,
|
||||
widthProp,
|
||||
isMobile,
|
||||
sectionWidth,
|
||||
}) => {
|
||||
const { userName, displayName, title, mobilePhone, email, statusType } = user;
|
||||
const groups = getFormattedGroups(user, selectGroup);
|
||||
@ -87,14 +88,15 @@ const UserContent = ({
|
||||
email,
|
||||
]);
|
||||
|
||||
const nameColor = "#333";
|
||||
const sideInfoColor = "#A3A9AE";
|
||||
const nameColor = statusType === "pending" ? "#A3A9AE" : "#333333";
|
||||
const sideInfoColor = statusType === "pending" ? "#D0D5DA" : "#A3A9AE";
|
||||
|
||||
return (
|
||||
<RowContent
|
||||
widthProp={widthProp}
|
||||
isMobile={isMobile}
|
||||
sideColor={sideInfoColor}
|
||||
sectionWidth={sectionWidth}
|
||||
>
|
||||
<Link
|
||||
containerWidth="28%"
|
||||
|
@ -36,6 +36,7 @@ import {
|
||||
ChangeUserTypeDialog,
|
||||
} from "../../../../dialogs";
|
||||
const { tablet, desktop } = utils.device;
|
||||
const { Consumer } = utils.context;
|
||||
|
||||
const { isAdmin } = store.auth.selectors;
|
||||
const { EmployeeType, EmployeeStatus } = constants;
|
||||
@ -57,9 +58,9 @@ const StyledContainer = styled.div`
|
||||
@media ${tablet} {
|
||||
& > div:first-child {
|
||||
${(props) =>
|
||||
props.isArticlePinned &&
|
||||
props.width &&
|
||||
css`
|
||||
width: calc(100% - 240px);
|
||||
width: ${props.width + 16 + "px"};
|
||||
`}
|
||||
position: absolute;
|
||||
top: 56px;
|
||||
@ -114,14 +115,10 @@ const SectionHeaderContent = (props) => {
|
||||
isAdmin,
|
||||
t,
|
||||
history,
|
||||
|
||||
customNames,
|
||||
homepage,
|
||||
|
||||
deleteGroup,
|
||||
|
||||
selection,
|
||||
|
||||
hasAnybodySelected,
|
||||
hasUsersToMakeEmployees,
|
||||
hasUsersToMakeGuests,
|
||||
@ -129,7 +126,6 @@ const SectionHeaderContent = (props) => {
|
||||
hasUsersToDisable,
|
||||
hasUsersToInvite,
|
||||
hasUsersToRemove,
|
||||
|
||||
isLoaded,
|
||||
} = props;
|
||||
|
||||
@ -351,132 +347,135 @@ const SectionHeaderContent = (props) => {
|
||||
onInvitationDialogClick /* , onSentInviteAgain */,
|
||||
]);
|
||||
|
||||
const isArticlePinned = window.localStorage.getItem("asc_article_pinned_key");
|
||||
|
||||
return (
|
||||
<StyledContainer
|
||||
isHeaderVisible={isHeaderVisible}
|
||||
isArticlePinned={isArticlePinned}
|
||||
>
|
||||
{employeeDialogVisible && (
|
||||
<ChangeUserTypeDialog
|
||||
visible={employeeDialogVisible}
|
||||
onClose={toggleEmployeeDialog}
|
||||
userType={EmployeeType.User}
|
||||
/>
|
||||
)}
|
||||
<Consumer>
|
||||
{(context) => (
|
||||
<StyledContainer
|
||||
isHeaderVisible={isHeaderVisible}
|
||||
width={context.sectionWidth}
|
||||
>
|
||||
{employeeDialogVisible && (
|
||||
<ChangeUserTypeDialog
|
||||
visible={employeeDialogVisible}
|
||||
onClose={toggleEmployeeDialog}
|
||||
userType={EmployeeType.User}
|
||||
/>
|
||||
)}
|
||||
|
||||
{guestDialogVisible && (
|
||||
<ChangeUserTypeDialog
|
||||
visible={guestDialogVisible}
|
||||
onClose={toggleGuestDialog}
|
||||
userType={EmployeeType.Guest}
|
||||
/>
|
||||
)}
|
||||
{activeDialogVisible && (
|
||||
<ChangeUserStatusDialog
|
||||
visible={activeDialogVisible}
|
||||
onClose={toggleActiveDialog}
|
||||
userStatus={EmployeeStatus.Active}
|
||||
/>
|
||||
)}
|
||||
{disableDialogVisible && (
|
||||
<ChangeUserStatusDialog
|
||||
visible={disableDialogVisible}
|
||||
onClose={toggleDisableDialog}
|
||||
userStatus={EmployeeStatus.Disabled}
|
||||
/>
|
||||
)}
|
||||
{guestDialogVisible && (
|
||||
<ChangeUserTypeDialog
|
||||
visible={guestDialogVisible}
|
||||
onClose={toggleGuestDialog}
|
||||
userType={EmployeeType.Guest}
|
||||
/>
|
||||
)}
|
||||
{activeDialogVisible && (
|
||||
<ChangeUserStatusDialog
|
||||
visible={activeDialogVisible}
|
||||
onClose={toggleActiveDialog}
|
||||
userStatus={EmployeeStatus.Active}
|
||||
/>
|
||||
)}
|
||||
{disableDialogVisible && (
|
||||
<ChangeUserStatusDialog
|
||||
visible={disableDialogVisible}
|
||||
onClose={toggleDisableDialog}
|
||||
userStatus={EmployeeStatus.Disabled}
|
||||
/>
|
||||
)}
|
||||
|
||||
{sendInviteDialogVisible && (
|
||||
<SendInviteDialog
|
||||
visible={sendInviteDialogVisible}
|
||||
onClose={toggleSendInviteDialog}
|
||||
/>
|
||||
)}
|
||||
{sendInviteDialogVisible && (
|
||||
<SendInviteDialog
|
||||
visible={sendInviteDialogVisible}
|
||||
onClose={toggleSendInviteDialog}
|
||||
/>
|
||||
)}
|
||||
|
||||
{deleteDialogVisible && (
|
||||
<DeleteUsersDialog
|
||||
visible={deleteDialogVisible}
|
||||
onClose={toggleDeleteDialog}
|
||||
/>
|
||||
)}
|
||||
{deleteDialogVisible && (
|
||||
<DeleteUsersDialog
|
||||
visible={deleteDialogVisible}
|
||||
onClose={toggleDeleteDialog}
|
||||
/>
|
||||
)}
|
||||
|
||||
{isHeaderVisible ? (
|
||||
<div className="group-button-menu-container">
|
||||
<GroupButtonsMenu
|
||||
checked={isHeaderChecked}
|
||||
isIndeterminate={isHeaderIndeterminate}
|
||||
onChange={onCheck}
|
||||
menuItems={menuItems}
|
||||
visible={isHeaderVisible}
|
||||
moreLabel={t("More")}
|
||||
closeTitle={t("CloseButton")}
|
||||
onClose={onClose}
|
||||
selected={menuItems[0].label}
|
||||
/>
|
||||
</div>
|
||||
) : (
|
||||
<div className="header-container">
|
||||
{!isLoaded ? (
|
||||
<Loaders.Headline />
|
||||
) : group ? (
|
||||
<>
|
||||
<Headline
|
||||
className="headline-header"
|
||||
type="content"
|
||||
truncate={true}
|
||||
>
|
||||
{group.name}
|
||||
</Headline>
|
||||
{isAdmin && (
|
||||
<ContextMenuButton
|
||||
className="action-button"
|
||||
directionX="right"
|
||||
title={t("Actions")}
|
||||
iconName="VerticalDotsIcon"
|
||||
size={17}
|
||||
color="#A3A9AE"
|
||||
getData={getContextOptionsGroup}
|
||||
isDisabled={false}
|
||||
/>
|
||||
)}
|
||||
</>
|
||||
{isHeaderVisible ? (
|
||||
<div className="group-button-menu-container">
|
||||
<GroupButtonsMenu
|
||||
checked={isHeaderChecked}
|
||||
isIndeterminate={isHeaderIndeterminate}
|
||||
onChange={onCheck}
|
||||
menuItems={menuItems}
|
||||
visible={isHeaderVisible}
|
||||
moreLabel={t("More")}
|
||||
closeTitle={t("CloseButton")}
|
||||
onClose={onClose}
|
||||
selected={menuItems[0].label}
|
||||
sectionWidth={context.sectionWidth}
|
||||
/>
|
||||
</div>
|
||||
) : (
|
||||
<>
|
||||
<Headline
|
||||
className="headline-header"
|
||||
truncate={true}
|
||||
type="content"
|
||||
>
|
||||
{groupsCaption}
|
||||
</Headline>
|
||||
{isAdmin && (
|
||||
<div className="header-container">
|
||||
{!isLoaded ? (
|
||||
<Loaders.Headline />
|
||||
) : group ? (
|
||||
<>
|
||||
<ContextMenuButton
|
||||
className="action-button"
|
||||
directionX="right"
|
||||
title={t("Actions")}
|
||||
iconName="PlusIcon"
|
||||
size={17}
|
||||
color="#657077"
|
||||
getData={getContextOptionsPlus}
|
||||
isDisabled={false}
|
||||
/>
|
||||
{invitationDialogVisible && (
|
||||
<InviteDialog
|
||||
visible={invitationDialogVisible}
|
||||
onClose={onInvitationDialogClick}
|
||||
onCloseButton={onInvitationDialogClick}
|
||||
<Headline
|
||||
className="headline-header"
|
||||
type="content"
|
||||
truncate={true}
|
||||
>
|
||||
{group.name}
|
||||
</Headline>
|
||||
{isAdmin && (
|
||||
<ContextMenuButton
|
||||
className="action-button"
|
||||
directionX="right"
|
||||
title={t("Actions")}
|
||||
iconName="VerticalDotsIcon"
|
||||
size={17}
|
||||
color="#A3A9AE"
|
||||
getData={getContextOptionsGroup}
|
||||
isDisabled={false}
|
||||
/>
|
||||
)}
|
||||
</>
|
||||
) : (
|
||||
<>
|
||||
<Headline
|
||||
className="headline-header"
|
||||
truncate={true}
|
||||
type="content"
|
||||
>
|
||||
{groupsCaption}
|
||||
</Headline>
|
||||
{isAdmin && (
|
||||
<>
|
||||
<ContextMenuButton
|
||||
className="action-button"
|
||||
directionX="right"
|
||||
title={t("Actions")}
|
||||
iconName="PlusIcon"
|
||||
size={17}
|
||||
color="#657077"
|
||||
getData={getContextOptionsPlus}
|
||||
isDisabled={false}
|
||||
/>
|
||||
{invitationDialogVisible && (
|
||||
<InviteDialog
|
||||
visible={invitationDialogVisible}
|
||||
onClose={onInvitationDialogClick}
|
||||
onCloseButton={onInvitationDialogClick}
|
||||
/>
|
||||
)}
|
||||
</>
|
||||
)}
|
||||
</>
|
||||
)}
|
||||
</>
|
||||
</div>
|
||||
)}
|
||||
</div>
|
||||
</StyledContainer>
|
||||
)}
|
||||
</StyledContainer>
|
||||
</Consumer>
|
||||
);
|
||||
};
|
||||
|
||||
|
@ -25,7 +25,7 @@ const i18n = createI18N({
|
||||
localesPath: "pages/Home",
|
||||
});
|
||||
const { changeLanguage } = utils;
|
||||
const { isAdmin } = store.auth.selectors;
|
||||
const { isAdmin, getIsLoaded, getOrganizationName } = store.auth.selectors;
|
||||
|
||||
class PureHome extends React.Component {
|
||||
constructor(props) {
|
||||
@ -101,10 +101,14 @@ class PureHome extends React.Component {
|
||||
selected,
|
||||
} = this.state;
|
||||
|
||||
const { isAdmin } = this.props;
|
||||
const { isAdmin, isLoaded } = this.props;
|
||||
|
||||
return (
|
||||
<PageLayout withBodyScroll={true} withBodyAutoFocus={!isMobile}>
|
||||
<PageLayout
|
||||
withBodyScroll={true}
|
||||
withBodyAutoFocus={!isMobile}
|
||||
isLoaded={isLoaded}
|
||||
>
|
||||
<PageLayout.ArticleHeader>
|
||||
<ArticleHeaderContent />
|
||||
</PageLayout.ArticleHeader>
|
||||
@ -174,7 +178,6 @@ Home.propTypes = {
|
||||
};
|
||||
|
||||
function mapStateToProps(state) {
|
||||
const { isLoaded, settings } = state.auth;
|
||||
const { users, selection, selected, selectedGroup, groups } = state.people;
|
||||
return {
|
||||
users,
|
||||
@ -182,10 +185,10 @@ function mapStateToProps(state) {
|
||||
selected,
|
||||
selectedGroup,
|
||||
groups,
|
||||
isLoaded,
|
||||
organizationName: settings.organizationName,
|
||||
organizationName: getOrganizationName(state),
|
||||
isAdmin: isAdmin(state),
|
||||
isLoading: getIsLoading(state),
|
||||
isLoaded: getIsLoaded(state),
|
||||
};
|
||||
}
|
||||
|
||||
|
@ -30,6 +30,7 @@
|
||||
"lodash": "4.17.19",
|
||||
"lodash-es": "4.17.15",
|
||||
"moment": "^2.24.0",
|
||||
"re-resizable": "^6.7.0",
|
||||
"react-content-loader": "^5.1.2",
|
||||
"react-device-detect": "^1.11.14",
|
||||
"react-hammerjs": "^1.0.1",
|
||||
|
@ -1,9 +1,11 @@
|
||||
import React from "react";
|
||||
import styled from "styled-components";
|
||||
import { isIOS } from "react-device-detect";
|
||||
import { isIOS, isFirefox } from "react-device-detect";
|
||||
|
||||
const StyledMain = styled.main`
|
||||
height: ${isIOS ? "calc(var(--vh, 1vh) * 100)" : "calc(100vh - 56px)"};
|
||||
height: ${isIOS && !isFirefox
|
||||
? "calc(var(--vh, 1vh) * 100)"
|
||||
: "calc(100vh - 56px)"};
|
||||
width: 100vw;
|
||||
z-index: 0;
|
||||
display: flex;
|
||||
|
@ -6,7 +6,6 @@ import store from "../../store";
|
||||
import { withTranslation } from "react-i18next";
|
||||
import i18n from "./i18n";
|
||||
import { ARTICLE_PINNED_KEY } from "../../constants";
|
||||
|
||||
import Article from "./sub-components/article";
|
||||
import SubArticleHeader from "./sub-components/article-header";
|
||||
import SubArticleMainButton from "./sub-components/article-main-button";
|
||||
@ -21,8 +20,10 @@ import SubSectionPaging from "./sub-components/section-paging";
|
||||
import SectionToggler from "./sub-components/section-toggler";
|
||||
import { changeLanguage } from "../../utils";
|
||||
import ReactResizeDetector from "react-resize-detector";
|
||||
|
||||
const { getLanguage } = store.auth.selectors;
|
||||
const { size } = utils.device;
|
||||
const { Provider } = utils.context;
|
||||
|
||||
function ArticleHeader() {
|
||||
return null;
|
||||
@ -105,8 +106,7 @@ class PageLayoutComponent extends React.Component {
|
||||
}
|
||||
|
||||
orientationChangeHandler = () => {
|
||||
const vh = (window.innerHeight - 57) * 0.01;
|
||||
document.documentElement.style.setProperty("--vh", `${vh}px`);
|
||||
this.updateMainHeight();
|
||||
|
||||
const isValueExist = !!localStorage.getItem(ARTICLE_PINNED_KEY);
|
||||
const isEnoughWidth = screen.availWidth > size.smallTablet;
|
||||
@ -119,6 +119,41 @@ class PageLayoutComponent extends React.Component {
|
||||
}
|
||||
};
|
||||
|
||||
updateMainHeight = () => {
|
||||
const intervalTime = 100;
|
||||
const endTimeoutTime = 1000;
|
||||
|
||||
let interval, timeout, lastInnerHeight, noChangeCount;
|
||||
|
||||
const updateHeight = () => {
|
||||
clearInterval(interval);
|
||||
clearTimeout(timeout);
|
||||
|
||||
interval = null;
|
||||
timeout = null;
|
||||
|
||||
const vh = (window.innerHeight - 57) * 0.01;
|
||||
document.documentElement.style.setProperty("--vh", `${vh}px`);
|
||||
};
|
||||
|
||||
interval = setInterval(() => {
|
||||
if (window.innerHeight === lastInnerHeight) {
|
||||
noChangeCount++;
|
||||
|
||||
if (noChangeCount === intervalTime) {
|
||||
updateHeight();
|
||||
}
|
||||
} else {
|
||||
lastInnerHeight = window.innerHeight;
|
||||
noChangeCount = 0;
|
||||
}
|
||||
});
|
||||
|
||||
timeout = setTimeout(() => {
|
||||
updateHeight();
|
||||
}, endTimeoutTime);
|
||||
};
|
||||
|
||||
backdropClick = () => {
|
||||
this.setState({
|
||||
isBackdropVisible: false,
|
||||
@ -155,10 +190,6 @@ class PageLayoutComponent extends React.Component {
|
||||
});
|
||||
};
|
||||
|
||||
onResize = (width, height) => {
|
||||
//console.log(`onResize height: ${height}, width: ${width}`);
|
||||
};
|
||||
|
||||
render() {
|
||||
const {
|
||||
onDrop,
|
||||
@ -172,6 +203,7 @@ class PageLayoutComponent extends React.Component {
|
||||
withBodyAutoFocus,
|
||||
withBodyScroll,
|
||||
children,
|
||||
isLoaded,
|
||||
} = this.props;
|
||||
|
||||
let articleHeaderContent = null;
|
||||
@ -248,6 +280,7 @@ class PageLayoutComponent extends React.Component {
|
||||
<Article
|
||||
visible={this.state.isArticleVisible}
|
||||
pinned={this.state.isArticlePinned}
|
||||
isLoaded={isLoaded}
|
||||
>
|
||||
{isArticleHeaderAvailable && (
|
||||
<SubArticleHeader>
|
||||
@ -281,81 +314,83 @@ class PageLayoutComponent extends React.Component {
|
||||
)}
|
||||
{isSectionAvailable && (
|
||||
<ReactResizeDetector
|
||||
onResize={this.onResize}
|
||||
refreshRate={200}
|
||||
refreshRate={100}
|
||||
refreshMode="debounce"
|
||||
refreshOptions={{ trailing: true }}
|
||||
>
|
||||
{({ width }) => (
|
||||
<Section widthProp={width}>
|
||||
{isSectionHeaderAvailable && (
|
||||
<SubSectionHeader
|
||||
isArticlePinned={this.state.isArticlePinned}
|
||||
borderBottom={this.props.headerBorderBottom}
|
||||
>
|
||||
{sectionHeaderContent
|
||||
? sectionHeaderContent.props.children
|
||||
: null}
|
||||
</SubSectionHeader>
|
||||
)}
|
||||
{isSectionFilterAvailable && (
|
||||
<SubSectionFilter className="section-header_filter">
|
||||
{sectionFilterContent
|
||||
? sectionFilterContent.props.children
|
||||
: null}
|
||||
</SubSectionFilter>
|
||||
)}
|
||||
{isSectionBodyAvailable && (
|
||||
<>
|
||||
<SubSectionBody
|
||||
onDrop={onDrop}
|
||||
uploadFiles={uploadFiles}
|
||||
setSelections={setSelections}
|
||||
withScroll={withBodyScroll}
|
||||
autoFocus={withBodyAutoFocus}
|
||||
pinned={this.state.isArticlePinned}
|
||||
viewAs={viewAs}
|
||||
<Provider
|
||||
value={{
|
||||
sectionWidth: width,
|
||||
}}
|
||||
>
|
||||
<Section widthProp={width}>
|
||||
{isSectionHeaderAvailable && (
|
||||
<SubSectionHeader
|
||||
isArticlePinned={this.state.isArticlePinned}
|
||||
>
|
||||
{isSectionFilterAvailable && (
|
||||
<SubSectionFilter className="section-body_filter">
|
||||
{sectionFilterContent
|
||||
? sectionFilterContent.props.children
|
||||
{sectionHeaderContent
|
||||
? sectionHeaderContent.props.children
|
||||
: null}
|
||||
</SubSectionHeader>
|
||||
)}
|
||||
{isSectionFilterAvailable && (
|
||||
<SubSectionFilter className="section-header_filter">
|
||||
{sectionFilterContent
|
||||
? sectionFilterContent.props.children
|
||||
: null}
|
||||
</SubSectionFilter>
|
||||
)}
|
||||
{isSectionBodyAvailable && (
|
||||
<>
|
||||
<SubSectionBody
|
||||
onDrop={onDrop}
|
||||
uploadFiles={uploadFiles}
|
||||
setSelections={setSelections}
|
||||
withScroll={withBodyScroll}
|
||||
autoFocus={withBodyAutoFocus}
|
||||
pinned={this.state.isArticlePinned}
|
||||
viewAs={viewAs}
|
||||
>
|
||||
{isSectionFilterAvailable && (
|
||||
<SubSectionFilter className="section-body_filter">
|
||||
{sectionFilterContent
|
||||
? sectionFilterContent.props.children
|
||||
: null}
|
||||
</SubSectionFilter>
|
||||
)}
|
||||
<SubSectionBodyContent>
|
||||
{sectionBodyContent
|
||||
? sectionBodyContent.props.children
|
||||
: null}
|
||||
</SubSectionFilter>
|
||||
</SubSectionBodyContent>
|
||||
{isSectionPagingAvailable && (
|
||||
<SubSectionPaging>
|
||||
{sectionPagingContent
|
||||
? sectionPagingContent.props.children
|
||||
: null}
|
||||
</SubSectionPaging>
|
||||
)}
|
||||
</SubSectionBody>
|
||||
{showProgressBar && (
|
||||
<ProgressBar
|
||||
className="layout-progress-bar"
|
||||
label={progressBarLabel}
|
||||
percent={progressBarValue}
|
||||
dropDownContent={progressBarDropDownContent}
|
||||
/>
|
||||
)}
|
||||
<SubSectionBodyContent>
|
||||
{sectionBodyContent
|
||||
? React.cloneElement(
|
||||
sectionBodyContent.props.children,
|
||||
{ widthProp: width }
|
||||
)
|
||||
: null}
|
||||
</SubSectionBodyContent>
|
||||
{isSectionPagingAvailable && (
|
||||
<SubSectionPaging>
|
||||
{sectionPagingContent
|
||||
? sectionPagingContent.props.children
|
||||
: null}
|
||||
</SubSectionPaging>
|
||||
)}
|
||||
</SubSectionBody>
|
||||
{showProgressBar && (
|
||||
<ProgressBar
|
||||
className="layout-progress-bar"
|
||||
label={progressBarLabel}
|
||||
percent={progressBarValue}
|
||||
dropDownContent={progressBarDropDownContent}
|
||||
/>
|
||||
)}
|
||||
</>
|
||||
)}
|
||||
</>
|
||||
)}
|
||||
|
||||
{isArticleAvailable && (
|
||||
<SectionToggler
|
||||
visible={!this.state.isArticleVisible}
|
||||
onClick={this.showArticle}
|
||||
/>
|
||||
)}
|
||||
</Section>
|
||||
{isArticleAvailable && (
|
||||
<SectionToggler
|
||||
visible={!this.state.isArticleVisible}
|
||||
onClick={this.showArticle}
|
||||
/>
|
||||
)}
|
||||
</Section>
|
||||
</Provider>
|
||||
)}
|
||||
</ReactResizeDetector>
|
||||
)}
|
||||
@ -369,7 +404,6 @@ PageLayoutComponent.propTypes = {
|
||||
withBodyScroll: PropTypes.bool,
|
||||
withBodyAutoFocus: PropTypes.bool,
|
||||
t: PropTypes.func,
|
||||
|
||||
showProgressBar: PropTypes.bool,
|
||||
progressBarValue: PropTypes.number,
|
||||
progressBarDropDownContent: PropTypes.any,
|
||||
@ -378,6 +412,8 @@ PageLayoutComponent.propTypes = {
|
||||
setSelections: PropTypes.func,
|
||||
uploadFiles: PropTypes.bool,
|
||||
hideAside: PropTypes.bool,
|
||||
isLoaded: PropTypes.bool,
|
||||
viewAs: PropTypes.string,
|
||||
};
|
||||
|
||||
PageLayoutComponent.defaultProps = {
|
||||
|
@ -1,64 +1,92 @@
|
||||
import React from "react";
|
||||
import styled from "styled-components";
|
||||
import styled, { css } from "styled-components";
|
||||
import PropTypes from "prop-types";
|
||||
import { utils } from "asc-web-components";
|
||||
import { Resizable } from "re-resizable";
|
||||
import { isMobile } from "react-device-detect";
|
||||
const { tablet } = utils.device;
|
||||
|
||||
const StyledArticle = styled.article`
|
||||
padding: 0 24px;
|
||||
background: #f8f9f9;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
width: 264px;
|
||||
min-width: 264px;
|
||||
/*transition: width 0.3s ease-in-out;*/
|
||||
overflow: hidden auto;
|
||||
box-sizing: border-box;
|
||||
resize: horizontal;
|
||||
|
||||
@media ${tablet} {
|
||||
padding: 0 16px;
|
||||
${(props) =>
|
||||
props.visible
|
||||
? props.pinned
|
||||
? `
|
||||
display: flex;
|
||||
width: 240px;
|
||||
props.visible &&
|
||||
!props.pinned &&
|
||||
css`
|
||||
position: fixed;
|
||||
z-index: 400;
|
||||
`}
|
||||
}
|
||||
.resizable-block {
|
||||
padding: 0 24px;
|
||||
background: #f8f9f9;
|
||||
min-width: 265px;
|
||||
height: 100% !important;
|
||||
max-width: ${(props) => (props.isLoaded ? "calc(100vw - 368px)" : "265px")};
|
||||
box-sizing: border-box;
|
||||
overflow: hidden auto;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
.resizable-border {
|
||||
div {
|
||||
cursor: ew-resize !important;
|
||||
}
|
||||
}
|
||||
@media ${tablet} {
|
||||
padding: 0 16px;
|
||||
${(props) =>
|
||||
props.visible
|
||||
? props.pinned
|
||||
? `
|
||||
min-width: 240px;
|
||||
z-index: 400;
|
||||
`
|
||||
: `
|
||||
width: 240px;
|
||||
: `
|
||||
position: fixed !important;
|
||||
width: 240px !important;
|
||||
min-width: 240px;
|
||||
max-width: 240px;
|
||||
position: fixed;
|
||||
height: 100%;
|
||||
height: 100% !important;
|
||||
top: 0;
|
||||
left: 0;
|
||||
z-index: 400;
|
||||
resize: none;
|
||||
.resizable-border {
|
||||
display: none;
|
||||
}
|
||||
`
|
||||
: `
|
||||
width: 240px;
|
||||
min-width: 240px;
|
||||
max-width: 240px;
|
||||
position: fixed;
|
||||
height: 100%;
|
||||
top: 0;
|
||||
left: -240px;
|
||||
z-index: 400;
|
||||
resize: none;
|
||||
: `
|
||||
display: none;
|
||||
`}
|
||||
}
|
||||
}
|
||||
`;
|
||||
|
||||
class Article extends React.Component {
|
||||
/*shouldComponentUpdate() {
|
||||
return false;
|
||||
}*/
|
||||
|
||||
render() {
|
||||
//console.log("PageLayout Article render");
|
||||
return <StyledArticle {...this.props} />;
|
||||
//console.log("PageLayout Article render", this.props);
|
||||
const { children, ...rest } = this.props;
|
||||
const enable = {
|
||||
top: false,
|
||||
right: !isMobile,
|
||||
bottom: false,
|
||||
left: false,
|
||||
};
|
||||
return (
|
||||
<StyledArticle {...rest}>
|
||||
<Resizable
|
||||
enable={enable}
|
||||
className="resizable-block"
|
||||
handleWrapperClass="resizable-border"
|
||||
>
|
||||
{children}
|
||||
</Resizable>
|
||||
</StyledArticle>
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
Article.propTypes = {
|
||||
children: PropTypes.any,
|
||||
};
|
||||
|
||||
export default Article;
|
||||
|
@ -19,8 +19,7 @@ const StyledSection = styled.section`
|
||||
flex-grow: 1;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
min-width: 344px;
|
||||
|
||||
/*width: ${(props) => `${props.widthProp}px`};*/
|
||||
.layout-progress-bar {
|
||||
bottom: 0;
|
||||
position: sticky;
|
||||
@ -38,9 +37,6 @@ const StyledSection = styled.section`
|
||||
.section-body_filter {
|
||||
display: none;
|
||||
}
|
||||
|
||||
/*${(props) => props.widthProp < 738 && tabletProps};*/
|
||||
|
||||
@media ${tablet} {
|
||||
padding: 0 0 0 16px;
|
||||
${tabletProps};
|
||||
|
@ -6017,6 +6017,11 @@ fast-levenshtein@~2.0.6:
|
||||
resolved "https://registry.yarnpkg.com/fast-levenshtein/-/fast-levenshtein-2.0.6.tgz#3d8a5c66883a16a30ca8643e851f19baa7797917"
|
||||
integrity sha1-PYpcZog6FqMMqGQ+hR8Zuqd5eRc=
|
||||
|
||||
fast-memoize@^2.5.1:
|
||||
version "2.5.2"
|
||||
resolved "https://registry.yarnpkg.com/fast-memoize/-/fast-memoize-2.5.2.tgz#79e3bb6a4ec867ea40ba0e7146816f6cdce9b57e"
|
||||
integrity sha512-Ue0LwpDYErFbmNnZSF0UH6eImUwDmogUO1jyE+JbN2gsQz/jICm1Ve7t9QT0rNSsfJt+Hs4/S3GnsDVjL4HVrw==
|
||||
|
||||
fastparse@^1.1.1, fastparse@^1.1.2:
|
||||
version "1.1.2"
|
||||
resolved "https://registry.yarnpkg.com/fastparse/-/fastparse-1.1.2.tgz#91728c5a5942eced8531283c79441ee4122c35a9"
|
||||
@ -10445,6 +10450,13 @@ rc-util@^4.15.3, rc-util@^4.5.1:
|
||||
react-lifecycles-compat "^3.0.4"
|
||||
shallowequal "^1.1.0"
|
||||
|
||||
re-resizable@^6.7.0:
|
||||
version "6.7.0"
|
||||
resolved "https://registry.yarnpkg.com/re-resizable/-/re-resizable-6.7.0.tgz#63324f0d2c8cd24fedda6bba5d638bd09c63ee6b"
|
||||
integrity sha512-uBrV59SZgxmZunL7MWoSnEKEfQW+GfevJqWqnA0slTe54Xbdfn1SgvUCP/C7Ak3hHkz3dSHN8xwpyapdx2Sgrw==
|
||||
dependencies:
|
||||
fast-memoize "^2.5.1"
|
||||
|
||||
react-autosize-textarea@^7.0.0:
|
||||
version "7.1.0"
|
||||
resolved "https://registry.yarnpkg.com/react-autosize-textarea/-/react-autosize-textarea-7.1.0.tgz#902c84fc395a689ca3a484dfb6bc2be9ba3694d1"
|
||||
|
@ -16,8 +16,7 @@ const StyledGroupButtonsMenu = styled.div`
|
||||
height: 57px;
|
||||
list-style: none;
|
||||
padding: 0 18px 19px 0;
|
||||
width: ${(props) =>
|
||||
props.containerWidth ? props.containerWidth + "px" : "100%"};
|
||||
width: 100%;
|
||||
white-space: nowrap;
|
||||
display: ${(props) => (props.visible ? "block" : "none")};
|
||||
z-index: 189;
|
||||
@ -77,7 +76,7 @@ class GroupButtonsMenu extends React.Component {
|
||||
visible: props.visible,
|
||||
};
|
||||
|
||||
this.throttledResize = throttle(this.updateMenu, 300);
|
||||
this.throttledResize = throttle(this.updateMenu, 200);
|
||||
}
|
||||
|
||||
closeMenu = (e) => {
|
||||
@ -129,6 +128,7 @@ class GroupButtonsMenu extends React.Component {
|
||||
}
|
||||
|
||||
if (
|
||||
this.props.sectionWidth !== prevProps.sectionWidth ||
|
||||
this.state.priorityItems.length !== prevState.priorityItems.length ||
|
||||
this.state.moreItems.length !== prevState.moreItems.length
|
||||
) {
|
||||
@ -150,17 +150,20 @@ class GroupButtonsMenu extends React.Component {
|
||||
};
|
||||
|
||||
updateMenu = () => {
|
||||
const moreMenuElement = document.getElementById("moreMenu");
|
||||
const groupMenuOuterElement = document.getElementById("groupMenuOuter");
|
||||
const { sectionWidth } = this.props;
|
||||
let groupMenuOuterWidth = sectionWidth;
|
||||
|
||||
const screenWidth = window.innerWidth;
|
||||
const groupMenuOuterValues =
|
||||
groupMenuOuterElement && groupMenuOuterElement.getBoundingClientRect();
|
||||
if (!sectionWidth) {
|
||||
const groupMenuOuterElement = document.getElementById("groupMenuOuter");
|
||||
const groupMenuOuterValues =
|
||||
groupMenuOuterElement && groupMenuOuterElement.getBoundingClientRect();
|
||||
const screenWidth = window.innerWidth;
|
||||
const xWidth = groupMenuOuterValues && groupMenuOuterValues.x;
|
||||
groupMenuOuterWidth = screenWidth - xWidth;
|
||||
}
|
||||
const moreMenuElement = document.getElementById("moreMenu");
|
||||
const moreMenuWidth =
|
||||
moreMenuElement && moreMenuElement.getBoundingClientRect().width;
|
||||
const xWidth = groupMenuOuterValues && groupMenuOuterValues.x;
|
||||
const groupMenuOuterWidth = screenWidth - xWidth;
|
||||
|
||||
const visibleItemsCount = this.countMenuItems(
|
||||
this.widthsArray,
|
||||
groupMenuOuterWidth,
|
||||
@ -177,7 +180,6 @@ class GroupButtonsMenu extends React.Component {
|
||||
this.setState({
|
||||
priorityItems: priorityItems,
|
||||
moreItems: moreItems,
|
||||
width: groupMenuOuterWidth,
|
||||
});
|
||||
};
|
||||
|
||||
@ -196,14 +198,10 @@ class GroupButtonsMenu extends React.Component {
|
||||
isIndeterminate,
|
||||
onChange,
|
||||
} = this.props;
|
||||
const { priorityItems, moreItems, visible, width } = this.state;
|
||||
const { priorityItems, moreItems, visible } = this.state;
|
||||
|
||||
return (
|
||||
<StyledGroupButtonsMenu
|
||||
id="groupMenuOuter"
|
||||
visible={visible}
|
||||
containerWidth={width}
|
||||
>
|
||||
<StyledGroupButtonsMenu id="groupMenuOuter" visible={visible}>
|
||||
<GroupMenuWrapper id="groupMenu">
|
||||
{priorityItems.map((item, i) => (
|
||||
<GroupButton
|
||||
@ -261,6 +259,7 @@ GroupButtonsMenu.propTypes = {
|
||||
visible: PropTypes.bool,
|
||||
moreLabel: PropTypes.string,
|
||||
closeTitle: PropTypes.string,
|
||||
sectionWidth: PropTypes.oneOfType([PropTypes.number, PropTypes.string]),
|
||||
};
|
||||
|
||||
GroupButtonsMenu.defaultProps = {
|
||||
|
@ -182,7 +182,7 @@ const RowContent = (props) => {
|
||||
style,
|
||||
sideColor,
|
||||
onClick,
|
||||
widthProp,
|
||||
sectionWidth,
|
||||
isMobile,
|
||||
} = props;
|
||||
|
||||
@ -197,18 +197,18 @@ const RowContent = (props) => {
|
||||
id={id}
|
||||
onClick={onClick}
|
||||
style={style}
|
||||
widthProp={widthProp}
|
||||
widthProp={sectionWidth}
|
||||
isMobile={isMobile}
|
||||
>
|
||||
<MainContainerWrapper
|
||||
disableSideInfo={disableSideInfo}
|
||||
mainContainerWidth={mainContainerWidth}
|
||||
widthProp={widthProp}
|
||||
widthProp={sectionWidth}
|
||||
isMobile={isMobile}
|
||||
>
|
||||
<MainContainer
|
||||
className="rowMainContainer"
|
||||
widthProp={widthProp}
|
||||
widthProp={sectionWidth}
|
||||
isMobile={isMobile}
|
||||
>
|
||||
{children[0]}
|
||||
@ -225,7 +225,7 @@ const RowContent = (props) => {
|
||||
containerMinWidth={
|
||||
element.props && element.props.containerMinWidth
|
||||
}
|
||||
widthProp={widthProp}
|
||||
widthProp={sectionWidth}
|
||||
isMobile={isMobile}
|
||||
>
|
||||
{element}
|
||||
@ -236,7 +236,7 @@ const RowContent = (props) => {
|
||||
{!disableSideInfo && (
|
||||
<TabletSideInfo
|
||||
color={sideColor}
|
||||
widthProp={widthProp}
|
||||
widthProp={sectionWidth}
|
||||
isMobile={isMobile}
|
||||
>
|
||||
{sideInfo}
|
||||
@ -254,7 +254,7 @@ RowContent.propTypes = {
|
||||
onClick: PropTypes.func,
|
||||
sideColor: PropTypes.string,
|
||||
style: PropTypes.oneOfType([PropTypes.object, PropTypes.array]),
|
||||
widthProp: PropTypes.oneOfType([PropTypes.string, PropTypes.number]),
|
||||
sectionWidth: PropTypes.oneOfType([PropTypes.string, PropTypes.number]),
|
||||
isMobile: PropTypes.bool,
|
||||
};
|
||||
|
||||
|
@ -118,7 +118,7 @@ class Row extends React.Component {
|
||||
indeterminate,
|
||||
onSelect,
|
||||
selectItem,
|
||||
widthProp,
|
||||
sectionWidth,
|
||||
} = this.props;
|
||||
|
||||
const renderCheckbox = Object.prototype.hasOwnProperty.call(
|
||||
@ -133,7 +133,7 @@ class Row extends React.Component {
|
||||
|
||||
const renderContentElement =
|
||||
Object.prototype.hasOwnProperty.call(this.props, "contentElement") &&
|
||||
widthProp > 500;
|
||||
sectionWidth > 500;
|
||||
|
||||
const renderContext =
|
||||
Object.prototype.hasOwnProperty.call(this.props, "contextOptions") &&
|
||||
@ -192,7 +192,7 @@ Row.propTypes = {
|
||||
checked: PropTypes.bool,
|
||||
children: PropTypes.element,
|
||||
className: PropTypes.string,
|
||||
contentElement: PropTypes.element,
|
||||
contentElement: PropTypes.any,
|
||||
contextButtonSpacerWidth: PropTypes.string,
|
||||
contextOptions: PropTypes.array,
|
||||
data: PropTypes.object,
|
||||
@ -203,7 +203,7 @@ Row.propTypes = {
|
||||
onSelect: PropTypes.func,
|
||||
selectItem: PropTypes.func,
|
||||
style: PropTypes.oneOfType([PropTypes.object, PropTypes.array]),
|
||||
widthProp: PropTypes.oneOfType([PropTypes.string, PropTypes.number]),
|
||||
sectionWidth: PropTypes.oneOfType([PropTypes.string, PropTypes.number]),
|
||||
};
|
||||
|
||||
Row.defaultProps = {
|
||||
|
5
web/ASC.Web.Components/src/utils/context.js
Normal file
5
web/ASC.Web.Components/src/utils/context.js
Normal file
@ -0,0 +1,5 @@
|
||||
import React from "react";
|
||||
|
||||
const { Provider, Consumer } = React.createContext();
|
||||
|
||||
export { Provider, Consumer };
|
@ -2,5 +2,6 @@ import * as array from "./array";
|
||||
import * as event from "./event";
|
||||
import * as device from "./device";
|
||||
import * as email from "./email";
|
||||
import * as context from "./context";
|
||||
|
||||
export default { array, event, device, email };
|
||||
export default { array, event, device, email, context };
|
||||
|
Loading…
Reference in New Issue
Block a user