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

clusters-menu

Signed-off-by: Roman <ixrock@gmail.com>
This commit is contained in:
Roman 2020-07-09 12:29:46 +03:00
parent ba4f5cb47d
commit a440f60ea3
9 changed files with 109 additions and 73 deletions

View File

@ -211,7 +211,7 @@ msgstr "Are you sure you want to drain <0>{nodeName}</0>?"
msgid "Arguments" msgid "Arguments"
msgstr "Arguments" msgstr "Arguments"
#: src/renderer/components/+workspaces/clusters-menu.tsx:55 #: src/renderer/components/+workspaces/clusters-menu.tsx:64
msgid "Associate clusters and choose the ones you want to access via quick launch menu by clicking the + button." msgid "Associate clusters and choose the ones you want to access via quick launch menu by clicking the + button."
msgstr "Associate clusters and choose the ones you want to access via quick launch menu by clicking the + button." msgstr "Associate clusters and choose the ones you want to access via quick launch menu by clicking the + button."
@ -678,7 +678,7 @@ msgstr "Description"
msgid "Desired number of replicas" msgid "Desired number of replicas"
msgstr "Desired number of replicas" msgstr "Desired number of replicas"
#: src/renderer/components/+workspaces/clusters-menu.tsx:38 #: src/renderer/components/+workspaces/clusters-menu.tsx:40
msgid "Disconnect" msgid "Disconnect"
msgstr "Disconnect" msgstr "Disconnect"
@ -2030,7 +2030,7 @@ msgstr "Set"
msgid "Set quota" msgid "Set quota"
msgstr "Set quota" msgstr "Set quota"
#: src/renderer/components/+workspaces/clusters-menu.tsx:31 #: src/renderer/components/+workspaces/clusters-menu.tsx:33
msgid "Settings" msgid "Settings"
msgstr "Settings" msgstr "Settings"
@ -2204,7 +2204,7 @@ msgstr "This field is required"
msgid "This field must contain only lowercase latin characters, numbers and dash." msgid "This field must contain only lowercase latin characters, numbers and dash."
msgstr "This field must contain only lowercase latin characters, numbers and dash." msgstr "This field must contain only lowercase latin characters, numbers and dash."
#: src/renderer/components/+workspaces/clusters-menu.tsx:53 #: src/renderer/components/+workspaces/clusters-menu.tsx:62
msgid "This is the quick launch menu." msgid "This is the quick launch menu."
msgstr "This is the quick launch menu." msgstr "This is the quick launch menu."
@ -2382,7 +2382,7 @@ msgstr "Worker"
msgid "Workloads" msgid "Workloads"
msgstr "Workloads" msgstr "Workloads"
#: src/renderer/components/+workspaces/workspaces.tsx:41 #: src/renderer/components/+workspaces/bottom-bar.tsx:31
msgid "Workspaces" msgid "Workspaces"
msgstr "Workspaces" msgstr "Workspaces"

View File

@ -211,7 +211,7 @@ msgstr ""
msgid "Arguments" msgid "Arguments"
msgstr "" msgstr ""
#: src/renderer/components/+workspaces/clusters-menu.tsx:55 #: src/renderer/components/+workspaces/clusters-menu.tsx:64
msgid "Associate clusters and choose the ones you want to access via quick launch menu by clicking the + button." msgid "Associate clusters and choose the ones you want to access via quick launch menu by clicking the + button."
msgstr "" msgstr ""
@ -674,7 +674,7 @@ msgstr ""
msgid "Desired number of replicas" msgid "Desired number of replicas"
msgstr "" msgstr ""
#: src/renderer/components/+workspaces/clusters-menu.tsx:38 #: src/renderer/components/+workspaces/clusters-menu.tsx:40
msgid "Disconnect" msgid "Disconnect"
msgstr "" msgstr ""
@ -2013,7 +2013,7 @@ msgstr ""
msgid "Set quota" msgid "Set quota"
msgstr "" msgstr ""
#: src/renderer/components/+workspaces/clusters-menu.tsx:31 #: src/renderer/components/+workspaces/clusters-menu.tsx:33
msgid "Settings" msgid "Settings"
msgstr "" msgstr ""
@ -2187,7 +2187,7 @@ msgstr ""
msgid "This field must contain only lowercase latin characters, numbers and dash." msgid "This field must contain only lowercase latin characters, numbers and dash."
msgstr "" msgstr ""
#: src/renderer/components/+workspaces/clusters-menu.tsx:53 #: src/renderer/components/+workspaces/clusters-menu.tsx:62
msgid "This is the quick launch menu." msgid "This is the quick launch menu."
msgstr "" msgstr ""
@ -2365,7 +2365,7 @@ msgstr ""
msgid "Workloads" msgid "Workloads"
msgstr "" msgstr ""
#: src/renderer/components/+workspaces/workspaces.tsx:41 #: src/renderer/components/+workspaces/bottom-bar.tsx:31
msgid "Workspaces" msgid "Workspaces"
msgstr "" msgstr ""

View File

@ -212,7 +212,7 @@ msgstr "Выполнить команду drain для ноды <0>{nodeName}</0
msgid "Arguments" msgid "Arguments"
msgstr "Аргументы" msgstr "Аргументы"
#: src/renderer/components/+workspaces/clusters-menu.tsx:55 #: src/renderer/components/+workspaces/clusters-menu.tsx:64
msgid "Associate clusters and choose the ones you want to access via quick launch menu by clicking the + button." msgid "Associate clusters and choose the ones you want to access via quick launch menu by clicking the + button."
msgstr "" msgstr ""
@ -679,7 +679,7 @@ msgstr "Описание"
msgid "Desired number of replicas" msgid "Desired number of replicas"
msgstr "Нужный уровень реплик" msgstr "Нужный уровень реплик"
#: src/renderer/components/+workspaces/clusters-menu.tsx:38 #: src/renderer/components/+workspaces/clusters-menu.tsx:40
msgid "Disconnect" msgid "Disconnect"
msgstr "" msgstr ""
@ -2031,7 +2031,7 @@ msgstr "Установлено"
msgid "Set quota" msgid "Set quota"
msgstr "Установить квоту" msgstr "Установить квоту"
#: src/renderer/components/+workspaces/clusters-menu.tsx:31 #: src/renderer/components/+workspaces/clusters-menu.tsx:33
msgid "Settings" msgid "Settings"
msgstr "" msgstr ""
@ -2205,7 +2205,7 @@ msgstr "Это обязательное поле"
msgid "This field must contain only lowercase latin characters, numbers and dash." msgid "This field must contain only lowercase latin characters, numbers and dash."
msgstr "Это поле может содержать только латинские буквы в нижнем регистре, номера и дефис." msgstr "Это поле может содержать только латинские буквы в нижнем регистре, номера и дефис."
#: src/renderer/components/+workspaces/clusters-menu.tsx:53 #: src/renderer/components/+workspaces/clusters-menu.tsx:62
msgid "This is the quick launch menu." msgid "This is the quick launch menu."
msgstr "" msgstr ""
@ -2383,7 +2383,7 @@ msgstr "Рабочие"
msgid "Workloads" msgid "Workloads"
msgstr "Ресурсы" msgstr "Ресурсы"
#: src/renderer/components/+workspaces/workspaces.tsx:41 #: src/renderer/components/+workspaces/bottom-bar.tsx:31
msgid "Workspaces" msgid "Workspaces"
msgstr "" msgstr ""

View File

@ -35,7 +35,9 @@ export class UserStore extends BaseStore<UserStoreModel> {
} }
@observable lastSeenAppVersion = "0.0.0" @observable lastSeenAppVersion = "0.0.0"
@observable seenContexts = observable.set(); @observable seenContexts: string[] = [];
@observable newContexts: string[] = []; // todo: detect new contexts from .kube/config since last open
@observable preferences: UserPreferences = { @observable preferences: UserPreferences = {
allowTelemetry: true, allowTelemetry: true,
colorTheme: "dark", colorTheme: "dark",
@ -54,16 +56,12 @@ export class UserStore extends BaseStore<UserStoreModel> {
@action @action
protected fromStore(data: Partial<UserStoreModel> = {}) { protected fromStore(data: Partial<UserStoreModel> = {}) {
const { lastSeenAppVersion, seenContexts, preferences } = data const { lastSeenAppVersion, seenContexts = [], preferences } = data
if (lastSeenAppVersion) { if (lastSeenAppVersion) {
this.lastSeenAppVersion = lastSeenAppVersion; this.lastSeenAppVersion = lastSeenAppVersion;
} }
if (seenContexts) { this.seenContexts = seenContexts;
this.seenContexts = observable.set(seenContexts); Object.assign(this.preferences, preferences);
}
if (preferences) {
Object.assign(this.preferences, preferences);
}
} }
toJSON() { toJSON() {

View File

@ -1,15 +1,50 @@
.ClustersMenu { .ClustersMenu {
@include hidden-scrollbar; @include hidden-scrollbar;
$menuBgc: #252729;
padding: $padding; padding: $padding * 1.5;
background: #252729; background: $menuBgc;
.add-cluster { .add-cluster {
cursor: pointer; position: relative;
opacity: 0.4;
&:hover { .Icon.add {
opacity: .75; border-radius: $radius;
padding: $padding / 3;
color: $menuBgc !important;
background: white !important;
font-weight: bold;
cursor: pointer;
opacity: 0.4;
&.active {
opacity: 1;
}
&:hover {
box-shadow: none;
opacity: .75;
}
}
// todo: reuse in cluster-icon.tsx
.Badge.new-contexts {
$boxSize: 17px;
$offset: -7px;
position: absolute;
font-size: $font-size-small;
right: $offset;
bottom: $offset;
line-height: $boxSize;
min-width: $boxSize;
min-height: $boxSize;
text-align: center;
color: white;
background: $colorSuccess;
font-weight: normal;
border-radius: 50%;
padding: 0;
} }
} }
} }

View File

@ -6,11 +6,16 @@ import React from "react";
import { observer } from "mobx-react"; import { observer } from "mobx-react";
import { _i18n } from "../../i18n"; import { _i18n } from "../../i18n";
import { t, Trans } from "@lingui/macro"; import { t, Trans } from "@lingui/macro";
import { ClusterId, clusterStore } from "../../../common/cluster-store"; import { userStore } from "../../../common/user-store";
import { clusterStore } from "../../../common/cluster-store";
import { WorkspaceId } from "../../../common/workspace-store"; import { WorkspaceId } from "../../../common/workspace-store";
import { ClusterIcon } from "../+cluster-settings/cluster-icon"; import { ClusterIcon } from "../+cluster-settings/cluster-icon";
import { Icon } from "../icon"; import { Icon } from "../icon";
import { cssNames, IClassName } from "../../utils"; import { cssNames, IClassName } from "../../utils";
import { Badge } from "../badge";
// fixme: allow to rearrange clusters with drag&drop
// fixme: make add-icon's tooltip visible on init
interface Props { interface Props {
className?: IClassName; className?: IClassName;
@ -28,43 +33,30 @@ export class ClustersMenu extends React.Component<Props> {
console.log('navigate: /add-cluster') console.log('navigate: /add-cluster')
} }
showContextMenu = (clusterId: ClusterId) => { showContextMenu = (cluster: Cluster) => {
const { Menu, MenuItem } = remote const { Menu, MenuItem } = remote
const menu = new Menu(); const menu = new Menu();
menu.append(new MenuItem({ menu.append(new MenuItem({
label: _i18n._(t`Settings`), label: _i18n._(t`Settings`),
click: () => { click: () => console.log(`navigate to cluster settings`, cluster)
console.log(`navigate to cluster=${clusterId} settings`) }));
} if (cluster.initialized) {
})) menu.append(new MenuItem({
// fixme: don't show item if cluster wasn't active during runtime label: _i18n._(t`Disconnect`),
menu.append(new MenuItem({ click: () => console.log(`disconnect cluster and navigate to workspaces`, cluster)
label: _i18n._(t`Disconnect`), }))
click: () => { }
console.log(`disconnect cluster=${clusterId} and navigate to landing-page`)
}
}))
menu.popup({ menu.popup({
window: remote.getCurrentWindow() window: remote.getCurrentWindow()
}) })
} }
// fixme: allow to rearrange clusters with drag&drop
render() { render() {
const { workspaceId, className } = this.props; const { workspaceId, className } = this.props;
const clusters = clusterStore.getByWorkspaceId(workspaceId); const clusters = clusterStore.getByWorkspaceId(workspaceId);
const addClusterTooltip = ( const { newContexts } = userStore;
<div className="flex column gaps">
<p><Trans>This is the quick launch menu.</Trans></p>
<p>
<Trans>
Associate clusters and choose the ones you want to access via quick launch menu by clicking the + button.
</Trans>
</p>
</div>
)
return ( return (
<div className={cssNames("ClustersMenu flex gaps column", className)}> <div className={cssNames("ClustersMenu flex gaps column", className)}>
{clusters.map(cluster => { {clusters.map(cluster => {
@ -75,18 +67,28 @@ export class ClustersMenu extends React.Component<Props> {
cluster={cluster} cluster={cluster}
className={cssNames({ active: isActive })} className={cssNames({ active: isActive })}
onClick={() => this.selectCluster(cluster)} onClick={() => this.selectCluster(cluster)}
onContextMenu={() => this.showContextMenu(cluster.id)} onContextMenu={() => this.showContextMenu(cluster)}
/> />
) )
})} })}
{/* todo: add badge for "newContexts" since last visit */} <div className="add-cluster">
{/* fixme: make tooltip visible on init + remove following to mouse pos */} <Icon
<Icon big material="add" className="add" onClick={this.addCluster}
big material="add" tooltip={(
className="add-cluster" <div className="flex column gaps">
tooltip={{ children: addClusterTooltip }} <p><Trans>This is the quick launch menu.</Trans></p>
onClick={this.addCluster} <p>
/> <Trans>
Associate clusters and choose the ones you want to access via quick launch menu by clicking the + button.
</Trans>
</p>
</div>
)}
/>
{newContexts.length > 0 && (
<Badge className="new-contexts" label={newContexts.length}/>
)}
</div>
</div> </div>
); );
} }

View File

@ -1,13 +1,14 @@
.Workspaces { .Workspaces {
display: grid; display: grid;
grid-template-areas: "draggable draggable" "menu lens-view" "bottom-bar bottom-bar"; grid-template-areas: "draggable draggable" "menu lens-view" "bottom-bar bottom-bar";
grid-template-rows: 20px 1fr min-content; grid-template-rows: auto 1fr min-content;
grid-template-columns: min-content 1fr; grid-template-columns: min-content 1fr;
height: 100%; height: 100%;
.draggable-top { .draggable-top {
@include set-draggable; @include set-draggable;
grid-area: draggable; grid-area: draggable;
height: 25px;
} }
#lens-view { #lens-view {

View File

@ -33,18 +33,13 @@
height: var(--big-size); height: var(--big-size);
} }
> span {
width: 100%;
height: 100%;
}
// material-icon // material-icon
&.material { &.material {
> span { > .icon {
font-family: "Material Icons"; font-family: "Material Icons";
font-size: inherit; font-size: inherit;
font-weight: normal; font-weight: inherit;
font-style: normal; font-style: inherit;
display: inline-block; display: inline-block;
line-height: 1; line-height: 1;
text-transform: none; text-transform: none;
@ -68,6 +63,11 @@
&.svg { &.svg {
box-sizing: content-box; box-sizing: content-box;
> .icon {
width: 100%;
height: 100%;
}
svg { svg {
pointer-events: none; pointer-events: none;
width: 100%; width: 100%;

View File

@ -87,12 +87,12 @@ export class Icon extends React.PureComponent<IconProps> {
// render as inline svg-icon // render as inline svg-icon
if (svg) { if (svg) {
const svgIconText = require("!!raw-loader!./" + svg + ".svg").default; const svgIconText = require("!!raw-loader!./" + svg + ".svg").default;
iconContent = <span dangerouslySetInnerHTML={{ __html: svgIconText }}/>; iconContent = <span className="icon" dangerouslySetInnerHTML={{ __html: svgIconText }}/>;
} }
// render as material-icon // render as material-icon
if (material) { if (material) {
iconContent = <span className="material-icons">{material}</span>; iconContent = <span className="icon">{material}</span>;
} }
// wrap icon's content passed from decorator // wrap icon's content passed from decorator