- Curved tip
- Bubble tip
Contact Support
Fancy Tooltip customization in EJ2 TypeScript Tooltip control
27 Feb 202524 minutes to read
The arrow of the Tooltip can be customized as needed by altering the CSS in the sample-side. The EJ2 Tooltip control is implemented using CSS3 formatting, allowing the tip arrow to be positioned according to the Tooltip positions like TopCenter
, BottomLeft
, RightTop
, and more.
Here, the tip arrow is customized as Curved Tooltip and Bubble Tooltip.
Curved tip
To customize the curved tip arrow, override the following CSS class for the tip arrow:
let tooltip: Tooltip = new Tooltip({
cssClass: 'curvetips e-tooltip-css',
content: 'Tooltip arrow customized',
});
tooltip.appendTo('#target');
.e-arrow-tip-outer.e-tip-bottom,
.e-arrow-tip-outer.e-tip-top {
border-left: none !important;
border-right: none !important;
border-top: none !important;
}
.e-arrow-tip.e-tip-top {
transform: rotate(170deg);
}
Bubble tip
The two divs
(inner div and outer div) have been added to achieve the bubble tip arrow. To customize the bubble tip arrow, override the following CSS class of tip arrow.
let bubble: Tooltip = new Tooltip({
cssClass: 'bubbletip e-tooltip-css',
position: 'TopRight',
content: 'Tooltip arrow customized as balloon tip'
});
bubble.appendTo('#bubbletip');
.e-arrow-tip-outer.e-tip-bottom, .e-arrow-tip-outer.e-tip-top
{
border-radius: 50px;
height: 10px;
width: 10px;
}
.e-arrow-tip-inner.e-tip-bottom, .e-arrow-tip-inner.e-tip-top
{
border-radius: 50px;
height: 10px;
width: 10px;
}
These tip arrow customizations are achieved through CSS changes at the sample level. The Tooltip position can be changed using the radio button click event.
The arrow tip pointer can also be disabled by using the showTipPointer
property in a Tooltip.
import { Tooltip } from '@syncfusion/ej2-popups';
import { RadioButton, ChangeArgs, Button } from '@syncfusion/ej2-buttons';
let tooltip: Tooltip = new Tooltip({
cssClass: 'curvetips e-tooltip-css',
content: 'Tooltip arrow customized',
});
tooltip.appendTo('#target');
let curvebutton: Button = new Button();
curvebutton.appendTo('#target');
let tipbutton: Button = new Button();
tipbutton.appendTo('#tooltip');
let bubblebutton: Button = new Button();
bubblebutton.appendTo('#bubbletip');
let curveRadio: RadioButton = new RadioButton({ label: 'TopCenter', name: 'default', value: 'TopCenter', checked: true, change: onChange });
// Render initialized radio button
curveRadio.appendTo('#element1');
let curveRadioLeft = new RadioButton({ label: 'BottomLeft', name: 'default', value: 'BottomLeft', change: onChange });
curveRadioLeft.appendTo('#element2');
let tippointer: Tooltip = new Tooltip({
cssClass: 'pointertip e-tooltip-css',
mouseTrail: true,
content: 'Disabled tooltip pointer',
showTipPointer: false
});
tippointer.appendTo('#tooltip');
let bubble: Tooltip = new Tooltip({
cssClass: 'bubbletip e-tooltip-css',
position: 'TopRight',
content: 'Tooltip arrow customized as balloon tip'
});
bubble.appendTo('#bubbletip');
let bubbleRadio: RadioButton = new RadioButton({ label: 'BottomLeft', name: 'position', value: 'BottomLeft', change: onChanged });
// Render initialized radio button
bubbleRadio.appendTo('#radio1');
let radiobutton = new RadioButton({ label: 'TopRight', name: 'position', value: 'TopRight', checked: true, change: onChanged });
radiobutton.appendTo('#radio2');
function onChange(args: ChangeArgs): void {
tooltip.position = args.value as any;
tooltip.dataBind();
}
function onChanged(args: ChangeArgs): void {
bubble.position = args.value as any;
if (bubble.position == 'BottomLeft') {
bubble.offsetY = -30;
} else {
bubble.offsetY = 0;
}
bubble.dataBind();
}
<!DOCTYPE html>
<html lang="en">
<head>
<title>EJ2 Tooltip</title>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<meta name="description" content="Typescript UI Controls" />
<meta name="author" content="Syncfusion" />
<link href="index.css" rel="stylesheet" />
<link href="https://cdn.syncfusion.com/ej2/29.1.33/ej2-base/styles/material.css" rel="stylesheet" />
<link href="https://cdn.syncfusion.com/ej2/29.1.33/ej2-popups/styles/material.css" rel="stylesheet" />
<link href="https://cdn.syncfusion.com/ej2/29.1.33/ej2-buttons/styles/material.css" rel="stylesheet" />
<script src="https://cdnjs.cloudflare.com/ajax/libs/systemjs/0.19.38/system.js"></script>
<script src="systemjs.config.js"></script>
<script src="https://cdn.syncfusion.com/ej2/syncfusion-helper.js" type ="text/javascript"></script>
</head>
<body>
<div id='loader'>LOADING....</div>
<div id='container'>
<div id="customization" class="customTipContainer">
<button id="target">
Customized Tip Arrow
</button>
<div id="positions">
<ul>
<li>
<input type='radio' id='element1' />
</li>
<li>
<input type='radio' id='element2' />
</li>
</ul>
</div>
</div>
<div id="balloon" class="customTipContainer">
<button id="bubbletip">
Bubble Tip Arrow
</button>
<div id="btn">
<ul>
<li>
<input type='radio' id='radio1' />
</li>
<li>
<input type='radio' id='radio2' />
</li>
</ul>
</div>
</div>
<div id="disabledContainer" class="customTipContainer">
<button id="tooltip">
Disabled Tip Arrow
</button>
</div>
</div>
<style>
#bubbletip {
border-color: #d2a679;
}
#target {
border-color: #e86238;
}
li {
list-style: none;
}
.e-radio-wrapper {
margin-top: 18px;
}
#target,
#bubbletip,
#tooltip {
box-sizing: border-box;
padding: 20px;
width: 200px;
text-align: center;
top: -17px;
margin-bottom: 40px;
}
/* csslint ignore:start */
@font-face {
font-family: "tip";
src: url("https://ej2.syncfusion.com/products/typescript/tooltip/customization/Fonts/tip.tff") format("truetype"), url("https://ej2.syncfusion.com/products/typescript/tooltip/customization/Fonts/tip.woff") format("woff"), url("https://ej2.syncfusion.com/products/typescript/tooltip/customization/Fonts/tip.eot") format("eot"), url("https://ej2.syncfusion.com/products/typescript/tooltip/customization/Fonts/tip.svg?#tip") format("svg");
font-weight: normal;
font-style: normal;
}
/* csslint ignore:end */
/* csslint ignore:start */
#container {
width: 100%;
}
.customTipContainer {
width: 400px;
position: relative;
left: 50%;
transform: translateX(-50%);
top: 50px;
}
#disabledContainer {
margin-top: 25px;
}
.pointertip.e-tooltip-wrap .e-tip-content,
.curvetips.e-tooltip-wrap .e-tip-content {
color: white;
}
.pointertip.e-tooltip-wrap.e-popup {
background-color: #80180d;
border: 3px solid #ff9999;
}
.curvetips .e-arrow-tip.e-tip-top {
margin-left: -20px;
top: -16px;
transform: rotate(177deg);
left: 50px;
}
.curvetips.e-tooltip-wrap {
padding: 17px;
border-radius: 5px;
}
.curvetips.e-tooltip-wrap .e-arrow-tip-outer.e-tip-bottom:before,
.curvetips.e-tooltip-wrap .e-arrow-tip-outer.e-tip-top:before {
font-family: "tip" !important;
speak-as: none;
font-size: 21px;
font-style: normal;
font-weight: normal;
font-variant: normal;
text-transform: none;
line-height: 1;
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
content: "\e700";
color: #e86238;
}
.curvetips.e-tooltip-wrap.e-popup {
background: #e86238;
border: none;
}
.curvetips.e-tooltip-wrap .e-arrow-tip-outer.e-tip-bottom,
.curvetips.e-tooltip-wrap .e-arrow-tip-outer.e-tip-top {
border-left: none;
border-right: none;
border-top: none;
}
.curvetips.e-tooltip-wrap .e-arrow-tip-inner.e-tip-bottom:before,
.curvetips.e-tooltip-wrap .e-arrow-tip-inner.e-tip-top:before {
content: none;
}
.curvetips.e-tooltip-wrap .e-arrow-tip-outer.e-tip-bottom,
.curvetips.e-tooltip-wrap .e-arrow-tip-outer.e-tip-top {
top: -1px;
}
.curvetips.e-tooltip-wrap .e-arrow-tip.e-tip-bottom,
.curvetips.e-tooltip-wrap .e-arrow-tip.e-tip-top {
position: absolute;
height: 18px;
width: 28px;
}
#positions {
display: inline-block;
}
#btn {
display: inline-block;
}
#target .e-tip-content {
padding: 0px;
}
.bubbletip.e-tooltip-wrap {
padding: 8px;
}
.bubbletip.e-tooltip-wrap .e-tip-content {
border-radius: 50%;
text-align: center;
color: white;
}
.bubbletip.e-tooltip-wrap .e-arrow-tip.e-tip-bottom {
height: 40px;
width: 50px;
}
.bubbletip.e-tooltip-wrap .e-arrow-tip.e-tip-top {
height: 40px;
width: 40px;
}
.bubbletip.e-tooltip-wrap .e-arrow-tip.e-tip-left {
height: 12px;
width: 20px;
}
.bubbletip.e-tooltip-wrap .e-arrow-tip.e-tip-right {
height: 12px;
width: 20px;
}
.bubbletip.e-tooltip-wrap.e-popup {
border: 5px solid #dfccad;
background-color: #7b5e32;
}
.bubbletip.e-tooltip-wrap .e-arrow-tip-outer.e-tip-bottom {
height: 10px;
width: 10px;
border: 1px solid #dfccad;
background-color: #7b5e32;
border-radius: 50px;
margin-top: 20px;
margin-right: 20px;
}
.e-arrow-tip.e-tip-top {
margin-left: 60px;
}
.bubbletip.e-tooltip-wrap .e-arrow-tip-outer.e-tip-top {
border: 1px solid #dfccad;
border-radius: 50px;
background-color: #7b5e32;
width: 10px;
height: 10px;
margin-left: 20px;
}
.bubbletip.e-tooltip-wrap .e-arrow-tip-outer.e-tip-left {
border-bottom: 6px solid transparent;
border-right: 20px solid #dfccad;
border-top: 6px solid transparent;
}
.bubbletip.e-tooltip-wrap .e-arrow-tip-outer.e-tip-right {
border-bottom: 6px solid transparent;
border-left: 20px solid #dfccad;
border-top: 6px solid transparent;
}
.bubbletip.e-tooltip-wrap .e-arrow-tip-inner.e-tip-bottom {
margin-top: -2px;
margin-left: 8px;
content: none;
top: 1px !important;
border: 2px solid #dfccad;
width: 20px;
height: 20px;
border-radius: 50px;
background-color: #7b5e32;
}
.bubbletip .e-arrow-tip.e-tip-top {
left: 44px !important;
top: -19px !important;
}
.bubbletip .e-arrow-tip.e-tip-bottom {
top: 88.9% !important;
left: 4px !important;
}
.bubbletip.e-tooltip-wrap .e-arrow-tip-inner.e-tip-top {
top: 10px !important;
border: 2px solid #dfccad;
width: 20px;
height: 20px;
border-radius: 50px;
background-color: #7b5e32;
}
.bubbletip.e-tooltip-wrap .e-arrow-tip-inner.e-tip-top:before {
content: None;
}
.bubbletip.e-tooltip-wrap .e-tip-content {
border-radius: inherit;
}
.bubbletip.e-tooltip-wrap.bubbletip {
width: 150px !important;
border-radius: 50%;
}
/* csslint ignore:end */
</style>
</body>
</html>
#container {
visibility: hidden;
}
#loader {
color: #008cff;
height: 40px;
left: 45%;
position: absolute;
top: 45%;
width: 30%;
}