Customization of Diarkis Module

This page introduces parts of the code from the directmessage_simple sample and explains how to customize and use the Diarkis Module. The actual sample source code is located in samples\directmessage_simple\directmessage_simple.cpp.

Customizing Each Feature of the Diarkis Module

You can integrate application-specific processing into the module you want to use. For example, the application can recognize when a user joins or leaves a Room and update the UI accordingly. In directmessage_simple, the DM feature of the Diarkis Module has been customized to determine whether any message has been received from another user at least once. To customize the features of Diarkis Module, you inherit from the base class of each feature (DiarkisModuleNameBase). The DM feature is implemented in DiarkisDirectMessageBase, and in the sample, this class is inherited to implement the necessary processing. The following code is a partial implementation.

/*
 * Implementation for customizing the DirectMessage-related processing on the application side.
 * On... series callbacks will be triggered when DirectMessage-related data is received, so the application should implement the desired processing.
 * In this sample, the received messages are displayed on the console.
 */
class DirectMessageSimple : public DiarkisDirectMessageBase
{
public:
    DirectMessageSimple() : DiarkisDirectMessageBase() {}
    virtual ~DirectMessageSimple() {}

    bool IsAnyMessageReceived() const
    {
        return anyMessageReceived_;
    }
private:
    /**
     * @~japanese
     * @brief Callback event obtained when the DirectMessage notification is disconnected.
     * @details Called when a DirectMessage Disconnect notification (Push from the server) is sent.
     * @~
     */
    virtual void OnDisconnect(const DiarkisDirectMessageEventArgs& e) override
    {
        ...
    }

    /**
     * @~japanese
     * @brief Callback event obtained when a DirectMessage is sent from another remote user.
     * @details Called when a DirectMessage Message notification (Push from the server) is sent.
     * @~
     */
    virtual void OnMessage(const DiarkisDirectMessageEventArgs& e) override
    {
        ...
        anyMessageReceived_ = true;
    }
private:
    bool anyMessageReceived_ = false;
};

DiarkisDirectMessageBase defines interfaces mainly for using the DM feature and for receiving events. The interface for using the DM feature can be used for purposes such as executing specific processing before calling the DM feature. On the other hand, the interface for receiving events allows implementing responses to notifications when certain events occur, such as receiving messages in the DM feature. In the sample implementation, DiarkisDirectMessageBase::OnMessage, which is triggered when a message is received via DM, is overridden to save the state of whether a message has been received.

Customizing DiarkisInterfaceBase

When using the Diarkis Module, instances of classes implementing each feature are all managed by the DiarkisInterfaceBase class, and the creation of instances is also handled within DiarkisInterfaceBase. When the base class is customized, the type of instance generated within DiarkisInterfaceBase needs to be changed, so a customized DiarkisInterfaceBase class is implemented by inheritance. Below is a part of the sample implementation.

/*
 * To replace the modules of each feature managed internally by DirectInterface with application-specific ones, a class inheriting from DiarkisInterfaceBase is implemented.
 */
class DiarkisInterfaceDirectMessageSimple : public DiarkisInterfaceBase
{
public:
    ...

    void SetupDirectMessage(void)
    {
        if (tcpBase_ != nullptr && tcpBase_->Get() != nullptr)
        {
            // Create the customized class on the application side.
            if (dmBase_ == nullptr)
                dmBase_ = Diarkis::DiarkisAllocShared<DirectMessageSimple>();

            // Initialize the DirectMessage class and register callback events
            dmBase_->SetupTcp(tcpBase_->Get(), this->GetLoggerFactory());
        }

        if (udpBase_ != nullptr && udpBase_->Get() != nullptr)
        {
            // Create the customized class on the application side.
            if (dmBase_ == nullptr)
                dmBase_ = Diarkis::DiarkisAllocShared<DirectMessageSimple>();
            // Initialize the DirectMessage class and register callback events
            dmBase_->SetupUdp(udpBase_->Get(), this->GetLoggerFactory());
        }
    }

    std::shared_ptr<DirectMessageSimple> GetDirectMessage()
    {
        return std::static_pointer_cast<DirectMessageSimple>(GetDirectMessageBase());
    }
};

Instances of each feature are generated in DiarkisInterfaceBase::Setup.... Since instances of the DM feature are generated in DiarkisInterfaceBase::SetupDirectMessage(), this method is overridden to generate user-customized DM feature classes. Additionally, a method to retrieve instances of the DM feature in the customized type is added.

By using these customized classes, you can integrate application-specific processing into the Diarkis Module.

std::shared_ptr<DiarkisInterfaceDirectMessageSimple> diarkis;

...

// Create a class inheriting from DiarkisInterface to access all features of Diarkis.
diarkis = Diarkis::DiarkisAllocShared<DiarkisInterfaceDirectMessageSimple>(uid);

...

std::shared_ptr<DirectMessageSimple> dm = diarkis->GetDirectMessage();

...

// An implementation for simple timing alignment.
// Data transmission from "1111" starts at the timing when the first message from "2222" arrives.
while (!dm->IsAnyMessageReceived())
{
    std::this_thread::sleep_for(std::chrono::milliseconds(1000));
}

Notes

Since the Diarkis Module is provided in source code, it is also possible to customize it by modifying it directly without inheriting the base class. However, the source code of the Diarkis Module may undergo significant changes during version upgrades, making merging difficult. To avoid such situations, it is recommended to customize using the method introduced on this page.

Last updated