From 0a5b1d68faf463026b36a9820f6ed59ec0ae3667 Mon Sep 17 00:00:00 2001 From: Yifan Wang Date: Fri, 23 Apr 2021 16:57:32 -0400 Subject: [PATCH 01/27] set up and edited textToSpeech page --- backend/app/analysis/text_parser.py | 74 +++++ backend/app/views.py | 17 +- backend/config/urls.py | 2 + frontend/src/index/index.js | 1 + frontend/src/textToSpeech/textToSpeech.js | 299 ++++++++++++++++++++ frontend/src/textToSpeech/textToSpeech.scss | 1 + 6 files changed, 393 insertions(+), 1 deletion(-) create mode 100644 backend/app/analysis/text_parser.py create mode 100644 frontend/src/textToSpeech/textToSpeech.js create mode 100644 frontend/src/textToSpeech/textToSpeech.scss diff --git a/backend/app/analysis/text_parser.py b/backend/app/analysis/text_parser.py new file mode 100644 index 0000000..55530f2 --- /dev/null +++ b/backend/app/analysis/text_parser.py @@ -0,0 +1,74 @@ +""" +Custom command to populate text model with definition, examples, and images +""" +import re +import urllib +import urllib.request +import urllib.parse +import tqdm + +# Ours + + +# Modified Code from Bing library +def get_sentences(text_obj): + """ + Given a Text object, stores the definitions, examples, and image urls for all the words + in this text. + :param text_obj: the Text object that we want to get sentences from + """ + + text_paragraph = text_obj.content + temp_sentences = text_paragraph.split(".") + + sentences = [] + for sent in temp_sentences: + sentences.extend(sent.split("!")) + + return sentences + + + + + + + + + + + # part_of_speech = ['noun', 'verb', 'adjective', 'adverb'] + # + # # Reused the old image url dictionary if we are not getting all of the urls + # word_urls = {} + # word_definitions = {} + # word_examples = {} + + # for pos in part_of_speech: + # print("Getting definitions and examples for " + pos + " in the text " + + # text_obj.title + "... (This might take a while)") + # words = get_valid_words(text_obj.content.lower(), pos) + # definitions = get_word_definition(words, pos) + # examples = get_word_examples(words, pos, text_obj.content.lower()) + # + # print("Updating database for " + pos + " in the text " + text_obj.title) + # for word in tqdm.tqdm(words): + # word = word.lower() + # if word not in word_urls: + # image_url = get_bing_image_url(word) + # if image_url is not None: + # word_urls[word.lower()] = image_url + # + # if word not in word_definitions: + # word_definitions[word] = {pos: definitions[word]} + # else: + # word_definitions[word][pos] = definitions[word] + # + # if word not in word_examples: + # word_examples[word] = {pos: examples[word]} + # else: + # word_examples[word][pos] = examples[word] + # + # text_obj.images = word_urls + # text_obj.definitions = word_definitions + # text_obj.examples = word_examples + # text_obj.save() diff --git a/backend/app/views.py b/backend/app/views.py index 74ae6fa..105bbf8 100644 --- a/backend/app/views.py +++ b/backend/app/views.py @@ -27,7 +27,13 @@ from .analysis.crosswords import ( get_crosswords, ) -from .quiz_creation.conjugation_quiz import get_quiz_sentences +from .quiz_creation.conjugation_quiz import ( + get_quiz_sentences, +) +from .analysis.text_parser import ( + get_sentences, +) + @api_view(['GET']) @@ -188,3 +194,12 @@ def get_quiz_data(request, text_id): text_obj = Text.objects.get(id=text_id) res = get_quiz_sentences(text_obj.content) return Response(res) + +@api_view(['GET']) +def get_indiv_sentences(request, text_id): + """ + API endpoint for getting the individual sentences from the given text. + """ + text_obj = Text.objects.get(id=text_id) + sentences = get_sentences(text_obj) + return Response(sentences) diff --git a/backend/config/urls.py b/backend/config/urls.py index f7cb10b..cddbbf3 100644 --- a/backend/config/urls.py +++ b/backend/config/urls.py @@ -56,6 +56,7 @@ def react_view_path(route, component_name): path('api/get_crossword//', get_crossword), path('api/get_quiz_data//', get_quiz_data), path('api/text/', text), + path('api/get_indiv_sentences/', get_indiv_sentences), # View paths react_view_path('', 'IndexView'), @@ -67,4 +68,5 @@ def react_view_path(route, component_name): react_view_path('flashcard//', 'FlashcardView'), react_view_path('quiz/', 'AllQuizView'), react_view_path('quiz//', 'QuizView'), + react_view_path('textToSpeech/', 'TextToSpeech') ] diff --git a/frontend/src/index/index.js b/frontend/src/index/index.js index 24cd826..57f17f1 100644 --- a/frontend/src/index/index.js +++ b/frontend/src/index/index.js @@ -12,6 +12,7 @@ const QUIZ_TYPES = { 'Flashcards': posLink, 'Quiz': idLink, 'Crossword': posLink, + 'TextToSpeech': idLink }; class TextInfo extends React.Component { diff --git a/frontend/src/textToSpeech/textToSpeech.js b/frontend/src/textToSpeech/textToSpeech.js new file mode 100644 index 0000000..049ada3 --- /dev/null +++ b/frontend/src/textToSpeech/textToSpeech.js @@ -0,0 +1,299 @@ +import React, { Component } from 'react'; +import * as PropTypes from 'prop-types'; + +import { Footer, Navbar, LoadingPage } from '../UILibrary/components'; + +const capitalize = (word) => { + return word.charAt(0).toUpperCase() + word.slice(1); +}; + +const play_button = (color) => { + return ( + + + + + ); +}; + +export class TextToSpeech extends Component { + constructor(props) { + super(props); + this.state = { + textData: null, + sentenceIndex: 0, + showModal: false, + nextSentence: false, + }; + this.modalHandler = this.modalHandler.bind(this); + } + + componentDidMount = async () => { + const apiURL = `/api/get_indiv_sentences/${this.props.textID}`; + const response = await fetch(apiURL); + const textData = await response.json(); + this.setState({ textData }); + document.addEventListener('keydown', this.handleKeyDown, true); + } + + componentWillUnmount() { + document.removeEventListener('keydown', this.handleKeyDown, false); + } + + getCurrentSentence = () => { + const { + sentenceIndex, + textData, + } = this.state; + return textData[sentenceIndex]; + } + + changeSentence = (delta) => { + const { textData, sentenceIndex } = this.state; + const listLength = textData.length; + const newsentenceIndex = (sentenceIndex + delta + listLength) % listLength; + this.setState({ + sentenceIndex: newsentenceIndex, + showNext: true, + }); + } + + playAudio = () => { + let utterance = new SpeechSynthesisUtterance(); + utterance.text = textData[sentenceIndex]; + utterance.lang = 'en-US'; + utterance.rate = 1.2; + speechSynthesis.speak(utterance); + } + + toggleStar = () => { + const { starredCards, starOnly, cardIndex } = this.state; + let currentIndex = starOnly ? starredCards[cardIndex] : cardIndex; + if (this.isStarred(currentIndex)) { + starredCards.splice(starredCards.indexOf(currentIndex), 1); + if (starOnly) { + if (starredCards.length > 0) { + currentIndex %= starredCards.length; + } else { + currentIndex = 0; + } + } + } else { + starredCards.push(this.state.cardIndex); + } + this.setState({ starredCards, cardIndex: currentIndex }); + } + + handleKeyDown = (e) => { + if (['ArrowLeft', 'ArrowRight'].includes(e.code)) { + e.preventDefault(); + const { code } = e; + if (code === 'ArrowLeft') { + this.changeSentence(-1); + } else if (code === 'ArrowRight') { + this.changeSentence(1); + } + } + } + + modalHandler = (event) => { + event.preventDefault(); + this.setState({ + showModal: !this.state.showModal, + }); + } + + checkProgress = () => { + const numSentences = this.state.textData.length; + const currentSentence = this.state.sentenceIndex + 1; + if (numSentences !== 0) { + return parseInt((currentSentence / numSentences) * 100); + } + return 0; + } + + render() { + const { + textData, + showNext, + sentenceIndex, + } = this.state; + + if (!textData) { + return (); + } + + /* Generate Text On Top of Progress Bar */ + const sentenceLength = textData.length; + const progressText = sentenceLength === 0 + ? 'No Sentences Available' + : `${sentenceIndex + 1}/${sentenceLength} Words`; + + /* Generate Flashcard */ + const card = this.getcurrentSentence(); + const flipcard =
+ {play_button('yellow')} +
+ + //
You do not have any starred cards
; + // const flipcard = card + // ? ( + //
+ //
this.changeCard(-1)} + // > + // < + //
+ //
+ //
+ //
+ //
+ //
+ //
+ //
+ // {card.word.toUpperCase()}/ + //
+ //
+ //
+ // {this.isStarred(starOnly + // ? starredCards[sentenceIndex] : sentenceIndex) + // ? filledStar('yellow') + // : star('white') + // } + //
+ //
+ //
+ //
+ //
+ //

+ // Click to flip + //

+ // + //
+ // + //
+ //
+ //
+ //
+ //
+ //

+ // {card.word.toUpperCase()} + //

+ //

+ // Definition: {card.definition[0]} + //

+ //

+ // Example: "{card.example[0]}" + //

+ //
+ //
+ //
+ // {this.isStarred(starOnly + // ? starredCards[sentenceIndex] : sentenceIndex) + // ? filledStar('yellow') + // : star('white') + // } + //
+ //
+ //
+ //
+ //
+ //

+ // Click to flip + //

+ //
+ //
+ //
+ //
this.changeCard(1)}> + // > + //
+ //
) + // :
You do not have any starred cards
; + + /* Actual Return statement */ + return ( + <> + +
+
+
+

Sentence

+ +
+
+ { + this.state.showModal + ?
+
+ : null + } +
+
+
Instructions
+ +
+
+

+
+
+ +
+
+
+ +
+
+ {progressText} +
+
+
+
+
+
+ {flipcard} +
+
+ + ); + } +} +TextToSpeech.propTypes = { + textID: PropTypes.number +}; diff --git a/frontend/src/textToSpeech/textToSpeech.scss b/frontend/src/textToSpeech/textToSpeech.scss new file mode 100644 index 0000000..6a7cab9 --- /dev/null +++ b/frontend/src/textToSpeech/textToSpeech.scss @@ -0,0 +1 @@ +/* Styles for the text to speech page */ From b27dca51b93bc69a8520a2cd7c16d0d9c6799170 Mon Sep 17 00:00:00 2001 From: taokinbo <70776613+taokinbo@users.noreply.github.com> Date: Fri, 30 Apr 2021 15:24:44 -0400 Subject: [PATCH 02/27] Fixed a few errors --- backend/config/urls.py | 1 + frontend/src/textToSpeech/textToSpeech.js | 45 ++++++++++++----------- 2 files changed, 25 insertions(+), 21 deletions(-) diff --git a/backend/config/urls.py b/backend/config/urls.py index cddbbf3..88bea14 100644 --- a/backend/config/urls.py +++ b/backend/config/urls.py @@ -27,6 +27,7 @@ get_crossword, get_quiz_data, text, + get_indiv_sentences ) diff --git a/frontend/src/textToSpeech/textToSpeech.js b/frontend/src/textToSpeech/textToSpeech.js index 049ada3..f526c05 100644 --- a/frontend/src/textToSpeech/textToSpeech.js +++ b/frontend/src/textToSpeech/textToSpeech.js @@ -7,6 +7,8 @@ const capitalize = (word) => { return word.charAt(0).toUpperCase() + word.slice(1); }; +const synth = window.speechSynthesis; + const play_button = (color) => { return ( { - const { starredCards, starOnly, cardIndex } = this.state; - let currentIndex = starOnly ? starredCards[cardIndex] : cardIndex; - if (this.isStarred(currentIndex)) { - starredCards.splice(starredCards.indexOf(currentIndex), 1); - if (starOnly) { - if (starredCards.length > 0) { - currentIndex %= starredCards.length; - } else { - currentIndex = 0; - } - } - } else { - starredCards.push(this.state.cardIndex); - } - this.setState({ starredCards, cardIndex: currentIndex }); - } + // toggleStar = () => { + // const { starredCards, starOnly, cardIndex } = this.state; + // let currentIndex = starOnly ? starredCards[cardIndex] : cardIndex; + // if (this.isStarred(currentIndex)) { + // starredCards.splice(starredCards.indexOf(currentIndex), 1); + // if (starOnly) { + // if (starredCards.length > 0) { + // currentIndex %= starredCards.length; + // } else { + // currentIndex = 0; + // } + // } + // } else { + // starredCards.push(this.state.cardIndex); + // } + // this.setState({ starredCards, cardIndex: currentIndex }); + // } handleKeyDown = (e) => { if (['ArrowLeft', 'ArrowRight'].includes(e.code)) { @@ -142,10 +144,11 @@ export class TextToSpeech extends Component { /* Generate Flashcard */ const card = this.getcurrentSentence(); - const flipcard =
- {play_button('yellow')} -
+ // const flipcard =
+ // {play_button('yellow')} + //
+ const flipcard =
Hello
//
You do not have any starred cards
; // const flipcard = card From 4f4fe66b4a25d73d22ed1460e0717102b69b1bbd Mon Sep 17 00:00:00 2001 From: taokinbo <70776613+taokinbo@users.noreply.github.com> Date: Fri, 30 Apr 2021 16:16:10 -0400 Subject: [PATCH 03/27] testing something --- backend/app/analysis/text_parser.py | 22 ++++++++++------------ backend/app/views.py | 8 ++++++-- backend/config/urls.py | 2 +- frontend/src/textToSpeech/textToSpeech.js | 15 ++++++++++----- 4 files changed, 27 insertions(+), 20 deletions(-) diff --git a/backend/app/analysis/text_parser.py b/backend/app/analysis/text_parser.py index 55530f2..331e613 100644 --- a/backend/app/analysis/text_parser.py +++ b/backend/app/analysis/text_parser.py @@ -1,30 +1,28 @@ """ Custom command to populate text model with definition, examples, and images """ -import re -import urllib -import urllib.request -import urllib.parse -import tqdm +import nltk # Ours # Modified Code from Bing library -def get_sentences(text_obj): +def get_sentences(text): """ Given a Text object, stores the definitions, examples, and image urls for all the words in this text. :param text_obj: the Text object that we want to get sentences from """ - text_paragraph = text_obj.content - temp_sentences = text_paragraph.split(".") - - sentences = [] - for sent in temp_sentences: - sentences.extend(sent.split("!")) + sentences = nltk.tokenize.sent_tokenize(text) + # text_paragraph = text_obj.content + # temp_sentences = text_paragraph.split(".") + # + # sentences = [] + # for sent in temp_sentences: + # sentences.extend(sent.split("!")) + print(sentences) return sentences diff --git a/backend/app/views.py b/backend/app/views.py index 105bbf8..003d231 100644 --- a/backend/app/views.py +++ b/backend/app/views.py @@ -200,6 +200,10 @@ def get_indiv_sentences(request, text_id): """ API endpoint for getting the individual sentences from the given text. """ + print("is this even running") text_obj = Text.objects.get(id=text_id) - sentences = get_sentences(text_obj) - return Response(sentences) + sentences = get_sentences(text_obj.content) + # return Response(sentences) + res = [{'sentence': sentence} for sentence in sentences] + print(sentences) + return Response(res) diff --git a/backend/config/urls.py b/backend/config/urls.py index 88bea14..9bdf729 100644 --- a/backend/config/urls.py +++ b/backend/config/urls.py @@ -27,7 +27,7 @@ get_crossword, get_quiz_data, text, - get_indiv_sentences + get_indiv_sentences, ) diff --git a/frontend/src/textToSpeech/textToSpeech.js b/frontend/src/textToSpeech/textToSpeech.js index f526c05..a0347de 100644 --- a/frontend/src/textToSpeech/textToSpeech.js +++ b/frontend/src/textToSpeech/textToSpeech.js @@ -42,11 +42,16 @@ export class TextToSpeech extends Component { } componentDidMount = async () => { - const apiURL = `/api/get_indiv_sentences/${this.props.textID}`; - const response = await fetch(apiURL); - const textData = await response.json(); - this.setState({ textData }); - document.addEventListener('keydown', this.handleKeyDown, true); + try { + const apiURL = `/api/get_indiv_sentences/${this.props.textID}`; + const response = await fetch(apiURL); + const textData = await response.json(); + console.log(textData) + // this.setState({ textData }); + // document.addEventListener('keydown', this.handleKeyDown, true); + } catch (e) { + console.log(e) + } } componentWillUnmount() { From 122b141d78fc2a323803ab6b9047d66720e39527 Mon Sep 17 00:00:00 2001 From: taokinbo <70776613+taokinbo@users.noreply.github.com> Date: Fri, 30 Apr 2021 16:32:53 -0400 Subject: [PATCH 04/27] properlly connected backend to front end --- backend/app/analysis/text_parser.py | 2 +- frontend/src/UILibrary/styles.scss | 1 + frontend/src/app.js | 2 ++ frontend/src/textToSpeech/textToSpeech.js | 18 +++++++++--------- 4 files changed, 13 insertions(+), 10 deletions(-) diff --git a/backend/app/analysis/text_parser.py b/backend/app/analysis/text_parser.py index 331e613..bfabcfc 100644 --- a/backend/app/analysis/text_parser.py +++ b/backend/app/analysis/text_parser.py @@ -11,7 +11,7 @@ def get_sentences(text): """ Given a Text object, stores the definitions, examples, and image urls for all the words in this text. - :param text_obj: the Text object that we want to get sentences from + :param text: the Text object that we want to get sentences from """ sentences = nltk.tokenize.sent_tokenize(text) diff --git a/frontend/src/UILibrary/styles.scss b/frontend/src/UILibrary/styles.scss index 96bb13f..8e9cae9 100644 --- a/frontend/src/UILibrary/styles.scss +++ b/frontend/src/UILibrary/styles.scss @@ -7,6 +7,7 @@ @import '../crosswordView/crosswordView'; @import '../instructorView/instructorView'; @import '../flashcard/flashcardView'; +@import '../textToSpeech/textToSpeech'; html { position: relative; diff --git a/frontend/src/app.js b/frontend/src/app.js index ae89ace..4737a4e 100644 --- a/frontend/src/app.js +++ b/frontend/src/app.js @@ -14,6 +14,7 @@ import { InstructorView } from './instructorView/instructorView'; import { AllQuizView } from './quizView/allQuizView'; import { FlashcardView } from './flashcard/flashcardView'; import { CrosswordView } from './crosswordView/crosswordView'; +import {TextToSpeech} from './textToSpeech/textToSpeech'; // Import all styles import './UILibrary/styles.scss'; @@ -30,4 +31,5 @@ window.app_modules = { CrosswordView, IndexView, QuizView, + TextToSpeech, }; diff --git a/frontend/src/textToSpeech/textToSpeech.js b/frontend/src/textToSpeech/textToSpeech.js index a0347de..98d71f8 100644 --- a/frontend/src/textToSpeech/textToSpeech.js +++ b/frontend/src/textToSpeech/textToSpeech.js @@ -9,17 +9,16 @@ const capitalize = (word) => { const synth = window.speechSynthesis; -const play_button = (color) => { +const playButton = (color) => { return ( { const { textData, sentenceIndex } = this.state; - const listLength = textData.length; + const listLength = textData.length; const newsentenceIndex = (sentenceIndex + delta + listLength) % listLength; this.setState({ sentenceIndex: newsentenceIndex, @@ -77,8 +76,9 @@ export class TextToSpeech extends Component { } playAudio = () => { - let utterance = new SpeechSynthesisUtterance(); - utterance.text = textData[sentenceIndex]; + const utterance = new SpeechSynthesisUtterance(); + // utterance.text = textData[sentenceIndex]; + utterance.text = 'hello'; utterance.lang = 'en-US'; utterance.rate = 1.2; speechSynthesis.speak(utterance); @@ -153,7 +153,7 @@ export class TextToSpeech extends Component { // onClick={this.playAudio}> // {play_button('yellow')} //
- const flipcard =
Hello
+ const flipcard =
Hello
; //
You do not have any starred cards
; // const flipcard = card From 18c708bfc72adc2883ce6cef0cbb9df932e5eda2 Mon Sep 17 00:00:00 2001 From: Yifan Wang Date: Fri, 30 Apr 2021 16:45:22 -0400 Subject: [PATCH 05/27] got page to show --- backend/app/views.py | 2 -- frontend/src/app.js | 2 +- frontend/src/index/index.js | 2 +- frontend/src/textToSpeech/textToSpeech.js | 27 ++++++++++------------- 4 files changed, 14 insertions(+), 19 deletions(-) diff --git a/backend/app/views.py b/backend/app/views.py index 003d231..5fe240f 100644 --- a/backend/app/views.py +++ b/backend/app/views.py @@ -200,10 +200,8 @@ def get_indiv_sentences(request, text_id): """ API endpoint for getting the individual sentences from the given text. """ - print("is this even running") text_obj = Text.objects.get(id=text_id) sentences = get_sentences(text_obj.content) # return Response(sentences) res = [{'sentence': sentence} for sentence in sentences] - print(sentences) return Response(res) diff --git a/frontend/src/app.js b/frontend/src/app.js index 4737a4e..2443a2d 100644 --- a/frontend/src/app.js +++ b/frontend/src/app.js @@ -14,7 +14,7 @@ import { InstructorView } from './instructorView/instructorView'; import { AllQuizView } from './quizView/allQuizView'; import { FlashcardView } from './flashcard/flashcardView'; import { CrosswordView } from './crosswordView/crosswordView'; -import {TextToSpeech} from './textToSpeech/textToSpeech'; +import { TextToSpeech } from './textToSpeech/textToSpeech'; // Import all styles import './UILibrary/styles.scss'; diff --git a/frontend/src/index/index.js b/frontend/src/index/index.js index 57f17f1..2fc7730 100644 --- a/frontend/src/index/index.js +++ b/frontend/src/index/index.js @@ -12,7 +12,7 @@ const QUIZ_TYPES = { 'Flashcards': posLink, 'Quiz': idLink, 'Crossword': posLink, - 'TextToSpeech': idLink + 'TextToSpeech': idLink, }; class TextInfo extends React.Component { diff --git a/frontend/src/textToSpeech/textToSpeech.js b/frontend/src/textToSpeech/textToSpeech.js index 98d71f8..869543e 100644 --- a/frontend/src/textToSpeech/textToSpeech.js +++ b/frontend/src/textToSpeech/textToSpeech.js @@ -41,16 +41,14 @@ export class TextToSpeech extends Component { } componentDidMount = async () => { - try { - const apiURL = `/api/get_indiv_sentences/${this.props.textID}`; - const response = await fetch(apiURL); - const textData = await response.json(); - console.log(textData); - // this.setState({ textData }); - // document.addEventListener('keydown', this.handleKeyDown, true); - } catch (e) { - console.log(e); - } + const apiURL = `/api/get_indiv_sentences/${this.props.textID}`; + const response = await fetch(apiURL); + const data = await response.json(); + this.setState({ + textData: data, + }); + console.log(this.state.textData); + document.addEventListener('keydown', this.handleKeyDown, true); } componentWillUnmount() { @@ -62,7 +60,7 @@ export class TextToSpeech extends Component { sentenceIndex, textData, } = this.state; - return textData[sentenceIndex]; + return this.state.textData[this.state.sentenceIndex]; } changeSentence = (delta) => { @@ -77,8 +75,7 @@ export class TextToSpeech extends Component { playAudio = () => { const utterance = new SpeechSynthesisUtterance(); - // utterance.text = textData[sentenceIndex]; - utterance.text = 'hello'; + utterance.text = this.state.textData[this.state.sentenceIndex]; utterance.lang = 'en-US'; utterance.rate = 1.2; speechSynthesis.speak(utterance); @@ -148,12 +145,12 @@ export class TextToSpeech extends Component { : `${sentenceIndex + 1}/${sentenceLength} Words`; /* Generate Flashcard */ - const card = this.getcurrentSentence(); + const card = this.getCurrentSentence(); // const flipcard =
// {play_button('yellow')} //
- const flipcard =
Hello
; + const flipcard =
Hello
; //
You do not have any starred cards
; // const flipcard = card From 8d85baedfad5f00686719b3ee7e67158bad79493 Mon Sep 17 00:00:00 2001 From: taokinbo <70776613+taokinbo@users.noreply.github.com> Date: Fri, 30 Apr 2021 17:03:09 -0400 Subject: [PATCH 06/27] Audio now plays --- frontend/src/textToSpeech/textToSpeech.js | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-) diff --git a/frontend/src/textToSpeech/textToSpeech.js b/frontend/src/textToSpeech/textToSpeech.js index 869543e..f0447cd 100644 --- a/frontend/src/textToSpeech/textToSpeech.js +++ b/frontend/src/textToSpeech/textToSpeech.js @@ -7,7 +7,7 @@ const capitalize = (word) => { return word.charAt(0).toUpperCase() + word.slice(1); }; -const synth = window.speechSynthesis; +// const synth = window.speechSynthesis; const playButton = (color) => { return ( @@ -60,7 +60,7 @@ export class TextToSpeech extends Component { sentenceIndex, textData, } = this.state; - return this.state.textData[this.state.sentenceIndex]; + return this.state.textData[this.state.sentenceIndex]['sentence']; } changeSentence = (delta) => { @@ -75,7 +75,7 @@ export class TextToSpeech extends Component { playAudio = () => { const utterance = new SpeechSynthesisUtterance(); - utterance.text = this.state.textData[this.state.sentenceIndex]; + utterance.text = this.getCurrentSentence(); utterance.lang = 'en-US'; utterance.rate = 1.2; speechSynthesis.speak(utterance); @@ -146,11 +146,12 @@ export class TextToSpeech extends Component { /* Generate Flashcard */ const card = this.getCurrentSentence(); - // const flipcard =
- // {play_button('yellow')} - //
- const flipcard =
Hello
; + const flipcard =
+ {playButton('yellow')} + +
; + // const flipcard =
{this.getCurrentSentence()}
; //
You do not have any starred cards
; // const flipcard = card From 613d146980dd24252b6ac005500a813f0377ecbe Mon Sep 17 00:00:00 2001 From: taokinbo <70776613+taokinbo@users.noreply.github.com> Date: Fri, 30 Apr 2021 17:18:33 -0400 Subject: [PATCH 07/27] Got the arrow keys working --- frontend/src/textToSpeech/textToSpeech.js | 30 ++++++++++++++++++++--- 1 file changed, 26 insertions(+), 4 deletions(-) diff --git a/frontend/src/textToSpeech/textToSpeech.js b/frontend/src/textToSpeech/textToSpeech.js index f0447cd..edcb0a4 100644 --- a/frontend/src/textToSpeech/textToSpeech.js +++ b/frontend/src/textToSpeech/textToSpeech.js @@ -107,6 +107,8 @@ export class TextToSpeech extends Component { this.changeSentence(-1); } else if (code === 'ArrowRight') { this.changeSentence(1); + } else if (code === 'Space') { + this.playAudio(); } } } @@ -146,11 +148,31 @@ export class TextToSpeech extends Component { /* Generate Flashcard */ const card = this.getCurrentSentence(); - const flipcard =
- {playButton('yellow')} + // const flipcard =
+ // {playButton('yellow')} + // + //
; + + const flipcard = +
+
+ {playButton('yellow')} + +
+
+
this.changeSentence(-1)} + > + < +
+
this.changeSentence(1)}> + > +
+
-
; +
; // const flipcard =
{this.getCurrentSentence()}
; //
You do not have any starred cards
; From 91db718bb1c0f50402a39b714d99889a6318f87d Mon Sep 17 00:00:00 2001 From: taokinbo <70776613+taokinbo@users.noreply.github.com> Date: Sun, 2 May 2021 21:29:05 -0400 Subject: [PATCH 08/27] fixed small error --- frontend/src/index/index.js | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/frontend/src/index/index.js b/frontend/src/index/index.js index c221624..d996027 100644 --- a/frontend/src/index/index.js +++ b/frontend/src/index/index.js @@ -14,7 +14,7 @@ const QUIZ_TYPES = { 'Quiz': ['quiz', idLink], 'Crossword': ['crossword', posLink], 'Story Generator': ['picturebook', posLink], - 'TextToSpeech': ["textToSpeech", idLink] + 'TextToSpeech': ['textToSpeech', idLink] }; class TextInfo extends React.Component { From f0019a35157ee64204df6cc2ba3ea17af5957b55 Mon Sep 17 00:00:00 2001 From: taokinbo <70776613+taokinbo@users.noreply.github.com> Date: Tue, 4 May 2021 16:53:40 -0400 Subject: [PATCH 09/27] started creatinf grader --- backend/app/analysis/text_parser.py | 29 +++++++++++++++++++++++++++++ 1 file changed, 29 insertions(+) diff --git a/backend/app/analysis/text_parser.py b/backend/app/analysis/text_parser.py index bfabcfc..3362f66 100644 --- a/backend/app/analysis/text_parser.py +++ b/backend/app/analysis/text_parser.py @@ -25,6 +25,35 @@ def get_sentences(text): print(sentences) return sentences +def correct_sentence(given_sent, correct_sent): + grade = {} + given_tok = nltk.tokenize.word_tokenize(given_sent) + correct_tok = nltk.tokenize.word_tokenize(correct_sent) + + + index = 0 + for word in given_tok: + match_found = False + for ind, match in enumerate(correct_tok[index:]): + print(word, match) + if word == match: + match_found = True + match_index = ind + index + break + if match_found: + grade[word] = "correct" + index = match_index + 1 + else: + grade[word] = "incorrect" + return grade + + +if __name__ == '__main__': + actual = "i like soup" + given = "i like" + print(actual, given) + print(correct_sentence(given, actual)) + From 75b9b5d2ed3acb2b4c3dcddc32520cdf9486c942 Mon Sep 17 00:00:00 2001 From: taokinbo <70776613+taokinbo@users.noreply.github.com> Date: Wed, 5 May 2021 11:04:31 -0400 Subject: [PATCH 10/27] updated grader to match which words are correct and incorrect --- backend/app/analysis/text_parser.py | 43 +++++++++++++++++------------ backend/app/views.py | 3 +- 2 files changed, 28 insertions(+), 18 deletions(-) diff --git a/backend/app/analysis/text_parser.py b/backend/app/analysis/text_parser.py index 3362f66..05c5108 100644 --- a/backend/app/analysis/text_parser.py +++ b/backend/app/analysis/text_parser.py @@ -2,6 +2,7 @@ Custom command to populate text model with definition, examples, and images """ import nltk +import string # Ours @@ -25,43 +26,51 @@ def get_sentences(text): print(sentences) return sentences + def correct_sentence(given_sent, correct_sent): grade = {} - given_tok = nltk.tokenize.word_tokenize(given_sent) - correct_tok = nltk.tokenize.word_tokenize(correct_sent) + print(given_sent.translate(str.maketrans('', '', string.punctuation))) + given_tok = nltk.tokenize.word_tokenize(given_sent.translate( + str.maketrans('', '', string.punctuation))) + correct_tok = nltk.tokenize.word_tokenize(correct_sent.translate( + str.maketrans('', '', string.punctuation))) + + words_missing = correct_tok.copy() + for word in given_tok: + if words_missing.count(word) != 0: + words_missing.remove(word) + grade["missing"] = words_missing index = 0 - for word in given_tok: + for ind_1, word in enumerate(given_tok): match_found = False - for ind, match in enumerate(correct_tok[index:]): - print(word, match) + for ind_2, match in enumerate(correct_tok[index:]): + # print(word, match) if word == match: match_found = True - match_index = ind + index + match_index = ind_2 + index break if match_found: - grade[word] = "correct" + grade[ind_1] = {"word": word, + "grade": "correct"} index = match_index + 1 else: - grade[word] = "incorrect" + grade[ind_1] = {"word": word, + "grade": "incorrect"} return grade if __name__ == '__main__': actual = "i like soup" - given = "i like" + given = "i like, soop" print(actual, given) print(correct_sentence(given, actual)) - - - - - - - - + # actual = ["i like soup", "soup likes me", "EOM"] + # + # res = [{'sentence': sentence} for sentence in actual] + # print(res) # part_of_speech = ['noun', 'verb', 'adjective', 'adverb'] # diff --git a/backend/app/views.py b/backend/app/views.py index bf6c82d..17f4319 100644 --- a/backend/app/views.py +++ b/backend/app/views.py @@ -123,7 +123,6 @@ def get_anagram(request, text_id, part_of_speech): return Response(res) - @api_view(['GET']) def get_picturebook_prompt(request, text_id, part_of_speech): """ @@ -231,6 +230,7 @@ def get_quiz_data(request, text_id): res = get_quiz_sentences(text_obj.content) return Response(res) + @api_view(['GET']) def get_indiv_sentences(request, text_id): """ @@ -241,3 +241,4 @@ def get_indiv_sentences(request, text_id): # return Response(sentences) res = [{'sentence': sentence} for sentence in sentences] return Response(res) + From b8f392ce65ec7930e6b7b0908d99c048fefb3fd0 Mon Sep 17 00:00:00 2001 From: adanna-a <70187411+adanna-a@users.noreply.github.com> Date: Sat, 8 May 2021 21:44:09 -0400 Subject: [PATCH 11/27] text box --- frontend/src/textToSpeech/textToSpeech.js | 66 +++++++++++++++++++++++ 1 file changed, 66 insertions(+) diff --git a/frontend/src/textToSpeech/textToSpeech.js b/frontend/src/textToSpeech/textToSpeech.js index edcb0a4..529b749 100644 --- a/frontend/src/textToSpeech/textToSpeech.js +++ b/frontend/src/textToSpeech/textToSpeech.js @@ -36,6 +36,7 @@ export class TextToSpeech extends Component { sentenceIndex: 0, showModal: false, nextSentence: false, + userText: '', }; this.modalHandler = this.modalHandler.bind(this); } @@ -81,6 +82,48 @@ export class TextToSpeech extends Component { speechSynthesis.speak(utterance); } + handleInput = (event) => { + const inputValue = event.target.value; + this.setState({ + userText: inputValue, + }); + + // if (';,. '.includes(inputValue.slice(-1))) { + // this.createPictureBook(inputValue); + // } + console.log('this is the input value:'); + console.log(inputValue); + console.log('this is the state value:'); + console.log(this.userText); + }; + + handleSubmit = (event) => { + // const inputValue = ; + // this.setState({ + // userText: inputValue, + // }); + + // if (';,. '.includes(inputValue.slice(-1))) { + this.gradeText(); + // } + console.log('You have submitted!!!'); + // console.log(inputValue); + // console.log('this is the state value:'); + // console.log(this.userText); + }; + + gradeText = async (input) => { + try { + const apiURL = '/api/get_picturebook_data?content=' + input; + const response = await fetch(apiURL); + const pictureBookWords = await response.json(); + pictureBookWords.pop(-1); + this.setState({ pictureBookWords }); + } catch (e) { + console.log(e); + } + } + // toggleStar = () => { // const { starredCards, starOnly, cardIndex } = this.state; // let currentIndex = starOnly ? starredCards[cardIndex] : cardIndex; @@ -316,6 +359,29 @@ export class TextToSpeech extends Component { {flipcard} +
+
+
+
+ + +
+
+
+
+ +
+