diff --git a/webapp/src/components/comment.scss b/webapp/src/components/comment.scss index 13bbf9aa7..681139eea 100644 --- a/webapp/src/components/comment.scss +++ b/webapp/src/components/comment.scss @@ -46,6 +46,9 @@ } .comment-text * { - user-select: text; + -webkit-user-select: text; /* Chrome all / Safari all */ + -moz-user-select: text; /* Firefox all */ + -ms-user-select: text; /* IE 10+ */ + user-select: text; /* Likely future */ } } diff --git a/webapp/src/components/dialog.scss b/webapp/src/components/dialog.scss index 2aaabf258..4efbc7f03 100644 --- a/webapp/src/components/dialog.scss +++ b/webapp/src/components/dialog.scss @@ -26,6 +26,11 @@ margin: 72px auto; max-width: 975px; height: calc(100% - 144px); + + .hideOnWidescreen { + /* Hide controls (e.g. close button) on larger screens */ + display: none !important; + } } @media screen and (max-width: 975px) { position: fixed; @@ -64,12 +69,5 @@ > .content.fullwidth { padding: 10px 0 10px 0; } - - .hideOnWidescreen { - /* Hide controls (e.g. close button) on larger screens */ - @media not screen and (max-width: 975px) { - display: none; - } - } } } diff --git a/webapp/src/components/filterComponent.scss b/webapp/src/components/filterComponent.scss index 9431900d2..100da01d8 100644 --- a/webapp/src/components/filterComponent.scss +++ b/webapp/src/components/filterComponent.scss @@ -4,12 +4,12 @@ left: -200px; z-index: 10; - min-width: 420px; + min-width: 430px; box-shadow: rgba(var(--main-fg), 0.1) 0px 0px 0px 1px, rgba(var(--main-fg), 0.1) 0px 2px 4px; background-color: rgb(var(--main-bg)); padding: 10px; - @media screen and (max-width: 420px) { + @media screen and (max-width: 430px) { position: fixed; top: 0; left: 0; @@ -20,7 +20,7 @@ .hideOnWidescreen { /* Hide controls (e.g. close button) on larger screens */ - @media not screen and (max-width: 420px) { + @media not screen and (max-width: 430px) { display: none !important; } } diff --git a/webapp/src/styles/main.scss b/webapp/src/styles/main.scss index b65f89f11..1cd90f8fc 100644 --- a/webapp/src/styles/main.scss +++ b/webapp/src/styles/main.scss @@ -9,8 +9,11 @@ * { box-sizing: border-box; - outline: 0; - user-select: none; + outline: 0; + -webkit-user-select: none; /* Chrome all / Safari all */ + -moz-user-select: none; /* Firefox all */ + -ms-user-select: none; /* IE 10+ */ + user-select: none; /* Likely future */ } html, body { diff --git a/webapp/src/widgets/buttons/button.scss b/webapp/src/widgets/buttons/button.scss index 8ebe941e3..92247fd60 100644 --- a/webapp/src/widgets/buttons/button.scss +++ b/webapp/src/widgets/buttons/button.scss @@ -1,5 +1,6 @@ .Button { display: flex; + flex: 0 0 auto; align-items: center; text-align: center; justify-content: center; diff --git a/webapp/src/widgets/menu/colorOption.tsx b/webapp/src/widgets/menu/colorOption.tsx index 8b4243072..87a8e2165 100644 --- a/webapp/src/widgets/menu/colorOption.tsx +++ b/webapp/src/widgets/menu/colorOption.tsx @@ -23,8 +23,8 @@ export default class ColorOption extends React.PureComponent { className='MenuOption ColorOption menu-option' onClick={this.handleOnClick} > + {icon ??
}
{name}
- {icon}
) diff --git a/webapp/src/widgets/menu/labelOption.tsx b/webapp/src/widgets/menu/labelOption.tsx index 610a3c819..85143bd0b 100644 --- a/webapp/src/widgets/menu/labelOption.tsx +++ b/webapp/src/widgets/menu/labelOption.tsx @@ -13,8 +13,9 @@ export default class LabelOption extends React.PureComponent { public render(): JSX.Element { return (
+ {this.props.icon ??
}
{this.props.children}
- {this.props.icon} +
) } diff --git a/webapp/src/widgets/menu/menu.scss b/webapp/src/widgets/menu/menu.scss index 96772e2b2..96d21441e 100644 --- a/webapp/src/widgets/menu/menu.scss +++ b/webapp/src/widgets/menu/menu.scss @@ -1,4 +1,6 @@ .Menu { + display: flex; + flex-direction: column; position: absolute; z-index: 15; min-width: 180px; @@ -8,11 +10,9 @@ border-radius: 3px; box-shadow: rgba(var(--main-fg), 0.05) 0px 0px 0px 1px, rgba(var(--main-fg), 0.1) 0px 3px 6px, rgba(var(--main-fg), 0.2) 0px 9px 24px; - &.top { - bottom: 100%; - } - &.left { - right: 0; + .menu-contents { + display: flex; + flex-direction: column; } .menu-options { @@ -20,47 +20,118 @@ flex-direction: column; flex-grow: 1; + position: relative; list-style: none; padding: 0; margin: 0; color: rgb(var(--main-fg)); + + >.menu-option { + display: flex; + flex-direction: row; + align-items: center; + + font-weight: 400; + padding: 2px 10px; + cursor: pointer; + + &:hover { + background: rgba(90, 90, 90, 0.1); + } + >* { + margin-left: 5px; + } + >*:first-child { + margin-left: 0; + } + + >.menu-name { + display: flex; + flex-grow: 1; + white-space: nowrap; + } + + >.SubmenuTriangleIcon { + fill: rgba(var(--main-fg), 0.7); + } + + >.Icon { + width: 16px; + height: 16px; + } + >.IconButton .Icon { + margin-right: 0; + } + } } - .menu-option { - display: flex; - flex-direction: row; - align-items: center; + .menu-spacer { + height: 20px; + width: 20px; + flex: 0 0 auto; + } +} - font-weight: 400; - padding: 2px 10px; - cursor: pointer; - touch-action: none; +.Menu, .SubMenuOption .SubMenu { + @media screen and (max-width: 430px) { + position: fixed; + top: 0; + left: 0; + right: 0; + bottom: 0; + min-width: 0; + background-color: rgba(var(--main-fg), 0.5); + border-radius: 0; + padding: 10px; - &:hover { - background: rgba(90, 90, 90, 0.1); + display: block; + overflow-y: auto; + + .menu-contents { + justify-content: flex-end; + min-height: 100%; } - .menu-name { - display: flex; - flex-grow: 1; - white-space: nowrap; - margin-right: 20px; + .menu-options { + align-items: center; + border-radius: 10px; + overflow: hidden; + + flex: 0 0 auto; + + >.menu-option { + min-height: 44px; + width: 100%; + padding: 0 20px; + background-color: rgb(var(--main-bg)); + + >* { + flex: 0 0 auto; + } + >.noicon { + width: 16px; + height: 16px; + } + >.menu-name { + font-size: 16px; + justify-content: center; + } + } + } + } + @media not screen and (max-width: 430px) { + &.top { + bottom: 100%; + } + &.left { + right: 0; } - .SubmenuTriangleIcon { - fill: rgba(var(--main-fg), 0.7); - } - - .Icon { - width: 16px; - height: 16px; - margin-right: 5px; - } - - .IconButton .Icon { - margin-right: 0; + .hideOnWidescreen { + /* Hide controls (e.g. close button) on larger screens */ + display: none !important; } } } diff --git a/webapp/src/widgets/menu/menu.tsx b/webapp/src/widgets/menu/menu.tsx index 3cd6a9f60..d0ff78c61 100644 --- a/webapp/src/widgets/menu/menu.tsx +++ b/webapp/src/widgets/menu/menu.tsx @@ -11,12 +11,12 @@ import LabelOption from './labelOption' import './menu.scss' -type MenuProps = { +type Props = { children: React.ReactNode position?: 'top'|'bottom'|'left' } -export default class Menu extends React.PureComponent { +export default class Menu extends React.PureComponent { static Color = ColorOption static SubMenu = SubMenuOption static Switch = SwitchOption @@ -28,10 +28,27 @@ export default class Menu extends React.PureComponent { const {position, children} = this.props return (
-
- {children} +
+
+ {children} +
+ +
+ +
+ +
) } + + private onCancel = () => { + // No need to do anything, as click bubbled up to MenuWrapper, which closes + } } diff --git a/webapp/src/widgets/menu/subMenuOption.scss b/webapp/src/widgets/menu/subMenuOption.scss index 327d13c46..2cd6c2d53 100644 --- a/webapp/src/widgets/menu/subMenuOption.scss +++ b/webapp/src/widgets/menu/subMenuOption.scss @@ -3,10 +3,11 @@ .SubMenu { position: absolute; - z-index: 15; + z-index: 16; min-width: 180px; background-color: rgb(var(--main-bg)); color: rgb(var(--main-fg)); + margin: 0 !important; border-radius: 3px; box-shadow: rgba(var(--main-fg), 0.05) 0px 0px 0px 1px, rgba(var(--main-fg), 0.1) 0px 3px 6px, rgba(var(--main-fg), 0.2) 0px 9px 24px; @@ -19,7 +20,9 @@ } } - .SubmenuTriangleIcon { - float: 'right' + @media screen and (max-width: 430px) { + .SubMenu { + background-color: rgba(var(--main-fg), 0.8) !important; + } } } diff --git a/webapp/src/widgets/menu/subMenuOption.tsx b/webapp/src/widgets/menu/subMenuOption.tsx index 2fdb1c65d..e49c77964 100644 --- a/webapp/src/widgets/menu/subMenuOption.tsx +++ b/webapp/src/widgets/menu/subMenuOption.tsx @@ -4,6 +4,8 @@ import React from 'react' import SubmenuTriangleIcon from '../icons/submenuTriangle' +import Menu from '.' + import './subMenuOption.scss' type SubMenuOptionProps = { @@ -23,7 +25,9 @@ export default class SubMenuOption extends React.PureComponent { - this.setState({isOpen: true}) + setTimeout(() => { + this.setState({isOpen: true}) + }, 50) } private close = (): void => { @@ -37,17 +41,34 @@ export default class SubMenuOption extends React.PureComponent - {this.props.icon} + {this.props.icon ??
}
{this.props.name}
{this.state.isOpen && -
-
- {this.props.children} +
+
+
+ {this.props.children} +
+
+ +
+ +
+
}
) } + + private onCancel = () => { + // No need to do anything, as click bubbled up to MenuWrapper, which closes + } } diff --git a/webapp/src/widgets/menu/switchOption.tsx b/webapp/src/widgets/menu/switchOption.tsx index 405d9098f..e51f082f8 100644 --- a/webapp/src/widgets/menu/switchOption.tsx +++ b/webapp/src/widgets/menu/switchOption.tsx @@ -24,8 +24,8 @@ export default class SwitchOption extends React.PureComponent className='MenuOption SwitchOption menu-option' onClick={this.handleOnClick} > + {icon ??
}
{name}
- {icon} {}} diff --git a/webapp/src/widgets/menu/textOption.tsx b/webapp/src/widgets/menu/textOption.tsx index 9dd75254c..897b0fe79 100644 --- a/webapp/src/widgets/menu/textOption.tsx +++ b/webapp/src/widgets/menu/textOption.tsx @@ -7,6 +7,7 @@ import {MenuOptionProps} from './menuItem' type TextOptionProps = MenuOptionProps & { icon?: React.ReactNode, rightIcon?: React.ReactNode, + className?: string } export default class TextOption extends React.PureComponent { @@ -17,14 +18,18 @@ export default class TextOption extends React.PureComponent { public render(): JSX.Element { const {name, icon, rightIcon} = this.props + let className = 'MenuOption TextOption menu-option' + if (this.props.className) { + className += ' ' + this.props.className + } return (
- {icon} + {icon ??
}
{name}
- {rightIcon} + {rightIcon ??
}
) }