首页 > 解决方案 > 在 botframework 网络聊天中发送消息(来自建议)后,如何清除聊天输入框?

问题描述

我正在使用 react js 和 botframework webchat 开发一个机器人应用程序。问题是我想在发送消息后清除文本输入框(从那里发送消息) - 这是从建议中选择的。建议列表(或自动完成组件)是自定义编码的。我的意思是,如果我输入“hr”,建议列表弹出窗口就会出现,如果我点击建议中的一个选项,比如“hr 门户”,它将被发送,但我写的内容,即“hr”仍然存在在输入字段中,我想清除它。请注意,如果我输入一些东西并发送它的工作正常。问题只是当我输入一些东西并从建议中选择一些东西时。其他一切都很好。我怎样才能清除它。任何帮助将非常感激。

请找到下图以获得更多理解。

这是我的代码;

import React from 'react';
import { DirectLine, ConnectionStatus } from 'botframework-directlinejs';
import ReactWebChat from 'botframework-webchat';
import './ChatComponent.css';
var val;
var apiParameters = [];
var currentFocus = -1;
export default class extends React.Component {
    constructor(props) {
        super(props);
        this.state = {
            token: '',
            conversationId: '',
            directLine: {},
            view: false,
            feedBack: null,
            value: '',
            popupContent: '',
            storeValue: '',
            suggestions: [],
            suggestionCallback: '',
            suggestionTypedText: "",
            typingChecking: "false",
        };
        this.handleTokenGeneration = this.handleTokenGeneration.bind(this);
        this.handleChange = this.handleChange.bind(this);
        this.handleSaveFeedback = this.handleSaveFeedback.bind(this);
        this.handleSuggestion = this.handleSuggestion.bind(this);
        this.handleClose = this.handleClose.bind(this);
        this.handleSuggestionClick = this.handleSuggestionClick.bind(this);
        this.handleKeyDown = this.handleKeyDown.bind(this);
        this.moveHighlight = this.moveHighlight.bind(this);
        this.getSuggestionHtml = this.getSuggestionHtml.bind(this);
    }
    getSuggestionHtml(suggestion) {
        const lowerCaseSuggestion = suggestion.toLowerCase();
        return {
            __html: lowerCaseSuggestion.includes(this.state.suggestionTypedText) ? lowerCaseSuggestion
                .replace(this.state.suggestionTypedText, `<b>${this.state.suggestionTypedText}</b>`) : lowerCaseSuggestion
        };
    }
    handleTokenGeneration = async () => {
        console.log("11111");
        const response = await fetch(`api/TokenGenerationService/GetToken`);
        const data = await response.json();
        this.setState({
            token: data.categoryObject.token, conversationId:
                data.categoryObject.conversationId
        });
        this.state.directLine = new DirectLine({ token: this.state.token });
        this.setState({ view: true });
        this.setState({ typingChecking: "true" });
        console.log("conversationId");
    };
    async handleSuggestion(val, store) {
        if (val === "") {
            this.setState({
                suggestions: []
            });
        }
        else {
            apiParameters = [];
            var valuess = null;
            const response = await fetch(`api/TokenGenerationService/GetAzureSearch?myparam1=${val}`);
            const data = await response.json();
            var values = ["Hello", "yes", "no", "exit", "Welcome", "Thank You", "Approve", "Apply leave", "Reject", "Absence Balance", "Leave Balance", "Upcoming Holidays", "Apply Comp-Off", "Approve Leave", "Raise Incident Tickets", "Project Allocation Info", "Reporting Manager Change", "Reporting Manager Approval", "Approve Isolve Tickets", "My Manager", "My Account Manager", "Generate Salary Certificate", "Isolve Ticket Status", "Internal Job Posting", "My Designation", "My Joining Date", "RM Approval", "RM Change", "Resource Allocation", "ESettlement Approval", "SO Approval", "Cash advance Approval", "Purchase Request Approval", "Referral status", "HR Ticket", "Platinum Support"];
            valuess = values.filter(s =>
                s.toLocaleLowerCase().startsWith(val.toLowerCase())
            );
            valuess = valuess.concat(data.az_search);
            this.setState({
                suggestions: valuess,
                suggestionCallback: store,
                suggestionTypedText: val.toLowerCase()
            });
            // alert(data.az_search);
            var totCount = data.az_search;
            console.log("kkkkkk" + totCount);
        }
    }
    moveHighlight(event, direction) {
        event.preventDefault();
        const { highlightedIndex, suggestions } = this.state;
        if (!suggestions.length) return;
        let newIndex = (highlightedIndex + direction + suggestions.length) % suggestions.length;
        if (newIndex !== highlightedIndex) {
            this.setState({
                highlightedIndex: newIndex,
            });
        }
    }
    keyDownHandlers = {
        ArrowDown(event) {
            this.moveHighlight(event, 1);
        },
        ArrowUp(event) {
            this.moveHighlight(event, -1);
        },
        Enter(event) {
            const { suggestions } = this.state;
            if (!suggestions.length) {
                // menu is closed so there is no selection to accept -> do nothing
                return
            }
            event.preventDefault()
            this.applySuggestion(suggestions[this.state.highlightedIndex]);
        },
    }
    handleKeyDown(event) {
        // console.log("lokkkkkkkkkkkk")
        if (this.keyDownHandlers[event.key])
            this.keyDownHandlers[event.key].call(this, event)
    }
    async handleSuggestionClick(event) {
        await this.applySuggestion(event.currentTarget.textContent);
    }
    async applySuggestion(newValue) {
        //newValue = null;
        await this.setState({ typingChecking: "false", suggestions: [], highlightedIndex: 0 });
        this.state.suggestionCallback.dispatch({
            type: 'WEB_CHAT/SEND_MESSAGE',
            payload: {
                text: newValue
            }
        });
        await this.setState({ typingChecking: "true" });
    }
    getSuggestionCss(index) {
        var HIGHLIGHTED_CSS = "HIGHLIGHTED_CSS";
        var SUGGESTION_CSS = "SUGGESTION_CSS";
        return index === this.state.highlightedIndex ? HIGHLIGHTED_CSS : SUGGESTION_CSS;
    }
    handleClose(elmnt) {
        var x = document.getElementsByClassName("autocomplete-items");
        for (var i = 0; i < x.length; i++) {
            if (elmnt !== x[i]) {
                x[i].parentNode.removeChild(x[i]);
            }
        }
    }
    async componentDidMount() {
        try {
            await this.handleTokenGeneration();
            const store =
                window.WebChat.createStore(
                    {},
                    ({ getState }) => next => action => {
                        this.state.directLine.connectionStatus$
                            .subscribe(connectionStatus => {
                                if (connectionStatus === ConnectionStatus.ExpiredToken) {
                                    console.log("expired");
                                }
                                if (action.type === 'WEB_CHAT/SET_SEND_BOX') {
                                    const val = action.payload.text;
                                    if (this.state.typingChecking === "true") {
                                        this.setState({
                                            highlightedIndex: -1,
                                        });
                                        console.log(this.state.typingChecking);
                                        this.handleSuggestion(val, store);
                                    }
                                }
                                if (action.type === 'DIRECT_LINE/DISCONNECT_FULFILLED') {
                                    console.log("final" + connectionStatus);
                                    console.log("finalexpired" + ConnectionStatus.ExpiredToken);
                                    console.log("final");
                                    this.handleTokenGeneration();
                                }
                            });
                        return next(action)
                    }
                );
            this.setState({ storeValue: store });
        } catch (error) {
            console.log("error in fetching token");
            console.log(error);
        }
        this.state.directLine.activity$
            .filter(activity => activity.type === 'message')
            .subscribe(function (activity) {
                //console.log("oooooooooooooooooooooo");
            }
                // message => console.log("received message ", message.text)
            );
    }
    handleSaveFeedback(ans) {
        // console.log(this.state.conversationId);
        //  console.log(this.state.feedBack);
        var userID = "C94570";
        var feedbackmsg = this.state.value;
        var feedbacktype = this.state.feedBack;
        var convId = this.state.conversationId;
        fetch('api/Feedback/SaveFeedback',
            {
                method: "POST",
                headers: { 'Content-Type': 'application/json' },
                body: JSON.stringify({ Uid: userID, FeedbackMessage: feedbackmsg, Convid: convId, FeedbackType: feedbacktype })
            }).
            then(response => response.text())
            .then(data => {
                console.log(data.getResult);
            });
        this.setState({ value: '' });
    }
    feedback(ans) {
        this.setState({ feedBack: ans });
        if (ans === "Send") {
            this.handleSaveFeedback(ans);
        }
        else if (ans === "Yes") {
            this.setState({ popupContent: "How was your experience?" });
            // console.log(this.state.value)
        }
        else if (ans === "No") {
            this.setState({ popupContent: "What went wrong?" });
            // console.log(this.state.value)
        }
    }
    handleChange = (event) => {
        this.setState({ value: event.target.value });
    }
    styleOptions = {
        bubbleBackground: 'rgba(0, 0, 255, .1)',
        bubbleFromUserBackground: 'rgba(0, 255, 0, .1)',
        botAvatarInitials: 'DIA',
        userAvatarInitials: 'ME'
    }
    render() {
        if (!this.state.view) {
            return
            <div />
        } else {
            const filteredSuggestions = this.state.suggestions.filter(
                suggestion =>
                    suggestion.toLowerCase().indexOf(this.state.suggestionTypedText.toLowerCase())
                    > -1
            );
            //   console.log(this.state.view);
            return (
                <div className="react-container webchat" >
                    <div onKeyDown={this.handleKeyDown.bind(this)}>
                        <div >
                            <ReactWebChat styleOptions={this.styleOptions} directLine={this.state.directLine} webSocket={true} userID='C94570' username='Thomas' store={this.state.storeValue} sendTypingIndicator={true} />
                        </div>
                    </div>
                    <div className="SuggestionParent" id="Suggestion1">
                        {this.state.suggestions.map((suggestion, index) => (
                            <div className={this.getSuggestionCss(index)} key={index} onClick={this.handleSuggestionClick} >
                                {suggestion
                                    .toLowerCase()
                                    .startsWith(this.state.suggestionTypedText) ? (
                                        <div>
                                            <b>{this.state.suggestionTypedText}</b>
                                            {suggestion
                                                .toLowerCase()
                                                .replace(this.state.suggestionTypedText, "")}
                                        </div>
                                    ) : (
                                        <div dangerouslySetInnerHTML={this.getSuggestionHtml(suggestion)} />
                                    )}
                            </div>
                        ))}
                    </div>
                    <footer className="chat-footer" >
                        <div className="foot-footer">
                            Was I helpful ?
         <span className="feedback" onClick={() => this.feedback("Yes")} >Yes</span><span>|</span><span className="feedback" onClick={() => this.feedback("No")}>No</span>
                            {
                                this.state.feedBack === "Yes" || this.state.feedBack === "No" ?
                                    (
                                        <div className="dialog" id="myform">
                                            <div id="textfeedback">
                                                <span id="closeFeedback" onClick={() => this.feedback("Close")}>X</span>
                                                <p>{this.state.popupContent}</p>
                                                <input type="text" id="feedbacktxtbox" required name="textfeedback" placeholder="Pleasure to hear from u!"
                                                    onChange={this.handleChange}
                                                    value={this.state.value} />
                                                <button type="button" id="btnfeedback" onClick={() => this.feedback("Send")}>send</button>
                                            </div>
                                        </div>
                                    ) : null
                            }
                        </div>
                    </footer>
                </div>
            );
        }
    }
}

标签: javascriptreactjsbotframeworkdirect-line-botframeworkweb-chat

解决方案


聊天输入框在网络聊天中称为发送框。清除发送框只是将发送框设置为空字符串。当您正常单击发送按钮时,此操作会自动完成。您可以在提交发送框传奇中看到,提交发送框意味着执行两个操作:发送消息和设置发送框。

if (sendBoxValue) {
  yield put(sendMessage(sendBoxValue.trim(), method, { channelData }));
  yield put(setSendBox(''));
}

这意味着如果您使用该SUBMIT_SEND_BOX操作,则发送框将自动清除。当然,如果您希望它与您的自动完成组件一起使用,那么您需要在提交之前使用自动完成文本设置发送框。您的另一个选择是SET_SEND_BOX在发送消息后仅使用带有空字符串的操作。


推荐阅读