Skip to content

Commit 2e2f70d

Browse files
committed
Add function components
- Add different component choices to backend engine that include both class and function components - Add Class to current Async and Component templates - AsynComponent.react.js -> AsyncClassComponent.react.js - Component.react.js -> ClassComponent.react.js - Add 2 additional function components templates. - Replace use_async boolean choice with component_type list choices
1 parent 994fb0a commit 2e2f70d

File tree

9 files changed

+143
-33
lines changed

9 files changed

+143
-33
lines changed

cookiecutter.json

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,12 @@
88
"author_email": "Enter your email (For package.json)",
99
"github_org": "",
1010
"description": "Project Description",
11-
"use_async": ["False", "True"],
11+
"component_type": [
12+
"Async with Class Component",
13+
"Async with Function Component",
14+
"Class Component",
15+
"Function Component"
16+
],
1217
"license": [
1318
"MIT License",
1419
"BSD License",

hooks/post_gen_project.py

Lines changed: 5 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -8,7 +8,7 @@
88

99
install_deps = '{{cookiecutter.install_dependencies}}'
1010
project_shortname = '{{cookiecutter.project_shortname}}'
11-
use_async = '{{cookiecutter.use_async}}'
11+
component_type = '{{cookiecutter.component_type}}'
1212

1313

1414
is_windows = sys.platform == 'win32'
@@ -41,11 +41,11 @@ def _execute_command(cmd):
4141
template_dir = os.path.join(os.getcwd(), 'cookiecutter_templates')
4242
shutil.rmtree(template_dir)
4343

44-
print("\n\n\nuse_async")
45-
print(use_async)
44+
print("\n\n\ncomponent_type")
45+
print(component_type)
4646
# If it doesn't use async, we can remove the fragments and lazyloader.js
47-
if use_async != "True":
48-
print('use_async is set to False, your component will not be lazy loaded and fragments will not be created.')
47+
if "Async" not in component_type:
48+
print('Since Async component is not in use, your component will not be lazy loaded and fragments will not be created.')
4949
shutil.rmtree(os.path.join(os.getcwd(), 'src', 'lib', 'fragments'))
5050
os.remove(os.path.join(os.getcwd(), 'src', 'lib', 'LazyLoader.js'))
5151

{{cookiecutter.project_shortname}}/cookiecutter_templates/AsyncComponent.react.js renamed to {{cookiecutter.project_shortname}}/cookiecutter_templates/AsyncClassComponent.react.js

File renamed without changes.
Lines changed: 48 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,48 @@
1+
import React from 'react';
2+
import PropTypes from 'prop-types';
3+
import { {{cookiecutter.component_name}} as RealComponent } from '../LazyLoader';
4+
5+
/**
6+
* ExampleComponent is an example component.
7+
* It takes a property, `label`, and
8+
* displays it.
9+
* It renders an input with the property `value`
10+
* which is editable by the user.
11+
*/
12+
const {{cookiecutter.component_name}} = (props) => {
13+
return (
14+
<React.Suspense fallback={null}>
15+
<RealComponent {...props}/>
16+
</React.Suspense>
17+
);
18+
};
19+
20+
{{cookiecutter.component_name}}.defaultProps = {};
21+
22+
{{cookiecutter.component_name}}.propTypes = {
23+
/**
24+
* The ID used to identify this component in Dash callbacks.
25+
*/
26+
id: PropTypes.string,
27+
28+
/**
29+
* A label that will be printed when this component is rendered.
30+
*/
31+
label: PropTypes.string.isRequired,
32+
33+
/**
34+
* The value displayed in the input.
35+
*/
36+
value: PropTypes.string,
37+
38+
/**
39+
* Dash-assigned callback that should be called to report property changes
40+
* to Dash, to make them available for callbacks.
41+
*/
42+
setProps: PropTypes.func
43+
};
44+
45+
export default {{cookiecutter.component_name}};
46+
47+
export const defaultProps = {{cookiecutter.component_name}}.defaultProps;
48+
export const propTypes = {{ cookiecutter.component_name }}.propTypes;

{{cookiecutter.project_shortname}}/cookiecutter_templates/Component.react.js renamed to {{cookiecutter.project_shortname}}/cookiecutter_templates/ClassComponent.react.js

File renamed without changes.
Lines changed: 61 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,61 @@
1+
import React, { useState } from 'react';
2+
import PropTypes from 'prop-types';
3+
4+
/**
5+
* ExampleComponent is an example component.
6+
* It takes a property, `label`, and
7+
* displays it.
8+
* It renders an input with the property `value`
9+
* which is editable by the user.
10+
*/
11+
const {{cookiecutter.component_name}} = (props) => {
12+
const {id, label, setProps, value} = props;
13+
14+
return (
15+
<div id={id}>
16+
ExampleComponent: {label}&nbsp;
17+
<input
18+
value={value}
19+
onChange={
20+
/*
21+
* Send the new value to the parent component.
22+
* setProps is a prop that is automatically supplied
23+
* by dash's front-end ("dash-renderer").
24+
* In a Dash app, this will update the component's
25+
* props and send the data back to the Python Dash
26+
* app server if a callback uses the modified prop as
27+
* Input or State.
28+
*/
29+
e => setProps({ value: e.target.value })
30+
}
31+
/>
32+
</div>
33+
);
34+
}
35+
36+
{{cookiecutter.component_name}}.defaultProps = {};
37+
38+
{{cookiecutter.component_name}}.propTypes = {
39+
/**
40+
* The ID used to identify this component in Dash callbacks.
41+
*/
42+
id: PropTypes.string,
43+
44+
/**
45+
* A label that will be printed when this component is rendered.
46+
*/
47+
label: PropTypes.string.isRequired,
48+
49+
/**
50+
* The value displayed in the input.
51+
*/
52+
value: PropTypes.string,
53+
54+
/**
55+
* Dash-assigned callback that should be called to report property changes
56+
* to Dash, to make them available for callbacks.
57+
*/
58+
setProps: PropTypes.func
59+
};
60+
61+
export default {{cookiecutter.component_name}};
Lines changed: 14 additions & 22 deletions
Original file line numberDiff line numberDiff line change
@@ -1,32 +1,24 @@
11
/* eslint no-magic-numbers: 0 */
2-
import React, {Component} from 'react';
2+
import React, { useState } from 'react';
33

44
import { {{cookiecutter.component_name}} } from '../lib';
55

6-
class App extends Component {
6+
const App = () => {
77

8-
constructor(props) {
9-
super(props);
10-
this.state = {
11-
value: ''
8+
const [state, setState] = useState({value:'', label:'Type Here'});
9+
const setProps = (newProps) => {
10+
setState(newProps);
1211
};
13-
this.setProps = this.setProps.bind(this);
14-
}
1512

16-
setProps(newProps) {
17-
this.setState(newProps);
18-
}
13+
return (
14+
<div>
15+
<{{cookiecutter.component_name}}
16+
setProps={setProps}
17+
{...state}
18+
/>
19+
</div>
20+
)
21+
};
1922

20-
render() {
21-
return (
22-
<div>
23-
<{{cookiecutter.component_name}}
24-
setProps={this.setProps}
25-
{...this.state}
26-
/>
27-
</div>
28-
)
29-
}
30-
}
3123

3224
export default App;
Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,9 @@
1-
{%- if cookiecutter.use_async == "True" -%}
2-
{%- include 'cookiecutter_templates/AsyncComponent.react.js' -%}
1+
{%- if "Async" in cookiecutter.component_type and "Class" in cookiecutter.component_type -%}
2+
{%- include 'cookiecutter_templates/AsyncClassComponent.react.js' -%}
3+
{%- elif "Async" in cookiecutter.component_type and "Function" in cookiecutter.component_type -%}
4+
{%- include 'cookiecutter_templates/AsyncFunctionComponent.react.js' -%}
5+
{%- elif "Class" in cookiecutter.component_type -%}
6+
{%- include 'cookiecutter_templates/ClassComponent.react.js' -%}
37
{%- else -%}
4-
{%- include 'cookiecutter_templates/Component.react.js' -%}
5-
{%- endif -%}
8+
{%- include 'cookiecutter_templates/FunctionComponent.react.js' -%}
9+
{%- endif -%}

{{cookiecutter.project_shortname}}/{{cookiecutter.project_shortname}}/__init__.py

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,7 @@
2929
_this_module = _sys.modules[__name__]
3030

3131
async_resources = [
32-
{%- if cookiecutter.use_async == "True" -%}
32+
{%- if "Async" in cookiecutter.component_type -%}
3333
"{{cookiecutter.component_name}}",
3434
{%- endif -%}
3535
]

0 commit comments

Comments
 (0)