2023-01-05 20:25:55 +08:00
/**************************************************************************/
/* camera_server.cpp */
/**************************************************************************/
/* This file is part of: */
/* GODOT ENGINE */
/* https://godotengine.org */
/**************************************************************************/
/* Copyright (c) 2014-present Godot Engine contributors (see AUTHORS.md). */
/* Copyright (c) 2007-2014 Juan Linietsky, Ariel Manzur. */
/* */
/* Permission is hereby granted, free of charge, to any person obtaining */
/* a copy of this software and associated documentation files (the */
/* "Software"), to deal in the Software without restriction, including */
/* without limitation the rights to use, copy, modify, merge, publish, */
/* distribute, sublicense, and/or sell copies of the Software, and to */
/* permit persons to whom the Software is furnished to do so, subject to */
/* the following conditions: */
/* */
/* The above copyright notice and this permission notice shall be */
/* included in all copies or substantial portions of the Software. */
/* */
/* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, */
/* EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF */
/* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. */
/* IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY */
/* CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, */
/* TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE */
/* SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE. */
/**************************************************************************/
2017-08-20 22:17:24 +08:00
# include "camera_server.h"
2022-08-05 09:41:48 +08:00
# include "core/variant/typed_array.h"
2020-03-28 02:21:27 +08:00
# include "rendering_server.h"
2017-08-20 22:17:24 +08:00
# include "servers/camera/camera_feed.h"
////////////////////////////////////////////////////////
// CameraServer
2020-04-02 07:20:12 +08:00
CameraServer : : CreateFunc CameraServer : : create_func = nullptr ;
2019-11-29 14:54:39 +08:00
2017-08-20 22:17:24 +08:00
void CameraServer : : _bind_methods ( ) {
ClassDB : : bind_method ( D_METHOD ( " get_feed " , " index " ) , & CameraServer : : get_feed ) ;
ClassDB : : bind_method ( D_METHOD ( " get_feed_count " ) , & CameraServer : : get_feed_count ) ;
ClassDB : : bind_method ( D_METHOD ( " feeds " ) , & CameraServer : : get_feeds ) ;
ClassDB : : bind_method ( D_METHOD ( " add_feed " , " feed " ) , & CameraServer : : add_feed ) ;
ClassDB : : bind_method ( D_METHOD ( " remove_feed " , " feed " ) , & CameraServer : : remove_feed ) ;
ADD_SIGNAL ( MethodInfo ( " camera_feed_added " , PropertyInfo ( Variant : : INT , " id " ) ) ) ;
ADD_SIGNAL ( MethodInfo ( " camera_feed_removed " , PropertyInfo ( Variant : : INT , " id " ) ) ) ;
BIND_ENUM_CONSTANT ( FEED_RGBA_IMAGE ) ;
2019-06-19 20:21:13 +08:00
BIND_ENUM_CONSTANT ( FEED_YCBCR_IMAGE ) ;
2017-08-20 22:17:24 +08:00
BIND_ENUM_CONSTANT ( FEED_Y_IMAGE ) ;
2019-06-19 20:21:13 +08:00
BIND_ENUM_CONSTANT ( FEED_CBCR_IMAGE ) ;
2017-08-20 22:17:24 +08:00
} ;
2020-04-02 07:20:12 +08:00
CameraServer * CameraServer : : singleton = nullptr ;
2017-08-20 22:17:24 +08:00
CameraServer * CameraServer : : get_singleton ( ) {
return singleton ;
} ;
int CameraServer : : get_free_id ( ) {
bool id_exists = true ;
int newid = 0 ;
// find a free id
while ( id_exists ) {
newid + + ;
id_exists = false ;
for ( int i = 0 ; i < feeds . size ( ) & & ! id_exists ; i + + ) {
if ( feeds [ i ] - > get_id ( ) = = newid ) {
id_exists = true ;
} ;
} ;
} ;
return newid ;
} ;
int CameraServer : : get_feed_index ( int p_id ) {
for ( int i = 0 ; i < feeds . size ( ) ; i + + ) {
if ( feeds [ i ] - > get_id ( ) = = p_id ) {
return i ;
} ;
} ;
return - 1 ;
} ;
Ref < CameraFeed > CameraServer : : get_feed_by_id ( int p_id ) {
int index = get_feed_index ( p_id ) ;
if ( index = = - 1 ) {
2020-04-02 07:20:12 +08:00
return nullptr ;
2017-08-20 22:17:24 +08:00
} else {
return feeds [ index ] ;
}
} ;
void CameraServer : : add_feed ( const Ref < CameraFeed > & p_feed ) {
2021-04-02 21:16:40 +08:00
ERR_FAIL_COND ( p_feed . is_null ( ) ) ;
2017-08-20 22:17:24 +08:00
// add our feed
feeds . push_back ( p_feed ) ;
2022-09-03 05:25:19 +08:00
print_verbose ( " CameraServer: Registered camera " + p_feed - > get_name ( ) + " with ID " + itos ( p_feed - > get_id ( ) ) + " and position " + itos ( p_feed - > get_position ( ) ) + " at index " + itos ( feeds . size ( ) - 1 ) ) ;
2017-08-20 22:17:24 +08:00
// let whomever is interested know
2021-07-18 05:22:52 +08:00
emit_signal ( SNAME ( " camera_feed_added " ) , p_feed - > get_id ( ) ) ;
2017-08-20 22:17:24 +08:00
} ;
void CameraServer : : remove_feed ( const Ref < CameraFeed > & p_feed ) {
for ( int i = 0 ; i < feeds . size ( ) ; i + + ) {
if ( feeds [ i ] = = p_feed ) {
int feed_id = p_feed - > get_id ( ) ;
2022-09-03 05:25:19 +08:00
print_verbose ( " CameraServer: Removed camera " + p_feed - > get_name ( ) + " with ID " + itos ( feed_id ) + " and position " + itos ( p_feed - > get_position ( ) ) ) ;
2017-08-20 22:17:24 +08:00
// remove it from our array, if this results in our feed being unreferenced it will be destroyed
2021-07-04 06:17:03 +08:00
feeds . remove_at ( i ) ;
2017-08-20 22:17:24 +08:00
// let whomever is interested know
2021-07-18 05:22:52 +08:00
emit_signal ( SNAME ( " camera_feed_removed " ) , feed_id ) ;
2017-08-20 22:17:24 +08:00
return ;
} ;
} ;
} ;
Ref < CameraFeed > CameraServer : : get_feed ( int p_index ) {
2020-04-02 07:20:12 +08:00
ERR_FAIL_INDEX_V ( p_index , feeds . size ( ) , nullptr ) ;
2017-08-20 22:17:24 +08:00
return feeds [ p_index ] ;
} ;
int CameraServer : : get_feed_count ( ) {
return feeds . size ( ) ;
} ;
2022-08-05 09:41:48 +08:00
TypedArray < CameraFeed > CameraServer : : get_feeds ( ) {
TypedArray < CameraFeed > return_feeds ;
2017-08-20 22:17:24 +08:00
int cc = get_feed_count ( ) ;
return_feeds . resize ( cc ) ;
for ( int i = 0 ; i < feeds . size ( ) ; i + + ) {
return_feeds [ i ] = get_feed ( i ) ;
} ;
return return_feeds ;
} ;
RID CameraServer : : feed_texture ( int p_id , CameraServer : : FeedImage p_texture ) {
int index = get_feed_index ( p_id ) ;
ERR_FAIL_COND_V ( index = = - 1 , RID ( ) ) ;
Ref < CameraFeed > feed = get_feed ( index ) ;
return feed - > get_texture ( p_texture ) ;
} ;
CameraServer : : CameraServer ( ) {
singleton = this ;
} ;
CameraServer : : ~ CameraServer ( ) {
2020-04-02 07:20:12 +08:00
singleton = nullptr ;
2017-08-20 22:17:24 +08:00
} ;