// SPDX-FileCopyrightText: 2021 Kitsune Ral // SPDX-License-Identifier: LGPL-2.1-or-later #pragma once #include "events/stateevent.h" #include namespace Quotient { class Room; class QUOTIENT_API RoomStateView : private QHash { Q_GADGET public: const QHash& events() const { return *this; } //! \brief Get a state event with the given event type and state key //! \return A state event corresponding to the pair of event type //! \p evtType and state key \p stateKey, or nullptr if there's //! no such \p evtType / \p stateKey combination in the current //! state. //! \warning In libQuotient 0.7 the return type changed to an OmittableCref //! which is effectively a nullable const reference wrapper. You //! have to check that it has_value() before using. Alternatively //! you can now use queryCurrentState() to access state safely. //! \sa getCurrentStateContentJson const StateEventBase* get(const QString& evtType, const QString& stateKey = {}) const; //! \brief Get a state event with the given event type and state key //! //! This is a typesafe overload that accepts a C++ event type instead of //! its Matrix name. //! \warning In libQuotient 0.7 the return type changed to an Omittable with //! a reference wrapper inside - you have to check that it //! has_value() before using. Alternatively you can now use //! queryCurrentState() to access state safely. template const EvT* get(const QString& stateKey = {}) const { static_assert(std::is_base_of_v); if (const auto* evt = get(EvT::matrixTypeId(), stateKey)) { Q_ASSERT(evt->matrixType() == EvT::matrixTypeId() && evt->stateKey() == stateKey); return eventCast(evt); } return nullptr; } using QHash::contains; bool contains(const QString& evtType, const QString& stateKey = {}) const; template bool contains(const QString& stateKey = {}) const { return contains(EvT::matrixTypeId(), stateKey); } //! \brief Get the content of the current state event with the given //! event type and state key //! \return An empty object if there's no event in the current state with //! this event type and state key; the contents of the event //! 'content' object otherwise Q_INVOKABLE QJsonObject contentJson(const QString& evtType, const QString& stateKey = {}) const; //! \brief Get all state events in the room of a certain type. //! //! This method returns all known state events that have occured in //! the room of the given type. const QVector eventsOfType(const QString& evtType) const; template auto query(const QString& evtType, const QString& stateKey, FnT&& fn) const { return lift(std::forward(fn), get(evtType, stateKey)); } template auto query(const QString& stateKey, FnT&& fn) const { using EventT = std::decay_t>; static_assert(std::is_base_of_v); return lift(std::forward(fn), get(stateKey)); } template auto queryOr(const QString& evtType, const QString& stateKey, FnT&& fn, FallbackT&& fallback) const { return lift(std::forward(fn), get(evtType, stateKey)) .value_or(std::forward(fallback)); } template auto query(FnT&& fn) const { return query({}, std::forward(fn)); } template auto queryOr(const QString& stateKey, FnT&& fn, FallbackT&& fallback) const { using EventT = std::decay_t>; static_assert(std::is_base_of_v); return lift(std::forward(fn), get(stateKey)) .value_or(std::forward(fallback)); } template auto queryOr(FnT&& fn, FallbackT&& fallback) const { return queryOr({}, std::forward(fn), std::forward(fallback)); } private: friend class Room; }; } // namespace Quotient