Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
35 changes: 29 additions & 6 deletions app/src/components/ExampleStory.js
Original file line number Diff line number Diff line change
Expand Up @@ -61,18 +61,41 @@ class ExampleStory extends Component {

let last_item = {};
let content = this.props.content;
let new_content = [];
let index = 0;

for (let i = 0, size = content.length; i < size; i++) {
if (last_item.type === "utter") {
content[i] = { ...content[i], sequence: true };

if (content[i].type === "checkpoint"){
let checkpoint = content[i].content;
for (let i = 0, size = checkpoint.length; i < size; i++) {

if (last_item.type === "utter") {
new_content[index] = { ...checkpoint[i], sequence: true };
} else {
new_content[index] = { ...checkpoint[i], sequence: false};
}
last_item = new_content[index];
index++;
}
} else if (last_item.type === "utter") {
new_content[index] = { ...content[i], sequence: true };
last_item = new_content[index];
index++;
} else if (content[i].sequence) {
content[i].sequence = false;
new_content[index].sequence = false;
last_item = new_content[index];
index++;
} else {
new_content[index] = content[i];
last_item = new_content[index];
index++;
}

last_item = content[i];

}

return content.map((item, index) => {
return new_content.map((item, index) => {
let element;
if (item.type === "intent") { element = this.exampleIntent(item, index) }
else if (item.sequence) { element = this.exampleSimpleUtter(item, index) }
Expand All @@ -94,4 +117,4 @@ class ExampleStory extends Component {
}
const mapStateToProps = state => { return { ...state.story } };

export default connect(mapStateToProps)(ExampleStory);
export default connect(mapStateToProps)(ExampleStory);
11 changes: 9 additions & 2 deletions app/src/components/StoryCard.js
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ import React, { Component } from "react";
import { Card } from '@material-ui/core';
import UtterIcon from '../icons/UtterIcon';
import IntentIcon from '../icons/IntentIcon';
import CheckpointIcon from '../icons/CheckpointIcon';
import Typography from '@material-ui/core/Typography';
import { setHighlight } from "../utils/utils";

Expand Down Expand Up @@ -44,14 +45,20 @@ export default class StoryCard extends Component {
{setHighlight(item.name, this.props.highlighted_text)}
</Typography>
)
}
else {
} else if (item.type === "utter") {
return (
<Typography key={'story_card_item_' + index} style={styles.utter} varant="body1" noWrap>
<UtterIcon style={styles.utter_icon} />
{setHighlight(item.name, this.props.highlighted_text)}
</Typography>
)
} else if (item.type === "checkpoint") {
return (
<Typography key={'story_card_item_' + index} style={styles.utter} varant="body1" noWrap>
<CheckpointIcon style={styles.utter_icon} />
{setHighlight(item.name, this.props.highlighted_text)}
</Typography>
)
}
})
return list;
Expand Down
8 changes: 7 additions & 1 deletion app/src/components/StoryList.js
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,7 @@ import { bindActionCreators } from 'redux';
import UtterIcon from '../icons/UtterIcon';
import { message } from "../utils/messages";
import IntentIcon from '../icons/IntentIcon';
import CheckpointIcon from '../icons/CheckpointIcon';
import { Grid, Card } from '@material-ui/core';
import DeleteIcon from '@material-ui/icons/Delete';
import IconButton from '@material-ui/core/IconButton';
Expand Down Expand Up @@ -76,7 +77,12 @@ class StoryList extends Component {
}

getIcon(type) {
return type === "intent" ? <IntentIcon style={styles.intent_icon} /> : <UtterIcon style={styles.utter_icon} />
if(type === "intent")
return <IntentIcon style={styles.intent_icon} />
else if (type === "utter")
return <UtterIcon style={styles.utter_icon} />
else
return <CheckpointIcon style={styles.utter_icon} />
}

onDragEnd(result) {
Expand Down
20 changes: 18 additions & 2 deletions app/src/components/ToolbarName.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,8 @@ import IconButton from '@material-ui/core/IconButton';
import MoreVertIcon from '@material-ui/icons/MoreVert';
import InfoIcon from '@material-ui/icons/InfoOutlined';
import Tooltip from '@material-ui/core/Tooltip';
import FormControlLabel from '@material-ui/core/FormControlLabel'
import Checkbox from '@material-ui/core/Checkbox'

const style = {
toolbar: {
Expand Down Expand Up @@ -92,12 +94,26 @@ export default class ToolbarName extends Component {
}
}

handleCheckbox(event){
this.props.setCheckpoint(event.target.checked);
}

render() {
return (
<Toolbar style={style.toolbar}>
<Grid item xs={2} />
<Grid item xs={4}>
{this.props.story ? null : (
{this.props.story ?
<FormControlLabel
control={
<Checkbox
checked={this.props.item.is_checkpoint}
onChange={e => this.handleCheckbox(e)}
/>
}
label="Checkpoint"
/>
: (
<NameField
name={this.props.name}
items={this.props.items}
Expand All @@ -118,7 +134,7 @@ export default class ToolbarName extends Component {
</Tooltip>
)}
</Grid>
<Grid item xs={2} />
<Grid item xs={2}/>
<Grid item xs={3}>
<Button
color="secondary"
Expand Down
51 changes: 47 additions & 4 deletions app/src/ducks/stories.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,18 +10,28 @@ const INITIAL_STATE = {
intents: [],
stories: [],
content: [],
checkpoints: [],
loading: true,
name: "",
old_content: [],
story_id: "",
notification_text: "",
content_text_validation: ""
content_text_validation: "",
is_checkpoint: false,
old_checkpoint: false
};

function createArrayObjCopyOf(samples = []) {
return samples.map(text => { return { ...text } });
}

export const getCheckpoints = (state = INITIAL_STATE, action) => {
return {
...state,
checkpoints: action.checkpoints
};
}

export const getIntents = (state = INITIAL_STATE, action) => {
return {
...state,
Expand Down Expand Up @@ -50,7 +60,9 @@ export const getStory = (state = INITIAL_STATE, action) => {
name: action.story.name,
story_id: action.story.id,
content: action.story.content,
old_content: action.story.content
old_content: action.story.content,
is_checkpoint: action.story.is_checkpoint,
old_checkpoint: action.story.is_checkpoint
};
}

Expand Down Expand Up @@ -105,7 +117,7 @@ export const deleteContent = (state = INITIAL_STATE, action) => {

export const undoDeleteContent = (state = INITIAL_STATE) => {
const text = validationContent(state.old_content);

return {
...state,
content_text_validation: text,
Expand Down Expand Up @@ -137,7 +149,15 @@ export const addToStory = (state = INITIAL_STATE, action) => {
content: new_content,
content_text_validation: text,
old_content: createArrayObjCopyOf(state.content),
}
};
}

export const setCheckpoint = (state = INITIAL_STATE, action) => {
return {
...state,
is_checkpoint: action.is_checkpoint,
old_checkpoint: !action.is_checkpoint
};
}

export const createNewStory = (state = INITIAL_STATE) => {
Expand Down Expand Up @@ -171,6 +191,7 @@ export const { Types, Creators } = createActions({
undoDeleteContent: [],
notifyAction: ['text'],
addToStory: ['item', 'mode'],
setCheckpoint: ['is_checkpoint'],
deleteContent: ['content_position'],
notifyContentTextValidation: ['text'],
reorderContent: ['start_index', 'end_index'],
Expand All @@ -194,6 +215,26 @@ export const { Types, Creators } = createActions({
}
}
},
addCheckpoint: (checkpoint) => {
return async (dispatch) => {
try {
const response = await axios.get(STORY_URL + checkpoint.id + '/checkpoint');
await dispatch({ type: Types.ADD_TO_STORY, item: response.data, mode: "checkpoint" });
} catch (error) {
throw (error);
}
}
},
getCheckpoints: () => {
return async (dispatch) => {
try {
const response = await axios.get(STORY_URL + 'checkpoints');
await dispatch({ type: Types.GET_CHECKPOINTS, checkpoints: response.data });
} catch (error) {
throw (error);
}
}
},
getIntents: () => {
return async (dispatch) => {
try {
Expand Down Expand Up @@ -262,10 +303,12 @@ export const { Types, Creators } = createActions({

export default createReducer(INITIAL_STATE, {
[Types.GET_STORY]: getStory,
[Types.GET_CHECKPOINTS]: getCheckpoints,
[Types.GET_UTTERS]: getUtters,
[Types.GET_STORIES]: getStories,
[Types.GET_INTENTS]: getIntents,
[Types.ADD_TO_STORY]: addToStory,
[Types.SET_CHECKPOINT]: setCheckpoint,
[Types.NOTIFY_ACTION]: notifyAction,
[Types.DELETE_CONTENT]: deleteContent,
[Types.REORDER_CONTENT]: reorderContent,
Expand Down
13 changes: 13 additions & 0 deletions app/src/icons/CheckpointIcon.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
import React from "react";

const SvgCheckpointIcon = props => (
<svg width={24} height={24} {...props}>
<path
d="M10 6l-1.41 1.41 4.58 4.59-4.58 4.59 1.41 1.41 6-6z"
fill="props.fill"
fillRule="evenodd"
/>
</svg>
);

export default SvgCheckpointIcon;
25 changes: 18 additions & 7 deletions app/src/pages/StoryEditPage.js
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ import { Creators as StoryAction } from "../ducks/stories";
import Button from '@material-ui/core/Button';
import IntentIcon from '../icons/IntentIcon';
import UtterIcon from '../icons/UtterIcon';
import CheckpointIcon from '../icons/CheckpointIcon'
import StoryList from '../components/StoryList';
import { Story } from '../utils/DataFormat.js';
import TextField from '@material-ui/core/TextField';
Expand Down Expand Up @@ -52,6 +53,7 @@ class StoryEditPage extends Component {
super(props);
this.props.getIntents()
this.props.getUtters()
this.props.getCheckpoints()

const id = this.props.history.location.pathname.split('/').pop();
isNaN(id) ? this.props.createNewStory() : this.getStory(id);
Expand Down Expand Up @@ -115,9 +117,9 @@ class StoryEditPage extends Component {
const first_element_is_intent = (this.props.content.length !== 0 && this.props.content[0].type !== 'utter');
const contents_changed = JSON.stringify(this.props.content) !== JSON.stringify(this.props.old_content);
let is_enabled = this.props.content_text_validation.length === 0;

return first_element_is_intent && contents_changed && is_enabled;
const checkpoint_changed = this.props.is_checkpoint !== this.props.old_checkpoint;

return first_element_is_intent && (contents_changed || checkpoint_changed) && is_enabled;
}

render() {
Expand Down Expand Up @@ -145,7 +147,6 @@ class StoryEditPage extends Component {
highlighted_text={this.state.value}
actionOnClick={this.props.addIntent}
items={this.filterItems(this.props.intents)}
content={this.props.content}
selected_item_position={this.props.selected_item_position}
/>
</Grid>
Expand All @@ -156,13 +157,22 @@ class StoryEditPage extends Component {
<ItemsList
story={true}
icon={<UtterIcon />}
isSelected={this.isSelected}
content={this.props.content}
highlighted_text={this.state.value}
actionOnClick={this.props.addUtter}
items={this.filterItems(this.props.utters)}
selected_item_position={this.props.selected_item_position}
/>
<Typography variant="body2" color="primary">
Checkpoints
</Typography>
<ItemsList
story={true}
icon={<CheckpointIcon />}
highlighted_text={this.state.value}
actionOnClick={this.props.addCheckpoint}
items={this.props.checkpoints}
selected_item_position={this.props.selected_item_position}
/>
</Grid>
</Grid>
<Grid container>
Expand All @@ -186,7 +196,8 @@ class StoryEditPage extends Component {
is_enabled={this.isButtonEnabled()}
saveData={this.props.saveData}
deleteItem={() => this.changeStatusDialog(true)}
item={new Story(this.props.story_id, this.props.content, this.props.name)}
item={new Story(this.props.story_id, this.props.content, this.props.name, this.props.is_checkpoint)}
setCheckpoint={this.props.setCheckpoint}
/>
<div style={{
height: "calc(100vh - 74px - 72px)",
Expand Down
5 changes: 3 additions & 2 deletions app/src/utils/DataFormat.js
Original file line number Diff line number Diff line change
Expand Up @@ -21,9 +21,10 @@ export class Intent {
};

export class Story {
constructor(id = '', content = [], name = ''){
constructor(id = '', content = [], name = '', is_checkpoint = false){
this.id = id;
this.name = name;
this.content = content;
this.is_checkpoint = is_checkpoint;
}
};
};