Repository: Sage/carbon (ts)

Issue:
`textOverflow` prop on `Typography` can't be used
### Current behaviour

In plain CSS to to use the `text-overflow` property, you need to set `overflow: hidden` and `white-space: nowrap` which in Carbon can be done by setting the truncate prop, but setting this prop explicity sets `text-overflow` to `ellipsis`, so the value of textOverflow never has any effect.

### Expected behaviour

To be able to specify `textOverflow` alongside the `truncate` prop.

### CodeSandbox or Storybook URL

https://codesandbox.io/s/crimson-flower-f0o3go?file=/src/App.js

### JIRA Ticket (Sage Only)

_No response_

### Suggested Solution

_No response_

### Carbon Version

116.2.0

### Design Tokens Version

_No response_

### What browsers are you seeing the problem on?

Firefox, Chrome

### What Operating System are you seeing the problem on?

Windows

### Anything else we should know?

_No response_

### Confidentiality

- [X] I confirm there is no confidential or commercially sensitive information included.

Pull request:
fix(typography): textOverflow prop has no effect when the truncate prop is set
fix #6098

### Proposed behaviour

<!--
A clear and concise description of what changes this PR makes. If applicable, include any UI screenshots to help explain your request. If you are a Sage contributor, please DO NOT share any commercially sensitive information, such as UI screenshots or code from Sage products.
-->

When the `truncate` prop is set, `textOverflow` can be overridden. 

### Current behaviour

<!--
A clear and concise description of the behaviour before this change. If applicable, include any UI screenshots to help explain your request. If you are a Sage contributor, please DO NOT share any commercially sensitive information, such as UI screenshots or code from Sage products.
-->

The `textOverflow` prop has no effect and cannot be overridden when the `truncate` prop is set. 

### Checklist

<!-- Each PR should include the following -->

- [x] Commits follow our style guide
- [x] Related issues linked in commit messages if required
- [ ] Screenshots are included in the PR if useful
- [ ] All themes are supported if required
- [x] Unit tests added or updated if required
- [ ] Playwright automation tests added or updated if required
- [x] Storybook added or updated if required
- [ ] Translations added or updated (including creating or amending translation keys table in storybook) if required
- [ ] Typescript `d.ts` file added or updated if required
- [ ] Related docs have been updated if required

#### QA

- [x] Tested in provided StackBlitz sandbox/Storybook
- [ ] Add new Playwright test coverage if required
- [ ] Carbon implementation matches Design System/designs
- [ ] UI Tests GitHub check reviewed if required

### Additional context

<!-- Add any other context or links about the pull request here. -->

### Testing instructions

<!--
How can a reviewer test this PR?

If this PR addresses a pre-existing bug, please include a link to a sandbox that reproduces the original bug. A starter template has been provided to help you do this:
<https://stackblitz.com/fork/github/Parsium/carbon-starter>
-->
 [Stackblitz with issue](https://stackblitz.com/edit/parsium-carbon-starter-hd4jq1?file=src%2FApp.tsx,package.json,src%2Fmain.tsx)

Go to "Truncated" story in storybook for fix. 

Patch:
diff --git a/src/components/typography/typography.component.tsx b/src/components/typography/typography.component.tsx
index 229322f55..23132d5cd 100644
--- a/src/components/typography/typography.component.tsx
+++ b/src/components/typography/typography.component.tsx
@@ -7,7 +7,7 @@ import {
 } from "../../style/utils";
 import StyledTypography from "./typography.style";
 
-const VARIANT_TYPES = [
+export const VARIANT_TYPES = [
   "h1-large",
   "h1",
   "h2",
diff --git a/src/components/typography/typography.mdx b/src/components/typography/typography.mdx
index a7ec51534..c61f16380 100644
--- a/src/components/typography/typography.mdx
+++ b/src/components/typography/typography.mdx
@@ -35,7 +35,9 @@ It's also possible to create ordered and unordered lists using the `List`, `List
 
 ## Example of truncate
 
-The `truncate` prop is a boolean prop that automatically applies the styles required to truncate a piece of text.
+The `truncate` prop is a boolean prop that automatically applies  `overflow: hidden` and `white-space: nowrap`, which are the styles required to truncate a piece of text.
+
+By default, this prop will truncate the text with an ellipsis, but you can also pass the `textOverflow` prop to override this behaviour. 
 
 This prop will only work with block level elements, so ensure `display="block"` or similar is set to enable this functionality.
 
diff --git a/src/components/typography/typography.spec.tsx b/src/components/typography/typography.spec.tsx
index ff1efcaf9..26cfd3b07 100644
--- a/src/components/typography/typography.spec.tsx
+++ b/src/components/typography/typography.spec.tsx
@@ -606,16 +606,20 @@ describe("Typography", () => {
     );
 
     it.each(["clip", "ellipsis", "string", "initial", "inherit"])(
-      "applies text-overflow of %s",
+      "applies text-overflow of %s when text is truncated",
       (prop) => {
         const wrapper = mount(
           <ThemeProvider theme={sageTheme}>
-            <Typography textOverflow={prop}>FooBar</Typography>
+            <Typography truncate textOverflow={prop}>
+              FooBar
+            </Typography>
           </ThemeProvider>
         );
 
         assertStyleMatch(
           {
+            whiteSpace: "nowrap",
+            overflow: "hidden",
             textOverflow: prop,
           },
           wrapper.find(Typography)
diff --git a/src/components/typography/typography.stories.tsx b/src/components/typography/typography.stories.tsx
index 47654f291..02a574ede 100644
--- a/src/components/typography/typography.stories.tsx
+++ b/src/components/typography/typography.stories.tsx
@@ -120,19 +120,23 @@ VariantsStory.parameters = { info: { disable: true } };
 
 export const TruncateStory: Story = () => (
   <>
-    <Box height={80} width={80} backgroundColor="yellow">
+    <Box height={80} width={350} backgroundColor="yellow">
       <Typography truncate>
-        The is an example of using the truncate prop. This is an example of some
-        text with applied.
+        The is an example of using the truncate prop with a block element.
       </Typography>
     </Box>
-    <Box height={80} width={80} backgroundColor="red">
+    <Box height={80} width={350} backgroundColor="red">
       <Typography truncate variant="b" display="block">
         The is an example of using the truncate prop with an inline element.
         Changing the display type to be a block element allows it to actually
         truncate.
       </Typography>
     </Box>
+    <Box height={80} width={350} backgroundColor="lightblue">
+      <Typography truncate textOverflow="clip">
+        The is an example of using the truncate prop with custom text-overflow.
+      </Typography>
+    </Box>
   </>
 );
 TruncateStory.storyName = "Truncate";
diff --git a/src/components/typography/typography.style.ts b/src/components/typography/typography.style.ts
index 161e35071..ee35bafb3 100644
--- a/src/components/typography/typography.style.ts
+++ b/src/components/typography/typography.style.ts
@@ -178,7 +178,7 @@ const StyledTypography = styled.span.attrs(
     white-space: ${truncate ? "nowrap" : whiteSpace};
     word-wrap: ${wordWrap};
     text-align: ${textAlign};
-    text-overflow: ${truncate ? "ellipsis" : textOverflow};
+    text-overflow: ${textOverflow || (truncate && "ellipsis")};
     ${truncate &&
     css`
       overflow: hidden;


Test patch:
diff --git a/src/components/typography/typography-test.stories.tsx b/src/components/typography/typography-test.stories.tsx
index 03e40810d..bfb08d014 100644
--- a/src/components/typography/typography-test.stories.tsx
+++ b/src/components/typography/typography-test.stories.tsx
@@ -1,30 +1,119 @@
 import React from "react";
-import Typography, { List, ListItem } from ".";
+import Typography, { TypographyProps, List, ListItem } from ".";
+import { VARIANT_TYPES } from "./typography.component";
 
 export default {
   title: "Typography/Test",
-  includeStories: ["Default"],
+  includeStories: ["Default", "ListComponent"],
   parameters: {
     info: { disable: true },
     chromatic: {
       disableSnapshot: true,
     },
   },
+  argTypes: {
+    variant: {
+      options: VARIANT_TYPES,
+      control: {
+        type: "select",
+      },
+    },
+    fontSize: {
+      control: {
+        type: "text",
+      },
+    },
+    fontWeight: {
+      control: {
+        type: "text",
+      },
+    },
+    lineHeight: {
+      control: {
+        type: "text",
+      },
+    },
+    textTransform: {
+      control: {
+        type: "text",
+      },
+    },
+    textDecoration: {
+      control: {
+        type: "text",
+      },
+    },
+    display: {
+      control: {
+        type: "text",
+      },
+    },
+    listStyleType: {
+      control: {
+        type: "text",
+      },
+    },
+    whiteSpace: {
+      control: {
+        type: "text",
+      },
+    },
+    wordWrap: {
+      control: {
+        type: "text",
+      },
+    },
+    textAlign: {
+      control: {
+        type: "text",
+      },
+    },
+    textOverflow: {
+      control: {
+        type: "text",
+      },
+    },
+    truncate: {
+      control: {
+        type: "boolean",
+      },
+    },
+    color: {
+      control: {
+        type: "text",
+      },
+    },
+    backgroundColor: {
+      control: {
+        type: "text",
+      },
+    },
+    bg: {
+      control: {
+        type: "text",
+      },
+    },
+    opacity: {
+      control: {
+        type: "text",
+      },
+    },
+  },
 };
 
-export const Default = ({ ...props }) => {
-  return (
-    <Typography {...props} variant="b">
-      Some text
-    </Typography>
-  );
+export const Default = ({ children, ...args }: TypographyProps) => {
+  return <Typography {...args}>{children}</Typography>;
 };
 Default.storyName = "default";
+Default.args = {
+  children: "Some text",
+  variant: "b",
+};
 
-export const ListComponent = ({ ...props }) => {
+export const ListComponent = ({ as, ...args }: TypographyProps) => {
   return (
-    <List {...props}>
-      <ListItem>
+    <List as={as}>
+      <ListItem {...args}>
         Milk <Typography variant="b">2L</Typography>{" "}
         <Typography variant="em">Skimmed</Typography>
       </ListItem>
@@ -38,3 +127,14 @@ export const ListComponent = ({ ...props }) => {
   );
 };
 ListComponent.storyName = "list component";
+ListComponent.args = {
+  as: "ul",
+};
+ListComponent.argTypes = {
+  as: {
+    options: ["ul", "ol"],
+    control: {
+      type: "select",
+    },
+  },
+};