import React, { Component, setState } from 'react'; import { Text, TouchableOpacity, Alert, View, StyleSheet } from 'react-native'; import Voice from '@react-native-community/voice'; import Icon from 'react-native-vector-icons/FontAwesome'; import { tr } from 'date-fns/locale'; import Modal from 'react-native-modalbox'; import { Icons } from '../globals'; import { MapContext } from '../contexts/MapContext' import RNLocation from 'react-native-location'; import { alternatives } from 'joi'; class VoiceView extends Component { static contextType = MapContext; constructor(props) { super(props); Voice.onSpeechStart = this.onSpeechStart; Voice.onSpeechResults = this.onSpeechResults; Voice.onSpeechRecognized = this.onSpeechRecognized; Voice.onSpeechPartialResults = this.onSpeechPartialResults; Voice.onSpeechError = this.onSpeechError; Voice.onSpeechEnd = this.onSpeechEnd; this.modalRef = React.createRef(); this.state = { recognized: false, started: false, ended: false, actionText: '', action: null, results: [], partialResults: [], error: '' } } addLandmark = (type) => { this.modalRef.current.close(); console.log(this.context.mapState.location.latitude) console.log(this.context.mapState.location.longitude) this.props.changeSelectedLandmark({icon: type, title: 'New landmark', latitude: this.context.mapState.location.latitude, longitude: this.context.mapState.location.longitude,}); this.props.editLandmark(); } open() { this.modalRef.current.open(); this._startRecognizing(); } close() { this.modalRef.current.close(); this._stopRecognizing(); } stop() { this._stopRecognizing() } componentWillUnmount() { this._stopRecognizing(); } onSpeechStart = (e) => { this.setState({ started: true }); }; onSpeechRecognized = (e) => { this.setState({ recognized: true }); }; onSpeechResults = (e) => { this.setState({ results: e.value }); let requestedAction = ''; if ((e.value[0].includes("add") || e.value[0].includes("ad") || e.value[0].includes("had"))) { if (e.value[0].includes('landmark')) { requestedAction = 'Add Landmark' this.state.action = () => this.addLandmark(); } if (Object.keys(Icons).some(icon => {return e.value[0].includes(icon)})) { const requestedTypes = Object.keys(Icons).filter(icon => {return e.value[0].includes(icon)}) requestedAction = 'Add ' + requestedTypes[0].toString(); this.state.action = () => this.addLandmark(requestedTypes[0]); } if (e.value[0].includes('road') && e.value[0].includes('block')) { requestedAction = 'Add ' + 'roadblock'; this.state.action = () => this.addLandmark('roadblock'); } } if (e.value) { } this.setState({ actionText: requestedAction }); }; onSpeechPartialResults = (e) => { this.setState({ partialResults: e.value }); }; onSpeechError = (e) => { this.setState({ error: e.value }) }; onSpeechEnd = (e) => { this.setState({ ended: true }) } _startRecognizing = async (e) => { this.setState({ started: false, ended: false, recognized: false, error: '', results: [], partialResults: [], }) try { await Voice.start('en-US') } catch (error) { } } _stopRecognizing = async (e) => { Voice.destroy().then(Voice.removeAllListeners); } render() { return ( Voice.destroy().then(Voice.removeAllListeners)}> this.modalRef.current.close()}> {this.state.started && !this.state.ended ? Listening... : null} {this.state.results.length ? We heard: {this.state.results[0]} : null} {this.state.partialResults.length > 0 && !this.state.ended ? {this.state.partialResults[0]} : null} {this.state.ended ? {this.state.actionText ? {this.state.actionText} - Confirm? : No valid action was percieved.} : null} ) } } const styles = StyleSheet.create({ voiceModal: { backgroundColor: '#df3f3f', height: 200, }, btnContainer: { paddingTop: 20, borderTopWidth: 1, borderColor: 'lightgrey', flexDirection: 'row', justifyContent: 'space-between', alignItems: 'center', position: 'absolute', width: 300, bottom: 30, right: 30, } }) export default VoiceView;