Skip to content

Instantly share code, notes, and snippets.

@yakneens
Created October 21, 2017 16:41
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save yakneens/8f9a68bcc15ab0e37defb14a5126c5ad to your computer and use it in GitHub Desktop.
Save yakneens/8f9a68bcc15ab0e37defb14a5126c5ad to your computer and use it in GitHub Desktop.
class EditableCell extends React.Component {
state = {
value: this.props.value,
editable: this.props.editable || false,
};
componentWillReceiveProps(nextProps) {
if (nextProps.editable !== this.state.editable) {
this.setState({ editable: nextProps.editable });
if (nextProps.editable) {
this.cacheValue = this.state.value;
}
}
if (nextProps.status && nextProps.status !== this.props.status) {
if (nextProps.status === 'save') {
this.props.onChange(this.state.value);
} else if (nextProps.status === 'cancel') {
this.setState({ value: this.cacheValue });
this.props.onChange(this.cacheValue);
}
}
}
shouldComponentUpdate(nextProps, nextState) {
return (
nextProps.editable !== this.state.editable ||
nextState.value !== this.state.value
);
}
handleChange(e) {
const value = e.target.value;
this.setState({ value });
}
render() {
const { value, editable, textarea } = this.state;
return (
<div>
{editable ? textarea ? (
<div>
<Input.TextArea
value={value}
onChange={e => this.handleChange(e)}
/>
</div>
) : (
<div>
<Input value={value} onChange={e => this.handleChange(e)} />
</div>
) : (
<div className="editable-row-text">{value.toString() || ' '}</div>
)}
</div>
);
}
}
class EditableTable extends React.Component {
constructor(props) {
super(props);
this.columns = [
{
title: 'Workflow ID',
dataIndex: 'workflowId',
width: '15%',
render: (text, record, index) =>
this.renderColumns(this.state.data, index, 'workflowId', text),
},
{
title: 'Workflow Name',
dataIndex: 'workflowName',
width: '15%',
render: (text, record, index) =>
this.renderColumns(this.state.data, index, 'workflowName', text),
},
{
title: 'Workflow Version',
dataIndex: 'workflowVersion',
width: '15%',
render: (text, record, index) =>
this.renderColumns(this.state.data, index, 'workflowVersion', text),
},
{
title: 'Configuration',
dataIndex: 'config',
width: '25%',
render: (text, record, index) =>
this.renderColumns(this.state.data, index, 'config', text),
},
{
title: 'operation',
dataIndex: 'operation',
render: (text, record, index) => {
const { editable } = this.state.data[index].workflowName;
return (
<div className="editable-row-operations">
{editable ? (
<span>
<a onClick={() => this.editDone(index, 'save')}>Save</a>
<Popconfirm
title="Sure to cancel?"
onConfirm={() => this.editDone(index, 'cancel')}
>
<a>Cancel</a>
</Popconfirm>
</span>
) : (
<span>
<a
onClick={() =>
this.expandedRowKeys.push(record.key) && this.edit(index)}
>
Edit
</a>
</span>
)}
</div>
);
},
},
];
this.state = {
data: [
{
key: '0',
workflowId: {
value: 1,
},
workflowName: {
editable: false,
value: 'Blalblala',
},
workflowVersion: {
editable: false,
value: '1.0',
},
config: {
editable: false,
textarea: true,
value: '{"blah":"blah"}',
},
},
],
};
}
renderColumns(data, index, key, text) {
const { editable, status } = data[index][key];
if (typeof editable === 'undefined') {
return text;
}
return (
<EditableCell
editable={editable}
value={text}
onChange={value => this.handleChange(key, index, value)}
status={status}
/>
);
}
handleChange(key, index, value) {
const { data } = this.state;
data[index][key].value = value;
this.setState({ data });
}
edit(index) {
const { data } = this.state;
Object.keys(data[index]).forEach(item => {
if (
data[index][item] &&
typeof data[index][item].editable !== 'undefined'
) {
data[index][item].editable = true;
}
});
this.setState({ data });
}
editDone(index, type) {
const { data } = this.state;
Object.keys(data[index]).forEach(item => {
if (
data[index][item] &&
typeof data[index][item].editable !== 'undefined'
) {
data[index][item].editable = false;
data[index][item].status = type;
}
});
this.setState({ data }, () => {
Object.keys(data[index]).forEach(item => {
if (
data[index][item] &&
typeof data[index][item].editable !== 'undefined'
) {
delete data[index][item].status;
}
});
});
}
render() {
const { data } = this.state;
const dataSource = data.map(item => {
const obj = {};
Object.keys(item).forEach(key => {
obj[key] = key === 'key' ? item[key] : item[key].value;
});
return obj;
});
const columns = this.columns;
return (
<Table
bordered
dataSource={dataSource}
columns={columns}
expandedRowRender={record => (
<pre>{JSON.stringify(JSON.parse(record.config), undefined, 2)}</pre>
)}
/>
);
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment