Как исправить положение текстового поля и добавить функцию прокрутки в сообщения - PullRequest
0 голосов
/ 18 июня 2020

Я пишу приложение для чата на React. Текущий дизайн компонента Messenger имеет левую боковую панель, центральный блок и правую боковую панель. В идеале нижняя часть центрального блока представляет собой текстовое поле фиксированного размера, а остальная часть пространства от верхнего края до блока до верха текстового поля - это область для сообщений, которая позволяет прокручивать при переполнении.

Однако я не уверен, как добавить в свое приложение эту «прокрутку» и функциональность текстового поля фиксированного размера. В настоящее время начало текстового поля следует за последним сообщением, и когда последнее сообщение превышает размер экрана по вертикали, текстовое поле не отображается.

Может кто-нибудь подсказать, как это сделать? Вот мой код реакции, содержащий только основные элементы, а файл App.css. При необходимости вы можете запросить дополнительный код.

Приложение. js

import React, { Component } from "react";
import "./App.css";

import classNames from "classnames";
import "./App.css";

// Components
import _ from "lodash";

const MESSENGER_HEIGHT = "height";
const MESSENGER_NEW_MESSAGE = "newMessage";
const MESSENGER_SEARCH_USER = "searchUser";
const MESSENGER_SHOW_SEARCH_USER = "showSearchUser";
const MESSENGER_ACTIVE_CHANNEL_ID = "channel_id";
const MESSENGER_MEMBERS = "members";
const MESSENGER_MESSAGES = "messages";
const MESSENGER_CHANNELS = "channels";
const MESSENGER_PROFILE_ID = "profile_id";

//remove the authentication routes



class App extends Component {
  constructor(props) {
    super(props);
    this.state = {};
    const locals = this.state;
    locals[MESSENGER_HEIGHT] = window.innerHeight;
    locals[MESSENGER_NEW_MESSAGE] = "";
    locals[MESSENGER_SEARCH_USER] = "";
    locals[MESSENGER_SHOW_SEARCH_USER] = false;
    locals[MESSENGER_ACTIVE_CHANNEL_ID] = "Mk3d9WJRiyifxgtJ1Ep1"; //TODO: trial run set default one
    locals[MESSENGER_MEMBERS] = ["person1", "person2"];
    locals[MESSENGER_MESSAGES] = [
      "1",
      "2",
      "3",
      "4",
      "5",
      "6",
      "7",
      "8",
      "9",
      "10",
      "11",
      "12",
      "13"
    ];
    locals[MESSENGER_CHANNELS] = [];
    locals[MESSENGER_PROFILE_ID] = "Testing profile_id";
  }

  render() {
    let component_variable = null;
    let members_list;
    //About the presence system
    if (this.state.members.length > 0) {
      members_list = (
        <div>
          <h2 className="title">Members</h2>
          <div className="members">
            {this.state.members.map(member => {
              return (
                <div className="member">
                  <div className="member-info">
                    <h2> {member}</h2>
                  </div>
                </div>
              );
            })}
          </div>
        </div>
      );
    } else {
      members_list = null;
    }

    let search_bar = null;

    let messages_list;
    if (this.state.messages !== undefined) {
      messages_list = (
        <div>
          <div ref={ref => (this.messagesRef = ref)} className="messages">
            {this.state.messages.map(message => {
              return (
                <div className={classNames("message", { me: true })}>
                  <div className="message-body">
                    <div className="message-author">{"You "} says:</div>
                    <div className="message-text">
                      {`Testing message ${message}`}
                    </div>
                    <div className="message-timestamp">Some Date</div>
                  </div>
                </div>
              );
            })}
          </div>
        </div>
      );
    } else {
      messages_list = null;
    }

    let text_box;

    if (this.state.members.length > 0) {
      text_box = (
        <div className="messenger-input">
          <div className="text-input">
            <textarea
              onKeyUp={this.handle_textbox_keyup}
              onChange={this.handle_textbox_set_state}
              value={this.state["newMessage"]}
              placeholder="Write your message..."
            />
          </div>
          <div className="actions">
            <button onClick={() => this.handleSend()} className="send">
              Send
            </button>
          </div>
        </div>
      );
    } else {
      text_box = null;
    }

    return (
      <div className="app-messenger">
        <div className="header">
          <div className="left">
            <button className="left-action">
              <i className="icon-settings-streamline-1" />
            </button>
            <button
              onClick={this.handle_create_channel}
              className="right-action"
            >
              <i className="icon-edit-modify-streamline" />
            </button>
            <h2>Messenger</h2>
          </div>
          <div className="content" />
          <div className="right">Hello world</div>
        </div>

        <div className="main">
          <div className="sidebar-left">
            <div className="chanels">
              {this.state.channels.map((channel, key) => {
                return (
                  <div
                    onClick={key => {
                      this.props.select_or_create_message_room({
                        id: channel._id
                      });
                    }}
                    key={channel._id}
                    className={classNames("chanel", {
                      notify: _.get(channel, "notify") === true
                    })}
                  >
                    <div className="channel-id">
                      {channel[MESSENGER_ACTIVE_CHANNEL_ID]}
                    </div>
                  </div>
                );
              })}
            </div>
          </div>

          <div className="content">
            {messages_list},{text_box}
          </div>

          {/*TODO: Member list*/}
          <div className="sidebar-right">{members_list}</div>
        </div>
      </div>
    );
  }
}

export default App;

Приложение. css

html,
  /*body {*/
  /*  font-family: -apple-system, BlinkMacSystemFont, 'Segoe UI', 'Roboto', 'Oxygen',*/
  /*    'Ubuntu', 'Cantarell', 'Fira Sans', 'Droid Sans', 'Helvetica Neue',*/
  /*    sans-serif;*/
  /*  background-color: rgb(245, 245, 245);*/
  /*}*/

.container {
  margin: 80px auto 0 auto;
  max-width: 1200px;
  /*Cannot hidden bc the home screen is ugly*/
}
.nav-container {
  margin: auto;
}
.nav-container svg {
  color: #fff;
}
a {
  text-decoration: none;
}



body, html {
  margin: 0;
  padding: 0;
  height: 100%;
  overflow: hidden;
}

body {
  color: #2c3e50;
  font-size: 13px;
  font-family: 'Open Sans', sans-serif;

}

* {
  box-sizing: border-box;
  padding: 0;
  margin: 0; }

.app-messenger {
  display: flex;
  flex-direction: column;
}
.app-messenger .header {
  height: 50px;
  display: flex;
  flex-direction: row;
  border-bottom: 1px solid rgba(0, 0, 0, 0.05); }
.app-messenger .header .left {
  width: 200px;
  position: relative; }
.app-messenger .header .left .left-action {
  position: absolute;
  left: 8px;
  top: 0; }
.app-messenger .header .left .right-action {
  position: absolute;
  right: 8px;
  top: 0; }
.app-messenger .header .left h2 {
  line-height: 50px;
  font-size: 14px;
  font-weight: 600;
  display: block;
  text-align: center; }
.app-messenger .header .left button {
  background: none;
  line-height: 50px;
  border: 0 none;
  font-size: 20px;
  cursor: pointer; }
.app-messenger .header .content {
  flex-grow: 1;
}
.app-messenger .header .content h2 {
  line-height: 50px;
  text-align: center; }
.app-messenger .header .right {
  width: 300px; }
.app-messenger .header .right .user-bar {
  line-height: 50px;
  display: flex;
  justify-content: flex-end;
  padding: 0 10px; }
.app-messenger .header .right .user-bar .profile-name {
  padding-right: 10px; }
.app-messenger .header .right .user-bar .profile-image {
  line-height: 50px; }
.app-messenger .header .right .user-bar .profile-image img {
  width: 30px;
  height: 30px;
  border-radius: 50%;
  margin: 10px 0 0 0; }
.app-messenger .main {
  height: 100%;
  display: flex;
  overflow: hidden; }
.app-messenger .main .sidebar-left {
  width: 200px;
  border-right: 1px solid rgba(0, 0, 0, 0.05); }
.app-messenger .main .sidebar-right {
  border-left: 1px solid rgba(0, 0, 0, 0.05);
  width: 300px; }
.app-messenger .main .sidebar-right .title {
  padding: 10px; }
.app-messenger .main .content {
  flex-grow: 1;
  overflow: scroll;
  display: flex;
  flex-direction: column; }
.app-messenger .main .content .messages {
  flex-grow: 1; }
.app-messenger .main .content .messenger-input {
  border-top: 1px solid rgba(0, 0, 0, 0.05);
  height: 50px;
  display: flex;
  flex-direction: row;
}
.app-messenger .main .content .messenger-input .text-input {
  flex-grow: 1; }
.app-messenger .main .content .messenger-input .text-input textarea {
  border: 0 none;
  width: 100%;
  height: 100%;
  padding: 8px 15px; }
.app-messenger .main .content .messenger-input .actions button.send {
  background: #2ecc71;
  color: #FFF;
  border: 0 none;
  padding: 7px 15px;
  line-height: 50px; }

.messages {
  display: flex;
  flex-direction: column;
  overflow-y: auto;
  height: 100%; }
.messages .message {
  display: flex;
  flex-direction: row;
  justify-content: flex-start;
  margin: 15px; }
.messages .message .message-user-image img {
  width: 20px;
  height: 20px;
  border-radius: 50%; }
.messages .message .message-body {
  padding-left: 10px; }

/*Try adding it manually, by right should make a message card, but will lose colour */

.messages .message .message-body .message-text {
  background: rgba(0, 0, 0, 0.05);
  padding: 10px;
  border-radius: 10px; }


.messages .message.me {
  justify-content: flex-end; }
.messages .message.me .message-body .message-text {
  background: #2ecc71;
  color: #FFF; }

.chanels {
  overflow-y: auto;
  height: 100%; }
.chanels .chanel {
  cursor: pointer;
  display: flex;
  border-bottom: 1px solid rgba(0, 0, 0, 0.05);
  padding: 8px; }
.chanels .chanel .user-image {
  width: 30px; }
.chanels .chanel .user-image img {
  max-width: 100%; }
.chanels .chanel .user-image .channel-avatars {
  overflow: hidden;
  width: 30px;
  height: 30px;
  border-radius: 50%;
  background-color: #ccc;
  position: relative; }
.chanels .chanel .user-image .channel-avatars.channel-avatars-1 img {
  width: 100%;
  height: 100%;
  border-radius: 50%; }
.chanels .chanel .user-image .channel-avatars.channel-avatars-2 img {
  width: 50%;
  height: 100%;
  position: absolute;
  right: 0;
  top: 0; }
.chanels .chanel .user-image .channel-avatars.channel-avatars-2 img:first-child {
  left: 0;
  top: 0; }
.chanels .chanel .user-image .channel-avatars.channel-avatars-3 img {
  position: absolute;
  width: 50%;
  height: 50%;
  right: 0;
  top: 0; }
.chanels .chanel .user-image .channel-avatars.channel-avatars-3 img:first-child {
  left: 0;
  top: 0;
  width: 50%;
  height: 100%; }
.chanels .chanel .user-image .channel-avatars.channel-avatars-3 img:last-child {
  bottom: 0;
  right: 0;
  top: 15px;
  width: 50%;
  height: 50%; }
.chanels .chanel .user-image .channel-avatars.channel-avatars-4 img {
  position: absolute;
  width: 50%;
  height: 50%;
  right: 0;
  top: 0; }
.chanels .chanel .user-image .channel-avatars.channel-avatars-4 img:first-child {
  left: 0;
  top: 0;
  width: 50%;
  height: 100%; }
.chanels .chanel .user-image .channel-avatars.channel-avatars-4 img:nth-child(3n) {
  bottom: 0;
  right: 0;
  top: 15px;
  width: 50%;
  height: 50%; }
.chanels .chanel .user-image .channel-avatars.channel-avatars-4 img:last-child {
  left: 0;
  bottom: 0;
  top: 15px; }
.chanels .chanel .chanel-info {
  flex-grow: 1;
  padding-left: 8px;
  padding-right: 8px;
  overflow: hidden; }
.chanels .chanel .chanel-info h2 {
  font-size: 13px;
  font-weight: 400;
  white-space: nowrap;
  text-overflow: ellipsis;
  overflow: hidden; }
.chanels .chanel .chanel-info p {
  font-size: 12px;
  white-space: nowrap;
  text-overflow: ellipsis;
  overflow: hidden; }
.chanels .chanel.active {
  background: rgba(0, 0, 0, 0.05); }
.chanels .chanel.notify .chanel-info p {
  color: #2ecc71; }

.members .member {
  display: flex;
  border-bottom: 1px solid rgba(0, 0, 0, 0.05);
  padding: 8px; }

.members .member .member-info {
  padding-left: 8px;
  flex-grow: 1; }
.members .member .member-info h2 {
  font-size: 14px; }
.members .member .member-info p {
  font-size: 12px; }

h2.title {
  font-size: 16px;
  font-weight: 600;
  color: rgba(0, 0, 0, 0.8); }


.app-message {
  line-height: 1.5em;
  padding: 10px;
  font-size: 12px;
  text-align: center;
  border: 1px solid #2ecc71;
  border-radius: 5px;
  margin: 0 0 10px 0; }
.app-message.error {
  background: #e74c3c;
  color: #FFF;
  border-color: #e74c3c; }


/*# sourceMappingURL=app.css.map */

Работающая версия также доступна на CodeSandBox

1 Ответ

0 голосов
/ 22 июня 2020

Вам нужно установить max-height на .messages:

.messages {
  display: flex;
  flex-direction: column;
  overflow-y: auto;
  height: 100%;
  max-height: 500px;
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...