@chayns-components/typewriter 5.0.0-beta.53 → 5.0.0-beta.55
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +45 -0
- package/lib/components/typewriter/Typewriter.d.ts +2 -2
- package/lib/components/typewriter/Typewriter.js +7 -5
- package/lib/components/typewriter/Typewriter.js.map +1 -1
- package/lib/components/typewriter/utils.js +16 -8
- package/lib/components/typewriter/utils.js.map +1 -1
- package/package.json +3 -3
package/README.md
ADDED
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
<div align="center">
|
|
2
|
+
<h1>
|
|
3
|
+
<img src="https://raw.githubusercontent.com/TobitSoftware/chayns-components/master/assets/logo.png" width="600px" alt="chayns-components" />
|
|
4
|
+
</h1>
|
|
5
|
+
<p>A set of beautiful React components for developing your own applications with chayns.</p>
|
|
6
|
+
<div>
|
|
7
|
+
<img src="https://img.shields.io/npm/dm/@chayns-components/typewriter.svg?style=for-the-badge" alt="" />
|
|
8
|
+
<img src="https://img.shields.io/npm/v/@chayns-components/typewriter?style=for-the-badge" alt="" />
|
|
9
|
+
<img src="https://img.shields.io/github/license/TobitSoftware/chayns-components?style=for-the-badge" alt="" />
|
|
10
|
+
<img src="https://img.shields.io/github/contributors/TobitSoftware/chayns-components?style=for-the-badge" alt="" />
|
|
11
|
+
</div>
|
|
12
|
+
</div>
|
|
13
|
+
|
|
14
|
+
---
|
|
15
|
+
|
|
16
|
+
## Installation
|
|
17
|
+
|
|
18
|
+
First you need to install the typewriter part of the chayns-components.
|
|
19
|
+
|
|
20
|
+
```bash
|
|
21
|
+
# NPM
|
|
22
|
+
npm install @chayns-components/typewriter
|
|
23
|
+
|
|
24
|
+
# Yarn
|
|
25
|
+
yarn add @chayns-components/typewriter
|
|
26
|
+
```
|
|
27
|
+
|
|
28
|
+
> **Information:** Since the components have now been implemented with the styled-components
|
|
29
|
+
> library, the styles are delivered directly with the components. There is no need to load an extra
|
|
30
|
+
> stylesheet anymore.
|
|
31
|
+
|
|
32
|
+
## Usage
|
|
33
|
+
|
|
34
|
+
You can use the components in your project as in the following example.
|
|
35
|
+
|
|
36
|
+
```typescript jsx
|
|
37
|
+
import { Typewriter } from '@chayns-components/typewriter';
|
|
38
|
+
|
|
39
|
+
<Typewriter>
|
|
40
|
+
Lorem ipsum dolor sit amet, consetetur sadipscing elitr, sed diam nonumy eirmod tempor invidunt
|
|
41
|
+
ut labore et dolore magna aliquyam erat, sed diam voluptua. At vero eos et accusam et justo duo
|
|
42
|
+
dolores et ea rebum. Stet clita kasd gubergren, no sea takimata sanctus est. Lorem ipsum dolor
|
|
43
|
+
sit amet.
|
|
44
|
+
</Typewriter>;
|
|
45
|
+
```
|
|
@@ -1,9 +1,9 @@
|
|
|
1
|
-
import { FC } from 'react';
|
|
1
|
+
import { FC, ReactElement } from 'react';
|
|
2
2
|
export type TypewriterProps = {
|
|
3
3
|
/**
|
|
4
4
|
* The text to type
|
|
5
5
|
*/
|
|
6
|
-
children: string;
|
|
6
|
+
children: ReactElement | string;
|
|
7
7
|
};
|
|
8
8
|
declare const Typewriter: FC<TypewriterProps>;
|
|
9
9
|
export default Typewriter;
|
|
@@ -5,6 +5,7 @@ Object.defineProperty(exports, "__esModule", {
|
|
|
5
5
|
});
|
|
6
6
|
exports.default = void 0;
|
|
7
7
|
var _react = _interopRequireWildcard(require("react"));
|
|
8
|
+
var _server = require("react-dom/server");
|
|
8
9
|
var _Typewriter = require("./Typewriter.styles");
|
|
9
10
|
var _utils = require("./utils");
|
|
10
11
|
function _getRequireWildcardCache(nodeInterop) { if (typeof WeakMap !== "function") return null; var cacheBabelInterop = new WeakMap(); var cacheNodeInterop = new WeakMap(); return (_getRequireWildcardCache = function (nodeInterop) { return nodeInterop ? cacheNodeInterop : cacheBabelInterop; })(nodeInterop); }
|
|
@@ -15,20 +16,21 @@ const Typewriter = _ref => {
|
|
|
15
16
|
} = _ref;
|
|
16
17
|
const [shownCharCount, setShownCharCount] = (0, _react.useState)(0);
|
|
17
18
|
const [shouldStopAnimation, setShouldStopAnimation] = (0, _react.useState)(false);
|
|
18
|
-
const
|
|
19
|
+
const textContent = /*#__PURE__*/_react.default.isValidElement(children) ? (0, _server.renderToString)(children) : children;
|
|
20
|
+
const isAnimatingText = shownCharCount !== textContent.length;
|
|
19
21
|
const handleClick = (0, _react.useCallback)(() => {
|
|
20
22
|
setShouldStopAnimation(true);
|
|
21
23
|
}, []);
|
|
22
24
|
(0, _react.useEffect)(() => {
|
|
23
25
|
let interval;
|
|
24
26
|
if (shouldStopAnimation) {
|
|
25
|
-
setShownCharCount(
|
|
27
|
+
setShownCharCount(textContent.length);
|
|
26
28
|
} else {
|
|
27
29
|
setShownCharCount(0);
|
|
28
30
|
interval = window.setInterval(() => {
|
|
29
31
|
setShownCharCount(prevState => {
|
|
30
32
|
const nextState = prevState + 1;
|
|
31
|
-
if (nextState ===
|
|
33
|
+
if (nextState === textContent.length) {
|
|
32
34
|
window.clearInterval(interval);
|
|
33
35
|
}
|
|
34
36
|
return nextState;
|
|
@@ -38,8 +40,8 @@ const Typewriter = _ref => {
|
|
|
38
40
|
return () => {
|
|
39
41
|
window.clearInterval(interval);
|
|
40
42
|
};
|
|
41
|
-
}, [
|
|
42
|
-
const shownText = (0, _react.useMemo)(() => (0, _utils.getSubTextFromHTML)(
|
|
43
|
+
}, [shouldStopAnimation, textContent.length]);
|
|
44
|
+
const shownText = (0, _react.useMemo)(() => (0, _utils.getSubTextFromHTML)(textContent, shownCharCount), [shownCharCount, textContent]);
|
|
43
45
|
return /*#__PURE__*/_react.default.createElement(_Typewriter.StyledTypewriter, {
|
|
44
46
|
onClick: handleClick
|
|
45
47
|
}, /*#__PURE__*/_react.default.createElement(_Typewriter.StyledTypewriterText, {
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"Typewriter.js","names":["Typewriter","children","shownCharCount","setShownCharCount","useState","shouldStopAnimation","setShouldStopAnimation","isAnimatingText","length","handleClick","useCallback","useEffect","interval","window","setInterval","prevState","nextState","clearInterval","shownText","useMemo","getSubTextFromHTML","__html","displayName"],"sources":["../../../src/components/typewriter/Typewriter.tsx"],"sourcesContent":["import React, { FC, useCallback, useEffect, useMemo, useState } from 'react';\nimport {\n StyledTypewriter,\n StyledTypewriterPseudoText,\n StyledTypewriterText,\n} from './Typewriter.styles';\nimport { getSubTextFromHTML } from './utils';\n\nexport type TypewriterProps = {\n /**\n * The text to type\n */\n children: string;\n};\n\nconst Typewriter: FC<TypewriterProps> = ({ children }) => {\n const [shownCharCount, setShownCharCount] = useState(0);\n const [shouldStopAnimation, setShouldStopAnimation] = useState(false);\n\n const isAnimatingText = shownCharCount !==
|
|
1
|
+
{"version":3,"file":"Typewriter.js","names":["Typewriter","children","shownCharCount","setShownCharCount","useState","shouldStopAnimation","setShouldStopAnimation","textContent","React","isValidElement","renderToString","isAnimatingText","length","handleClick","useCallback","useEffect","interval","window","setInterval","prevState","nextState","clearInterval","shownText","useMemo","getSubTextFromHTML","__html","displayName"],"sources":["../../../src/components/typewriter/Typewriter.tsx"],"sourcesContent":["import React, { FC, ReactElement, useCallback, useEffect, useMemo, useState } from 'react';\nimport { renderToString } from 'react-dom/server';\nimport {\n StyledTypewriter,\n StyledTypewriterPseudoText,\n StyledTypewriterText,\n} from './Typewriter.styles';\nimport { getSubTextFromHTML } from './utils';\n\nexport type TypewriterProps = {\n /**\n * The text to type\n */\n children: ReactElement | string;\n};\n\nconst Typewriter: FC<TypewriterProps> = ({ children }) => {\n const [shownCharCount, setShownCharCount] = useState(0);\n const [shouldStopAnimation, setShouldStopAnimation] = useState(false);\n\n const textContent = React.isValidElement(children) ? renderToString(children) : children;\n\n const isAnimatingText = shownCharCount !== textContent.length;\n\n const handleClick = useCallback(() => {\n setShouldStopAnimation(true);\n }, []);\n\n useEffect(() => {\n let interval: number | undefined;\n\n if (shouldStopAnimation) {\n setShownCharCount(textContent.length);\n } else {\n setShownCharCount(0);\n\n interval = window.setInterval(() => {\n setShownCharCount((prevState) => {\n const nextState = prevState + 1;\n\n if (nextState === textContent.length) {\n window.clearInterval(interval);\n }\n\n return nextState;\n });\n }, 35);\n }\n\n return () => {\n window.clearInterval(interval);\n };\n }, [shouldStopAnimation, textContent.length]);\n\n const shownText = useMemo(\n () => getSubTextFromHTML(textContent, shownCharCount),\n [shownCharCount, textContent]\n );\n\n return (\n <StyledTypewriter onClick={handleClick}>\n <StyledTypewriterText\n dangerouslySetInnerHTML={{ __html: shownText }}\n isAnimatingText={isAnimatingText}\n />\n {isAnimatingText && <StyledTypewriterPseudoText>{children}</StyledTypewriterPseudoText>}\n </StyledTypewriter>\n );\n};\n\nTypewriter.displayName = 'Typewriter';\n\nexport default Typewriter;\n"],"mappings":";;;;;;AAAA;AACA;AACA;AAKA;AAA6C;AAAA;AAS7C,MAAMA,UAA+B,GAAG,QAAkB;EAAA,IAAjB;IAAEC;EAAS,CAAC;EACjD,MAAM,CAACC,cAAc,EAAEC,iBAAiB,CAAC,GAAG,IAAAC,eAAQ,EAAC,CAAC,CAAC;EACvD,MAAM,CAACC,mBAAmB,EAAEC,sBAAsB,CAAC,GAAG,IAAAF,eAAQ,EAAC,KAAK,CAAC;EAErE,MAAMG,WAAW,GAAG,aAAAC,cAAK,CAACC,cAAc,CAACR,QAAQ,CAAC,GAAG,IAAAS,sBAAc,EAACT,QAAQ,CAAC,GAAGA,QAAQ;EAExF,MAAMU,eAAe,GAAGT,cAAc,KAAKK,WAAW,CAACK,MAAM;EAE7D,MAAMC,WAAW,GAAG,IAAAC,kBAAW,EAAC,MAAM;IAClCR,sBAAsB,CAAC,IAAI,CAAC;EAChC,CAAC,EAAE,EAAE,CAAC;EAEN,IAAAS,gBAAS,EAAC,MAAM;IACZ,IAAIC,QAA4B;IAEhC,IAAIX,mBAAmB,EAAE;MACrBF,iBAAiB,CAACI,WAAW,CAACK,MAAM,CAAC;IACzC,CAAC,MAAM;MACHT,iBAAiB,CAAC,CAAC,CAAC;MAEpBa,QAAQ,GAAGC,MAAM,CAACC,WAAW,CAAC,MAAM;QAChCf,iBAAiB,CAAEgB,SAAS,IAAK;UAC7B,MAAMC,SAAS,GAAGD,SAAS,GAAG,CAAC;UAE/B,IAAIC,SAAS,KAAKb,WAAW,CAACK,MAAM,EAAE;YAClCK,MAAM,CAACI,aAAa,CAACL,QAAQ,CAAC;UAClC;UAEA,OAAOI,SAAS;QACpB,CAAC,CAAC;MACN,CAAC,EAAE,EAAE,CAAC;IACV;IAEA,OAAO,MAAM;MACTH,MAAM,CAACI,aAAa,CAACL,QAAQ,CAAC;IAClC,CAAC;EACL,CAAC,EAAE,CAACX,mBAAmB,EAAEE,WAAW,CAACK,MAAM,CAAC,CAAC;EAE7C,MAAMU,SAAS,GAAG,IAAAC,cAAO,EACrB,MAAM,IAAAC,yBAAkB,EAACjB,WAAW,EAAEL,cAAc,CAAC,EACrD,CAACA,cAAc,EAAEK,WAAW,CAAC,CAChC;EAED,oBACI,6BAAC,4BAAgB;IAAC,OAAO,EAAEM;EAAY,gBACnC,6BAAC,gCAAoB;IACjB,uBAAuB,EAAE;MAAEY,MAAM,EAAEH;IAAU,CAAE;IAC/C,eAAe,EAAEX;EAAgB,EACnC,EACDA,eAAe,iBAAI,6BAAC,sCAA0B,QAAEV,QAAQ,CAA8B,CACxE;AAE3B,CAAC;AAEDD,UAAU,CAAC0B,WAAW,GAAG,YAAY;AAAC,eAEvB1B,UAAU;AAAA"}
|
|
@@ -19,9 +19,9 @@ const getSubTextFromHTML = (html, length) => {
|
|
|
19
19
|
div.innerHTML = html;
|
|
20
20
|
let text = '';
|
|
21
21
|
let currLength = 0;
|
|
22
|
-
const traverse =
|
|
23
|
-
if (
|
|
24
|
-
const nodeText =
|
|
22
|
+
const traverse = element => {
|
|
23
|
+
if (element.nodeType === 3 && typeof element.textContent === 'string') {
|
|
24
|
+
const nodeText = element.textContent;
|
|
25
25
|
if (currLength + nodeText.length <= length) {
|
|
26
26
|
text += nodeText;
|
|
27
27
|
currLength += nodeText.length;
|
|
@@ -29,11 +29,19 @@ const getSubTextFromHTML = (html, length) => {
|
|
|
29
29
|
text += nodeText.substring(0, length - currLength);
|
|
30
30
|
return false;
|
|
31
31
|
}
|
|
32
|
-
} else if (
|
|
33
|
-
const nodeName =
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
32
|
+
} else if (element.nodeType === 1) {
|
|
33
|
+
const nodeName = element.nodeName.toLowerCase();
|
|
34
|
+
let attributes = '';
|
|
35
|
+
|
|
36
|
+
// @ts-expect-error: Type is correct here
|
|
37
|
+
// eslint-disable-next-line no-restricted-syntax
|
|
38
|
+
for (const attribute of element.attributes) {
|
|
39
|
+
// eslint-disable-next-line @typescript-eslint/no-unsafe-member-access,@typescript-eslint/restrict-template-expressions
|
|
40
|
+
attributes += ` ${attribute.name}="${attribute.value}"`;
|
|
41
|
+
}
|
|
42
|
+
text += `<${nodeName}${attributes}>`;
|
|
43
|
+
for (let i = 0; i < element.childNodes.length; i++) {
|
|
44
|
+
const childNode = element.childNodes[i];
|
|
37
45
|
if (childNode && !traverse(childNode)) {
|
|
38
46
|
return false;
|
|
39
47
|
}
|
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"utils.js","names":["getSubTextFromHTML","html","length","div","document","createElement","innerHTML","text","currLength","traverse","
|
|
1
|
+
{"version":3,"file":"utils.js","names":["getSubTextFromHTML","html","length","div","document","createElement","innerHTML","text","currLength","traverse","element","nodeType","textContent","nodeText","substring","nodeName","toLowerCase","attributes","attribute","name","value","i","childNodes","childNode"],"sources":["../../../src/components/typewriter/utils.ts"],"sourcesContent":["/**\n * This function extracts a part of the text from an HTML text. The HTML elements themselves are\n * returned in the result. In addition, the function ensures that the closing tag of the Bold HTML\n * element is also returned for text that is cut off in the middle of a Bold element, for example.\n *\n * @param html - The text from which a part should be taken\n * @param length - The length of the text to be extracted\n *\n * @return string - The text part with the specified length - additionally the HTML elements are added\n */\nexport const getSubTextFromHTML = (html: string, length: number): string => {\n const div = document.createElement('div');\n\n div.innerHTML = html;\n\n let text = '';\n let currLength = 0;\n\n const traverse = (element: Element): boolean => {\n if (element.nodeType === 3 && typeof element.textContent === 'string') {\n const nodeText = element.textContent;\n\n if (currLength + nodeText.length <= length) {\n text += nodeText;\n currLength += nodeText.length;\n } else {\n text += nodeText.substring(0, length - currLength);\n\n return false;\n }\n } else if (element.nodeType === 1) {\n const nodeName = element.nodeName.toLowerCase();\n\n let attributes = '';\n\n // @ts-expect-error: Type is correct here\n // eslint-disable-next-line no-restricted-syntax\n for (const attribute of element.attributes) {\n // eslint-disable-next-line @typescript-eslint/no-unsafe-member-access,@typescript-eslint/restrict-template-expressions\n attributes += ` ${attribute.name}=\"${attribute.value}\"`;\n }\n\n text += `<${nodeName}${attributes}>`;\n\n for (let i = 0; i < element.childNodes.length; i++) {\n const childNode = element.childNodes[i];\n\n if (childNode && !traverse(childNode as Element)) {\n return false;\n }\n }\n\n text += `</${nodeName}>`;\n }\n\n return true;\n };\n\n for (let i = 0; i < div.childNodes.length; i++) {\n const childNode = div.childNodes[i];\n\n if (childNode && !traverse(childNode as Element)) {\n return text;\n }\n }\n\n return text;\n};\n"],"mappings":";;;;;;AAAA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACA;AACO,MAAMA,kBAAkB,GAAG,CAACC,IAAY,EAAEC,MAAc,KAAa;EACxE,MAAMC,GAAG,GAAGC,QAAQ,CAACC,aAAa,CAAC,KAAK,CAAC;EAEzCF,GAAG,CAACG,SAAS,GAAGL,IAAI;EAEpB,IAAIM,IAAI,GAAG,EAAE;EACb,IAAIC,UAAU,GAAG,CAAC;EAElB,MAAMC,QAAQ,GAAIC,OAAgB,IAAc;IAC5C,IAAIA,OAAO,CAACC,QAAQ,KAAK,CAAC,IAAI,OAAOD,OAAO,CAACE,WAAW,KAAK,QAAQ,EAAE;MACnE,MAAMC,QAAQ,GAAGH,OAAO,CAACE,WAAW;MAEpC,IAAIJ,UAAU,GAAGK,QAAQ,CAACX,MAAM,IAAIA,MAAM,EAAE;QACxCK,IAAI,IAAIM,QAAQ;QAChBL,UAAU,IAAIK,QAAQ,CAACX,MAAM;MACjC,CAAC,MAAM;QACHK,IAAI,IAAIM,QAAQ,CAACC,SAAS,CAAC,CAAC,EAAEZ,MAAM,GAAGM,UAAU,CAAC;QAElD,OAAO,KAAK;MAChB;IACJ,CAAC,MAAM,IAAIE,OAAO,CAACC,QAAQ,KAAK,CAAC,EAAE;MAC/B,MAAMI,QAAQ,GAAGL,OAAO,CAACK,QAAQ,CAACC,WAAW,EAAE;MAE/C,IAAIC,UAAU,GAAG,EAAE;;MAEnB;MACA;MACA,KAAK,MAAMC,SAAS,IAAIR,OAAO,CAACO,UAAU,EAAE;QACxC;QACAA,UAAU,IAAK,IAAGC,SAAS,CAACC,IAAK,KAAID,SAAS,CAACE,KAAM,GAAE;MAC3D;MAEAb,IAAI,IAAK,IAAGQ,QAAS,GAAEE,UAAW,GAAE;MAEpC,KAAK,IAAII,CAAC,GAAG,CAAC,EAAEA,CAAC,GAAGX,OAAO,CAACY,UAAU,CAACpB,MAAM,EAAEmB,CAAC,EAAE,EAAE;QAChD,MAAME,SAAS,GAAGb,OAAO,CAACY,UAAU,CAACD,CAAC,CAAC;QAEvC,IAAIE,SAAS,IAAI,CAACd,QAAQ,CAACc,SAAS,CAAY,EAAE;UAC9C,OAAO,KAAK;QAChB;MACJ;MAEAhB,IAAI,IAAK,KAAIQ,QAAS,GAAE;IAC5B;IAEA,OAAO,IAAI;EACf,CAAC;EAED,KAAK,IAAIM,CAAC,GAAG,CAAC,EAAEA,CAAC,GAAGlB,GAAG,CAACmB,UAAU,CAACpB,MAAM,EAAEmB,CAAC,EAAE,EAAE;IAC5C,MAAME,SAAS,GAAGpB,GAAG,CAACmB,UAAU,CAACD,CAAC,CAAC;IAEnC,IAAIE,SAAS,IAAI,CAACd,QAAQ,CAACc,SAAS,CAAY,EAAE;MAC9C,OAAOhB,IAAI;IACf;EACJ;EAEA,OAAOA,IAAI;AACf,CAAC;AAAC"}
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@chayns-components/typewriter",
|
|
3
|
-
"version": "5.0.0-beta.
|
|
3
|
+
"version": "5.0.0-beta.55",
|
|
4
4
|
"description": "A set of beautiful React components for developing your own applications with chayns.",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"chayns",
|
|
@@ -49,7 +49,7 @@
|
|
|
49
49
|
"typescript": "^4.9.5"
|
|
50
50
|
},
|
|
51
51
|
"dependencies": {
|
|
52
|
-
"@chayns-components/core": "^5.0.0-beta.
|
|
52
|
+
"@chayns-components/core": "^5.0.0-beta.54",
|
|
53
53
|
"@chayns/colors": "^2.0.0",
|
|
54
54
|
"clsx": "^1.2.1",
|
|
55
55
|
"framer-motion": "^6.5.1",
|
|
@@ -63,5 +63,5 @@
|
|
|
63
63
|
"publishConfig": {
|
|
64
64
|
"access": "public"
|
|
65
65
|
},
|
|
66
|
-
"gitHead": "
|
|
66
|
+
"gitHead": "abd83d36213c4255cf265e0890deb154a5f2229c"
|
|
67
67
|
}
|