Files
weave-scope/client/app/styles/_base.scss
Roland Schilter 8188b7aed2 Append links directly to metrics
The initial idea was to keep it separate since the unattached
links were also to be displayed distinctively from the metrics.
With the new design, unattached links are rendered in the same
list as metrics with attached links.

Therefore, we treat unattached metric links as an empty metric.
2017-08-11 16:45:13 +01:00

2183 lines
38 KiB
SCSS

@import '~xterm/dist/xterm.css';
@import '~font-awesome/scss/font-awesome.scss';
@import '~rc-slider/dist/rc-slider.css';
@font-face {
font-family: "Roboto";
src: url("../../node_modules/materialize-css/fonts/roboto/Roboto-Regular.woff2"),
url("../../node_modules/materialize-css/fonts/roboto/Roboto-Regular.woff"),
url("../../node_modules/materialize-css/fonts/roboto/Roboto-Regular.ttf");
}
// TODO: Remove this line once Service UI CONFIGURE button stops being added to Scope.
.scope-wrapper .setup-nav-button { display: none; }
a {
text-decoration: none;
}
.browsehappy {
margin: 0.2em 0;
background: #ccc;
color: #000;
padding: 0.2em 0;
}
/* add this class to truncate text with ellipsis, container needs width */
.truncate {
white-space: nowrap;
overflow: hidden;
text-overflow: ellipsis;
}
.colorable {
transition: background-color .3s $base-ease;
}
.palable {
transition: all .2s $base-ease;
}
.hideable {
transition: opacity .5s $base-ease;
}
.blinkable {
animation: blinking 1.5s infinite $base-ease;
}
.hang-around {
transition-delay: .5s;
}
// From https://stackoverflow.com/a/18294634
.grabbable {
cursor: move; /* fallback if grab cursor is unsupported */
cursor: grab;
cursor: -moz-grab;
cursor: -webkit-grab;
}
.grabbing {
cursor: grabbing;
cursor: -moz-grabbing;
cursor: -webkit-grabbing;
}
.shadow-2 {
box-shadow: 0 3px 10px rgba(0, 0, 0, 0.16), 0 3px 10px rgba(0, 0, 0, 0.23);
}
.shadow-3 {
box-shadow: 0 10px 30px rgba(0, 0, 0, 0.19), 0 6px 10px rgba(0, 0, 0, 0.23);
}
.overlay {
@extend .hideable;
background-color: white;
position: absolute;
width: 100%;
height: 100%;
top: 0;
left: 0;
opacity: 0;
pointer-events: none;
z-index: 2000;
&.faded {
// NOTE: Not sure if we should block the pointer events here..
pointer-events: all;
cursor: wait;
opacity: 0.5;
}
}
.overlay-wrapper {
align-items: center;
background-color: fade-out($background-average-color, 0.1);
border-radius: 4px;
color: $text-tertiary-color;
display: flex;
font-size: 0.7rem;
justify-content: center;
padding: 5px;
position: absolute;
bottom: 11px;
a {
@extend .btn-opacity;
border: 1px solid transparent;
border-radius: 4px;
color: $text-secondary-color;
cursor: pointer;
padding: 1px 3px;
.fa {
font-size: 150%;
position: relative;
top: 2px;
}
&:hover, &.selected {
border: 1px solid $text-tertiary-color;
}
&.active {
& > * { @extend .blinkable; }
border: 1px solid $text-tertiary-color;
}
}
}
.btn-opacity {
@extend .palable;
opacity: $btn-opacity-default;
&-selected {
opacity: $btn-opacity-selected;
}
&[disabled] {
cursor: default;
opacity: $btn-opacity-disabled;
}
&:not([disabled]):hover {
opacity: $btn-opacity-hover;
}
}
.hide {
opacity: 0;
}
.scope-app, .terminal-app {
-webkit-font-smoothing: antialiased;
background: $body-background-color;
bottom: 0;
color: $text-color;
font-family: $base-font;
font-size: 13px;
height: auto;
left: 0;
line-height: 150%;
margin: 0;
overflow: auto;
position: fixed;
right: 0;
top: 0;
width: 100%;
* {
box-sizing: border-box;
-webkit-tap-highlight-color: rgba(0, 0, 0, 0);
}
*:before,
*:after {
box-sizing: border-box;
}
p {
line-height: 20px;
padding-top: 6px;
margin-bottom: 14px;
letter-spacing: 0;
font-weight: 400;
color: $text-color;
}
h2 {
font-size: 34px;
line-height: 40px;
padding-top: 8px;
margin-bottom: 12px;
font-weight: 400;
}
&.time-travel-open {
.details-wrapper {
margin-top: $timeline-height + 15px;
}
}
}
.header {
padding: 15px 10px 0;
pointer-events: none;
width: 100%;
.selectors {
display: flex;
position: relative;
> * { z-index: 20; }
.time-control { z-index: 2001; }
.logo {
margin: -16px 0 0 64px;
height: 64px;
width: 250px;
}
}
}
.rc-slider {
.rc-slider-step { cursor: pointer; }
.rc-slider-track { background-color: $text-tertiary-color; }
.rc-slider-rail { background-color: $border-light-color; }
.rc-slider-handle { border-color: $text-tertiary-color; }
}
.footer {
@extend .overlay-wrapper;
right: 43px;
&-status {
margin-right: 1em;
}
&-label, .pause-text {
text-transform: uppercase;
margin: 0 0.25em;
}
&-versionupdate {
margin-right: 0.5em;
text-transform: uppercase;
}
&-tools {
display: flex;
}
&-icon {
margin-left: 0.5em;
}
.tooltip {
// above everything
z-index: 20000;
}
}
.time-travel {
position: relative;
margin-bottom: 15px;
z-index: 2001;
transition: all .15s $base-ease;
overflow: hidden;
height: 0;
&.visible {
height: $timeline-height + 35px;
margin-bottom: 15px;
margin-top: -5px;
}
.button {
padding: 2px;
pointer-events: all;
}
.time-travel-timeline {
align-items: center;
display: flex;
height: $timeline-height;
svg {
@extend .grabbable;
background-color: rgba(255, 255, 255, 0.85);
box-shadow: inset 0 0 7px #aaa;
pointer-events: all;
margin: 0 7px;
width: 100%;
height: 100%;
&.panning { @extend .grabbing; }
.available-range {
fill: #888;
fill-opacity: 0.1;
}
.timestamp-label {
margin-left: 2px;
padding: 3px;
&[disabled] {
color: #aaa;
cursor: inherit;
}
}
}
&:before, &:after {
content: '';
position: absolute;
display: block;
left: 50%;
border: 1px solid white;
border-top: 0;
border-bottom: 0;
background-color: red;
margin-left: -1px;
width: 3px;
}
&:before {
top: 0;
height: $timeline-height;
}
&:after {
top: $timeline-height;
height: 9px;
opacity: 0.15;
}
}
&-timestamp {
background-color: $background-lighter-color;
border: 1px solid #ccc;
border-radius: 4px;
padding: 2px 8px;
pointer-events: all;
margin: 8px 0 25px 50%;
transform: translateX(-50%);
opacity: 0.8;
display: inline-block;
input {
border: 0;
background-color: transparent;
font-size: 1rem;
width: 165px;
font-family: "Roboto", sans-serif;
text-align: center;
outline: 0;
}
}
}
.topologies {
margin: 0 4px;
display: flex;
.topologies-item {
margin: 0px 8px;
&-label {
font-size: .8rem;
text-transform: uppercase;
}
}
.topologies-sub {
&-item {
&-label {
font-size: .7rem;
text-transform: uppercase;
}
}
}
.topologies-item-main,
.topologies-sub-item {
// border: 1px solid $background-darker-secondary-color;
pointer-events: all;
color: $text-secondary-color;
@extend .btn-opacity;
cursor: pointer;
padding: 4px 8px;
border-radius: $border-radius;
opacity: 0.9;
margin-bottom: 3px;
border: 1px solid transparent;
white-space: nowrap;
&-active, &:hover {
color: $text-color;
background-color: $background-darker-secondary-color;
}
&-active {
opacity: 0.85;
}
&-matched {
border-color: $weave-blue;
}
}
.topologies-sub-item {
padding: 2px 8px;
}
}
.nodes-chart-overlay {
pointer-events: none;
opacity: 0;
&.active {
opacity: $node-elements-in-background-opacity;
}
}
.nodes-chart, .nodes-resources {
&-error, &-loading {
@extend .hideable;
pointer-events: none;
position: absolute;
left: 50%;
top: 50%;
margin-left: -16.5%;
margin-top: -275px;
color: $text-secondary-color;
width: 33%;
height: 550px;
.heading {
font-size: 125%;
}
&-icon {
text-align: center;
opacity: 0.25;
font-size: 320px;
}
li { padding-top: 5px; }
}
// Make watermarks blink only if actually shown (otherwise the FF performance decreses weirdly).
&-loading:not(.hide) &-error-icon-container {
@extend .blinkable;
}
&-loading {
text-align: center;
}
svg {
@extend .hideable;
position: absolute;
top: 0px;
}
.logo {
display: none;
}
svg.exported {
.logo {
display: inline;
}
}
text {
font-family: $base-font;
fill: $text-secondary-color;
}
.nodes-chart-elements .node {
text-align: center;
.node-label {
color: $text-color;
}
.node-label-minor {
line-height: 125%;
}
.node-labels-container {
transform: scale($node-text-scale);
pointer-events: none;
}
.node-label-wrapper {
//
// Base line height doesn't hop across foreignObject =/
//
line-height: 150%;
//
// inline-block so wrapper is only as wide as content.
//
display: inline-block;
//
// - inline-block gets a different baseline depending on overflow value
// - this element gets its overflow value changed sometimes.
// - explicitly set the baseline so the text doesn't jump up and down.
// http://stackoverflow.com/questions/9273016
//
vertical-align: top;
cursor: pointer;
pointer-events: all;
font-size: 12px;
width: 100%;
}
.node-label-minor {
color: $text-secondary-color;
font-size: 0.85em;
}
.node-label, .node-label-minor {
span {
border-radius: 2px;
}
span:not(.match) {
padding: 0 0.25em;
background-color: $label-background-color;
}
span:empty {
padding: 0;
}
}
.matched-results {
background-color: $label-background-color;
}
&.pseudo {
cursor: default;
.node-label {
fill: $text-secondary-color;
}
.node-label-minor {
fill: $text-tertiary-color;
}
.node {
opacity: $node-pseudo-opacity;
}
.border {
opacity: $node-pseudo-opacity;
stroke: $text-tertiary-color;
}
}
.node-label, .node-label-minor {
text-align: center;
}
.match {
background-color: lighten(rgba(0, 210, 255, 0.5), 30%);
border: 1px solid $weave-blue;
}
}
.edge {
.link {
fill: none;
stroke: $edge-color;
}
.shadow {
fill: none;
stroke: $weave-blue;
stroke-opacity: 0;
}
&.highlighted {
.shadow {
stroke-opacity: $edge-highlight-opacity;
}
}
}
.stack .highlight-only {
.background { display: none; }
.shadow { display: none; }
.border { display: none; }
.node { display: none; }
}
.stack .shape .metric-fill {
display: none;
}
.shape {
transform: scale(1);
cursor: pointer;
.highlight-border {
fill: none;
stroke: $weave-blue;
stroke-width: 0.7 + $node-highlight-stroke-width * 2;
stroke-opacity: $node-highlight-stroke-opacity;
}
.highlight-shadow {
fill: none;
stroke: white;
stroke-width: 0.7;
stroke-opacity: $node-highlight-shadow-opacity;
}
.background {
stroke: none;
fill: $background-lighter-color;
}
.metric-fill {
stroke: none;
fill: #A0BE7E;
fill-opacity: 0.7;
}
.border {
fill: none;
stroke-opacity: 1;
stroke-width: $node-border-stroke-width;
}
&.metrics .border {
stroke-opacity: 0.3;
}
.shadow {
fill: none;
stroke: $background-color;
stroke-width: $node-shadow-stroke-width;
}
.node {
fill: $text-color;
stroke: $background-lighter-color;
stroke-width: 0.05;
}
text {
transform: scale($node-text-scale);
font-size: 10px;
dominant-baseline: middle;
text-anchor: middle;
}
}
.stack .shape .border {
stroke-width: $node-border-stroke-width * 0.8;
}
.edge-marker {
color: $edge-color;
fill: $edge-color;
}
}
.matched-results {
text-align: center;
&-match {
font-size: 0.8em;
&-wrapper {
display: inline-block;
margin: 1px;
padding: 2px 4px;
background-color: fade-out($weave-blue, .9);
}
&-label {
color: $text-secondary-color;
margin-right: 0.5em;
}
}
&-more {
text-transform: uppercase;
font-size: 0.7em;
color: darken($weave-blue, 10%);
margin-top: -2px;
}
}
.details {
&-wrapper {
position: fixed;
display: flex;
z-index: 1024;
right: $details-window-padding-left;
top: 100px;
bottom: 48px;
transition: transform 0.33333s cubic-bezier(0,0,0.21,1), margin-top .15s $base-ease;
}
}
.node-details {
height: 100%;
width: $details-window-width;
background-color: rgba(255, 255, 255, 0.86);
display: flex;
flex-flow: column;
margin-bottom: 12px;
padding-bottom: 2px;
border-radius: 2px;
background-color: #fff;
@extend .shadow-2;
// keep node-details above the terminal.
z-index: 2;
&:last-child {
margin-bottom: 0;
}
&-tools-wrapper {
position: relative;
}
&-tools {
position: absolute;
top: 6px;
right: 8px;
> span {
@extend .btn-opacity;
padding: 4px 5px;
margin-left: 2px;
font-size: 110%;
color: $white;
cursor: pointer;
border: 1px solid rgba(255, 255, 255, 0);
border-radius: 4px;
span {
font-family: $base-font;
font-size: 0.9em;
margin-left: 4px;
span {
font-size: 1em;
margin-left: 0;
text-transform: uppercase;
}
}
&:hover {
border-color: rgba(255, 255, 255, 0.6);
}
}
}
.match {
background-color: fade-out($weave-blue, .7);
border: 1px solid $weave-blue;
}
&-header {
@extend .colorable;
&-wrapper {
padding: 36px 36px 8px 36px;
}
&-label {
color: white;
margin: 0;
width: 348px;
padding-top: 0;
}
.details-tools {
position: absolute;
top: 16px;
right: 24px;
}
&-notavailable {
background-color: $background-dark-color;
}
}
&-relatives {
margin-top: 4px;
font-size: 120%;
color: $white;
&-link {
@extend .truncate;
@extend .btn-opacity;
display: inline-block;
margin-right: 0.5em;
cursor: pointer;
text-decoration: underline;
opacity: $link-opacity-default;
max-width: 12em;
}
&-more {
@extend .btn-opacity;
padding: 0 2px;
text-transform: uppercase;
cursor: pointer;
font-size: 60%;
font-weight: bold;
display: inline-block;
position: relative;
top: -5px;
}
}
&-controls {
white-space: nowrap;
padding: 8px 0;
&-wrapper {
padding: 0 36px 0 32px;
}
.node-control-button {
color: $white;
}
&-spinner {
@extend .hideable;
color: $white;
margin-left: 8px;
}
&-error {
@extend .truncate;
float: right;
width: 55%;
padding-top: 6px;
text-align: left;
color: $white;
&-icon {
@extend .blinkable;
margin-right: 0.5em;
}
}
}
&-content {
flex: 1;
padding: 0 36px 0 36px;
overflow-y: auto;
&-loading {
margin-top: 48px;
text-align: center;
font-size: 48px;
color: $text-tertiary-color;
}
&-section {
margin: 16px 0;
&-header {
text-transform: uppercase;
font-size: 90%;
color: $text-tertiary-color;
padding: 4px 0;
}
}
}
&-health {
&-wrapper {
display: flex;
justify-content: space-around;
align-content: center;
text-align: center;
flex-wrap: wrap;
}
&-overflow {
@extend .btn-opacity;
flex-basis: 33%;
display: flex;
flex-direction: row;
flex-wrap: wrap;
align-items: center;
opacity: 0.85;
cursor: pointer;
position: relative;
padding-bottom: 16px;
&-item {
padding: 4px 8px;
line-height: 1.2;
flex-basis: 48%;
&-value {
color: $text-secondary-color;
font-size: 100%;
}
&-label {
color: $text-secondary-color;
text-transform: uppercase;
font-size: 60%;
}
}
}
&-item {
padding: 8px 16px;
width: 33%;
display: flex;
flex-direction: column;
flex-grow: 1;
&-label {
color: $text-secondary-color;
text-transform: uppercase;
font-size: 80%;
.fa {
margin-left: 0.5em;
}
}
&-sparkline {
margin-top: auto;
}
&-placeholder {
font-size: 200%;
opacity: 0.2;
margin-bottom: 0.2em;
}
}
&-link-item {
@extend .palable;
cursor: pointer;
opacity: $link-opacity-default;
width: 33%;
display: flex;
color: inherit;
.label {
text-transform: uppercase;
}
.node-details-health-item {
width: auto;
}
}
}
&-info {
&-field {
display: flex;
align-items: baseline;
&-label {
text-align: right;
width: 30%;
color: $text-secondary-color;
padding: 0 0.5em 0 0;
white-space: nowrap;
text-transform: uppercase;
font-size: 80%;
&::after {
content: ':';
}
}
&-value {
font-size: 105%;
flex: 1;
// Now required (from chrome 48) to get overflow + flexbox behaving:
min-width: 0;
color: $text-color;
}
}
}
&-property-list {
&-controls {
margin-left: -4px;
}
&-field {
display: flex;
align-items: baseline;
&-label {
text-align: right;
width: 50%;
color: $text-secondary-color;
padding: 0 0.5em 0 0;
white-space: nowrap;
text-transform: uppercase;
font-size: 80%;
&::after {
content: ':';
}
}
&-value {
font-size: 105%;
flex: 1;
// Now required (from chrome 48) to get overflow + flexbox behaving:
min-width: 0;
color: $text-color;
}
}
}
&-generic-table {
width: 100%;
tr {
display: flex;
th, td {
padding: 0 5px;
}
}
}
&-table {
width: 100%;
border-spacing: 0;
/* need fixed for truncating, but that does not extend wide columns dynamically */
table-layout: fixed;
&-wrapper {
margin: 24px -4px;
}
&-header {
text-transform: uppercase;
color: $text-tertiary-color;
font-size: 90%;
text-align: right;
cursor: pointer;
padding: 0 4px;
&-sorted {
color: $text-secondary-color;
}
&-sorter {
margin: 0 0.25em;
}
&:first-child {
margin-right: 0;
text-align: left;
}
}
tbody {
position: relative;
.min-height-constraint {
position: absolute;
width: 0 !important;
opacity: 0;
top: 0;
}
}
&-node {
font-size: 105%;
line-height: 1.5;
&:hover, &.selected {
background-color: lighten($background-color, 5%);
}
> * {
padding: 0 4px;
}
&-link {
@extend .btn-opacity;
text-decoration: underline;
cursor: pointer;
opacity: $link-opacity-default;
}
&-value, &-metric {
flex: 1;
margin-left: 0.5em;
text-align: right;
}
&-metric-link {
@extend .btn-opacity;
text-decoration: underline;
cursor: pointer;
opacity: $link-opacity-default;
color: $text-color;
}
&-value-scalar {
// width: 2em;
text-align: right;
margin-right: 0.5em;
}
&-value-minor,
&-value-unit {
font-size: 95%;
color: $text-secondary-color;
}
&-value-sparkline {
> div {
display: inline-block;
}
span {
margin-left: 1em;
}
}
}
}
.image-status {
.progress-wrapper {
position: relative;
min-height: 35px;
}
.node-details-content-section-header {
display: flex;
justify-content: space-between;
line-height: 26px;
}
.images .wrapper{
display: flex;
justify-content: space-between;
}
.weave-circular-progress-wrapper {
position: absolute;
left: 50%;
}
.new-image {
color: $success-green;
}
a {
&:hover {
background-color: #f1f1f6;
cursor: pointer;
}
}
.node-details-table-node-link,
.node-details-table-node-label,
.node-details-table-node-value {
flex: 1;
font-size: 14px;
color: $text-color;
line-height: 24px;
text-transform: none;
}
}
}
.node-resources {
&-metric-box {
@extend .palable;
cursor: pointer;
fill: rgba(150, 150, 150, 0.4);
&-info {
background-color: rgba(white, 0.6);
border-radius: 2px;
cursor: inherit;
padding: 5px;
.wrapper {
display: block;
&.label { font-size: 15px; }
&.consumption { font-size: 12px; }
}
}
}
&-layer-topology {
background-color: rgba(#eee, 0.95);
border: 1px solid #ccc;
color: $text-tertiary-color;
font-size: 16px;
font-weight: bold;
padding-right: 20px;
text-align: right;
text-transform: uppercase;
}
}
// This part sets the styles only for the 'real' node details table, not applying
// them to the nodes grid, because there we control hovering from the JS.
// NOTE: Maybe it would be nice to separate the class names between the two places
// where node tables are used - i.e. it doesn't make sense that node-details-table
// can also refer to the tables in the nodes grid.
.details-wrapper .node-details-table {
&-node {
&:hover, &.selected {
background-color: lighten($background-color, 5%);
}
}
}
.node-control-button {
@extend .btn-opacity;
padding: 6px;
margin-left: 2px;
font-size: 110%;
color: $text-secondary-color;
cursor: pointer;
border: 1px solid rgba(255, 255, 255, 0);
border-radius: 10%;
&:hover {
border-color: rgba(255, 255, 255, 0.6);
}
&-pending, &-pending:hover {
opacity: 0.2;
border-color: rgba(255, 255, 255, 0);
cursor: not-allowed;
}
}
.terminal {
&-app {
display: flex;
flex-flow: column;
}
&-embedded {
position: relative;
// shadow of animation-wrapper is 10px, let it fit in here without being
// overflow hiddened.
flex: 1;
overflow-x: hidden;
}
&-animation-wrapper {
position: absolute;
// some room for the drop shadow.
top: 10px;
left: 10px;
bottom: 10px;
right: 0;
transition: transform 0.5s cubic-bezier(0.230, 1.000, 0.320, 1.000);
@extend .shadow-2;
}
&-wrapper {
width: 100%;
height: 100%;
border: 0px solid #000000;
color: #f0f0f0;
}
&-header {
@extend .truncate;
color: $white;
height: $terminal-header-height;
padding: 8px 24px;
background-color: $text-color;
position: relative;
font-size: 14px;
line-height: 28px;
border-radius: 4px 0 0 0;
&-title {
cursor: default;
}
&-tools {
position: absolute;
right: 8px;
top: 6px;
&-item, &-item-icon {
@extend .palable;
padding: 4px 5px;
color: $white;
cursor: pointer;
opacity: 0.7;
border: 1px solid rgba(255, 255, 255, 0);
border-radius: 10%;
font-size: 0.8em;
font-weight: bold;
text-transform: uppercase;
&:hover {
opacity: 1;
border-color: rgba(255, 255, 255, 0.6);
}
}
&-item-icon {
font-size: 1em;
}
}
}
&-embedded &-inner { top: $terminal-header-height; }
&-app &-inner { top: 0; }
&-inner {
cursor: text;
font-family: $mono-font;
position: absolute;
bottom: 0;
left: 0;
right: 0;
background-color: black;
padding: 8px;
border-radius: 0 0 0 4px;
.terminal {
background-color: transparent !important;
}
}
&-status-bar {
font-family: $base-font;
position: absolute;
bottom: 16px;
right: 16px;
width: 50%;
padding: 16px 16px;
opacity: 0.8;
border-radius: 4px;
h3 {
margin: 4px 0;
}
&-message {
margin: 4px 0;
color: $white;
}
.link {
text-transform: uppercase;
font-weight: bold;
cursor: pointer;
float: right;
}
}
&-cursor {
color: #000;
background: #f0f0f0;
}
}
.terminal-inactive .terminal-cursor {
visibility: hidden;
}
.metric {
&-unit {
padding-left: 0.25em;
}
}
.show-more {
@extend .btn-opacity;
border-top: 1px dotted $border-light-color;
padding: 0px 0;
margin-top: 4px;
text-align: right;
text-transform: uppercase;
cursor: pointer;
color: $text-secondary-color;
font-size: 90%;
&-icon {
color: $text-tertiary-color;
font-size: 120%;
position: relative;
top: 1px;
}
}
.plugins {
margin-right: 0.5em;
&-label {
text-transform: uppercase;
margin-right: 0.25em;
}
&-plugin {
cursor: default;
}
&-plugin + &-plugin:before {
content: ', ';
}
&-plugin-icon {
top: 1px;
position: relative;
font-size: 120%;
margin-right: 2px;
}
.error {
animation: blinking 2.0s 60 $base-ease; // blink for 2 minutes
color: $text-secondary-color;
}
&-empty {
opacity: $text-secondary-color;
}
}
.status {
text-transform: uppercase;
padding: 2px 12px;
border-radius: $border-radius;
color: $text-secondary-color;
display: inline-block;
&-icon {
font-size: 1rem;
position: relative;
top: 0.125rem;
margin-right: 0.25rem;
}
&.status-loading {
animation: blinking 2.0s 150 $base-ease; // keep blinking for 5 minutes
text-transform: none;
color: $text-color;
}
}
.topology-option, .metric-selector, .network-selector, .view-mode-selector, .time-control {
color: $text-secondary-color;
margin-bottom: 6px;
&:last-child {
margin-bottom: 0;
}
.fa {
margin-left: 4px;
color: darkred;
}
&-wrapper {
pointer-events: all;
border-radius: $border-radius;
border: 1px solid $background-darker-color;
display: inline-block;
white-space: nowrap;
}
&-action {
@extend .btn-opacity;
padding: 3px 12px;
cursor: pointer;
display: inline-block;
background-color: $background-color;
&-selected, &:not([disabled]):hover {
color: $text-darker-color;
background-color: $background-darker-color;
}
&:first-child {
border-left: none;
border-top-left-radius: $border-radius;
border-bottom-left-radius: $border-radius;
}
&:last-child {
border-top-right-radius: $border-radius;
border-bottom-right-radius: $border-radius;
}
}
}
.metric-selector {
margin-top: 6px;
}
.view-mode-selector, .time-control {
margin-left: 20px;
min-width: 161px;
&-wrapper {
pointer-events: all;
border-color: $background-darker-secondary-color;
overflow: hidden;
}
&:first-child,
&:last-child {
.view-mode-selector-action {
border-radius: 0;
}
}
&-action {
background-color: transparent;
text-transform: uppercase;
&-selected, &:not([disabled]):hover {
background-color: $background-darker-secondary-color;
}
&:not(:last-child) {
border-right: 1px solid $background-darker-secondary-color;
}
}
}
.time-control {
position: absolute;
right: 20px;
&-controls {
align-items: center;
justify-content: flex-end;
display: flex;
}
&-spinner {
display: inline-block;
margin-right: 15px;
margin-top: 3px;
.fa {
color: $text-secondary-color;
font-size: 125%;
}
}
&-info {
@extend .blinkable;
display: block;
margin-top: 5px;
text-align: right;
pointer-events: all;
}
}
.topology-option {
&-action {
&-selected {
cursor: default;
}
}
}
.view-mode-selector-wrapper, .time-control-wrapper {
.label { margin-left: 4px; }
.fa {
margin-left: 0;
color: $text-secondary-color;
}
}
.network-selector-action {
border-top: 3px solid transparent;
border-bottom: 3px solid $background-dark-color;
}
.warning {
display: inline-block;
cursor: pointer;
border: 1px dashed transparent;
text-transform: none;
border-radius: $border-radius;
margin-left: 4px;
&-wrapper {
display: flex;
}
&-text {
display: inline-block;
color: $text-secondary-color;
padding-left: 0.5em;
}
&-icon {
@extend .btn-opacity;
}
&-expanded {
margin-left: 0;
padding: 2px 4px;
border-color: $text-tertiary-color;
}
&-expanded &-icon {
position: relative;
top: 4px;
left: 2px;
}
}
.sidebar {
position: fixed;
bottom: 11px;
left: 11px;
padding: 5px;
font-size: .7rem;
border-radius: 8px;
border: 1px solid transparent;
pointer-events: none;
}
.sidebar-gridmode {
background-color: #e9e9f1;
border-color: $background-darker-color;
opacity: 0.9;
}
.search {
pointer-events: all;
display: inline-block;
position: relative;
width: 10em;
transition: width 0.3s 0s $base-ease;
&-wrapper {
flex: 0 1 20%;
margin: 0 8px;
text-align: right;
}
&-disabled {
opacity: 0.5;
cursor: disabled;
}
&-hint {
font-size: 0.7rem;
position: absolute;
padding: 0 1em;
color: $text-tertiary-color;
top: 0;
opacity: 0;
transition: transform 0.3s 0s $base-ease, opacity 0.3s 0s $base-ease;
text-align: left;
}
&-help-link {
@extend .btn-opacity;
cursor: pointer;
font-size: 150%;
}
&-label {
position: absolute;
pointer-events: none;
user-select: none;
top: 0;
left: 4px;
z-index: 1024;
padding: 4px;
color: $text-secondary-color;
&-icon {
margin-right: 0.5em;
}
&-hint {
font-size: 0.8rem;
text-transform: uppercase;
transition: opacity 0.3s 0.5s $base-ease;
opacity: 1;
}
}
&-input {
overflow: hidden;
background: #fff;
position: relative;
z-index: 1;
display: flex;
border-radius: $border-radius;
width: 100%;
border: $search-border-width solid $search-border-color;
padding: 2px 4px;
text-align: left;
flex-wrap: wrap;
&-field {
font-size: 0.8rem;
line-height: 150%;
position: relative;
padding: 1px 4px 1px 1.5em;
border: none;
border-radius: 0;
background: transparent;
color: $text-color;
width: 100px;
&:focus {
outline: none;
}
}
}
&-focused &-label-hint,
&-pinned &-label-hint,
&-filled &-label-hint {
transition: opacity 0.1s 0s $base-ease;
opacity: 0;
}
&-focused &-hint,
&-filled &-hint,
&-pinned &-hint {
opacity: 1;
transform: translate3d(0, 2.75em, 0);
transition: transform 0.3s 0.3s $base-ease, opacity 0.3s 0.3s $base-ease;
}
&-focused &-input-field,
&-filled &-input-field,
&-pinned &-input-field {
flex: 1;
}
&-focused,
&-filled,
&-pinned {
width: 100%;
}
&-matched &-input {
border-color: $weave-blue;
}
}
.search-item {
background-color: fade-out($weave-blue, .2);
border-radius: $border-radius / 2;
margin: 1px 0 1px 1.5em;
display: inline-block;
& + .search-item {
margin-left: 4px;
}
& + .search-input-field {
padding-left: 4px;
}
&-label {
padding: 2px 4px;
}
&-icon {
@extend .btn-opacity;
padding: 2px 4px 2px 2px;
cursor: pointer;
font-size: 80%;
position: relative;
top: -1px;
}
}
@keyframes blinking {
0%, 50%, 100% {
opacity: 1.0;
} 25% {
opacity: 0.5;
}
}
//
// Help panel!
//
.help-panel {
z-index: 2048;
background-color: white;
@extend .shadow-2;
display: flex;
position: relative;
&-wrapper {
position: absolute;
width: 100%;
height: 100%;
display: flex;
justify-content: center;
align-items: flex-start;
}
&-header {
background-color: $weave-blue;
padding: 12px 24px;
color: white;
h2 {
margin: 0;
text-transform: uppercase;
font-size: 125%;
}
}
&-tools {
position: absolute;
top: 6px;
right: 8px;
span {
@extend .btn-opacity;
padding: 4px 5px;
margin-left: 2px;
font-size: 110%;
color: #8383ac;
cursor: pointer;
border: 1px solid rgba(131, 131, 172, 0);
border-radius: 10%;
&:hover {
border-color: rgba(131, 131, 172, 0.6);
}
}
}
&-main {
display: flex;
padding: 12px 36px 36px 36px;
flex-direction: row;
align-items: stretch;
h2 {
text-transform: uppercase;
line-height: 150%;
font-size: 125%;
color: #8383ac;
padding: 4px 0;
border-bottom: 1px solid rgba(131, 131, 172, 0.1);
}
h3 {
text-transform: uppercase;
font-size: 90%;
color: #8383ac;
padding: 4px 0;
}
p {
margin: 0;
}
}
&-shortcuts {
margin-right: 36px;
&-shortcut {
kbd {
display: inline-block;
padding: 3px 5px;
font-size: 11px;
line-height: 10px;
color: #555;
vertical-align: middle;
background-color: #fcfcfc;
border: solid 1px #ccc;
border-bottom-color: #bbb;
border-radius: 3px;
box-shadow: inset 0 -1px 0 #bbb;
}
div.key {
width: 60px;
display: inline-block;
}
div.label {
display: inline-block;
}
}
}
&-search {
margin-right: 36px;
&-row {
display: flex;
flex-direction: row;
&-term {
flex: 1;
color: $text-secondary-color;
}
&-term-label {
flex: 1;
b {
color: $text-secondary-color;
}
}
}
}
&-fields {
display: flex;
flex-direction: column;
&-current-topology {
text-transform: uppercase;
color: #8383ac;
}
&-fields {
display: flex;
align-items: stretch;
&-column {
display: flex;
flex-direction: column;
flex: 1;
margin-right: 12px;
&-content {
overflow: auto;
// 160px for top and bottom margins and the rest of the help window
// is about 160px too.
// Notes: Firefox gets a bit messy if you try and bubble
// heights + overflow up (min-height issue + still doesn't work v.well),
// so this is a bit of a hack.
max-height: calc(100vh - 160px - 160px - 160px);
}
}
}
}
}
//
// Zoom control
//
.zoom-control {
@extend .overlay-wrapper;
flex-direction: column;
padding: 5px 7px 0;
bottom: 50px;
right: 40px;
a:hover { border-color: transparent; }
.rc-slider {
margin: 5px 0;
height: 60px;
}
}
//
// Debug panel!
//
.debug-panel {
@extend .shadow-2;
background-color: #fff;
top: 80px;
position: absolute;
padding: 10px;
left: 10px;
z-index: 10000;
opacity: 0.3;
&:hover {
opacity: 1;
}
table {
display: inline-block;
border-collapse: collapse;
margin: 4px 2px;
td {
width: 10px;
height: 10px;
}
}
}
//
// Nodes grid.
//
.nodes-grid {
// TODO: Would be good to have relative positioning here.
position: absolute;
top: 0;
tr {
border-radius: 6px;
}
&-label-minor {
opacity: 0.7;
}
&-id-column {
margin: -3px -4px;
padding: 2px 4px;
display: flex;
div {
flex: 1;
}
}
.node-details-table-wrapper-wrapper {
flex: 1;
display: flex;
flex-direction: row;
width: 100%;
.node-details-table-wrapper {
margin: 0;
flex: 1;
}
.nodes-grid-graph {
position: relative;
margin-top: 24px;
}
.node-details-table-node > * {
padding: 3px 4px;
}
// Keeping the row height fixed is important for locking the rows on hover.
.node-details-table-node, thead tr {
height: 28px;
}
tr:nth-child(even) {
background: $background-color;
}
tbody tr {
border: 1px solid transparent;
border-radius: 4px;
cursor: pointer;
}
// We fully control hovering of the grid rows from JS,
// because we want consistent behaviour between the
// visual and row locking logic that happens on hover.
tbody tr.selected, tbody tr.focused {
background-color: #d7ecf5;
border: 1px solid $weave-blue;
}
tbody tr.selected {
// box-shadow: 0 4px 2px -2px rgba(0, 0, 0, 0.16);
}
}
.scroll-body {
table {
border-bottom: 1px solid #ccc;
}
thead {
// osx scrollbar width: 0
// linux scrollbar width: 16
// avg scrollbar width: 8
padding-right: 8px;
}
thead, tbody tr {
display: table;
width: 100%;
table-layout: fixed;
}
tbody:after {
content: '';
display: block;
// height of the controls so you can scroll the last row up above them
// and have a good look.
height: 140px;
}
thead {
box-shadow: 0 4px 2px -2px rgba(0, 0, 0, 0.16);
border-bottom: 1px solid #aaa;
}
tbody {
display: block;
overflow-y: scroll;
}
}
}
.troubleshooting-menu {
display: flex;
position: relative;
&-wrapper {
height: 100%;
width: 100%;
align-items: center;
display: flex;
justify-content: center;
position: absolute;
}
&-content {
position: relative;
background-color: $white;
padding: 20px;
@extend .shadow-2;
z-index: 2048;
}
&-item {
height: 40px;
}
.fa {
width: 20px;
text-align: center;
margin-right: 10px;
}
.fa-close {
width: 25px;
}
}
@media (max-width: 1330px) {
.view-mode-selector .label { display: none; }
}