1
0
mirror of https://github.com/lensapp/lens.git synced 2025-05-20 05:10:56 +00:00

tooltip fixes, embed latest material-icons font, added page-layout

Signed-off-by: Roman <ixrock@gmail.com>
This commit is contained in:
Roman 2020-10-19 21:21:49 +03:00
parent 36cc10d222
commit 2e662e834b
15 changed files with 235 additions and 156 deletions

View File

@ -312,7 +312,6 @@
"jest": "^26.0.1",
"jest-mock-extended": "^1.0.10",
"make-plural": "^6.2.1",
"material-design-icons": "^3.0.1",
"mini-css-extract-plugin": "^0.9.0",
"mobx-react": "^6.2.2",
"moment": "^2.26.0",

View File

@ -57,7 +57,7 @@ export class Nodes extends React.Component<Props> {
max={cores}
value={usage}
tooltip={{
position: TooltipPosition.BOTTOM,
preferredPositions: TooltipPosition.BOTTOM,
children: _i18n._(t`CPU:`) + ` ${Math.ceil(usage * 100) / cores}\%, ` + _i18n._(t`cores:`) + ` ${cores}`
}}
/>
@ -74,7 +74,7 @@ export class Nodes extends React.Component<Props> {
max={capacity}
value={usage}
tooltip={{
position: TooltipPosition.BOTTOM,
preferredPositions: TooltipPosition.BOTTOM,
children: _i18n._(t`Memory:`) + ` ${Math.ceil(usage * 100 / capacity)}%, ${bytesToUnits(usage, 3)}`
}}
/>
@ -91,7 +91,7 @@ export class Nodes extends React.Component<Props> {
max={capacity}
value={usage}
tooltip={{
position: TooltipPosition.BOTTOM,
preferredPositions: TooltipPosition.BOTTOM,
children: _i18n._(t`Disk:`) + ` ${Math.ceil(usage * 100 / capacity)}%, ${bytesToUnits(usage, 3)}`
}}
/>

View File

@ -1,67 +1,3 @@
// TODO: figure out how to consume extra styles from extensions
.Support {
position: fixed!important; // Allows to cover ClustersMenu
z-index: 1;
.WizardLayout {
grid-template-columns: unset;
grid-template-rows: 76px 1fr;
padding: 0;
.content-col {
padding: $padding * 8 0;
background-color: $clusterSettingsBackground;
h2 {
margin-bottom: $margin * 2;
&:not(:first-child) {
margin-top: $margin * 3;
}
}
.SubTitle {
text-transform: none;
margin: 0!important;
}
.repos {
position: relative;
.Badge {
display: flex;
margin: 0;
margin-bottom: 1px;
padding: $padding $padding * 2;
}
}
.hint {
margin-top: -$margin;
}
}
span.supportLink {
cursor: pointer;
color: $primary;
text-decoration: underline;
position: relative;
}
}
.is-mac & {
.WizardLayout .head-col {
padding-top: 32px;
overflow: hidden;
.Icon {
margin-top: -$margin * 2;
}
}
}
.Select {
&__control {
box-shadow: 0 0 0 1px $borderFaintColor;
}
}
}

View File

@ -1,51 +1,28 @@
import "./support.scss"
import React from "react"
import { observer } from "mobx-react"
import { Icon } from "../icon"
import { WizardLayout } from "../layout/wizard-layout"
import { history } from "../../navigation"
import { Trans } from "@lingui/macro"
import { shell } from "electron"
import { issuesTrackerUrl, slackUrl } from "../../../common/vars";
import { t } from "@lingui/macro";
import { _i18n } from "../../i18n";
import { PageLayout } from "../layout/page-layout";
@observer
export class Support extends React.Component {
async componentDidMount() {
window.addEventListener('keydown', this.onEscapeKey);
}
componentWillUnmount() {
window.removeEventListener('keydown', this.onEscapeKey);
}
onEscapeKey = (evt: KeyboardEvent) => {
if (evt.code === "Escape") {
evt.stopPropagation();
history.goBack();
}
}
render() {
const header = (
<>
<h2>Support</h2>
<Icon material="close" big onClick={history.goBack}/>
</>
);
return (
<div className="Support">
<WizardLayout header={header} centered>
<h2><Trans>Community Slack Channel</Trans></h2>
<p>{_i18n._(t`Ask a question, see what's being discussed, join the conversation`)} <span className="supportLink" title={_i18n._(t`here`)} onClick={() => shell.openExternal(slackUrl) }>here</span></p>
<h2><Trans>Report an Issue</Trans></h2>
<p>{_i18n._(t`Review existing issues or open a new one`)} <span className="supportLink" title={_i18n._(t`here`)} onClick={() => shell.openExternal(issuesTrackerUrl) }>here</span></p>
<h2><Trans>Commercial Support</Trans></h2>
<p>TBD</p>
</WizardLayout>
</div>
<PageLayout fullScreen className="Support" header={<h2>Support</h2>}>
<h2><Trans>Community Slack Channel</Trans></h2>
<p>
<Trans>Ask a question, see what's being discussed, join the conversation <a className="supportLink" href={slackUrl} target="_blank">here</a></Trans>{" "}
</p>
<h2><Trans>Report an Issue</Trans></h2>
<p>
<Trans>Review existing issues or open a new one <a className="supportLink" href={issuesTrackerUrl} target="_blank">here</a></Trans>
</p>
{/*<h2><Trans>Commercial Support</Trans></h2>*/}
</PageLayout>
);
}
}

View File

@ -10,9 +10,4 @@
--flex-gap: #{$spacing};
cursor: pointer;
}
#support {
--flex-gap: #{$spacing};
cursor: pointer;
}
}

View File

@ -1,10 +1,10 @@
import "./bottom-bar.scss"
import React from "react";
import { observer } from "mobx-react";
import { Icon } from "../icon";
import { WorkspaceMenu } from "../+workspaces/workspace-menu";
import { workspaceStore } from "../../../common/workspace-store";
import { supportURL } from "../+support/support.route";
import { navigate } from "../../navigation";
@ -19,13 +19,13 @@ export class BottomBar extends React.Component {
<span className="workspace-name">{currentWorkspace.name}</span>
</div>
<WorkspaceMenu htmlFor="current-workspace"/>
<div id="support" className="flex gaps align-center box right">
<Icon
small
svg="support"
onClick={() => navigate(supportURL())}
/>
</div>
<Icon
small
material="support"
tooltip="Support"
className="support-icon box right"
onClick={() => navigate(supportURL())}
/>
</div>
)
}

View File

@ -1,7 +1,15 @@
// Custom fonts
@import "~material-design-icons/iconfont/material-icons.css";
@import "~typeface-roboto/index.css";
// Material Design Icons, used primarily in icon.tsx
// Latest: https://github.com/google/material-design-icons/tree/master/font
@font-face {
font-family: "Material Icons";
font-style: normal;
font-weight: 400;
src: url("../fonts/MaterialIcons-Regular.ttf") format("truetype");
}
// Patched RobotoMono font with icons
// RobotoMono Windows Compatible for using in terminal
// https://github.com/ryanoasis/nerd-fonts/tree/master/patched-fonts/RobotoMono

View File

@ -1 +0,0 @@
<svg xmlns="http://www.w3.org/2000/svg" enable-background="new 0 0 24 24" viewBox="0 0 24 24" <g><path d="M12,2C6.48,2,2,6.48,2,12c0,5.52,4.48,10,10,10s10-4.48,10-10C22,6.48,17.52,2,12,2z M19.46,9.12l-2.78,1.15 c-0.51-1.36-1.58-2.44-2.95-2.94l1.15-2.78C16.98,5.35,18.65,7.02,19.46,9.12z M12,15c-1.66,0-3-1.34-3-3s1.34-3,3-3s3,1.34,3,3 S13.66,15,12,15z M9.13,4.54l1.17,2.78c-1.38,0.5-2.47,1.59-2.98,2.97L4.54,9.13C5.35,7.02,7.02,5.35,9.13,4.54z M4.54,14.87 l2.78-1.15c0.51,1.38,1.59,2.46,2.97,2.96l-1.17,2.78C7.02,18.65,5.35,16.98,4.54,14.87z M14.88,19.46l-1.15-2.78 c1.37-0.51,2.45-1.59,2.95-2.97l2.78,1.17C18.65,16.98,16.98,18.65,14.88,19.46z"/></g></svg>

Before

Width:  |  Height:  |  Size: 656 B

View File

@ -0,0 +1,55 @@
.PageLayout {
$spacing: $padding * 2;
position: relative;
height: 100%;
display: grid !important;
grid-template-rows: min-content 1fr;
// global page, covers whole app screen
&.global {
position: fixed !important; // allow to cover ClustersMenu
z-index: 1;
}
> .header {
position: sticky;
padding: $spacing;
background-color: $layoutTabsBackground;
// add extra spacing for traffic-light top buttons (mac only)
.is-mac & {
padding-top: $spacing * 2;
}
}
> .content-wrapper {
@include custom-scrollbar-themed;
padding: $spacing * 2;
> .content {
margin: 0 auto;
width: 60%;
min-width: 570px;
max-width: 1000px;
}
}
h2:not(:first-of-type) {
margin-top: $spacing;
}
p {
line-height: 140%;
}
a {
color: $colorInfo;
}
.Select {
&__control {
box-shadow: 0 0 0 1px $borderFaintColor;
}
}
}

View File

@ -0,0 +1,73 @@
import "./page-layout.scss"
import React from "react";
import { observer } from "mobx-react";
import { cssNames, IClassName } from "../../utils";
import { Icon } from "../icon";
import { navigation } from "../../navigation";
export interface PageLayoutProps extends React.DOMAttributes<any> {
className?: IClassName;
header: React.ReactNode;
headerClass?: IClassName;
contentClass?: IClassName;
provideBackButtonNavigation?: boolean;
contentGaps?: boolean;
fullScreen?: boolean; // covers whole app view
}
const defaultProps: Partial<PageLayoutProps> = {
provideBackButtonNavigation: true,
contentGaps: true,
}
@observer
export class PageLayout extends React.Component<PageLayoutProps> {
static defaultProps = defaultProps as object;
back = () => navigation.goBack();
async componentDidMount() {
window.addEventListener('keydown', this.onEscapeKey);
}
componentWillUnmount() {
window.removeEventListener('keydown', this.onEscapeKey);
}
onEscapeKey = (evt: KeyboardEvent) => {
if (!this.props.provideBackButtonNavigation) {
return;
}
if (evt.code === "Escape") {
evt.stopPropagation();
this.back();
}
}
render() {
const {
className, contentClass, header, headerClass, provideBackButtonNavigation,
contentGaps, fullScreen, children, ...elemProps
} = this.props;
return (
<div {...elemProps} className={cssNames("PageLayout", className, { global: fullScreen })}>
<div className={cssNames("header flex gaps align-center", headerClass)}>
{header}
{provideBackButtonNavigation && (
<Icon
big material="close"
className="back box right"
onClick={this.back}
/>
)}
</div>
<div className="content-wrapper">
<div className={cssNames("content", contentGaps && "flex column gaps", contentClass)}>
{children}
</div>
</div>
</div>
)
}
}

View File

@ -8,13 +8,9 @@
grid-template-columns: 1fr 40%;
> * {
@include custom-scrollbar;
@include custom-scrollbar-themed;
--flex-gap: #{$spacing};
padding: $spacing;
.theme-light & {
@include custom-scrollbar(dark);
}
}
> .head-col {

View File

@ -6,6 +6,21 @@
@import "table/table.mixins";
@import "+network/network-mixins";
@mixin custom-scrollbar-themed($invert: false) {
@if ($invert) {
@include custom-scrollbar(dark);
.theme-light & {
@include custom-scrollbar(light);
}
} @else {
// fits better with dark background
@include custom-scrollbar(light);
.theme-light & {
@include custom-scrollbar(dark);
}
}
}
@mixin custom-scrollbar($theme: light, $size: 7px, $borderSpacing: 5px) {
$themes: (
light: #5f6064,

View File

@ -11,6 +11,10 @@ export enum TooltipPosition {
BOTTOM = "bottom",
LEFT = "left",
RIGHT = "right",
TOP_LEFT = "top_left",
TOP_RIGHT = "top_right",
BOTTOM_LEFT = "bottom_left",
BOTTOM_RIGHT = "bottom_right",
}
export interface TooltipProps {
@ -19,7 +23,7 @@ export interface TooltipProps {
visible?: boolean; // initial visibility
offset?: number; // offset from target element in pixels (all sides)
usePortal?: boolean; // renders element outside of parent (in body), disable for "easy-styling", default: true
position?: TooltipPosition;
preferredPositions?: TooltipPosition | TooltipPosition[];
className?: IClassName;
formatters?: TooltipContentFormatters;
style?: React.CSSProperties;
@ -82,17 +86,25 @@ export class Tooltip extends React.Component<TooltipProps> {
@autobind()
refreshPosition() {
const { position } = this.props;
const { preferredPositions } = this.props;
const { elem, targetElem } = this;
const positionPreference = new Set<TooltipPosition>();
if (typeof position !== "undefined") {
positionPreference.add(position);
let positions = new Set<TooltipPosition>([
TooltipPosition.RIGHT,
TooltipPosition.BOTTOM,
TooltipPosition.TOP,
TooltipPosition.LEFT,
TooltipPosition.TOP_RIGHT,
TooltipPosition.TOP_LEFT,
TooltipPosition.BOTTOM_RIGHT,
TooltipPosition.BOTTOM_LEFT,
]);
if (preferredPositions) {
positions = new Set([
...[preferredPositions].flat(),
...positions,
])
}
positionPreference.add(TooltipPosition.RIGHT)
.add(TooltipPosition.BOTTOM)
.add(TooltipPosition.TOP)
.add(TooltipPosition.LEFT)
// reset position first and get all possible client-rect area for tooltip element
this.setPosition({ left: 0, top: 0 });
@ -102,20 +114,20 @@ export class Tooltip extends React.Component<TooltipProps> {
const { innerWidth: viewportWidth, innerHeight: viewportHeight } = window;
// find proper position
for (const pos of positionPreference) {
for (const pos of positions) {
const { left, top, right, bottom } = this.getPosition(pos, selfBounds, targetBounds)
const fitsToWindow = left >= 0 && top >= 0 && right <= viewportWidth && bottom <= viewportHeight;
if (fitsToWindow) {
this.activePosition = pos;
this.setPosition({ top, left });
return;
}
}
const preferedPosition = Array.from(positionPreference)[0];
const { left, top } = this.getPosition(preferedPosition, selfBounds, targetBounds)
this.activePosition = preferedPosition;
// apply fallback position if nothing helped from above
const fallbackPosition = Array.from(positions)[0];
const { left, top } = this.getPosition(fallbackPosition, selfBounds, targetBounds)
this.activePosition = fallbackPosition;
this.setPosition({ left, top });
}
@ -125,35 +137,54 @@ export class Tooltip extends React.Component<TooltipProps> {
elemStyle.top = pos.top + "px"
}
protected getPosition(position: TooltipPosition, selfBounds: DOMRect, targetBounds: DOMRect) {
let left: number
let top: number
protected getPosition(position: TooltipPosition, tooltipBounds: DOMRect, targetBounds: DOMRect) {
let left: number;
let top: number;
const offset = this.props.offset;
const horizontalCenter = targetBounds.left + (targetBounds.width - selfBounds.width) / 2;
const verticalCenter = targetBounds.top + (targetBounds.height - selfBounds.height) / 2;
const horizontalCenter = targetBounds.left + (targetBounds.width - tooltipBounds.width) / 2;
const verticalCenter = targetBounds.top + (targetBounds.height - tooltipBounds.height) / 2;
const topCenter = targetBounds.top - tooltipBounds.height - offset;
const bottomCenter = targetBounds.bottom + offset;
switch (position) {
case "top":
left = horizontalCenter;
top = targetBounds.top - selfBounds.height - offset;
top = topCenter;
break;
case "bottom":
left = horizontalCenter;
top = targetBounds.bottom + offset;
top = bottomCenter;
break;
case "left":
top = verticalCenter;
left = targetBounds.left - selfBounds.width - offset;
left = targetBounds.left - tooltipBounds.width - offset;
break;
case "right":
top = verticalCenter;
left = targetBounds.right + offset;
break;
case "top_left":
left = targetBounds.left;
top = topCenter;
break;
case "top_right":
default:
left = targetBounds.right - tooltipBounds.width;
top = topCenter;
break;
case "bottom_left":
top = bottomCenter;
left = targetBounds.left;
break;
case "bottom_right":
top = bottomCenter;
left = targetBounds.right - tooltipBounds.width;
break;
}
return {
left: left,
top: top,
right: left + selfBounds.width,
bottom: top + selfBounds.height,
right: left + tooltipBounds.width,
bottom: top + tooltipBounds.height,
};
}

Binary file not shown.

View File

@ -8644,11 +8644,6 @@ matcher@^3.0.0:
dependencies:
escape-string-regexp "^4.0.0"
material-design-icons@^3.0.1:
version "3.0.1"
resolved "https://registry.yarnpkg.com/material-design-icons/-/material-design-icons-3.0.1.tgz#9a71c48747218ebca51e51a66da682038cdcb7bf"
integrity sha1-mnHEh0chjrylHlGmbaaCA4zct78=
md5-file@^5.0.0:
version "5.0.0"
resolved "https://registry.yarnpkg.com/md5-file/-/md5-file-5.0.0.tgz#e519f631feca9c39e7f9ea1780b63c4745012e20"