Skip to content

Commit f6b788c

Browse files
committed
🚀 base playground
1 parent 9e66db8 commit f6b788c

File tree

7 files changed

+252
-28
lines changed

7 files changed

+252
-28
lines changed

Diff for: README.md

+2-2
Original file line numberDiff line numberDiff line change
@@ -15,12 +15,12 @@ npm install --save react-code-playground
1515
```jsx
1616
import React, { Component } from 'react'
1717

18-
import MyComponent from 'react-code-playground'
18+
import CodePlayground from 'react-code-playground'
1919
import 'react-code-playground/dist/index.css'
2020

2121
class Example extends Component {
2222
render() {
23-
return <MyComponent />
23+
return <CodePlayground />
2424
}
2525
}
2626
```

Diff for: example/src/App.js

+2-2
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,10 @@
11
import React from 'react'
22

3-
import { ExampleComponent } from 'react-code-playground'
3+
import { CodePlayground } from 'react-code-playground'
44
import 'react-code-playground/dist/index.css'
55

66
const App = () => {
7-
return <ExampleComponent text="Create React Library Example 😄" />
7+
return <CodePlayground />
88
}
99

1010
export default App

Diff for: example/src/index.css

+48-9
Original file line numberDiff line numberDiff line change
@@ -1,14 +1,53 @@
1-
body {
1+
html {
2+
box-sizing: border-box;
3+
}
4+
5+
*, *::before, *::after {
6+
box-sizing: inherit;
27
margin: 0;
38
padding: 0;
4-
font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', 'Roboto', 'Oxygen',
5-
'Ubuntu', 'Cantarell', 'Fira Sans', 'Droid Sans', 'Helvetica Neue',
6-
sans-serif;
7-
-webkit-font-smoothing: antialiased;
8-
-moz-osx-font-smoothing: grayscale;
99
}
1010

11-
code {
12-
font-family: source-code-pro, Menlo, Monaco, Consolas, 'Courier New',
13-
monospace;
11+
.playground {
12+
position: fixed;
13+
top: 0;
14+
bottom: 0;
15+
left: 0;
16+
width: 600px;
17+
background-color: #1E1E2C;
18+
}
19+
20+
.code-editor {
21+
height: 33.33%;
22+
overflow: hidden;
23+
position: relative;
24+
}
25+
26+
.editor-header {
27+
height: 30px;
28+
content: attr(title);
29+
display: flex;
30+
align-items: center;
31+
padding-left: 20px;
32+
font-size: 18px;
33+
color: #fafafa;
1434
}
35+
36+
.react-codemirror2 {
37+
max-height: calc(100% - 30px);
38+
overflow: auto;
39+
}
40+
41+
.result {
42+
position: fixed;
43+
top: 0;
44+
right: 0;
45+
bottom: 0;
46+
left: 600px;
47+
overflow: hidden;
48+
}
49+
50+
.iframe {
51+
width: 100%;
52+
height: 100%;
53+
}

Diff for: package-lock.json

+39-2
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

Diff for: package.json

+8-1
Original file line numberDiff line numberDiff line change
@@ -49,5 +49,12 @@
4949
},
5050
"files": [
5151
"dist"
52-
]
52+
],
53+
"dependencies": {
54+
"axios": "^0.21.1",
55+
"codemirror": "^5.59.0",
56+
"pusher-js": "^7.0.2",
57+
"pushid": "^1.0.0",
58+
"react-codemirror2": "^7.2.1"
59+
}
5360
}

Diff for: src/index.js

+153-3
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,156 @@
1-
import React from 'react'
1+
import React, { Component } from 'react'
22
import styles from './styles.module.css'
3+
import { Controlled as CodeMirror } from 'react-codemirror2';
4+
import Pusher from 'pusher-js';
5+
import pushid from 'pushid';
6+
import axios from 'axios';
37

4-
export const ExampleComponent = ({ text }) => {
5-
return <div className={styles.test}>Example Component: {text}</div>
8+
import 'codemirror/lib/codemirror.css';
9+
import 'codemirror/theme/material.css';
10+
11+
import 'codemirror/mode/htmlmixed/htmlmixed';
12+
import 'codemirror/mode/css/css';
13+
import 'codemirror/mode/javascript/javascript';
14+
15+
export class CodePlayground extends Component {
16+
constructor() {
17+
super();
18+
this.state = {
19+
id: '',
20+
html: '',
21+
css: '',
22+
js: '',
23+
};
24+
25+
this.pusher = new Pusher("68c737789ee47b308987", {
26+
cluster: "us3",
27+
forceTLS: true
28+
});
29+
30+
this.channel = this.pusher.subscribe("editor");
31+
}
32+
33+
componentDidUpdate() {
34+
this.runCode();
35+
}
36+
37+
componentDidMount() {
38+
this.setState({
39+
id: pushid(),
40+
});
41+
42+
this.channel.bind("code-update", data => {
43+
const { id } = this.state;
44+
if (data.id === id) return;
45+
46+
this.setState({
47+
html: data.html,
48+
css: data.css,
49+
js: data.js,
50+
});
51+
});
52+
}
53+
54+
syncUpdates = () => {
55+
const data = { ...this.state };
56+
console.log(data);
57+
58+
axios
59+
.post("http://localhost:5000/update-editor", data)
60+
.catch(console.error);
61+
};
62+
63+
runCode = () => {
64+
const { html, css, js } = this.state;
65+
66+
const iframe = this.refs.iframe;
67+
const document = iframe.contentDocument;
68+
const documentContents = `
69+
<!DOCTYPE html>
70+
<html lang="en">
71+
<head>
72+
<meta charset="UTF-8">
73+
<meta name="viewport" content="width=device-width, initial-scale=1.0">
74+
<meta http-equiv="X-UA-Compatible" content="ie=edge">
75+
<title>Document</title>
76+
<style>
77+
${css} !important
78+
</style>
79+
</head>
80+
<body>
81+
${html}
82+
83+
<script type="text/javascript">
84+
${js}
85+
</script>
86+
</body>
87+
</html>
88+
`;
89+
90+
console.log(document);
91+
92+
document.open();
93+
document.write(documentContents);
94+
document.close();
95+
};
96+
97+
render(){
98+
const { html, js, css } = this.state;
99+
const codeMirrorOptions = {
100+
theme: 'material',
101+
lineNumbers: true,
102+
scrollbarStyle: null,
103+
lineWrapping: true,
104+
};
105+
106+
107+
return (
108+
<div className="playground-container">
109+
<section className="playground">
110+
<div className="code-editor html-code">
111+
<div className="editor-header">HTML</div>
112+
<CodeMirror
113+
value={html}
114+
options={{
115+
mode: "htmlmixed",
116+
...codeMirrorOptions
117+
}}
118+
onBeforeChange={(editor, data, html) => {
119+
this.setState({ html }, () => this.syncUpdates()); // update this line
120+
}}
121+
/>
122+
</div>
123+
<div className="code-editor css-code">
124+
<div className="editor-header">CSS</div>
125+
<CodeMirror
126+
value={css}
127+
options={{
128+
mode: "css",
129+
...codeMirrorOptions
130+
}}
131+
onBeforeChange={(editor, data, css) => {
132+
this.setState({ css }, () => this.syncUpdates()); // update this line
133+
}}
134+
/>
135+
</div>
136+
<div className="code-editor js-code">
137+
<div className="editor-header">JavaScript</div>
138+
<CodeMirror
139+
value={js}
140+
options={{
141+
mode: "javascript",
142+
...codeMirrorOptions
143+
}}
144+
onBeforeChange={(editor, data, js) => {
145+
this.setState({ js }, () => this.syncUpdates()); // update this line
146+
}}
147+
/>
148+
</div>
149+
</section>
150+
<section className="result">
151+
<iframe title="result" className="iframe" ref="iframe" />
152+
</section>
153+
</div>
154+
)
155+
}
6156
}

Diff for: src/styles.module.css

-9
Original file line numberDiff line numberDiff line change
@@ -1,9 +0,0 @@
1-
/* add css module styles here (optional) */
2-
3-
.test {
4-
margin: 2em;
5-
padding: 0.5em;
6-
border: 2px solid #000;
7-
font-size: 2em;
8-
text-align: center;
9-
}

0 commit comments

Comments
 (0)