mirror of
https://github.com/RPCS3/rpcs3.git
synced 2025-02-15 09:40:05 +00:00
cellCamera: add error handling to qt camera
This commit is contained in:
parent
e4b242955c
commit
81c216f330
@ -1328,17 +1328,6 @@ error_code cellCameraReadEx(s32 dev_num, vm::ptr<CellCameraReadEx> read)
|
|||||||
|
|
||||||
// can call cellCameraReset() and cellCameraStop() in some cases
|
// can call cellCameraReset() and cellCameraStop() in some cases
|
||||||
|
|
||||||
if (read) // NULL returns CELL_OK
|
|
||||||
{
|
|
||||||
read->timestamp = (get_guest_system_time() - g_camera.start_timestamp);
|
|
||||||
read->frame = g_camera.frame_num;
|
|
||||||
read->bytesread = g_camera.is_streaming ? get_video_buffer_size(g_camera.info) : 0;
|
|
||||||
|
|
||||||
auto& shared_data = g_fxo->get<gem_camera_shared>();
|
|
||||||
|
|
||||||
shared_data.frame_timestamp.exchange(read->timestamp);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (g_camera.handler)
|
if (g_camera.handler)
|
||||||
{
|
{
|
||||||
u32 width{};
|
u32 width{};
|
||||||
@ -1347,7 +1336,7 @@ error_code cellCameraReadEx(s32 dev_num, vm::ptr<CellCameraReadEx> read)
|
|||||||
u64 bytes_read{};
|
u64 bytes_read{};
|
||||||
|
|
||||||
atomic_t<bool> wake_up = false;
|
atomic_t<bool> wake_up = false;
|
||||||
bool result = false;
|
camera_handler_base::camera_handler_state result = camera_handler_base::camera_handler_state::not_available;
|
||||||
|
|
||||||
Emu.CallAfter([&]()
|
Emu.CallAfter([&]()
|
||||||
{
|
{
|
||||||
@ -1361,10 +1350,9 @@ error_code cellCameraReadEx(s32 dev_num, vm::ptr<CellCameraReadEx> read)
|
|||||||
thread_ctrl::wait_on(wake_up, false);
|
thread_ctrl::wait_on(wake_up, false);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!result)
|
if (error_code error = g_camera.on_handler_state(result); error != CELL_OK)
|
||||||
{
|
{
|
||||||
g_camera.send_attach_state(false);
|
return error;
|
||||||
return CELL_CAMERA_ERROR_DEVICE_NOT_FOUND;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (read)
|
if (read)
|
||||||
@ -1377,6 +1365,21 @@ error_code cellCameraReadEx(s32 dev_num, vm::ptr<CellCameraReadEx> read)
|
|||||||
frame_number, width, height, bytes_read, read ? read->frame.get() : 0, read ? read->bytesread.get() : 0);
|
frame_number, width, height, bytes_read, read ? read->frame.get() : 0, read ? read->bytesread.get() : 0);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (read) // NULL returns CELL_OK
|
||||||
|
{
|
||||||
|
read->timestamp = (get_guest_system_time() - g_camera.start_timestamp);
|
||||||
|
|
||||||
|
if (!g_camera.handler)
|
||||||
|
{
|
||||||
|
read->frame = g_camera.frame_num;
|
||||||
|
read->bytesread = g_camera.is_streaming ? get_video_buffer_size(g_camera.info) : 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
auto& shared_data = g_fxo->get<gem_camera_shared>();
|
||||||
|
|
||||||
|
shared_data.frame_timestamp.exchange(read->timestamp);
|
||||||
|
}
|
||||||
|
|
||||||
return CELL_OK;
|
return CELL_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1624,7 +1627,7 @@ void camera_context::operator()()
|
|||||||
if (handler && send_frame_update_event)
|
if (handler && send_frame_update_event)
|
||||||
{
|
{
|
||||||
atomic_t<bool> wake_up = false;
|
atomic_t<bool> wake_up = false;
|
||||||
bool result = false;
|
camera_handler_base::camera_handler_state result = camera_handler_base::camera_handler_state::not_available;
|
||||||
|
|
||||||
Emu.CallAfter([&]()
|
Emu.CallAfter([&]()
|
||||||
{
|
{
|
||||||
@ -1645,15 +1648,12 @@ void camera_context::operator()()
|
|||||||
|
|
||||||
pbuf_write_index = pbuf_next_index();
|
pbuf_write_index = pbuf_next_index();
|
||||||
|
|
||||||
if (!result)
|
send_frame_update_event = on_handler_state(result) = CELL_OK;
|
||||||
{
|
|
||||||
send_attach_state(false);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
send_frame_update_event = true;
|
send_frame_update_event = on_handler_state(handler->get_state()) = CELL_OK;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1731,32 +1731,21 @@ void camera_context::reset_state()
|
|||||||
|
|
||||||
void camera_context::send_attach_state(bool attached)
|
void camera_context::send_attach_state(bool attached)
|
||||||
{
|
{
|
||||||
if (!attached)
|
|
||||||
{
|
|
||||||
is_streaming = false;
|
|
||||||
is_open = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
std::lock_guard lock(mutex_notify_data_map);
|
std::lock_guard lock(mutex_notify_data_map);
|
||||||
|
|
||||||
if (!notify_data_map.empty())
|
for (const auto& [key, evt_data] : notify_data_map)
|
||||||
{
|
{
|
||||||
for (const auto& [key, evt_data] : notify_data_map)
|
if (auto queue = lv2_event_queue::find(key))
|
||||||
{
|
{
|
||||||
if (auto queue = lv2_event_queue::find(key))
|
if (queue->send(evt_data.source, attached ? CELL_CAMERA_ATTACH : CELL_CAMERA_DETACH, 0, 0) == 0) [[likely]]
|
||||||
{
|
{
|
||||||
if (queue->send(evt_data.source, attached ? CELL_CAMERA_ATTACH : CELL_CAMERA_DETACH, 0, 0) == 0) [[likely]]
|
is_attached = attached;
|
||||||
{
|
|
||||||
is_attached = attached;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
|
||||||
{
|
// We're not expected to send any events for attaching/detaching
|
||||||
// We're not expected to send any events for attaching/detaching
|
is_attached = attached;
|
||||||
is_attached = attached;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void camera_context::set_attr(s32 attrib, u32 arg1, u32 arg2)
|
void camera_context::set_attr(s32 attrib, u32 arg1, u32 arg2)
|
||||||
@ -1817,3 +1806,52 @@ u32 camera_context::pbuf_next_index() const
|
|||||||
// The read buffer index cannot be the same as the write index
|
// The read buffer index cannot be the same as the write index
|
||||||
return (pbuf_write_index + 1u) % 2;
|
return (pbuf_write_index + 1u) % 2;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
error_code camera_context::on_handler_state(camera_handler_base::camera_handler_state state)
|
||||||
|
{
|
||||||
|
switch (state)
|
||||||
|
{
|
||||||
|
case camera_handler_base::camera_handler_state::not_available:
|
||||||
|
case camera_handler_base::camera_handler_state::closed:
|
||||||
|
{
|
||||||
|
if (is_attached)
|
||||||
|
{
|
||||||
|
send_attach_state(false);
|
||||||
|
}
|
||||||
|
if (handler)
|
||||||
|
{
|
||||||
|
if (is_streaming)
|
||||||
|
{
|
||||||
|
cellCamera.warning("Camera closed or disconnected (state=%d). Trying to start camera...", static_cast<int>(state));
|
||||||
|
handler->start_camera();
|
||||||
|
}
|
||||||
|
else if (is_open)
|
||||||
|
{
|
||||||
|
cellCamera.warning("Camera closed or disconnected (state=%d). Trying to open camera...", static_cast<int>(state));
|
||||||
|
handler->open_camera();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return CELL_CAMERA_ERROR_DEVICE_NOT_FOUND;
|
||||||
|
}
|
||||||
|
case camera_handler_base::camera_handler_state::running:
|
||||||
|
{
|
||||||
|
if (!is_attached)
|
||||||
|
{
|
||||||
|
cellCamera.warning("Camera handler not attached. Sending attach event...", static_cast<int>(state));
|
||||||
|
send_attach_state(true);
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
case camera_handler_base::camera_handler_state::open:
|
||||||
|
{
|
||||||
|
if (handler && is_streaming)
|
||||||
|
{
|
||||||
|
cellCamera.warning("Camera handler not running (state=%d). Trying to start camera...", static_cast<int>(state));
|
||||||
|
handler->start_camera();
|
||||||
|
}
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return CELL_OK;
|
||||||
|
}
|
||||||
|
@ -442,6 +442,7 @@ public:
|
|||||||
static constexpr auto thread_name = "Camera Thread"sv;
|
static constexpr auto thread_name = "Camera Thread"sv;
|
||||||
|
|
||||||
std::shared_ptr<camera_handler_base> handler;
|
std::shared_ptr<camera_handler_base> handler;
|
||||||
|
error_code on_handler_state(camera_handler_base::camera_handler_state state);
|
||||||
};
|
};
|
||||||
|
|
||||||
using camera_thread = named_thread<camera_context>;
|
using camera_thread = named_thread<camera_context>;
|
||||||
|
@ -1351,7 +1351,7 @@ error_code cellGemPrepareVideoConvert(vm::cptr<CellGemVideoConvertAttribute> vc_
|
|||||||
return CELL_GEM_ERROR_INVALID_PARAMETER;
|
return CELL_GEM_ERROR_INVALID_PARAMETER;
|
||||||
}
|
}
|
||||||
|
|
||||||
const auto vc = *vc_attribute;
|
const CellGemVideoConvertAttribute vc = *vc_attribute;
|
||||||
|
|
||||||
if (!vc_attribute || vc.version != CELL_GEM_VERSION)
|
if (!vc_attribute || vc.version != CELL_GEM_VERSION)
|
||||||
{
|
{
|
||||||
|
@ -7,10 +7,10 @@ class null_camera_handler final : public camera_handler_base
|
|||||||
public:
|
public:
|
||||||
null_camera_handler() : camera_handler_base() {}
|
null_camera_handler() : camera_handler_base() {}
|
||||||
|
|
||||||
void open_camera() override {};
|
void open_camera() override { m_state = camera_handler_state::open; };
|
||||||
void close_camera() override {};
|
void close_camera() override { m_state = camera_handler_state::closed; };
|
||||||
void start_camera() override {};
|
void start_camera() override { m_state = camera_handler_state::running; };
|
||||||
void stop_camera() override {};
|
void stop_camera() override { m_state = camera_handler_state::open; };
|
||||||
|
|
||||||
void set_format(s32 format, u32 bytes_per_pixel) override
|
void set_format(s32 format, u32 bytes_per_pixel) override
|
||||||
{
|
{
|
||||||
@ -39,12 +39,12 @@ public:
|
|||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool get_image(u8* /*buf*/, u64 /*size*/, u32& width, u32& height, u64& frame_number, u64& bytes_read) override
|
camera_handler_state get_image(u8* /*buf*/, u64 /*size*/, u32& width, u32& height, u64& frame_number, u64& bytes_read) override
|
||||||
{
|
{
|
||||||
width = 0;
|
width = 0;
|
||||||
height = 0;
|
height = 0;
|
||||||
frame_number = 0;
|
frame_number = 0;
|
||||||
bytes_read = 0;
|
bytes_read = 0;
|
||||||
return true;
|
return m_state;
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
@ -8,6 +8,7 @@ class camera_handler_base
|
|||||||
public:
|
public:
|
||||||
enum class camera_handler_state
|
enum class camera_handler_state
|
||||||
{
|
{
|
||||||
|
not_available,
|
||||||
closed,
|
closed,
|
||||||
open,
|
open,
|
||||||
running
|
running
|
||||||
@ -26,13 +27,13 @@ public:
|
|||||||
virtual void set_mirrored(bool mirrored) = 0;
|
virtual void set_mirrored(bool mirrored) = 0;
|
||||||
|
|
||||||
virtual u64 frame_number() const = 0; // Convenience function to check if there's a new frame.
|
virtual u64 frame_number() const = 0; // Convenience function to check if there's a new frame.
|
||||||
virtual bool get_image(u8* buf, u64 size, u32& width, u32& height, u64& frame_number, u64& bytes_read) = 0;
|
virtual camera_handler_state get_image(u8* buf, u64 size, u32& width, u32& height, u64& frame_number, u64& bytes_read) = 0;
|
||||||
|
|
||||||
camera_handler_state get_state() const { return m_state.load(); };
|
camera_handler_state get_state() const { return m_state.load(); };
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
std::mutex m_mutex;
|
std::mutex m_mutex;
|
||||||
atomic_t<camera_handler_state> m_state = camera_handler_state::closed;
|
atomic_t<camera_handler_state> m_state = camera_handler_state::not_available;
|
||||||
bool m_mirrored = false;
|
bool m_mirrored = false;
|
||||||
s32 m_format = 2; // CELL_CAMERA_RAW8
|
s32 m_format = 2; // CELL_CAMERA_RAW8
|
||||||
u32 m_bytes_per_pixel = 1;
|
u32 m_bytes_per_pixel = 1;
|
||||||
|
@ -303,6 +303,9 @@
|
|||||||
<ClCompile Include="QTGeneratedFiles\Debug\moc_pkg_install_dialog.cpp">
|
<ClCompile Include="QTGeneratedFiles\Debug\moc_pkg_install_dialog.cpp">
|
||||||
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|x64'">true</ExcludedFromBuild>
|
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|x64'">true</ExcludedFromBuild>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
|
<ClCompile Include="QTGeneratedFiles\Debug\moc_qt_camera_error_handler.cpp">
|
||||||
|
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|x64'">true</ExcludedFromBuild>
|
||||||
|
</ClCompile>
|
||||||
<ClCompile Include="QTGeneratedFiles\Debug\moc_recvmessage_dialog_frame.cpp">
|
<ClCompile Include="QTGeneratedFiles\Debug\moc_recvmessage_dialog_frame.cpp">
|
||||||
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|x64'">true</ExcludedFromBuild>
|
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Release|x64'">true</ExcludedFromBuild>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
@ -501,6 +504,9 @@
|
|||||||
<ClCompile Include="QTGeneratedFiles\Release\moc_pkg_install_dialog.cpp">
|
<ClCompile Include="QTGeneratedFiles\Release\moc_pkg_install_dialog.cpp">
|
||||||
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">true</ExcludedFromBuild>
|
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">true</ExcludedFromBuild>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
|
<ClCompile Include="QTGeneratedFiles\Release\moc_qt_camera_error_handler.cpp">
|
||||||
|
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">true</ExcludedFromBuild>
|
||||||
|
</ClCompile>
|
||||||
<ClCompile Include="QTGeneratedFiles\Release\moc_recvmessage_dialog_frame.cpp">
|
<ClCompile Include="QTGeneratedFiles\Release\moc_recvmessage_dialog_frame.cpp">
|
||||||
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">true</ExcludedFromBuild>
|
<ExcludedFromBuild Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">true</ExcludedFromBuild>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
@ -594,6 +600,7 @@
|
|||||||
<ClCompile Include="rpcs3qt\patch_manager_dialog.cpp" />
|
<ClCompile Include="rpcs3qt\patch_manager_dialog.cpp" />
|
||||||
<ClCompile Include="rpcs3qt\pkg_install_dialog.cpp" />
|
<ClCompile Include="rpcs3qt\pkg_install_dialog.cpp" />
|
||||||
<ClCompile Include="rpcs3qt\persistent_settings.cpp" />
|
<ClCompile Include="rpcs3qt\persistent_settings.cpp" />
|
||||||
|
<ClCompile Include="rpcs3qt\qt_camera_error_handler.cpp" />
|
||||||
<ClCompile Include="rpcs3qt\qt_camera_handler.cpp" />
|
<ClCompile Include="rpcs3qt\qt_camera_handler.cpp" />
|
||||||
<ClCompile Include="rpcs3qt\recvmessage_dialog_frame.cpp" />
|
<ClCompile Include="rpcs3qt\recvmessage_dialog_frame.cpp" />
|
||||||
<ClCompile Include="rpcs3qt\render_creator.cpp" />
|
<ClCompile Include="rpcs3qt\render_creator.cpp" />
|
||||||
@ -1090,6 +1097,16 @@
|
|||||||
<Outputs Condition="'$(Configuration)|$(Platform)'=='Release|x64'">.\QTGeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp</Outputs>
|
<Outputs Condition="'$(Configuration)|$(Platform)'=='Release|x64'">.\QTGeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp</Outputs>
|
||||||
<Command Condition="'$(Configuration)|$(Platform)'=='Release|x64'">"$(QTDIR)\bin\moc.exe" "%(FullPath)" -o ".\QTGeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp" -D_WINDOWS -DUNICODE -DWIN32 -DWIN64 -DWITH_DISCORD_RPC -DQT_NO_DEBUG -DQT_WIDGETS_LIB -DQT_GUI_LIB -DQT_CORE_LIB -DNDEBUG -DQT_WINEXTRAS_LIB -DQT_CONCURRENT_LIB -D%(PreprocessorDefinitions) "-I.\..\3rdparty\flatbuffers\include" "-I.\..\3rdparty\wolfssl\wolfssl" "-I.\..\3rdparty\curl\curl\include" "-I.\..\3rdparty\libusb\libusb\libusb" "-I$(VULKAN_SDK)\Include" "-I.\..\3rdparty\XAudio2Redist\include" "-I$(QTDIR)\include" "-I$(QTDIR)\include\QtWidgets" "-I$(QTDIR)\include\QtGui" "-I$(QTDIR)\include\QtANGLE" "-I$(QTDIR)\include\QtCore" "-I.\release" "-I$(QTDIR)\mkspecs\win32-msvc2015" "-I.\QTGeneratedFiles\$(ConfigurationName)" "-I.\QTGeneratedFiles" "-I$(QTDIR)\include\QtWinExtras" "-I$(QTDIR)\include\QtConcurrent"</Command>
|
<Command Condition="'$(Configuration)|$(Platform)'=='Release|x64'">"$(QTDIR)\bin\moc.exe" "%(FullPath)" -o ".\QTGeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp" -D_WINDOWS -DUNICODE -DWIN32 -DWIN64 -DWITH_DISCORD_RPC -DQT_NO_DEBUG -DQT_WIDGETS_LIB -DQT_GUI_LIB -DQT_CORE_LIB -DNDEBUG -DQT_WINEXTRAS_LIB -DQT_CONCURRENT_LIB -D%(PreprocessorDefinitions) "-I.\..\3rdparty\flatbuffers\include" "-I.\..\3rdparty\wolfssl\wolfssl" "-I.\..\3rdparty\curl\curl\include" "-I.\..\3rdparty\libusb\libusb\libusb" "-I$(VULKAN_SDK)\Include" "-I.\..\3rdparty\XAudio2Redist\include" "-I$(QTDIR)\include" "-I$(QTDIR)\include\QtWidgets" "-I$(QTDIR)\include\QtGui" "-I$(QTDIR)\include\QtANGLE" "-I$(QTDIR)\include\QtCore" "-I.\release" "-I$(QTDIR)\mkspecs\win32-msvc2015" "-I.\QTGeneratedFiles\$(ConfigurationName)" "-I.\QTGeneratedFiles" "-I$(QTDIR)\include\QtWinExtras" "-I$(QTDIR)\include\QtConcurrent"</Command>
|
||||||
</CustomBuild>
|
</CustomBuild>
|
||||||
|
<CustomBuild Include="rpcs3qt\qt_camera_error_handler.h">
|
||||||
|
<AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">$(QTDIR)\bin\moc.exe;%(FullPath)</AdditionalInputs>
|
||||||
|
<Message Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">Moc%27ing %(Identity)...</Message>
|
||||||
|
<Outputs Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">.\QTGeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp</Outputs>
|
||||||
|
<Command Condition="'$(Configuration)|$(Platform)'=='Debug|x64'">"$(QTDIR)\bin\moc.exe" "%(FullPath)" -o ".\QTGeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp" -D_WINDOWS -DUNICODE -DWIN32 -DWIN64 -DQT_WIDGETS_LIB -DQT_GUI_LIB -DQT_CORE_LIB -DQT_WINEXTRAS_LIB -DQT_CONCURRENT_LIB -DQT_MULTIMEDIA_LIB -D%(PreprocessorDefinitions) "-I.\..\3rdparty\flatbuffers\include" "-I.\..\3rdparty\wolfssl\wolfssl" "-I.\..\3rdparty\curl\curl\include" "-I.\..\3rdparty\libusb\libusb\libusb" "-I$(VULKAN_SDK)\Include" "-I.\..\3rdparty\XAudio2Redist\include" "-I$(QTDIR)\include" "-I$(QTDIR)\include\QtWidgets" "-I$(QTDIR)\include\QtGui" "-I$(QTDIR)\include\QtANGLE" "-I$(QTDIR)\include\QtCore" "-I.\debug" "-I$(QTDIR)\mkspecs\win32-msvc2015" "-I.\QTGeneratedFiles\$(ConfigurationName)" "-I.\QTGeneratedFiles" "-I$(QTDIR)\include\QtWinExtras" "-I$(QTDIR)\include\QtConcurrent" "-I$(QTDIR)\include\QtMultimedia"</Command>
|
||||||
|
<AdditionalInputs Condition="'$(Configuration)|$(Platform)'=='Release|x64'">$(QTDIR)\bin\moc.exe;%(FullPath)</AdditionalInputs>
|
||||||
|
<Message Condition="'$(Configuration)|$(Platform)'=='Release|x64'">Moc%27ing %(Identity)...</Message>
|
||||||
|
<Outputs Condition="'$(Configuration)|$(Platform)'=='Release|x64'">.\QTGeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp</Outputs>
|
||||||
|
<Command Condition="'$(Configuration)|$(Platform)'=='Release|x64'">"$(QTDIR)\bin\moc.exe" "%(FullPath)" -o ".\QTGeneratedFiles\$(ConfigurationName)\moc_%(Filename).cpp" -D_WINDOWS -DUNICODE -DWIN32 -DWIN64 -DWITH_DISCORD_RPC -DQT_NO_DEBUG -DQT_WIDGETS_LIB -DQT_GUI_LIB -DQT_CORE_LIB -DNDEBUG -DQT_WINEXTRAS_LIB -DQT_CONCURRENT_LIB -DQT_MULTIMEDIA_LIB -D%(PreprocessorDefinitions) "-I.\..\3rdparty\flatbuffers\include" "-I.\..\3rdparty\wolfssl\wolfssl" "-I.\..\3rdparty\curl\curl\include" "-I.\..\3rdparty\libusb\libusb\libusb" "-I$(VULKAN_SDK)\Include" "-I.\..\3rdparty\XAudio2Redist\include" "-I$(QTDIR)\include" "-I$(QTDIR)\include\QtWidgets" "-I$(QTDIR)\include\QtGui" "-I$(QTDIR)\include\QtANGLE" "-I$(QTDIR)\include\QtCore" "-I.\release" "-I$(QTDIR)\mkspecs\win32-msvc2015" "-I.\QTGeneratedFiles\$(ConfigurationName)" "-I.\QTGeneratedFiles" "-I$(QTDIR)\include\QtWinExtras" "-I$(QTDIR)\include\QtConcurrent" "-I$(QTDIR)\include\QtMultimedia"</Command>
|
||||||
|
</CustomBuild>
|
||||||
<ClInclude Include="rpcs3qt\qt_camera_handler.h" />
|
<ClInclude Include="rpcs3qt\qt_camera_handler.h" />
|
||||||
<ClInclude Include="rpcs3qt\richtext_item_delegate.h" />
|
<ClInclude Include="rpcs3qt\richtext_item_delegate.h" />
|
||||||
<CustomBuild Include="rpcs3qt\sendmessage_dialog_frame.h">
|
<CustomBuild Include="rpcs3qt\sendmessage_dialog_frame.h">
|
||||||
|
@ -786,6 +786,15 @@
|
|||||||
<ClCompile Include="rpcs3qt\qt_camera_video_surface.cpp">
|
<ClCompile Include="rpcs3qt\qt_camera_video_surface.cpp">
|
||||||
<Filter>Io\camera</Filter>
|
<Filter>Io\camera</Filter>
|
||||||
</ClCompile>
|
</ClCompile>
|
||||||
|
<ClCompile Include="rpcs3qt\qt_camera_error_handler.cpp">
|
||||||
|
<Filter>Io\camera</Filter>
|
||||||
|
</ClCompile>
|
||||||
|
<ClCompile Include="QTGeneratedFiles\Debug\moc_qt_camera_error_handler.cpp">
|
||||||
|
<Filter>Generated Files\Debug</Filter>
|
||||||
|
</ClCompile>
|
||||||
|
<ClCompile Include="QTGeneratedFiles\Release\moc_qt_camera_error_handler.cpp">
|
||||||
|
<Filter>Generated Files\Release</Filter>
|
||||||
|
</ClCompile>
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<ClInclude Include="Input\ds4_pad_handler.h">
|
<ClInclude Include="Input\ds4_pad_handler.h">
|
||||||
@ -1153,6 +1162,9 @@
|
|||||||
<CustomBuild Include="rpcs3qt\recvmessage_dialog_frame.h">
|
<CustomBuild Include="rpcs3qt\recvmessage_dialog_frame.h">
|
||||||
<Filter>Gui\message dialog</Filter>
|
<Filter>Gui\message dialog</Filter>
|
||||||
</CustomBuild>
|
</CustomBuild>
|
||||||
|
<CustomBuild Include="rpcs3qt\qt_camera_error_handler.h">
|
||||||
|
<Filter>Io\camera</Filter>
|
||||||
|
</CustomBuild>
|
||||||
</ItemGroup>
|
</ItemGroup>
|
||||||
<ItemGroup>
|
<ItemGroup>
|
||||||
<Image Include="rpcs3.ico" />
|
<Image Include="rpcs3.ico" />
|
||||||
|
@ -49,6 +49,7 @@ set(SRC_FILES
|
|||||||
persistent_settings.cpp
|
persistent_settings.cpp
|
||||||
pkg_install_dialog.cpp
|
pkg_install_dialog.cpp
|
||||||
progress_dialog.cpp
|
progress_dialog.cpp
|
||||||
|
qt_camera_error_handler.cpp
|
||||||
qt_camera_handler.cpp
|
qt_camera_handler.cpp
|
||||||
qt_camera_video_surface.cpp
|
qt_camera_video_surface.cpp
|
||||||
qt_utils.cpp
|
qt_utils.cpp
|
||||||
|
58
rpcs3/rpcs3qt/qt_camera_error_handler.cpp
Normal file
58
rpcs3/rpcs3qt/qt_camera_error_handler.cpp
Normal file
@ -0,0 +1,58 @@
|
|||||||
|
#include "stdafx.h"
|
||||||
|
#include "qt_camera_error_handler.h"
|
||||||
|
|
||||||
|
LOG_CHANNEL(camera_log, "Camera");
|
||||||
|
|
||||||
|
qt_camera_error_handler::qt_camera_error_handler(std::shared_ptr<QCamera> camera, std::function<void(QCamera::Status)> status_callback)
|
||||||
|
: m_camera(std::move(camera))
|
||||||
|
, m_status_callback(std::move(status_callback))
|
||||||
|
{
|
||||||
|
if (m_camera)
|
||||||
|
{
|
||||||
|
connect(m_camera.get(), QOverload<QMultimedia::AvailabilityStatus>::of(&QCamera::availabilityChanged), this, &qt_camera_error_handler::handle_availability);
|
||||||
|
connect(m_camera.get(), &QCamera::stateChanged, this, &qt_camera_error_handler::handle_camera_state);
|
||||||
|
connect(m_camera.get(), &QCamera::statusChanged, this, &qt_camera_error_handler::handle_camera_status);
|
||||||
|
connect(m_camera.get(), &QCamera::errorOccurred, this, &qt_camera_error_handler::handle_camera_error);
|
||||||
|
connect(m_camera.get(), &QCamera::captureModeChanged, this, &qt_camera_error_handler::handle_capture_modes);
|
||||||
|
connect(m_camera.get(), QOverload<QCamera::LockStatus, QCamera::LockChangeReason>::of(&QCamera::lockStatusChanged), this, &qt_camera_error_handler::handle_lock_status);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
qt_camera_error_handler::~qt_camera_error_handler()
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
void qt_camera_error_handler::handle_availability(QMultimedia::AvailabilityStatus availability)
|
||||||
|
{
|
||||||
|
camera_log.notice("Camera availability changed to %d", static_cast<int>(availability));
|
||||||
|
}
|
||||||
|
|
||||||
|
void qt_camera_error_handler::handle_camera_state(QCamera::State state)
|
||||||
|
{
|
||||||
|
camera_log.notice("Camera state changed to %d", static_cast<int>(state));
|
||||||
|
}
|
||||||
|
|
||||||
|
void qt_camera_error_handler::handle_camera_status(QCamera::Status status)
|
||||||
|
{
|
||||||
|
camera_log.notice("Camera status changed to %d", static_cast<int>(status));
|
||||||
|
|
||||||
|
if (m_status_callback)
|
||||||
|
{
|
||||||
|
m_status_callback(status);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void qt_camera_error_handler::handle_lock_status(QCamera::LockStatus status, QCamera::LockChangeReason reason)
|
||||||
|
{
|
||||||
|
camera_log.notice("Camera lock status changed to %d (reason=%d)", static_cast<int>(status), static_cast<int>(reason));
|
||||||
|
}
|
||||||
|
|
||||||
|
void qt_camera_error_handler::handle_capture_modes(QCamera::CaptureModes capture_modes)
|
||||||
|
{
|
||||||
|
camera_log.notice("Camera capture modes changed to %d", static_cast<int>(capture_modes));
|
||||||
|
}
|
||||||
|
|
||||||
|
void qt_camera_error_handler::handle_camera_error(QCamera::Error error)
|
||||||
|
{
|
||||||
|
camera_log.error("Error event: \"%s\" (error=%d)", m_camera ? m_camera->errorString().toStdString() : "", static_cast<int>(error));
|
||||||
|
}
|
25
rpcs3/rpcs3qt/qt_camera_error_handler.h
Normal file
25
rpcs3/rpcs3qt/qt_camera_error_handler.h
Normal file
@ -0,0 +1,25 @@
|
|||||||
|
#pragma once
|
||||||
|
|
||||||
|
#include <QObject>
|
||||||
|
#include <QCamera>
|
||||||
|
|
||||||
|
class qt_camera_error_handler : public QObject
|
||||||
|
{
|
||||||
|
Q_OBJECT
|
||||||
|
|
||||||
|
public:
|
||||||
|
qt_camera_error_handler(std::shared_ptr<QCamera> camera, std::function<void(QCamera::Status)> status_callback);
|
||||||
|
virtual ~qt_camera_error_handler();
|
||||||
|
|
||||||
|
private Q_SLOTS:
|
||||||
|
void handle_availability(QMultimedia::AvailabilityStatus availability);
|
||||||
|
void handle_lock_status(QCamera::LockStatus, QCamera::LockChangeReason);
|
||||||
|
void handle_capture_modes(QCamera::CaptureModes capture_modes);
|
||||||
|
void handle_camera_state(QCamera::State state);
|
||||||
|
void handle_camera_status(QCamera::Status status);
|
||||||
|
void handle_camera_error(QCamera::Error error);
|
||||||
|
|
||||||
|
private:
|
||||||
|
std::shared_ptr<QCamera> m_camera;
|
||||||
|
std::function<void(QCamera::Status)> m_status_callback = nullptr;
|
||||||
|
};
|
@ -32,21 +32,37 @@ void qt_camera_handler::set_camera(const QCameraInfo& cameraInfo)
|
|||||||
// Create camera and video surface
|
// Create camera and video surface
|
||||||
m_surface.reset(new qt_camera_video_surface(front_facing, nullptr));
|
m_surface.reset(new qt_camera_video_surface(front_facing, nullptr));
|
||||||
m_camera.reset(new QCamera(cameraInfo));
|
m_camera.reset(new QCamera(cameraInfo));
|
||||||
|
m_error_handler.reset(new qt_camera_error_handler(m_camera,
|
||||||
// Create connects (may not work due to threading)
|
[this](QCamera::Status status)
|
||||||
connect(m_camera.get(), &QCamera::stateChanged, this, [this](QCamera::State state){ handle_camera_state(state); });
|
{
|
||||||
connect(m_camera.get(), &QCamera::statusChanged, this, [this](QCamera::Status status){ handle_camera_status(status); });
|
switch (status)
|
||||||
connect(m_camera.get(), &QCamera::errorOccurred, this, [this](QCamera::Error error){ handle_camera_error(error); });
|
{
|
||||||
connect(m_camera.get(), &QCamera::captureModeChanged, this, [this](QCamera::CaptureModes modes){ handle_capture_modes(modes); });
|
case QCamera::UnavailableStatus:
|
||||||
connect(m_camera.get(), QOverload<QCamera::LockStatus, QCamera::LockChangeReason>::of(&QCamera::lockStatusChanged), this, [this](QCamera::LockStatus status, QCamera::LockChangeReason reason){ handle_lock_status(status, reason); });
|
m_state = camera_handler_state::not_available;
|
||||||
|
break;
|
||||||
|
case QCamera::UnloadedStatus:
|
||||||
|
case QCamera::UnloadingStatus:
|
||||||
|
m_state = camera_handler_state::closed;
|
||||||
|
break;
|
||||||
|
case QCamera::StandbyStatus:
|
||||||
|
case QCamera::StoppingStatus:
|
||||||
|
case QCamera::LoadedStatus:
|
||||||
|
case QCamera::LoadingStatus:
|
||||||
|
m_state = camera_handler_state::open;
|
||||||
|
break;
|
||||||
|
case QCamera::StartingStatus:
|
||||||
|
case QCamera::ActiveStatus:
|
||||||
|
m_state = camera_handler_state::running;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
camera_log.error("Ignoring unknown status %d", static_cast<int>(status));
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
}));
|
||||||
|
|
||||||
// Set view finder and update the settings
|
// Set view finder and update the settings
|
||||||
m_camera->setViewfinder(m_surface.get());
|
m_camera->setViewfinder(m_surface.get());
|
||||||
update_camera_settings();
|
update_camera_settings();
|
||||||
|
|
||||||
// Log some states
|
|
||||||
handle_camera_state(m_camera->state());
|
|
||||||
handle_lock_status(m_camera->lockStatus(), QCamera::UserRequest);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void qt_camera_handler::open_camera()
|
void qt_camera_handler::open_camera()
|
||||||
@ -65,7 +81,7 @@ void qt_camera_handler::open_camera()
|
|||||||
if (!m_camera)
|
if (!m_camera)
|
||||||
{
|
{
|
||||||
camera_log.error("No camera found");
|
camera_log.error("No camera found");
|
||||||
m_state = camera_handler_state::closed;
|
m_state = camera_handler_state::not_available;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -93,8 +109,6 @@ void qt_camera_handler::open_camera()
|
|||||||
|
|
||||||
// Update camera and view finder settings
|
// Update camera and view finder settings
|
||||||
update_camera_settings();
|
update_camera_settings();
|
||||||
|
|
||||||
m_state = camera_handler_state::open;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void qt_camera_handler::close_camera()
|
void qt_camera_handler::close_camera()
|
||||||
@ -104,7 +118,7 @@ void qt_camera_handler::close_camera()
|
|||||||
if (!m_camera)
|
if (!m_camera)
|
||||||
{
|
{
|
||||||
camera_log.error("No camera found");
|
camera_log.error("No camera found");
|
||||||
m_state = camera_handler_state::closed;
|
m_state = camera_handler_state::not_available;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -115,7 +129,6 @@ void qt_camera_handler::close_camera()
|
|||||||
|
|
||||||
// Unload/close camera
|
// Unload/close camera
|
||||||
m_camera->unload();
|
m_camera->unload();
|
||||||
m_state = camera_handler_state::closed;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void qt_camera_handler::start_camera()
|
void qt_camera_handler::start_camera()
|
||||||
@ -125,7 +138,7 @@ void qt_camera_handler::start_camera()
|
|||||||
if (!m_camera)
|
if (!m_camera)
|
||||||
{
|
{
|
||||||
camera_log.error("No camera found");
|
camera_log.error("No camera found");
|
||||||
m_state = camera_handler_state::closed;
|
m_state = camera_handler_state::not_available;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -141,7 +154,6 @@ void qt_camera_handler::start_camera()
|
|||||||
|
|
||||||
// Start camera. We will start receiving frames now.
|
// Start camera. We will start receiving frames now.
|
||||||
m_camera->start();
|
m_camera->start();
|
||||||
m_state = camera_handler_state::running;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void qt_camera_handler::stop_camera()
|
void qt_camera_handler::stop_camera()
|
||||||
@ -151,7 +163,7 @@ void qt_camera_handler::stop_camera()
|
|||||||
if (!m_camera)
|
if (!m_camera)
|
||||||
{
|
{
|
||||||
camera_log.error("No camera found");
|
camera_log.error("No camera found");
|
||||||
m_state = camera_handler_state::closed;
|
m_state = camera_handler_state::not_available;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -162,7 +174,6 @@ void qt_camera_handler::stop_camera()
|
|||||||
|
|
||||||
// Stop camera. The camera will still be drawing power.
|
// Stop camera. The camera will still be drawing power.
|
||||||
m_camera->stop();
|
m_camera->stop();
|
||||||
m_state = camera_handler_state::open;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void qt_camera_handler::set_format(s32 format, u32 bytes_per_pixel)
|
void qt_camera_handler::set_format(s32 format, u32 bytes_per_pixel)
|
||||||
@ -200,53 +211,34 @@ u64 qt_camera_handler::frame_number() const
|
|||||||
return m_surface ? m_surface->frame_number() : 0;
|
return m_surface ? m_surface->frame_number() : 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool qt_camera_handler::get_image(u8* buf, u64 size, u32& width, u32& height, u64& frame_number, u64& bytes_read)
|
camera_handler_base::camera_handler_state qt_camera_handler::get_image(u8* buf, u64 size, u32& width, u32& height, u64& frame_number, u64& bytes_read)
|
||||||
{
|
{
|
||||||
width = 0;
|
width = 0;
|
||||||
height = 0;
|
height = 0;
|
||||||
frame_number = 0;
|
frame_number = 0;
|
||||||
bytes_read = 0;
|
bytes_read = 0;
|
||||||
|
|
||||||
// Check for errors
|
if (!m_camera || !m_surface)
|
||||||
if (!m_camera || !m_surface || m_state != camera_handler_state::running)
|
|
||||||
{
|
{
|
||||||
camera_log.error("Error: camera invalid");
|
camera_log.fatal("Error: camera invalid");
|
||||||
m_state = camera_handler_state::closed;
|
m_state = camera_handler_state::not_available;
|
||||||
return false;
|
return camera_handler_state::not_available;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (QCamera::Error error = m_camera->error(); error != QCamera::NoError)
|
// Backup current state. State may change through events.
|
||||||
|
const camera_handler_state current_state = m_state;
|
||||||
|
|
||||||
|
if (current_state == camera_handler_state::running)
|
||||||
{
|
{
|
||||||
camera_log.error("Error: \"%s\" (error=%d)", m_camera ? m_camera->errorString().toStdString() : "", static_cast<int>(error));
|
// Copy latest image into out buffer.
|
||||||
m_state = camera_handler_state::closed;
|
m_surface->get_image(buf, size, width, height, frame_number, bytes_read);
|
||||||
return false;
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
camera_log.error("Camera not running (m_state=%d)", static_cast<int>(current_state));
|
||||||
}
|
}
|
||||||
|
|
||||||
switch (QCamera::Status status = m_camera->status())
|
return current_state;
|
||||||
{
|
|
||||||
case QCamera::UnavailableStatus:
|
|
||||||
case QCamera::UnloadedStatus:
|
|
||||||
case QCamera::UnloadingStatus:
|
|
||||||
camera_log.error("Camera not open. State=%d", static_cast<int>(status));
|
|
||||||
m_state = camera_handler_state::closed;
|
|
||||||
return false;
|
|
||||||
case QCamera::LoadedStatus:
|
|
||||||
case QCamera::StandbyStatus:
|
|
||||||
case QCamera::StoppingStatus:
|
|
||||||
camera_log.error("Camera not active. State=%d", static_cast<int>(status));
|
|
||||||
m_state = camera_handler_state::open;
|
|
||||||
return false;
|
|
||||||
case QCamera::LoadingStatus:
|
|
||||||
case QCamera::StartingStatus:
|
|
||||||
case QCamera::ActiveStatus:
|
|
||||||
default:
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Copy latest image into out buffer.
|
|
||||||
m_surface->get_image(buf, size, width, height, frame_number, bytes_read);
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
void qt_camera_handler::update_camera_settings()
|
void qt_camera_handler::update_camera_settings()
|
||||||
@ -306,28 +298,3 @@ void qt_camera_handler::update_camera_settings()
|
|||||||
m_surface->set_mirrored(m_mirrored);
|
m_surface->set_mirrored(m_mirrored);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void qt_camera_handler::handle_camera_state(QCamera::State state)
|
|
||||||
{
|
|
||||||
camera_log.notice("Camera state changed to %d", static_cast<int>(state));
|
|
||||||
}
|
|
||||||
|
|
||||||
void qt_camera_handler::handle_camera_status(QCamera::Status status)
|
|
||||||
{
|
|
||||||
camera_log.notice("Camera status changed to %d", static_cast<int>(status));
|
|
||||||
}
|
|
||||||
|
|
||||||
void qt_camera_handler::handle_lock_status(QCamera::LockStatus status, QCamera::LockChangeReason reason)
|
|
||||||
{
|
|
||||||
camera_log.notice("Camera lock status changed to %d (reason=%d)", static_cast<int>(status), static_cast<int>(reason));
|
|
||||||
}
|
|
||||||
|
|
||||||
void qt_camera_handler::handle_capture_modes(QCamera::CaptureModes capture_modes)
|
|
||||||
{
|
|
||||||
camera_log.notice("Camera capture modes changed to %d", static_cast<int>(capture_modes));
|
|
||||||
}
|
|
||||||
|
|
||||||
void qt_camera_handler::handle_camera_error(QCamera::Error error)
|
|
||||||
{
|
|
||||||
camera_log.error("Error: \"%s\" (error=%d)", m_camera ? m_camera->errorString().toStdString() : "", static_cast<int>(error));
|
|
||||||
}
|
|
||||||
|
@ -2,20 +2,19 @@
|
|||||||
|
|
||||||
#include "Emu/Io/camera_handler_base.h"
|
#include "Emu/Io/camera_handler_base.h"
|
||||||
#include "qt_camera_video_surface.h"
|
#include "qt_camera_video_surface.h"
|
||||||
|
#include "qt_camera_error_handler.h"
|
||||||
|
|
||||||
#include <QCamera>
|
#include <QCamera>
|
||||||
#include <QCameraImageCapture>
|
#include <QCameraImageCapture>
|
||||||
#include <QAbstractVideoSurface>
|
#include <QAbstractVideoSurface>
|
||||||
|
|
||||||
class video_surface;
|
class qt_camera_handler final : public camera_handler_base
|
||||||
|
|
||||||
class qt_camera_handler final : public camera_handler_base, public QObject
|
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
qt_camera_handler();
|
qt_camera_handler();
|
||||||
virtual ~qt_camera_handler();
|
virtual ~qt_camera_handler();
|
||||||
|
|
||||||
void set_camera(const QCameraInfo &cameraInfo);
|
void set_camera(const QCameraInfo& cameraInfo);
|
||||||
|
|
||||||
void open_camera() override;
|
void open_camera() override;
|
||||||
void close_camera() override;
|
void close_camera() override;
|
||||||
@ -26,16 +25,12 @@ public:
|
|||||||
void set_resolution(u32 width, u32 height) override;
|
void set_resolution(u32 width, u32 height) override;
|
||||||
void set_mirrored(bool mirrored) override;
|
void set_mirrored(bool mirrored) override;
|
||||||
u64 frame_number() const override;
|
u64 frame_number() const override;
|
||||||
bool get_image(u8* buf, u64 size, u32& width, u32& height, u64& frame_number, u64& bytes_read) override;
|
camera_handler_state get_image(u8* buf, u64 size, u32& width, u32& height, u64& frame_number, u64& bytes_read) override;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void handle_lock_status(QCamera::LockStatus, QCamera::LockChangeReason);
|
|
||||||
void handle_capture_modes(QCamera::CaptureModes capture_modes);
|
|
||||||
void handle_camera_state(QCamera::State state);
|
|
||||||
void handle_camera_status(QCamera::Status status);
|
|
||||||
void handle_camera_error(QCamera::Error error);
|
|
||||||
void update_camera_settings();
|
void update_camera_settings();
|
||||||
|
|
||||||
std::unique_ptr<QCamera> m_camera;
|
std::shared_ptr<QCamera> m_camera;
|
||||||
std::unique_ptr<qt_camera_video_surface> m_surface;
|
std::unique_ptr<qt_camera_video_surface> m_surface;
|
||||||
|
std::unique_ptr<qt_camera_error_handler> m_error_handler;
|
||||||
};
|
};
|
||||||
|
Loading…
x
Reference in New Issue
Block a user