mirror of https://github.com/portainer/portainer
feat(app): add tooltip component [EE-2047] (#6088)
parent
41993ad378
commit
1a6af5d58f
|
@ -129,25 +129,6 @@ a[ng-click] {
|
||||||
background-color: var(--bg-service-datatable-tbody);
|
background-color: var(--bg-service-datatable-tbody);
|
||||||
}
|
}
|
||||||
|
|
||||||
.tooltip.portainer-tooltip .tooltip-inner {
|
|
||||||
font-family: Montserrat;
|
|
||||||
background-color: var(--bg-tooltip-color);
|
|
||||||
padding: 0.833em 1em;
|
|
||||||
color: var(--text-tooltip-color);
|
|
||||||
border: 1px solid var(--border-tooltip-color);
|
|
||||||
border-radius: 0.14285714rem;
|
|
||||||
box-shadow: 0 2px 4px 0 rgba(34, 36, 38, 0.12), 0 2px 10px 0 rgba(34, 36, 38, 0.15);
|
|
||||||
}
|
|
||||||
|
|
||||||
.tooltip.portainer-tooltip .tooltip-arrow {
|
|
||||||
display: none;
|
|
||||||
}
|
|
||||||
|
|
||||||
.fa.tooltip-icon {
|
|
||||||
margin-left: 5px;
|
|
||||||
font-size: 1.3em;
|
|
||||||
}
|
|
||||||
|
|
||||||
.fa.green-icon {
|
.fa.green-icon {
|
||||||
color: #23ae89;
|
color: #23ae89;
|
||||||
}
|
}
|
||||||
|
|
|
@ -0,0 +1,18 @@
|
||||||
|
.tooltip.portainer-tooltip .tooltip-inner {
|
||||||
|
font-family: Montserrat;
|
||||||
|
background-color: var(--bg-tooltip-color);
|
||||||
|
padding: 0.833em 1em;
|
||||||
|
color: var(--text-tooltip-color);
|
||||||
|
border: 1px solid var(--border-tooltip-color);
|
||||||
|
border-radius: 0.14285714rem;
|
||||||
|
box-shadow: 0 2px 4px 0 rgba(34, 36, 38, 0.12), 0 2px 10px 0 rgba(34, 36, 38, 0.15);
|
||||||
|
}
|
||||||
|
|
||||||
|
.tooltip.portainer-tooltip .tooltip-arrow {
|
||||||
|
display: none;
|
||||||
|
}
|
||||||
|
|
||||||
|
.fa.tooltip-icon {
|
||||||
|
margin-left: 5px;
|
||||||
|
font-size: 1.3em;
|
||||||
|
}
|
|
@ -0,0 +1,19 @@
|
||||||
|
.tooltip-wrapper {
|
||||||
|
display: inline-block;
|
||||||
|
position: relative;
|
||||||
|
}
|
||||||
|
|
||||||
|
.tooltip {
|
||||||
|
font-family: Montserrat !important;
|
||||||
|
background-color: var(--bg-tooltip-color) !important;
|
||||||
|
padding: 0.833em 1em !important;
|
||||||
|
color: var(--text-tooltip-color) !important;
|
||||||
|
border: 1px solid var(--border-tooltip-color) !important;
|
||||||
|
border-radius: 0.14285714rem !important;
|
||||||
|
box-shadow: 0 2px 4px 0 rgba(34, 36, 38, 0.12), 0 2px 10px 0 rgba(34, 36, 38, 0.15) !important;
|
||||||
|
}
|
||||||
|
|
||||||
|
.icon {
|
||||||
|
margin-left: 5px;
|
||||||
|
font-size: 1.3em;
|
||||||
|
}
|
|
@ -0,0 +1,23 @@
|
||||||
|
import { Meta, Story } from '@storybook/react';
|
||||||
|
|
||||||
|
import { Tooltip, Props } from './Tooltip';
|
||||||
|
|
||||||
|
export default {
|
||||||
|
component: Tooltip,
|
||||||
|
title: 'Components/Tooltip',
|
||||||
|
} as Meta;
|
||||||
|
|
||||||
|
function Template({ message, position }: JSX.IntrinsicAttributes & Props) {
|
||||||
|
return (
|
||||||
|
<div className="col-sm-3 col-lg-2">
|
||||||
|
Example tooltip
|
||||||
|
<Tooltip message={message} position={position} />
|
||||||
|
</div>
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
export const Primary: Story<Props> = Template.bind({});
|
||||||
|
Primary.args = {
|
||||||
|
message: 'Tooltip example',
|
||||||
|
position: 'bottom',
|
||||||
|
};
|
|
@ -0,0 +1,31 @@
|
||||||
|
import ReactTooltip from 'react-tooltip';
|
||||||
|
import clsx from 'clsx';
|
||||||
|
|
||||||
|
import styles from './Tooltip.module.css';
|
||||||
|
|
||||||
|
type Place = 'top' | 'right' | 'bottom' | 'left';
|
||||||
|
|
||||||
|
export interface Props {
|
||||||
|
position?: Place;
|
||||||
|
message: string;
|
||||||
|
}
|
||||||
|
|
||||||
|
export function Tooltip({ message, position = 'bottom' }: Props) {
|
||||||
|
return (
|
||||||
|
<span className="interactive">
|
||||||
|
<i
|
||||||
|
className={clsx('fa fa-question-circle blue-icon', styles.icon)}
|
||||||
|
aria-hidden="true"
|
||||||
|
data-tip={message}
|
||||||
|
/>
|
||||||
|
<ReactTooltip
|
||||||
|
multiline
|
||||||
|
type="info"
|
||||||
|
place={position}
|
||||||
|
effect="solid"
|
||||||
|
className={styles.tooltip}
|
||||||
|
arrowColor="transparent"
|
||||||
|
/>
|
||||||
|
</span>
|
||||||
|
);
|
||||||
|
}
|
|
@ -0,0 +1,21 @@
|
||||||
|
import { IComponentOptions } from 'angular';
|
||||||
|
import './Tooltip.css';
|
||||||
|
|
||||||
|
export const TooltipAngular: IComponentOptions = {
|
||||||
|
bindings: {
|
||||||
|
message: '@',
|
||||||
|
position: '@',
|
||||||
|
},
|
||||||
|
template: `<span
|
||||||
|
class="interactive"
|
||||||
|
tooltip-append-to-body="true"
|
||||||
|
tooltip-placement="{{$ctrl.position}}"
|
||||||
|
tooltip-class="portainer-tooltip"
|
||||||
|
uib-tooltip="{{$ctrl.message}}"
|
||||||
|
>
|
||||||
|
<i
|
||||||
|
class="fa fa-question-circle blue-icon tooltip-icon"
|
||||||
|
aria-hidden="true"
|
||||||
|
></i>
|
||||||
|
</span>`,
|
||||||
|
};
|
|
@ -0,0 +1,4 @@
|
||||||
|
import { Tooltip } from './Tooltip';
|
||||||
|
import { TooltipAngular } from './TooltipAngular';
|
||||||
|
|
||||||
|
export { Tooltip, TooltipAngular };
|
|
@ -6,7 +6,9 @@ import porAccessManagementModule from './accessManagement';
|
||||||
import formComponentsModule from './form-components';
|
import formComponentsModule from './form-components';
|
||||||
|
|
||||||
import { ReactExampleAngular } from './ReactExample';
|
import { ReactExampleAngular } from './ReactExample';
|
||||||
|
import { TooltipAngular } from './Tooltip';
|
||||||
|
|
||||||
export default angular
|
export default angular
|
||||||
.module('portainer.app.components', [sidebarModule, gitFormModule, porAccessManagementModule, formComponentsModule])
|
.module('portainer.app.components', [sidebarModule, gitFormModule, porAccessManagementModule, formComponentsModule])
|
||||||
|
.component('portainerTooltip', TooltipAngular)
|
||||||
.component('reactExample', ReactExampleAngular).name;
|
.component('reactExample', ReactExampleAngular).name;
|
||||||
|
|
|
@ -1,17 +0,0 @@
|
||||||
angular.module('portainer.app').directive('portainerTooltip', [
|
|
||||||
function portainerTooltip() {
|
|
||||||
var directive = {
|
|
||||||
scope: {
|
|
||||||
message: '@',
|
|
||||||
position: '@',
|
|
||||||
customStyle: '<?',
|
|
||||||
},
|
|
||||||
template: `
|
|
||||||
<span class="interactive" tooltip-append-to-body="true" tooltip-placement="{{position}}" tooltip-class="portainer-tooltip" uib-tooltip="{{message}}">
|
|
||||||
<i class="" ng-class="['fa fa-question-circle blue-icon', {'tooltip-icon': !customStyle}]" ng-style="customStyle" aria-hidden="true"></i>
|
|
||||||
</span>`,
|
|
||||||
restrict: 'E',
|
|
||||||
};
|
|
||||||
return directive;
|
|
||||||
},
|
|
||||||
]);
|
|
|
@ -106,6 +106,7 @@
|
||||||
"parse-duration": "^1.0.0",
|
"parse-duration": "^1.0.0",
|
||||||
"react": "^17.0.2",
|
"react": "^17.0.2",
|
||||||
"react-dom": "^17.0.2",
|
"react-dom": "^17.0.2",
|
||||||
|
"react-tooltip": "^4.2.21",
|
||||||
"source-map-loader": "^1.1.2",
|
"source-map-loader": "^1.1.2",
|
||||||
"spinkit": "^2.0.1",
|
"spinkit": "^2.0.1",
|
||||||
"splitargs": "github:deviantony/splitargs#semver:~0.2.0",
|
"splitargs": "github:deviantony/splitargs#semver:~0.2.0",
|
||||||
|
|
13
yarn.lock
13
yarn.lock
|
@ -15568,6 +15568,14 @@ react-textarea-autosize@^8.3.0:
|
||||||
use-composed-ref "^1.0.0"
|
use-composed-ref "^1.0.0"
|
||||||
use-latest "^1.0.0"
|
use-latest "^1.0.0"
|
||||||
|
|
||||||
|
react-tooltip@^4.2.21:
|
||||||
|
version "4.2.21"
|
||||||
|
resolved "https://registry.yarnpkg.com/react-tooltip/-/react-tooltip-4.2.21.tgz#840123ed86cf33d50ddde8ec8813b2960bfded7f"
|
||||||
|
integrity sha512-zSLprMymBDowknr0KVDiJ05IjZn9mQhhg4PRsqln0OZtURAJ1snt1xi5daZfagsh6vfsziZrc9pErPTDY1ACig==
|
||||||
|
dependencies:
|
||||||
|
prop-types "^15.7.2"
|
||||||
|
uuid "^7.0.3"
|
||||||
|
|
||||||
react@^17.0.2:
|
react@^17.0.2:
|
||||||
version "17.0.2"
|
version "17.0.2"
|
||||||
resolved "https://registry.yarnpkg.com/react/-/react-17.0.2.tgz#d0b5cc516d29eb3eee383f75b62864cfb6800037"
|
resolved "https://registry.yarnpkg.com/react/-/react-17.0.2.tgz#d0b5cc516d29eb3eee383f75b62864cfb6800037"
|
||||||
|
@ -18325,6 +18333,11 @@ uuid@^3.0.1, uuid@^3.3.2, uuid@^3.4.0:
|
||||||
resolved "https://registry.yarnpkg.com/uuid/-/uuid-3.4.0.tgz#b23e4358afa8a202fe7a100af1f5f883f02007ee"
|
resolved "https://registry.yarnpkg.com/uuid/-/uuid-3.4.0.tgz#b23e4358afa8a202fe7a100af1f5f883f02007ee"
|
||||||
integrity sha512-HjSDRw6gZE5JMggctHBcjVak08+KEVhSIiDzFnT9S9aegmp85S/bReBVTb4QTFaRNptJ9kuYaNhnbNEOkbKb/A==
|
integrity sha512-HjSDRw6gZE5JMggctHBcjVak08+KEVhSIiDzFnT9S9aegmp85S/bReBVTb4QTFaRNptJ9kuYaNhnbNEOkbKb/A==
|
||||||
|
|
||||||
|
uuid@^7.0.3:
|
||||||
|
version "7.0.3"
|
||||||
|
resolved "https://registry.yarnpkg.com/uuid/-/uuid-7.0.3.tgz#c5c9f2c8cf25dc0a372c4df1441c41f5bd0c680b"
|
||||||
|
integrity sha512-DPSke0pXhTZgoF/d+WSt2QaKMCFSfx7QegxEWT+JOuHF5aWrKEn0G+ztjuJg/gG8/ItK+rbPCD/yNv8yyih6Cg==
|
||||||
|
|
||||||
v8-compile-cache@^2.0.3:
|
v8-compile-cache@^2.0.3:
|
||||||
version "2.3.0"
|
version "2.3.0"
|
||||||
resolved "https://registry.yarnpkg.com/v8-compile-cache/-/v8-compile-cache-2.3.0.tgz#2de19618c66dc247dcfb6f99338035d8245a2cee"
|
resolved "https://registry.yarnpkg.com/v8-compile-cache/-/v8-compile-cache-2.3.0.tgz#2de19618c66dc247dcfb6f99338035d8245a2cee"
|
||||||
|
|
Loading…
Reference in New Issue