tomato/src/tox_av_voip_model.hpp

93 lines
2.8 KiB
C++
Raw Normal View History

#pragma once
#include <solanaceae/object_store/fwd.hpp>
2025-03-06 20:14:13 +01:00
#include <solanaceae/contact/fwd.hpp>
#include <solanaceae/tox_contacts/tox_contact_model2.hpp>
#include "./frame_streams/voip_model.hpp"
#include "./tox_av.hpp"
2024-09-30 12:37:40 +02:00
#include <unordered_map>
2024-10-05 11:17:44 +02:00
#include <variant>
#include <deque>
#include <mutex>
2025-03-07 16:56:24 +01:00
#include <atomic>
2024-10-05 11:17:44 +02:00
// fwd
struct ToxAVCallAudioSink;
struct ToxAVCallVideoSink;
2024-09-30 12:37:40 +02:00
2024-10-01 11:13:27 +02:00
class ToxAVVoIPModel : protected ToxAVEventI, public VoIPModelI {
ObjectStore2& _os;
ToxAVI& _av;
2024-10-25 13:46:00 +02:00
ToxAVI::SubscriptionReference _av_sr;
2025-03-06 20:14:13 +01:00
ContactStore4I& _cs;
ToxContactModel2& _tcm;
2024-10-05 11:17:44 +02:00
uint64_t _pad0;
// these events need to be worked on the main thread instead
2025-03-07 16:56:24 +01:00
// TODO: replace with lockless queue
2024-10-05 11:17:44 +02:00
std::deque<
std::variant<
Events::FriendCall,
Events::FriendCallState
// bitrates
>> _e_queue;
std::mutex _e_queue_mutex;
uint64_t _pad1;
std::vector<ToxAVCallAudioSink*> _audio_sinks;
std::mutex _audio_sinks_mutex;
uint64_t _pad2;
std::vector<ToxAVCallVideoSink*> _video_sinks;
std::mutex _video_sinks_mutex;
uint64_t _pad3;
2025-03-07 16:56:24 +01:00
// filled with min() in video_thread_tick()
// ms, 10sec means none
std::atomic<uint64_t> _video_recent_interval{10'000'000};
uint64_t _pad4;
2024-09-30 12:37:40 +02:00
// for faster lookup
std::unordered_map<uint32_t, ObjectHandle> _audio_sources;
2024-10-02 11:28:36 +02:00
std::unordered_map<uint32_t, ObjectHandle> _video_sources;
2024-09-30 12:37:40 +02:00
2024-10-01 11:13:27 +02:00
// TODO: virtual? strategy? protected?
virtual void addAudioSource(ObjectHandle session, uint32_t friend_number);
virtual void addAudioSink(ObjectHandle session, uint32_t friend_number);
2024-10-02 11:28:36 +02:00
virtual void addVideoSource(ObjectHandle session, uint32_t friend_number);
virtual void addVideoSink(ObjectHandle session, uint32_t friend_number);
void destroySession(ObjectHandle session);
2025-03-07 16:56:24 +01:00
// we use "events" as pre/post audio/video iterate...
2024-10-05 11:17:44 +02:00
void audio_thread_tick(void);
void video_thread_tick(void);
void handleEvent(const Events::FriendCall&);
void handleEvent(const Events::FriendCallState&);
2024-10-01 11:13:27 +02:00
public:
2025-03-06 20:14:13 +01:00
ToxAVVoIPModel(ObjectStore2& os, ToxAVI& av, ContactStore4I& cs, ToxContactModel2& tcm);
2024-10-01 11:13:27 +02:00
~ToxAVVoIPModel(void);
2024-10-05 11:17:44 +02:00
// handle events coming from toxav thread(s)
2025-03-07 16:56:24 +01:00
float tick(void);
public: // voip model
2025-03-06 20:14:13 +01:00
ObjectHandle enter(const Contact4 c, const Components::VoIP::DefaultConfig& defaults) override;
2024-10-01 11:13:27 +02:00
bool accept(ObjectHandle session, const Components::VoIP::DefaultConfig& defaults) override;
bool leave(ObjectHandle session) override;
protected: // toxav events
bool onEvent(const Events::FriendCall&) override;
bool onEvent(const Events::FriendCallState&) override;
bool onEvent(const Events::FriendAudioBitrate&) override;
bool onEvent(const Events::FriendVideoBitrate&) override;
bool onEvent(const Events::FriendAudioFrame&) override;
bool onEvent(const Events::FriendVideoFrame&) override;
2024-10-05 11:17:44 +02:00
bool onEvent(const Events::IterateAudio&) override;
bool onEvent(const Events::IterateVideo&) override;
};