Source code of the Chat example

Browse below the source code for Wt's Chat example.

  • simplechat
    • class PopupChatWidget
      • PopupChatWidget.C
        • PopupChatWidget.h
        • class SimpleChatServer
          • class SimpleChatWidget
            • chatapp.css
              • chatwidget.css
                • chatwidget_ie6.css
                  • simpleChat.C
                    • simplechat.xml
                      • simplechat_ru.xml
                        • sounds
                          • icons
                          /*
                           * Copyright (C) 2010 Emweb bv, Herent, Belgium.
                           *
                           * See the LICENSE file for terms of use.
                           */
                          
                          #include <Wt/WApplication.h>
                          #include <Wt/WEnvironment.h>
                          #include <Wt/WImage.h>
                          #include <Wt/WText.h>
                          #include <Wt/WVBoxLayout.h>
                          
                          #include "PopupChatWidget.h"
                          #include "SimpleChatServer.h"
                          
                          // TODO:
                          //  - i18n
                          
                          PopupChatWidget::PopupChatWidget(SimpleChatServer& server,
                                                           const std::string& id)
                            : SimpleChatWidget(server),
                              missedMessages_(0)
                          {
                            setId(id);
                          
                            if (Wt::WApplication::instance()->environment().agentIsIE()) {
                              if (Wt::WApplication::instance()->environment().agent()
                                  == Wt::UserAgent::IE6)
                                setPositionScheme(Wt::PositionScheme::Absolute);
                              else
                                setPositionScheme(Wt::PositionScheme::Fixed);
                            }
                          
                            implementJavaScript
                              (&PopupChatWidget::toggleSize,
                               "{"
                               """let s = " WT_CLASS ".$('" + id + "');"
                               """s.classList.toggle('chat-maximized');"
                               """s.classList.toggle('chat-minimized');"
                               "}");
                          
                            online_ = false;
                            minimized_ = true;
                            setStyleClass("chat-widget chat-minimized");
                          
                            clear();
                            addWidget(createBar());
                            updateUsers();
                          
                            connect();
                          }
                          
                          void PopupChatWidget::setName(const Wt::WString& name)
                          {
                            if (name.empty())
                              return;
                          
                            if (online_) {
                              int tries = 1;
                              Wt::WString n = name;
                              while (!server().changeName(name_, n))
                                n = name + std::to_string(++tries);
                          
                              name_ = n;
                            } else
                              name_ = name;
                          }
                          
                          std::unique_ptr<Wt::WContainerWidget> PopupChatWidget::createBar()
                          {
                            auto bar(std::make_unique<Wt::WContainerWidget>());
                            bar->setStyleClass("chat-bar");
                          
                            auto toggleButton(std::make_unique<Wt::WText>());
                            toggleButton->setInline(false);
                            toggleButton->setStyleClass("chat-minmax");
                            bar->clicked().connect(this, &PopupChatWidget::toggleSize);
                            bar->clicked().connect(this, &PopupChatWidget::goOnline);
                          
                            bar->addWidget(std::move(toggleButton));
                          
                            title_ = bar->addWidget(std::make_unique<Wt::WText>());
                          
                            bar_ = bar.get();
                          
                            return bar;
                          }
                          
                          void PopupChatWidget::toggleSize()
                          {
                            minimized_ = !minimized_;
                          }
                          
                          void PopupChatWidget::goOnline()
                          {
                            if (!online_) {
                              online_ = true;
                          
                              int tries = 1;
                              Wt::WString name = name_;
                              if (name.empty())
                                name = server().suggestGuest();
                          
                              while (!startChat(name)) {
                                if (name_.empty())
                                  name = server().suggestGuest();
                                else
                                  name = name_ + std::to_string(++tries);
                              }
                          
                              name_ = name;
                            }
                          
                            missedMessages_ = 0;
                            bar_->removeStyleClass("alert");
                          }
                          
                          void PopupChatWidget::createLayout(std::unique_ptr<Wt::WWidget> messages,
                                                             std::unique_ptr<Wt::WWidget> userList,
                                                             std::unique_ptr<Wt::WWidget> messageEdit,
                                                             std::unique_ptr<Wt::WWidget> sendButton,
                                                             std::unique_ptr<Wt::WWidget> logoutButton)
                          {
                            auto layout(std::make_unique<Wt::WVBoxLayout>());
                            layout->setContentsMargins(0, 0, 0, 0);
                            layout->setSpacing(0);
                          
                            auto bar = layout->addWidget(createBar());
                            bar->setMinimumSize(Wt::WLength::Auto, 20);
                            layout->addWidget(std::move(messages), 1);
                            layout->addWidget(std::move(messageEdit));
                          
                            setLayout(std::move(layout));
                          }
                          
                          void PopupChatWidget::updateUsers()
                          {
                            SimpleChatWidget::updateUsers();
                          
                            int count = server().users().size();
                          
                            if (!loggedIn()) {
                              if (count == 0)
                                title_->setText("Thoughts? Ventilate.");
                              else if (count == 1)
                                title_->setText("Chat: 1 user online");
                              else
                                title_->setText(Wt::WString("Chat: {1} users online").arg(count));
                            } else {
                              title_->setText(Wt::WString("Chat: <span class=\"self\">{1}</span>"
                                                          " <span class=\"online\">({2} user{3})</span>")
                                              .arg(userName()).arg(count).arg(count == 1 ? "" : "s"));
                            }
                          }
                          
                          void PopupChatWidget::newMessage()
                          {
                            if (loggedIn() && minimized()) {
                              ++missedMessages_;
                              if (missedMessages_ == 1) {
                                bar_->addStyleClass("alert");
                              }
                            }
                          }
                          
                          bool PopupChatWidget::minimized() const
                          {
                            return minimized_;
                          }