= {
+ children: bs5Props.children,
+ id: bs5Props.id,
+ description: bs5Props.description,
+ overlayProps: {},
+ ...bs3Props,
+ }
+
+ if ('hidden' in bs5Props) {
+ bs3TooltipProps.hidden = bs5Props.hidden
+ }
+
+ const delay = bs5Props.overlayProps?.delay
+ if (delay && typeof delay !== 'number') {
+ bs3TooltipProps.overlayProps = {
+ ...bs3TooltipProps.overlayProps,
+ delayShow: delay.show,
+ delayHide: delay.hide,
+ }
+ }
+
+ return (
+ }
+ bs5={}
+ />
+ )
+}
+
+export default TooltipWrapper
diff --git a/services/web/frontend/stories/ui/tooltip.stories.tsx b/services/web/frontend/stories/ui/tooltip.stories.tsx
new file mode 100644
index 0000000000..916ca6397c
--- /dev/null
+++ b/services/web/frontend/stories/ui/tooltip.stories.tsx
@@ -0,0 +1,41 @@
+import { Button } from 'react-bootstrap-5'
+import Tooltip from '@/features/ui/components/bootstrap-5/tooltip'
+import { Meta } from '@storybook/react'
+
+export const Tooltips = () => {
+ const placements = ['top', 'right', 'bottom', 'left'] as const
+
+ return (
+
+ {placements.map(placement => (
+
+
+
+ ))}
+
+ )
+}
+
+const meta: Meta = {
+ title: 'Shared / Components / Bootstrap 5 / Tooltip',
+ component: Tooltip,
+ parameters: {
+ bootstrap5: true,
+ },
+}
+
+export default meta
diff --git a/services/web/frontend/stylesheets/bootstrap-5/abstracts/variable-overrides.scss b/services/web/frontend/stylesheets/bootstrap-5/abstracts/variable-overrides.scss
index 106d521f23..c70aa433d4 100644
--- a/services/web/frontend/stylesheets/bootstrap-5/abstracts/variable-overrides.scss
+++ b/services/web/frontend/stylesheets/bootstrap-5/abstracts/variable-overrides.scss
@@ -21,3 +21,9 @@ $btn-border-radius-sm: $border-radius-full;
// Colors
$primary: $bg-accent-01;
$secondary: $bg-light-primary;
+
+// Tooltips
+$tooltip-max-width: 320px;
+$tooltip-border-radius: $border-radius-base;
+$tooltip-padding-y: $spacing-04;
+$tooltip-padding-x: $spacing-06;
diff --git a/services/web/frontend/stylesheets/bootstrap-5/bootstrap.scss b/services/web/frontend/stylesheets/bootstrap-5/bootstrap.scss
index 16a2b46ff7..1d78b7f7ec 100644
--- a/services/web/frontend/stylesheets/bootstrap-5/bootstrap.scss
+++ b/services/web/frontend/stylesheets/bootstrap-5/bootstrap.scss
@@ -29,6 +29,7 @@
@import 'bootstrap-5/scss/buttons';
@import 'bootstrap-5/scss/dropdown';
@import 'bootstrap-5/scss/modal';
+@import 'bootstrap-5/scss/tooltip';
@import 'bootstrap-5/scss/spinners';
// Helpers
diff --git a/services/web/frontend/stylesheets/bootstrap-5/components/all.scss b/services/web/frontend/stylesheets/bootstrap-5/components/all.scss
index 684cfac373..c8b62aa7a7 100644
--- a/services/web/frontend/stylesheets/bootstrap-5/components/all.scss
+++ b/services/web/frontend/stylesheets/bootstrap-5/components/all.scss
@@ -2,3 +2,4 @@
@import 'dropdown-menu';
@import 'split-button';
@import 'notifications';
+@import 'tooltip';
diff --git a/services/web/frontend/stylesheets/bootstrap-5/components/tooltip.scss b/services/web/frontend/stylesheets/bootstrap-5/components/tooltip.scss
new file mode 100644
index 0000000000..4a2916c85c
--- /dev/null
+++ b/services/web/frontend/stylesheets/bootstrap-5/components/tooltip.scss
@@ -0,0 +1,27 @@
+.tooltip {
+ line-height: 20px;
+ @include shadow-md;
+
+ &.#{$prefix}tooltip-top {
+ bottom: -1px !important;
+ }
+ &.#{$prefix}tooltip-end {
+ top: 1px !important;
+ left: -1px !important;
+ }
+ &.#{$prefix}tooltip-bottom {
+ top: -1px !important;
+ }
+ &.#{$prefix}tooltip-start {
+ top: 1px !important;
+ right: -1px !important;
+ }
+}
+
+.tooltip-inner {
+ text-align: initial;
+
+ .tooltip-wide & {
+ max-width: unset;
+ }
+}