diff --git a/web/packages/design/src/DataTable/StyledTable.tsx b/web/packages/design/src/DataTable/StyledTable.tsx index 0b73cf358528a..85a6c23b8dc19 100644 --- a/web/packages/design/src/DataTable/StyledTable.tsx +++ b/web/packages/design/src/DataTable/StyledTable.tsx @@ -18,12 +18,16 @@ import styled from 'styled-components'; import { space, borderRadius } from 'design/system'; +import { decomposeColor, emphasize } from 'design/theme/utils/colorManipulator'; + import Icon from '../Icon'; export const StyledTable = styled.table( props => ` background: ${props.theme.colors.levels.surface}; + border-collapse: collapse; border-spacing: 0; + border-style: hidden; font-size: 12px; width: 100%; @@ -73,11 +77,8 @@ export const StyledTable = styled.table( line-height: 16px; } - // When border-collapse: collapse is set on a table element, Safari incorrectly renders the row border with alpha channel. - // It looks like the collapsed border was rendered twice, that is, opacity 0.07 looks like opacity 0.14. - // A workaround is to not use collapse and apply border to td elements. - & > tbody > tr:not(:last-of-type) > td { - border-bottom: 1px solid ${props.theme.colors.spotBackground[0]}; + tbody tr { + border-bottom: 1px solid ${getSolidRowBorderColor(props.theme)}; } tbody tr:hover { @@ -89,6 +90,20 @@ export const StyledTable = styled.table( borderRadius ); +// When `border-collapse: collapse` is set on a table element, Safari incorrectly renders row border with alpha channel. +// It looks like the collapsed border was rendered twice, that is, opacity 0.07 looks like opacity 0.14 (this is more visible +// on the dark theme). +// Sometimes, there is also an artifact visible after hovering the rows - some of them have correct border color, some not. +// WebKit issue https://bugs.webkit.org/show_bug.cgi?id=35456. +// +// `getSolidRowBorderColor` is a workaround. Instead of setting a color with an alpha channel to the border and letting +// the browser mix it with the background color, we calculate the final (non-alpha) color in the JS code. +// The final color is created by lightening or darkening the table background color by the value of the alpha channel of theme.colors.spotBackground[0]. +function getSolidRowBorderColor(theme) { + const alpha = decomposeColor(theme.colors.spotBackground[0]).values[3] || 0; + return emphasize(theme.colors.levels.surface, alpha); +} + export const StyledPanel = styled.nav<{ showTopBorder: boolean }>` padding: 16px 24px; display: flex; diff --git a/web/packages/teleport/src/Account/ManageDevices/__snapshots__/ManageDevices.story.test.tsx.snap b/web/packages/teleport/src/Account/ManageDevices/__snapshots__/ManageDevices.story.test.tsx.snap index 7b69e761eab5b..6cbca9def4f78 100644 --- a/web/packages/teleport/src/Account/ManageDevices/__snapshots__/ManageDevices.story.test.tsx.snap +++ b/web/packages/teleport/src/Account/ManageDevices/__snapshots__/ManageDevices.story.test.tsx.snap @@ -140,7 +140,9 @@ exports[`render device dashboard 1`] = ` .c11 { background: #222C59; + border-collapse: collapse; border-spacing: 0; + border-style: hidden; font-size: 12px; width: 100%; border-top-left-radius: 0px; @@ -204,8 +206,8 @@ exports[`render device dashboard 1`] = ` line-height: 16px; } -.c11 > tbody > tr:not(:last-of-type) > td { - border-bottom: 1px solid rgba(255,255,255,0.07); +.c11 tbody tr { + border-bottom: 1px solid rgb(49,58,100); } .c11 tbody tr:hover { @@ -682,7 +684,9 @@ exports[`render failed state for creating restricted privilege token 1`] = ` .c12 { background: #222C59; + border-collapse: collapse; border-spacing: 0; + border-style: hidden; font-size: 12px; width: 100%; border-top-left-radius: 0px; @@ -746,8 +750,8 @@ exports[`render failed state for creating restricted privilege token 1`] = ` line-height: 16px; } -.c12 > tbody > tr:not(:last-of-type) > td { - border-bottom: 1px solid rgba(255,255,255,0.07); +.c12 tbody tr { + border-bottom: 1px solid rgb(49,58,100); } .c12 tbody tr:hover { diff --git a/web/packages/teleport/src/Apps/__snapshots__/Apps.story.test.tsx.snap b/web/packages/teleport/src/Apps/__snapshots__/Apps.story.test.tsx.snap index da073b1963d87..d7ec613f43ced 100644 --- a/web/packages/teleport/src/Apps/__snapshots__/Apps.story.test.tsx.snap +++ b/web/packages/teleport/src/Apps/__snapshots__/Apps.story.test.tsx.snap @@ -605,7 +605,9 @@ exports[`failed state 1`] = ` .c24 { background: #222C59; + border-collapse: collapse; border-spacing: 0; + border-style: hidden; font-size: 12px; width: 100%; } @@ -667,8 +669,8 @@ exports[`failed state 1`] = ` line-height: 16px; } -.c24 > tbody > tr:not(:last-of-type) > td { - border-bottom: 1px solid rgba(255,255,255,0.07); +.c24 tbody tr { + border-bottom: 1px solid rgb(49,58,100); } .c24 tbody tr:hover { @@ -1718,7 +1720,9 @@ exports[`loaded state 1`] = ` .c24 { background: #222C59; + border-collapse: collapse; border-spacing: 0; + border-style: hidden; font-size: 12px; width: 100%; } @@ -1780,8 +1784,8 @@ exports[`loaded state 1`] = ` line-height: 16px; } -.c24 > tbody > tr:not(:last-of-type) > td { - border-bottom: 1px solid rgba(255,255,255,0.07); +.c24 tbody tr { + border-bottom: 1px solid rgb(49,58,100); } .c24 tbody tr:hover { diff --git a/web/packages/teleport/src/Audit/__snapshots__/Audit.story.test.tsx.snap b/web/packages/teleport/src/Audit/__snapshots__/Audit.story.test.tsx.snap index 7cf55616808ee..ac7b414fb89a9 100644 --- a/web/packages/teleport/src/Audit/__snapshots__/Audit.story.test.tsx.snap +++ b/web/packages/teleport/src/Audit/__snapshots__/Audit.story.test.tsx.snap @@ -185,7 +185,9 @@ exports[`list of all events 1`] = ` .c17 { background: #222C59; + border-collapse: collapse; border-spacing: 0; + border-style: hidden; font-size: 12px; width: 100%; border-top-left-radius: 0px; @@ -251,8 +253,8 @@ exports[`list of all events 1`] = ` line-height: 16px; } -.c17 > tbody > tr:not(:last-of-type) > td { - border-bottom: 1px solid rgba(255,255,255,0.07); +.c17 tbody tr { + border-bottom: 1px solid rgb(49,58,100); } .c17 tbody tr:hover { @@ -7699,7 +7701,9 @@ exports[`loaded audit log screen 1`] = ` .c21 { background: #222C59; + border-collapse: collapse; border-spacing: 0; + border-style: hidden; font-size: 12px; width: 100%; border-top-left-radius: 0px; @@ -7765,8 +7769,8 @@ exports[`loaded audit log screen 1`] = ` line-height: 16px; } -.c21 > tbody > tr:not(:last-of-type) > td { - border-bottom: 1px solid rgba(255,255,255,0.07); +.c21 tbody tr { + border-bottom: 1px solid rgb(49,58,100); } .c21 tbody tr:hover { diff --git a/web/packages/teleport/src/Clusters/__snapshots__/Clusters.story.test.tsx.snap b/web/packages/teleport/src/Clusters/__snapshots__/Clusters.story.test.tsx.snap index e3c73a8fabbb3..ba7365f3b1dba 100644 --- a/web/packages/teleport/src/Clusters/__snapshots__/Clusters.story.test.tsx.snap +++ b/web/packages/teleport/src/Clusters/__snapshots__/Clusters.story.test.tsx.snap @@ -238,7 +238,9 @@ exports[`render clusters 1`] = ` .c19 { background: #222C59; + border-collapse: collapse; border-spacing: 0; + border-style: hidden; font-size: 12px; width: 100%; border-top-left-radius: 0px; @@ -304,8 +306,8 @@ exports[`render clusters 1`] = ` line-height: 16px; } -.c19 > tbody > tr:not(:last-of-type) > td { - border-bottom: 1px solid rgba(255,255,255,0.07); +.c19 tbody tr { + border-bottom: 1px solid rgb(49,58,100); } .c19 tbody tr:hover { diff --git a/web/packages/teleport/src/Console/DocumentNodes/__snapshots__/DocumentNodes.story.test.tsx.snap b/web/packages/teleport/src/Console/DocumentNodes/__snapshots__/DocumentNodes.story.test.tsx.snap index 43d2d77692cff..42c219e916227 100644 --- a/web/packages/teleport/src/Console/DocumentNodes/__snapshots__/DocumentNodes.story.test.tsx.snap +++ b/web/packages/teleport/src/Console/DocumentNodes/__snapshots__/DocumentNodes.story.test.tsx.snap @@ -253,7 +253,9 @@ exports[`render DocumentNodes 1`] = ` .c30 { background: #222C59; + border-collapse: collapse; border-spacing: 0; + border-style: hidden; font-size: 12px; width: 100%; } @@ -315,8 +317,8 @@ exports[`render DocumentNodes 1`] = ` line-height: 16px; } -.c30 > tbody > tr:not(:last-of-type) > td { - border-bottom: 1px solid rgba(255,255,255,0.07); +.c30 tbody tr { + border-bottom: 1px solid rgb(49,58,100); } .c30 tbody tr:hover { diff --git a/web/packages/teleport/src/Databases/__snapshots__/Databases.story.test.tsx.snap b/web/packages/teleport/src/Databases/__snapshots__/Databases.story.test.tsx.snap index 05023e17a7e66..e1b00cafc8116 100644 --- a/web/packages/teleport/src/Databases/__snapshots__/Databases.story.test.tsx.snap +++ b/web/packages/teleport/src/Databases/__snapshots__/Databases.story.test.tsx.snap @@ -534,7 +534,9 @@ exports[`failed 1`] = ` .c24 { background: #222C59; + border-collapse: collapse; border-spacing: 0; + border-style: hidden; font-size: 12px; width: 100%; } @@ -596,8 +598,8 @@ exports[`failed 1`] = ` line-height: 16px; } -.c24 > tbody > tr:not(:last-of-type) > td { - border-bottom: 1px solid rgba(255,255,255,0.07); +.c24 tbody tr { + border-bottom: 1px solid rgb(49,58,100); } .c24 tbody tr:hover { @@ -1385,7 +1387,9 @@ exports[`open source loaded 1`] = ` .c24 { background: #222C59; + border-collapse: collapse; border-spacing: 0; + border-style: hidden; font-size: 12px; width: 100%; } @@ -1447,8 +1451,8 @@ exports[`open source loaded 1`] = ` line-height: 16px; } -.c24 > tbody > tr:not(:last-of-type) > td { - border-bottom: 1px solid rgba(255,255,255,0.07); +.c24 tbody tr { + border-bottom: 1px solid rgb(49,58,100); } .c24 tbody tr:hover { diff --git a/web/packages/teleport/src/Kubes/__snapshots__/Kubes.story.test.tsx.snap b/web/packages/teleport/src/Kubes/__snapshots__/Kubes.story.test.tsx.snap index ee3904ec5194c..f2e367681409f 100644 --- a/web/packages/teleport/src/Kubes/__snapshots__/Kubes.story.test.tsx.snap +++ b/web/packages/teleport/src/Kubes/__snapshots__/Kubes.story.test.tsx.snap @@ -494,7 +494,9 @@ exports[`failed 1`] = ` .c24 { background: #222C59; + border-collapse: collapse; border-spacing: 0; + border-style: hidden; font-size: 12px; width: 100%; } @@ -556,8 +558,8 @@ exports[`failed 1`] = ` line-height: 16px; } -.c24 > tbody > tr:not(:last-of-type) > td { - border-bottom: 1px solid rgba(255,255,255,0.07); +.c24 tbody tr { + border-bottom: 1px solid rgb(49,58,100); } .c24 tbody tr:hover { @@ -1304,7 +1306,9 @@ exports[`loaded 1`] = ` .c24 { background: #222C59; + border-collapse: collapse; border-spacing: 0; + border-style: hidden; font-size: 12px; width: 100%; } @@ -1366,8 +1370,8 @@ exports[`loaded 1`] = ` line-height: 16px; } -.c24 > tbody > tr:not(:last-of-type) > td { - border-bottom: 1px solid rgba(255,255,255,0.07); +.c24 tbody tr { + border-bottom: 1px solid rgb(49,58,100); } .c24 tbody tr:hover { diff --git a/web/packages/teleport/src/Nodes/__snapshots__/Nodes.story.test.tsx.snap b/web/packages/teleport/src/Nodes/__snapshots__/Nodes.story.test.tsx.snap index 2f5d020af59bb..2333136102ad4 100644 --- a/web/packages/teleport/src/Nodes/__snapshots__/Nodes.story.test.tsx.snap +++ b/web/packages/teleport/src/Nodes/__snapshots__/Nodes.story.test.tsx.snap @@ -545,7 +545,9 @@ exports[`failed 1`] = ` .c24 { background: #222C59; + border-collapse: collapse; border-spacing: 0; + border-style: hidden; font-size: 12px; width: 100%; } @@ -607,8 +609,8 @@ exports[`failed 1`] = ` line-height: 16px; } -.c24 > tbody > tr:not(:last-of-type) > td { - border-bottom: 1px solid rgba(255,255,255,0.07); +.c24 tbody tr { + border-bottom: 1px solid rgb(49,58,100); } .c24 tbody tr:hover { @@ -1640,7 +1642,9 @@ exports[`loaded 1`] = ` .c27 { background: #222C59; + border-collapse: collapse; border-spacing: 0; + border-style: hidden; font-size: 12px; width: 100%; } @@ -1702,8 +1706,8 @@ exports[`loaded 1`] = ` line-height: 16px; } -.c27 > tbody > tr:not(:last-of-type) > td { - border-bottom: 1px solid rgba(255,255,255,0.07); +.c27 tbody tr { + border-bottom: 1px solid rgb(49,58,100); } .c27 tbody tr:hover { diff --git a/web/packages/teleport/src/Recordings/__snapshots__/Recordings.story.test.tsx.snap b/web/packages/teleport/src/Recordings/__snapshots__/Recordings.story.test.tsx.snap index 1810350d2cbb3..c20431404e5f5 100644 --- a/web/packages/teleport/src/Recordings/__snapshots__/Recordings.story.test.tsx.snap +++ b/web/packages/teleport/src/Recordings/__snapshots__/Recordings.story.test.tsx.snap @@ -390,7 +390,9 @@ exports[`rendering of Session Recordings 1`] = ` .c21 { background: #222C59; + border-collapse: collapse; border-spacing: 0; + border-style: hidden; font-size: 12px; width: 100%; border-top-left-radius: 0px; @@ -456,8 +458,8 @@ exports[`rendering of Session Recordings 1`] = ` line-height: 16px; } -.c21 > tbody > tr:not(:last-of-type) > td { - border-bottom: 1px solid rgba(255,255,255,0.07); +.c21 tbody tr { + border-bottom: 1px solid rgb(49,58,100); } .c21 tbody tr:hover { diff --git a/web/packages/teleport/src/Sessions/__snapshots__/Sessions.story.test.tsx.snap b/web/packages/teleport/src/Sessions/__snapshots__/Sessions.story.test.tsx.snap index 1b91ec1c65cb4..656ac00d54b18 100644 --- a/web/packages/teleport/src/Sessions/__snapshots__/Sessions.story.test.tsx.snap +++ b/web/packages/teleport/src/Sessions/__snapshots__/Sessions.story.test.tsx.snap @@ -238,7 +238,9 @@ exports[`loaded 1`] = ` .c19 { background: #222C59; + border-collapse: collapse; border-spacing: 0; + border-style: hidden; font-size: 12px; width: 100%; border-top-left-radius: 0px; @@ -304,8 +306,8 @@ exports[`loaded 1`] = ` line-height: 16px; } -.c19 > tbody > tr:not(:last-of-type) > td { - border-bottom: 1px solid rgba(255,255,255,0.07); +.c19 tbody tr { + border-bottom: 1px solid rgb(49,58,100); } .c19 tbody tr:hover { diff --git a/web/packages/teleport/src/Users/__snapshots__/Users.story.test.tsx.snap b/web/packages/teleport/src/Users/__snapshots__/Users.story.test.tsx.snap index 490fe5dcef5fb..f0b9d700030c9 100644 --- a/web/packages/teleport/src/Users/__snapshots__/Users.story.test.tsx.snap +++ b/web/packages/teleport/src/Users/__snapshots__/Users.story.test.tsx.snap @@ -289,7 +289,9 @@ exports[`success state 1`] = ` .c20 { background: #222C59; + border-collapse: collapse; border-spacing: 0; + border-style: hidden; font-size: 12px; width: 100%; border-top-left-radius: 0px; @@ -355,8 +357,8 @@ exports[`success state 1`] = ` line-height: 16px; } -.c20 > tbody > tr:not(:last-of-type) > td { - border-bottom: 1px solid rgba(255,255,255,0.07); +.c20 tbody tr { + border-bottom: 1px solid rgb(49,58,100); } .c20 tbody tr:hover {