kotii-markdown-render 1.0.0-beta.1.0

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/index.js ADDED
@@ -0,0 +1,2 @@
1
+ import { MarkdownRender } from "./src/index.js";
2
+ export { MarkdownRender };
package/package.json ADDED
@@ -0,0 +1,63 @@
1
+ {
2
+ "name": "kotii-markdown-render",
3
+ "version": "1.0.0-beta.1.0",
4
+ "description": "is the **React renderer** used by Kotii after Markdown is parsed and transformed",
5
+ "author": "ntsakosurprise <mashelesepru@gmail.com>",
6
+ "homepage": "https://github.com/kotii",
7
+ "license": "MIT",
8
+ "type": "module",
9
+ "exports": {
10
+ ".": {
11
+ "import": "./dist/index.mjs",
12
+ "require": "./dist/index.cjs",
13
+ "default": "./dist/index.cjs"
14
+ }
15
+ },
16
+ "directories": {
17
+ "lib": "dist",
18
+ "test": "__tests__"
19
+ },
20
+ "files": [
21
+ "dist/",
22
+ "index.js",
23
+ "src/",
24
+ "README.md",
25
+ "package.json"
26
+ ],
27
+ "publishConfig": {
28
+ "access": "public"
29
+ },
30
+ "devDependencies": {
31
+ "@babel/core": "^7.17.5",
32
+ "@babel/preset-env": "^7.16.11",
33
+ "@babel/preset-react": "^7.16.7",
34
+ "@testing-library/jest-dom": "^5.17.0",
35
+ "@testing-library/react": "^14.0.0",
36
+ "@testing-library/user-event": "^14.4.3",
37
+ "@types/jest": "^29.5.3",
38
+ "@types/styled-components": "^5.1.26",
39
+ "babel-cli": "^6.26.0",
40
+ "babel-loader": "^8.2.3",
41
+ "cross-env": "^7.0.3",
42
+ "jest": "^29.5.0",
43
+ "jest-environment-jsdom": "^29.6.1",
44
+ "webpack": "^5.69.1",
45
+ "webpack-cli": "^4.9.2",
46
+ "webpack-dev-server": "^4.7.4",
47
+ "webpack-node-externals": "^3.0.0"
48
+ },
49
+ "peerDependencies": {
50
+ "kotii-languages": "1.0.0-beta.3.0",
51
+ "react": "^18.2.0",
52
+ "react-dom": "^18.2.0"
53
+ },
54
+ "dependencies": {
55
+ "html-react-parser": "^4.0.0",
56
+ "kotii-styled": "^1.0.0-beta.2.0",
57
+ "prop-types": "^15.7.2"
58
+ },
59
+ "scripts": {
60
+ "compile:esm": "cross-env NODE_ENV=development NODE_MODE=esm webpack",
61
+ "compile:cjs": "cross-env NODE_ENV=development NODE_MODE=cjs webpack"
62
+ }
63
+ }
@@ -0,0 +1,12 @@
1
+ import PropTypes from "prop-types";
2
+ import React from "react";
3
+
4
+ const MarkdownAd = ({ children }) => {
5
+ return <div>{children}</div>;
6
+ };
7
+
8
+ MarkdownAd.propTypes = {
9
+ children: PropTypes.element,
10
+ };
11
+
12
+ export default MarkdownAd;
@@ -0,0 +1,7 @@
1
+ import React from "react";
2
+
3
+ const MarkdownDemo = () => {
4
+ return <></>;
5
+ };
6
+
7
+ export default MarkdownDemo;
@@ -0,0 +1,24 @@
1
+ /* eslint-disable react/react-in-jsx-scope */
2
+ /* eslint-disable react/prop-types */
3
+ import parse from "html-react-parser";
4
+ import PropTypes from "prop-types";
5
+ import { StyledMarkdown } from "../StyledMarkdown/index.jsx";
6
+
7
+ const MarkdownElement = ({ children, setCustom = false, htmlString }) => {
8
+ if (setCustom) return <>{children}</>;
9
+ return (
10
+ <>
11
+ <StyledMarkdown>
12
+ {children ? children : <div>{parse(htmlString)}</div>}
13
+ </StyledMarkdown>
14
+ </>
15
+ );
16
+ };
17
+
18
+ MarkdownElement.propTypes = {
19
+ children: PropTypes.element,
20
+ setCustom: PropTypes.bool,
21
+ htmlString: PropTypes.string,
22
+ };
23
+
24
+ export default MarkdownElement;
@@ -0,0 +1,110 @@
1
+ /* eslint-disable no-unused-vars */
2
+ /* eslint-disable react/prop-types */
3
+ // eslint-disable unused-imports/no-unused-imports */
4
+ import { LanguageSwitcher, useLanguage } from "kotii-languages";
5
+ import { ThemeSwitcher, useKotiiTheme } from "kotii-theme";
6
+ import { Button } from "kotii-ui";
7
+
8
+ import PropTypes from "prop-types";
9
+ import styled from "styled-components";
10
+
11
+ const Header = styled("header")((theme) => {
12
+ return {
13
+ width: "100%",
14
+ position: "fixed",
15
+ height: "100px",
16
+ backgroundColor: theme.backgroundColor,
17
+ top: 0,
18
+ zIndex: 2,
19
+ display: "flex",
20
+ flexDirection: "row",
21
+ };
22
+ });
23
+ const List = styled("ul")(() => ({
24
+ position: "relative",
25
+ display: "flex",
26
+ padding: "2px",
27
+ flexDirection: "row",
28
+ width: "95%",
29
+ paddingLeft: "5px",
30
+
31
+ "& ul": {
32
+ backgroundColor: "green",
33
+ position: "relative",
34
+ paddingLeft: "5px",
35
+ "& ul": {
36
+ backgroundColor: "yellow",
37
+ },
38
+ },
39
+ }));
40
+
41
+ const ListItem = styled("li")(() => ({
42
+ display: "flex",
43
+ position: "relative",
44
+ padding: "2px",
45
+ marginBottom: "2px",
46
+ // "&.active": {
47
+ // ".nav__item-icon": {
48
+ // marginTop: "-26px",
49
+ // boxShadow: "0px 0px 16px 0px #4444",
50
+ // },
51
+ // ".nav__item-text": { transform: "scale(1)" },
52
+ //},
53
+ }));
54
+
55
+ const ListLink = styled("a")(() => ({
56
+ display: "block",
57
+ // flexDirection: "column",
58
+ alignItems: "center",
59
+ color: "#2f3046",
60
+ textDecoration: "none",
61
+ }));
62
+
63
+ const renderItems = (items) => {
64
+ return items.map((ite, i) => {
65
+ return (
66
+ <ListItem key={i}>
67
+ <ListLink href={`${ite.text}`}>{ite.text}</ListLink>
68
+ </ListItem>
69
+ );
70
+ });
71
+ };
72
+
73
+ const MarkdownHeader = () => {
74
+ const { get } = useLanguage();
75
+ const { theme, grommetTheme } = useKotiiTheme();
76
+ console.log("THE CURRENT THEME IN REACT-MODULES;", grommetTheme);
77
+ console.log("THEMEBACKGROUND;;;", theme.backgroundColor);
78
+ const listItems = [
79
+ {
80
+ text: `${get("navigation.home")}`,
81
+ },
82
+ {
83
+ text: `${get("navigation.about")}`,
84
+ },
85
+ {
86
+ text: `${get("navigation.contact")}`,
87
+ },
88
+ {
89
+ text: `${get("navigation.help")}`,
90
+ },
91
+ ];
92
+ return (
93
+ <Header>
94
+ <List>{renderItems(listItems)}</List>
95
+ <div style={{ width: "300px", display: "flex" }}>
96
+ <LanguageSwitcher />
97
+ <Button text="I'm a Kotii-ui-button" />
98
+ </div>
99
+ <div style={{ width: "300px", display: "flex" }}>
100
+ <ThemeSwitcher />
101
+ </div>
102
+ </Header>
103
+ );
104
+ };
105
+
106
+ MarkdownHeader.propTypes = {
107
+ toc: PropTypes.array,
108
+ };
109
+
110
+ export default MarkdownHeader;
@@ -0,0 +1,186 @@
1
+ /* eslint-disable no-unused-vars */
2
+ /* eslint-disable react/prop-types */
3
+ // eslint-disable unused-imports/no-unused-imports */
4
+ import { useLanguage } from "kotii-languages";
5
+ import PropTypes from "prop-types";
6
+ import React from "react";
7
+
8
+ import styled from "kotii-styled";
9
+ import MarkdownAd from "../MarkdownAd/index.jsx";
10
+ // import MarkdownHeader from "../MarkdownHeader/index.js";
11
+ import MarkdownVideo from "../MarkdownVideo/index.jsx";
12
+ import StandardComponent from "../StandardComponent/index.jsx";
13
+ import MarkdownElement from "../MarkdownElement/index.jsx";
14
+
15
+ const MarkdownRenderCanvas = styled("div")(() => ({
16
+ width: "100%",
17
+ display: "flex",
18
+ flexDirection: "column",
19
+ // overflow: "hidden",
20
+ }));
21
+
22
+ const MarkdownContentArea = styled("div")(() => ({
23
+ width: "100%",
24
+ display: "flex",
25
+ flexDirection: "row",
26
+ // top: "100px",
27
+ // position: "relative",
28
+ }));
29
+ const MainArea = styled("div")(() => ({
30
+ width: "60%",
31
+ order: 1,
32
+ }));
33
+ const TestDemo = () => {
34
+ return <div>I am the Demo</div>;
35
+ };
36
+
37
+ const getSetLanguageContent = (contents, setLanguage) => {
38
+ let content = [];
39
+
40
+ contents.forEach((element) => {
41
+ if (element.locale.toLowerCase() === setLanguage.toLowerCase())
42
+ content = element;
43
+ });
44
+
45
+ return content;
46
+ };
47
+
48
+ const getLanguagePosts = (routes, setLanguage) => {
49
+ let posts = [];
50
+
51
+ routes.forEach((element) => {
52
+ element.markdownData.forEach((languageItem) => {
53
+ if (languageItem.locale.toLowerCase() === setLanguage.toLowerCase()) {
54
+ posts.push({
55
+ ...languageItem.parsedMarkdown.metaDataKeys,
56
+ path: element.path,
57
+ });
58
+ }
59
+ });
60
+ });
61
+
62
+ return posts;
63
+ };
64
+
65
+ // const capitalizeFirstLetter = (text) => {
66
+ // console.log("The text Uppercasing;;;", text);
67
+ // return `${text.slice(0, 1).toUpperCase()}${text.slice(1)}`;
68
+ // };
69
+
70
+ const isHtmlString = (itemChecked) => {
71
+ if (typeof itemChecked === "string" && itemChecked.length) return true;
72
+ return false;
73
+ };
74
+ const getHtmlBody = (itemChecked) => {
75
+ if (typeof itemChecked === "string" && itemChecked.length) return itemChecked;
76
+ return null;
77
+ };
78
+
79
+ const markdownComponentType = (mkComponent, index, options) => {
80
+ const {
81
+ languagePosts: posts,
82
+ markdownComponents,
83
+ markdownHtmlBody: body,
84
+ post: currentPost,
85
+ } = options;
86
+ console.log("THE MARKDOWN COMPONENT", mkComponent, markdownComponents, posts);
87
+ const componentType = Object.keys(mkComponent)[0];
88
+ const currentComponent = Object.entries(markdownComponents).find(
89
+ ([key, value]) => {
90
+ if (value.pathID === mkComponent[componentType]) return value;
91
+ }
92
+ )[1];
93
+ const isServer = typeof window != "undefined" ? false : true;
94
+ console.log("THE CURRENT COMPONENT", currentComponent);
95
+ const ComponentInContext = currentComponent.component;
96
+ console.log("THE COMPONENT IN CONTEXT", ComponentInContext);
97
+
98
+ switch (componentType) {
99
+ case "demo":
100
+ return <TestDemo key={index} posts={posts} post={currentPost} />;
101
+ case "component":
102
+ return <ComponentInContext posts={posts} post={currentPost} />;
103
+ case "video":
104
+ return (
105
+ <MarkdownVideo key={index}>
106
+ <ComponentInContext posts={posts} post={currentPost} />
107
+ </MarkdownVideo>
108
+ );
109
+ case "ad":
110
+ return (
111
+ <MarkdownAd key={index}>
112
+ <ComponentInContext posts={posts} post={currentPost} />
113
+ </MarkdownAd>
114
+ );
115
+ default:
116
+ return null;
117
+ }
118
+ };
119
+
120
+ const MarkdownRender = ({
121
+ markdownData,
122
+ markdownComponents,
123
+ routes = null,
124
+ }) => {
125
+ console.log("MARKDOWN RENDER PROPS: docs", markdownData);
126
+ console.log("MARKDODWN RENDER PROPS: modules", markdownComponents);
127
+ const { language } = useLanguage();
128
+ const englishContent = getSetLanguageContent(markdownData, language);
129
+ const languagePosts = getLanguagePosts(routes, language);
130
+ console.log("THE ENGLISH CONTENT", englishContent);
131
+ const { fileName, parsedMarkdown } = englishContent;
132
+ const { html, toc, metaDataKeys } = parsedMarkdown;
133
+ const { useCustomRender = false } = metaDataKeys;
134
+ const markdownHtmlBody = getHtmlBody(html);
135
+ const componentsOptions = {
136
+ languagePosts,
137
+ markdownComponents,
138
+ markdownHtmlBody,
139
+ useCustomRender,
140
+ post: metaDataKeys,
141
+ };
142
+ console.log("THE PARSED MARKDOWN", parsedMarkdown);
143
+ console.log("Kotii-markdown set Language:::", language, React.lazy, toc);
144
+
145
+ // console.log("Filename;;;", fileName);
146
+ // console.log("html", html);
147
+ if (useCustomRender) {
148
+ return html.map((markdownHtmlItem, i) => {
149
+ if (!isHtmlString(markdownHtmlItem)) {
150
+ return markdownComponentType(markdownHtmlItem, i, componentsOptions);
151
+ }
152
+
153
+ return null;
154
+ });
155
+ }
156
+
157
+ return (
158
+ <MarkdownRenderCanvas>
159
+ {/* <MarkdownHeader /> */}
160
+
161
+ <MarkdownContentArea>
162
+ {/* <MarkdownSidebar /> */}
163
+ <MainArea>
164
+ {html.map((markdownHtmlItem, i) => {
165
+ if (isHtmlString(markdownHtmlItem))
166
+ return <MarkdownElement htmlString={markdownHtmlItem} key={i} />;
167
+ return markdownComponentType(
168
+ markdownHtmlItem,
169
+ markdownComponents,
170
+ i,
171
+ languagePosts
172
+ );
173
+ })}
174
+ </MainArea>
175
+ {/* <MarkdownTOC toc={toc} /> */}
176
+ </MarkdownContentArea>
177
+ </MarkdownRenderCanvas>
178
+ );
179
+ };
180
+
181
+ MarkdownRender.propTypes = {
182
+ markdownData: PropTypes.array.isRequired,
183
+ // markdownComponents: PropTypes.object.isRequired,
184
+ };
185
+
186
+ export default MarkdownRender;
@@ -0,0 +1,27 @@
1
+ import styled from "kotii-styled";
2
+ import PropTypes from "prop-types";
3
+
4
+ const Sidebar = styled("div")(() => {
5
+ return { width: "18%", order: -1, height: "100vh" };
6
+ });
7
+ const StickyContent = styled("section")(() => ({
8
+ position: "fixed",
9
+ top: "100px",
10
+ }));
11
+
12
+ const createTableOfContents = () => {
13
+ return (
14
+ <StickyContent>
15
+ <p>I AM THE P</p>
16
+ </StickyContent>
17
+ );
18
+ };
19
+ const MarkdownSidebar = ({ toc }) => {
20
+ return <Sidebar>{createTableOfContents(toc)}</Sidebar>;
21
+ };
22
+
23
+ MarkdownSidebar.propTypes = {
24
+ toc: PropTypes.array.isRequired,
25
+ };
26
+
27
+ export default MarkdownSidebar;
@@ -0,0 +1,98 @@
1
+ import styled from "kotii-styled";
2
+ import PropTypes from "prop-types";
3
+
4
+ const TableOfContents = styled("div")(() => {
5
+ return { width: "15%", order: 2, paddingLeft: "3%" };
6
+ });
7
+ const StickyContent = styled("section")(() => ({
8
+ position: "fixed",
9
+ top: "100px",
10
+ }));
11
+
12
+ const List = styled("ul")(() => ({
13
+ position: "relative",
14
+ padding: "2px",
15
+ flexDirection: "column",
16
+ width: "95%",
17
+ paddingLeft: "5px",
18
+ display: "block",
19
+ "& ul": {
20
+ backgroundColor: "green",
21
+ position: "relative",
22
+ paddingLeft: "5px",
23
+ "& ul": {
24
+ backgroundColor: "yellow",
25
+ },
26
+ },
27
+ }));
28
+
29
+ const ListItem = styled("li")(() => ({
30
+ display: "block",
31
+ position: "relative",
32
+ padding: "2px",
33
+ marginBottom: "2px",
34
+ // "&.active": {
35
+ // ".nav__item-icon": {
36
+ // marginTop: "-26px",
37
+ // boxShadow: "0px 0px 16px 0px #4444",
38
+ // },
39
+ // ".nav__item-text": { transform: "scale(1)" },
40
+ //},
41
+ }));
42
+
43
+ const ListLink = styled("a")(() => ({
44
+ display: "block",
45
+ flexDirection: "column",
46
+ alignItems: "center",
47
+ color: "#2f3046",
48
+ textDecoration: "none",
49
+ }));
50
+
51
+ // const ListIcon = styled("div")(() => ({
52
+ // display: "flex",
53
+ // alignItems: "center",
54
+ // justifyContent: "center",
55
+ // fontSize: "1.6em",
56
+ // backgroundColor: "#fff",
57
+ // borderRadius: "50%",
58
+ // height: "25px",
59
+ // width: "25px",
60
+ // transition: "margin-top 250ms ease-in-out, box-shadow 250ms ease-in-out",
61
+ // }));
62
+
63
+ // const ListText = styled("span")(() => ({
64
+ // position: "absolute",
65
+ // bottom: "0",
66
+ // transform: "scale(0)",
67
+ // transition: "transform 250ms ease-in-out",
68
+ // }));
69
+
70
+ const getLevelChild = (content) => {
71
+ // if (content.children) return getLevelChild(content);
72
+ return (
73
+ <List>
74
+ {content.map((it, ii) => {
75
+ return (
76
+ <ListItem key={ii}>
77
+ <ListLink href={`#${it.id}`}>{it.id}</ListLink>
78
+ {it.children && it.children.length > 0
79
+ ? getLevelChild(it.children)
80
+ : null}
81
+ </ListItem>
82
+ );
83
+ })}
84
+ </List>
85
+ );
86
+ };
87
+ const createTableOfContents = (toc) => {
88
+ return <StickyContent>{getLevelChild(toc)}</StickyContent>;
89
+ };
90
+ const MarkdownTOC = ({ toc }) => {
91
+ return <TableOfContents>{createTableOfContents(toc)}</TableOfContents>;
92
+ };
93
+
94
+ MarkdownTOC.propTypes = {
95
+ toc: PropTypes.array.isRequired,
96
+ };
97
+
98
+ export default MarkdownTOC;
@@ -0,0 +1,15 @@
1
+ import PropTypes from "prop-types";
2
+ import React from "react";
3
+
4
+ const MarkdownVideo = ({ children, isNotChildVideo = false }) => {
5
+ console.log("THE CHILDREN", children, isNotChildVideo);
6
+ if (isNotChildVideo) return <video>{children}</video>;
7
+ return <div>{children}</div>;
8
+ };
9
+
10
+ MarkdownVideo.propTypes = {
11
+ children: PropTypes.element,
12
+ isNotChildVideo: PropTypes.bool,
13
+ };
14
+
15
+ export default MarkdownVideo;
@@ -0,0 +1,18 @@
1
+ /* eslint-disable react/prop-types */
2
+ import styled from "kotii-styled";
3
+ import PropTtypes from "prop-types";
4
+ import React from "react";
5
+
6
+ const StyledStandardComponent = styled("div")(() => ({
7
+ width: "100%",
8
+ }));
9
+
10
+ const StandardComponent = ({ children }) => {
11
+ return <StyledStandardComponent>{children}</StyledStandardComponent>;
12
+ };
13
+
14
+ StandardComponent.propTypes = {
15
+ children: PropTtypes.element.isRequired,
16
+ };
17
+
18
+ export default StandardComponent;