mirror of
				https://github.com/hyperion-project/hyperion.ng.git
				synced 2025-03-01 10:33:28 +00:00 
			
		
		
		
	Added simple direct implementation of the frame-grabber using dispmanx (copied from https://github.com/brooc/boblight-rpi/tree/master/src/clients/boblight-dispmanx)
This commit is contained in:
		| @@ -29,8 +29,8 @@ set(CMAKE_FIND_LIBRARY_SUFFIXES ".a;.so") | ||||
| set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++0x -Wall") | ||||
|  | ||||
| configure_file(bin/install_hyperion.sh ${LIBRARY_OUTPUT_PATH} @ONLY) | ||||
| configure_file(config/Hyperion.config.json ${LIBRARY_OUTPUT_PATH} @ONLY) | ||||
| configure_file(config/Hyperion.schema.json ${LIBRARY_OUTPUT_PATH} @ONLY) | ||||
| configure_file(config/hyperion.config.json ${LIBRARY_OUTPUT_PATH} @ONLY) | ||||
| configure_file(config/hyperion.schema.json ${LIBRARY_OUTPUT_PATH} @ONLY) | ||||
|  | ||||
| # Add the source/lib directories | ||||
| add_subdirectory(dependencies) | ||||
|   | ||||
| @@ -20,7 +20,8 @@ inline Hyperion* rasp_cast(void* hyperion_ptr) | ||||
|  | ||||
| void* boblight_init() | ||||
| { | ||||
| 	syslog(LOG_INFO, __PRETTY_FUNCTION__); | ||||
| 	std::cout << __PRETTY_FUNCTION__ << std::endl; | ||||
| //	syslog(LOG_INFO, __PRETTY_FUNCTION__); | ||||
|  | ||||
| 	const char* homeDir = getenv("RASPILIGHT_HOME"); | ||||
| 	if (!homeDir) | ||||
| @@ -83,6 +84,7 @@ int boblight_sendrgb(void* hyperion_ptr, int sync, int* outputused) | ||||
|  | ||||
| int boblight_connect(void* hyperion_ptr, const char* address, int port, int usectimeout) | ||||
| { | ||||
| 	std::cout << "SUCCESFULL NO CONNECTION WITH BOBLIGHT" << std::endl; | ||||
| 	return 1; | ||||
| } | ||||
|  | ||||
| @@ -93,6 +95,7 @@ const char* boblight_geterror(void* hyperion_ptr) | ||||
|  | ||||
| int boblight_setpriority(void* hyperion_ptr, int priority) | ||||
| { | ||||
| 	std::cout << __PRETTY_FUNCTION__ << std::endl; | ||||
| 	return 1; | ||||
| } | ||||
|  | ||||
|   | ||||
| @@ -65,20 +65,21 @@ void Hyperion::setInputSize(const unsigned width, const unsigned height) | ||||
| void Hyperion::commit() | ||||
| { | ||||
| 	// Derive the color per led | ||||
| 	const std::vector<RgbColor> ledColors = mLedsMap.getMedianLedColor(); | ||||
| 	std::vector<RgbColor> ledColors = mLedsMap.getMeanLedColor(); | ||||
| //	const std::vector<RgbColor> ledColors = mLedsMap.getMedianLedColor(); | ||||
|  | ||||
| 	// Write the Led colors to the led-string | ||||
| 	mDevice->write(ledColors); | ||||
| } | ||||
|  | ||||
| void Hyperion::operator() (const RgbImage& inputImage) | ||||
| { | ||||
| 	std::cout << "Cached image size: [" << mImage->width() << "x" << mImage->height() << "]. Input image size: [" << inputImage.width() << "x" << inputImage.height() << "]" << std::endl; | ||||
| 	// Copy the input-image into the buffer | ||||
| 	mImage->copy(inputImage); | ||||
|  | ||||
| 	// Derive the color per led | ||||
| //	std::vector<RgbColor> ledColors = mLedsMap.getMeanLedColor(); | ||||
| 	std::vector<RgbColor> ledColors = mLedsMap.getMedianLedColor(); | ||||
| 	std::vector<RgbColor> ledColors = mLedsMap.getMeanLedColor(); | ||||
| //	std::vector<RgbColor> ledColors = mLedsMap.getMedianLedColor(); | ||||
| 	applyTransform(ledColors); | ||||
|  | ||||
| 	// Write the Led colors to the led-string | ||||
|   | ||||
| @@ -42,3 +42,37 @@ add_executable(Test2BobLight | ||||
|  | ||||
| target_link_libraries(Test2BobLight | ||||
| 		bob2hyperion) | ||||
|  | ||||
| add_executable(boblight-dispmanx | ||||
| 		boblight-dispmanx.cpp | ||||
| 		flagmanager.h | ||||
| 		flagmanager.cpp | ||||
| 		flagmanager-dispmanx.h | ||||
| 		flagmanager-dispmanx.cpp | ||||
| 		grabber-dispmanx.h | ||||
| 		grabber-dispmanx.cpp | ||||
| 		misc.h | ||||
| 		misc.cpp | ||||
| 		timer.h | ||||
| 		timer.cpp | ||||
| 		timeutils.h | ||||
| 		timeutils.cpp) | ||||
|  | ||||
| SET(VC_INCLUDE_DIRS  | ||||
| 		/opt/vc/include | ||||
| 		/opt/vc/include/interface/vcos/pthreads | ||||
| 		/opt/vc/include/interface/vmcs_host/linux) | ||||
| SET(VC_LIBS  | ||||
| 	/home/pi/.xbmc-current/xbmc-bin/lib/xbmc/system/libbcm_host.so) | ||||
| #	/home/pi/.xbmc-current/xbmc-bin/lib/xbmc/system/libGLESv2.so | ||||
| #	/home/pi/.xbmc-current/xbmc-bin/lib/xbmc/system/libEGL.so | ||||
| #	/home/pi/.xbmc-current/xbmc-bin/lib/xbmc/system/libopenmaxil.so | ||||
| #	/home/pi/.xbmc-current/xbmc-bin/lib/xbmc/system/libvcos.so | ||||
| #	/home/pi/.xbmc-current/xbmc-bin/lib/xbmc/system/libvchiq_arm.so) | ||||
|  | ||||
| include_directories(${VC_INCLUDE_DIRS}) | ||||
|  | ||||
| target_link_libraries(boblight-dispmanx | ||||
| #		hyperion-png | ||||
| 		bob2hyperion | ||||
| 		${VC_LIBS}) | ||||
|   | ||||
| @@ -18,15 +18,29 @@ ofstream& indent(ofstream& ofs, unsigned indent) | ||||
|  | ||||
| struct LedFrame | ||||
| { | ||||
| 	unsigned topLedCnt    = 17; | ||||
| 	unsigned rightLedCnt  = 8; | ||||
| 	unsigned bottomLedCnt = 17; | ||||
| 	unsigned leftLedCnt   = 8; | ||||
| 	unsigned topLedCnt; | ||||
| 	unsigned rightLedCnt; | ||||
| 	unsigned bottomLedCnt; | ||||
| 	unsigned leftLedCnt; | ||||
|  | ||||
| 	unsigned topLeftOffset = 17; | ||||
| 	unsigned topLeftOffset; | ||||
|  | ||||
| 	unsigned borderWidth  = 10; | ||||
| 	unsigned borderHeight = 10; | ||||
| 	unsigned borderWidth; | ||||
| 	unsigned borderHeight; | ||||
|  | ||||
| 	LedFrame() : | ||||
| 		topLedCnt(17), | ||||
| 		rightLedCnt(8), | ||||
| 		bottomLedCnt(17), | ||||
| 		leftLedCnt(8), | ||||
|  | ||||
| 		topLeftOffset(17), | ||||
|  | ||||
| 		borderWidth(10), | ||||
| 		borderHeight(10) | ||||
| 	{ | ||||
| 		// empty | ||||
| 	} | ||||
|  | ||||
| 	unsigned totalLedCnt() const | ||||
| 	{ | ||||
|   | ||||
							
								
								
									
										179
									
								
								src/boblight-dispmanx.cpp
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										179
									
								
								src/boblight-dispmanx.cpp
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,179 @@ | ||||
| /* | ||||
|  * boblight | ||||
|  * Copyright (C) Bob  2009  | ||||
|  *  | ||||
|  * boblight is free software: you can redistribute it and/or modify it | ||||
|  * under the terms of the GNU General Public License as published by the | ||||
|  * Free Software Foundation, either version 3 of the License, or | ||||
|  * (at your option) any later version. | ||||
|  *  | ||||
|  * boblight is distributed in the hope that it will be useful, but | ||||
|  * WITHOUT ANY WARRANTY; without even the implied warranty of | ||||
|  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. | ||||
|  * See the GNU General Public License for more details. | ||||
|  *  | ||||
|  * You should have received a copy of the GNU General Public License along | ||||
|  * with this program.  If not, see <http://www.gnu.org/licenses/>. | ||||
|  */ | ||||
|  | ||||
| //#define BOBLIGHT_DLOPEN | ||||
| #include "boblight.h" | ||||
|  | ||||
| #include <iostream> | ||||
| #include <string> | ||||
| #include <vector> | ||||
| #include <signal.h> | ||||
| #include <unistd.h> | ||||
|  | ||||
| //#include "config.h" | ||||
| #include "misc.h" | ||||
| #include "flagmanager-dispmanx.h" | ||||
| #include "grabber-dispmanx.h" | ||||
|  | ||||
| //OpenMax includes | ||||
| #include "bcm_host.h" | ||||
| #include <assert.h> | ||||
|  | ||||
| using namespace std; | ||||
|  | ||||
| #define TEST_SAVE_IMAGE 0 | ||||
| #define PRINT_RET_VAL(ret, func, ...) ret = func(__VA_ARGS__); printf(#func " returned %d\n", ret); | ||||
|  | ||||
| int  Run(); | ||||
| void SignalHandler(int signum); | ||||
|  | ||||
| volatile bool stop = false; | ||||
|  | ||||
| CFlagManagerDispmanX g_flagmanager; | ||||
|  | ||||
| int main(int argc, char *argv[]) | ||||
| { | ||||
| 	std::cout << "HACKED VERSION WITH TIMOLIGHT" << std::endl; | ||||
|   //load the boblight lib, if it fails we get a char* from dlerror() | ||||
| //  char* boblight_error = boblight_loadlibrary(NULL); | ||||
| //  if (boblight_error) | ||||
| //  { | ||||
| //    PrintError(boblight_error); | ||||
| //    return 1; | ||||
| //  } | ||||
|  | ||||
|   //try to parse the flags and bitch to stderr if there's an error | ||||
|   try | ||||
|   { | ||||
|     g_flagmanager.ParseFlags(argc, argv); | ||||
|   } | ||||
|   catch (string error) | ||||
|   { | ||||
|     PrintError(error); | ||||
|     g_flagmanager.PrintHelpMessage(); | ||||
|     return 1; | ||||
|   } | ||||
|  | ||||
|   if (g_flagmanager.m_printhelp) //print help message | ||||
|   { | ||||
|     g_flagmanager.PrintHelpMessage(); | ||||
|     return 1; | ||||
|   } | ||||
|  | ||||
|   if (g_flagmanager.m_printboblightoptions) //print boblight options (-o [light:]option=value) | ||||
|   { | ||||
|     g_flagmanager.PrintBoblightOptions(); | ||||
|     return 1; | ||||
|   } | ||||
|  | ||||
|   if (g_flagmanager.m_fork) | ||||
|   { | ||||
|     if (fork()) | ||||
|       return 0; | ||||
|   } | ||||
|  | ||||
|   //set up signal handlers | ||||
|   signal(SIGTERM, SignalHandler); | ||||
|   signal(SIGINT, SignalHandler); | ||||
|  | ||||
|   //keep running until we want to quit | ||||
|   return Run(); | ||||
| } | ||||
|  | ||||
| int Run() | ||||
| { | ||||
| 	while(!stop) | ||||
| 	{ | ||||
| 		//init boblight | ||||
| 		void* boblight = boblight_init(); | ||||
|  | ||||
| 		cout << "Connecting to boblightd\n"; | ||||
|  | ||||
| 		//try to connect, if we can't then bitch to stderr and destroy boblight | ||||
| 		if (!boblight_connect(boblight, g_flagmanager.m_address, g_flagmanager.m_port, 5000000) || | ||||
| 				!boblight_setpriority(boblight, g_flagmanager.m_priority)) | ||||
| 		{ | ||||
| 			PrintError(boblight_geterror(boblight)); | ||||
| 			cout << "Waiting 10 seconds before trying again\n"; | ||||
| 			boblight_destroy(boblight); | ||||
| 			sleep(10); | ||||
| 			continue; | ||||
| 		} | ||||
|  | ||||
| 		cout << "Connection to boblightd opened\n"; | ||||
|  | ||||
| 		//try to parse the boblight flags and bitch to stderr if we can't | ||||
| 		try | ||||
| 		{ | ||||
| 			g_flagmanager.ParseBoblightOptions(boblight); | ||||
| 		} | ||||
| 		catch (string error) | ||||
| 		{ | ||||
| 			PrintError(error); | ||||
| 			return 1; | ||||
| 		} | ||||
|  | ||||
| 		CGrabberDispmanX *grabber = new CGrabberDispmanX(boblight, stop, g_flagmanager.m_sync); | ||||
|  | ||||
| 		grabber->SetInterval(g_flagmanager.m_interval); | ||||
| 		grabber->SetSize(g_flagmanager.m_pixels); | ||||
|  | ||||
| 		if (!grabber->Setup()) //just exit if we can't set up the grabber | ||||
| 		{ | ||||
| 			PrintError(grabber->GetError()); | ||||
| 			delete grabber; | ||||
| 			boblight_destroy(boblight); | ||||
| 			return 1; | ||||
| 		} | ||||
|  | ||||
| 		if (!grabber->Run()) //just exit if some unrecoverable error happens | ||||
| 		{ | ||||
| 			PrintError(grabber->GetError()); | ||||
| 			delete grabber; | ||||
| 			boblight_destroy(boblight); | ||||
| 			return 1; | ||||
| 		} | ||||
| 		else //boblightd probably timed out, so just try to reconnect | ||||
| 		{ | ||||
| 			if (!grabber->GetError().empty()) | ||||
| 				PrintError(grabber->GetError()); | ||||
| 		} | ||||
|  | ||||
| 		delete grabber; | ||||
|  | ||||
| 		boblight_destroy(boblight); | ||||
| 	} | ||||
|  | ||||
| 	cout << "Exiting\n"; | ||||
|  | ||||
| 	return 0; | ||||
| } | ||||
|  | ||||
| void SignalHandler(int signum) | ||||
| { | ||||
|   if (signum == SIGTERM) | ||||
|   { | ||||
|     cout << "caught SIGTERM\n"; | ||||
|     stop = true; | ||||
|   } | ||||
|   else if (signum == SIGINT) | ||||
|   { | ||||
|     cout << "caught SIGINT\n"; | ||||
|     stop = true; | ||||
|   } | ||||
| } | ||||
							
								
								
									
										106
									
								
								src/flagmanager-dispmanx.cpp
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										106
									
								
								src/flagmanager-dispmanx.cpp
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,106 @@ | ||||
| /* | ||||
|  * boblight | ||||
|  * Copyright (C) Bob  2009  | ||||
|  *  | ||||
|  * boblight is free software: you can redistribute it and/or modify it | ||||
|  * under the terms of the GNU General Public License as published by the | ||||
|  * Free Software Foundation, either version 3 of the License, or | ||||
|  * (at your option) any later version. | ||||
|  *  | ||||
|  * boblight is distributed in the hope that it will be useful, but | ||||
|  * WITHOUT ANY WARRANTY; without even the implied warranty of | ||||
|  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. | ||||
|  * See the GNU General Public License for more details. | ||||
|  *  | ||||
|  * You should have received a copy of the GNU General Public License along | ||||
|  * with this program.  If not, see <http://www.gnu.org/licenses/>. | ||||
|  */ | ||||
|  | ||||
| #include <iostream> | ||||
|  | ||||
| #include "flagmanager-dispmanx.h" | ||||
| //#include "config.h" | ||||
| #include "misc.h" | ||||
|  | ||||
| using namespace std; | ||||
|  | ||||
| CFlagManagerDispmanX::CFlagManagerDispmanX() | ||||
| { | ||||
|   //extend the base getopt flags | ||||
|   //i = interval, u = pixels, x = xgetimage, d = debug | ||||
|   m_flags += "i:u:d::"; | ||||
|  | ||||
|   m_interval = 0.1;    //default interval is 100 milliseconds | ||||
|   m_pixels = 64;       //-1 says to the capture classes to use default | ||||
|   m_debug = false;     //no debugging by default | ||||
|   m_debugdpy = NULL;   //default debug dpy is system default | ||||
|   m_sync = true;       //sync mode enabled by default | ||||
| } | ||||
|  | ||||
| void CFlagManagerDispmanX::ParseFlagsExtended(int& argc, char**& argv, int& c, char*& optarg) //we load our own flags here | ||||
| { | ||||
| 	  if (c == 'i') //interval | ||||
| 	  { | ||||
| 	    bool vblank = false; | ||||
|  | ||||
| 	    if (optarg[0] == 'v') //starting interval with v means vblank interval | ||||
| 	    { | ||||
| 	#ifdef HAVE_LIBGL | ||||
| 	      optarg++; | ||||
| 	      vblank = true; | ||||
| 	#else | ||||
| 	      throw string("Compiled without opengl support"); | ||||
| 	#endif | ||||
| 	    } | ||||
|  | ||||
| 	    if (!StrToFloat(optarg, m_interval) || m_interval <= 0.0) | ||||
| 	    { | ||||
| 	      throw string("Wrong value " + string(optarg) + " for interval"); | ||||
| 	    } | ||||
|  | ||||
| 	    if (vblank) | ||||
| 	    { | ||||
| 	      if (m_interval < 1.0) | ||||
| 	      { | ||||
| 	        throw string("Wrong value " + string(optarg) + " for vblank interval"); | ||||
| 	      } | ||||
| 	      m_interval *= -1.0; //negative interval means vblank | ||||
| 	      optarg--; | ||||
| 	    } | ||||
| 	  } | ||||
| 	  else if (c == 'u') //nr of pixels to use | ||||
| 	  { | ||||
| 	    if (!StrToInt(optarg, m_pixels) || m_pixels <= 0) | ||||
| 	    { | ||||
| 	      throw string("Wrong value " + string(optarg) + " for pixels"); | ||||
| 	    } | ||||
| 	  } | ||||
| 	  else if (c == 'd') //turn on debug mode | ||||
| 	  { | ||||
| 	    m_debug = true; | ||||
| 	    if (optarg)      //optional debug dpy | ||||
| 	    { | ||||
| 	      m_strdebugdpy = optarg; | ||||
| 	      m_debugdpy = m_strdebugdpy.c_str(); | ||||
| 	    } | ||||
| 	  } | ||||
| } | ||||
|  | ||||
| void CFlagManagerDispmanX::PrintHelpMessage() | ||||
| { | ||||
| 	  cout << "Usage: boblight-dispmanx [OPTION]\n"; | ||||
| 	  cout << "\n"; | ||||
| 	  cout << "  options:\n"; | ||||
| 	  cout << "\n"; | ||||
| 	  cout << "  -p  priority, from 0 to 255, default is 128\n"; | ||||
| 	  cout << "  -s  address:[port], set the address and optional port to connect to\n"; | ||||
| 	  cout << "  -o  add libboblight option, syntax: [light:]option=value\n"; | ||||
| 	  cout << "  -l  list libboblight options\n"; | ||||
| 	  cout << "  -i  set the interval in seconds, default is 0.1\n"; | ||||
| 	  cout << "  -u  set the number of pixels/rows to use\n"; | ||||
| 	  cout << "      default is 64 for xrender and 16 for xgetimage\n"; | ||||
| 	  cout << "  -d  debug mode\n"; | ||||
| 	  cout << "  -f  fork\n"; | ||||
| 	  cout << "  -y  set the sync mode, default is on, valid options are \"on\" and \"off\"\n"; | ||||
| 	  cout << "\n"; | ||||
| } | ||||
							
								
								
									
										44
									
								
								src/flagmanager-dispmanx.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										44
									
								
								src/flagmanager-dispmanx.h
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,44 @@ | ||||
| /* | ||||
|  * boblight | ||||
|  * Copyright (C) Bob  2009  | ||||
|  *  | ||||
|  * boblight is free software: you can redistribute it and/or modify it | ||||
|  * under the terms of the GNU General Public License as published by the | ||||
|  * Free Software Foundation, either version 3 of the License, or | ||||
|  * (at your option) any later version. | ||||
|  *  | ||||
|  * boblight is distributed in the hope that it will be useful, but | ||||
|  * WITHOUT ANY WARRANTY; without even the implied warranty of | ||||
|  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. | ||||
|  * See the GNU General Public License for more details. | ||||
|  *  | ||||
|  * You should have received a copy of the GNU General Public License along | ||||
|  * with this program.  If not, see <http://www.gnu.org/licenses/>. | ||||
|  */ | ||||
|  | ||||
| #ifndef FLAGMANAGERDISPMANX | ||||
| #define FLAGMANAGERDISPMANX | ||||
|  | ||||
| #include "flagmanager.h" | ||||
|  | ||||
| class CFlagManagerDispmanX : public CFlagManager | ||||
| { | ||||
| public: | ||||
| 	CFlagManagerDispmanX(); | ||||
|  | ||||
| 	int  m_color; | ||||
|  | ||||
| 	void        ParseFlagsExtended(int& argc, char**& argv, int& c, char*& optarg); //we load our own flags here | ||||
| 	void        PrintHelpMessage(); | ||||
|  | ||||
| 	double      m_interval;           //grab interval in seconds, or vertical blanks when negative | ||||
| 	int         m_pixels;             //number of pixels on lines to capture | ||||
| 	bool        m_debug;              //if true we make a little window where we put our captured output on, looks pretty | ||||
| 	const char* m_debugdpy;           //display to place the debug window on, default is NULL | ||||
|  | ||||
| private: | ||||
|  | ||||
| 	std::string m_strdebugdpy;        //place to store the debug dpy, cause our copied argv is destroyed | ||||
| }; | ||||
|  | ||||
| #endif //FLAGMANAGEROPENMAX | ||||
							
								
								
									
										257
									
								
								src/flagmanager.cpp
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										257
									
								
								src/flagmanager.cpp
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,257 @@ | ||||
| /* | ||||
|  * boblight | ||||
|  * Copyright (C) Bob  2009  | ||||
|  *  | ||||
|  * boblight is free software: you can redistribute it and/or modify it | ||||
|  * under the terms of the GNU General Public License as published by the | ||||
|  * Free Software Foundation, either version 3 of the License, or | ||||
|  * (at your option) any later version. | ||||
|  *  | ||||
|  * boblight is distributed in the hope that it will be useful, but | ||||
|  * WITHOUT ANY WARRANTY; without even the implied warranty of | ||||
|  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. | ||||
|  * See the GNU General Public License for more details. | ||||
|  *  | ||||
|  * You should have received a copy of the GNU General Public License along | ||||
|  * with this program.  If not, see <http://www.gnu.org/licenses/>. | ||||
|  */ | ||||
|  | ||||
| #include <string.h> | ||||
| #include <unistd.h> | ||||
| #include <iostream> | ||||
|  | ||||
| #include "flagmanager.h" | ||||
| #include "misc.h" | ||||
|  | ||||
| //#define BOBLIGHT_DLOPEN_EXTERN | ||||
| #include "boblight.h" | ||||
|  | ||||
| using namespace std; | ||||
|  | ||||
| //very simple, store a copy of argc and argv | ||||
| CArguments::CArguments(int argc, char** argv) | ||||
| { | ||||
|   m_argc = argc; | ||||
|  | ||||
|   if (m_argc == 0) | ||||
|   { | ||||
|     m_argv = NULL; | ||||
|   } | ||||
|   else | ||||
|   { | ||||
|     m_argv = new char*[m_argc]; | ||||
|     for (int i = 0; i < m_argc; i++) | ||||
|     { | ||||
|       m_argv[i] = new char[strlen(argv[i]) + 1]; | ||||
|       strcpy(m_argv[i], argv[i]); | ||||
|     } | ||||
|   } | ||||
| } | ||||
|  | ||||
| //delete the copy of argv | ||||
| CArguments::~CArguments() | ||||
| { | ||||
|   if (m_argv) | ||||
|   { | ||||
|     for (int i = 0; i < m_argc; i++) | ||||
|     { | ||||
|       delete[] m_argv[i]; | ||||
|     } | ||||
|     delete[] m_argv; | ||||
|   } | ||||
| } | ||||
|  | ||||
| CFlagManager::CFlagManager() | ||||
| { | ||||
|   m_port = -1;                    //-1 tells libboblight to use default port | ||||
|   m_address = NULL;               //NULL tells libboblight to use default address | ||||
|   m_priority = 128;               //default priority | ||||
|   m_printhelp = false;            //don't print helpmessage unless asked to | ||||
|   m_printboblightoptions = false; //same for libboblight options | ||||
|   m_fork = false;                 //don't fork by default | ||||
|   m_sync = false;                 //sync mode disabled by default | ||||
|  | ||||
|   // default getopt flags, can be extended in derived classes | ||||
|   // p = priority, s = address[:port], o = boblight option, l = list boblight options, h = print help message, f = fork | ||||
|   m_flags = "p:s:o:lhfy:"; | ||||
| } | ||||
|  | ||||
| void CFlagManager::ParseFlags(int tempargc, char** tempargv) | ||||
| { | ||||
|   //that copy class sure comes in handy now! | ||||
|   CArguments arguments(tempargc, tempargv); | ||||
|   int    argc = arguments.m_argc; | ||||
|   char** argv = arguments.m_argv; | ||||
|  | ||||
|   string option; | ||||
|   int    c; | ||||
|  | ||||
|   opterr = 0; //we don't want to print error messages | ||||
|    | ||||
|   while ((c = getopt(argc, argv, m_flags.c_str())) != -1) | ||||
|   { | ||||
|     if (c == 'p') //priority | ||||
|     { | ||||
|       option = optarg; | ||||
|       if (!StrToInt(option, m_priority) || m_priority < 0 || m_priority > 255) | ||||
|       { | ||||
|         throw string("Wrong option " + string(optarg) + " for argument -p"); | ||||
|       } | ||||
|     } | ||||
|     else if (c == 's') //address[:port] | ||||
|     { | ||||
|       option = optarg; | ||||
|       //store address in string and set the char* to it | ||||
|       m_straddress = option.substr(0, option.find(':')); | ||||
|       m_address = m_straddress.c_str(); | ||||
|  | ||||
|       if (option.find(':') != string::npos) //check if we have a port | ||||
|       { | ||||
|         option = option.substr(option.find(':') + 1); | ||||
|         string word; | ||||
|         if (!StrToInt(option, m_port) || m_port < 0 || m_port > 65535) | ||||
|         { | ||||
|           throw string("Wrong option " + string(optarg) + " for argument -s"); | ||||
|         } | ||||
|       } | ||||
|     } | ||||
|     else if (c == 'o') //option for libboblight | ||||
|     { | ||||
|       m_options.push_back(optarg); | ||||
|     } | ||||
|     else if (c == 'l') //list libboblight options | ||||
|     { | ||||
|       m_printboblightoptions = true; | ||||
|       return; | ||||
|     } | ||||
|     else if (c == 'h') //print help message | ||||
|     { | ||||
|       m_printhelp = true; | ||||
|       return; | ||||
|     } | ||||
|     else if (c == 'f') | ||||
|     { | ||||
|       m_fork = true; | ||||
|     } | ||||
|     else if (c == 'y') | ||||
|     { | ||||
|       if (!StrToBool(optarg, m_sync)) | ||||
|       { | ||||
|         throw string("Wrong value " + string(optarg) + " for sync mode"); | ||||
|       } | ||||
|     } | ||||
|     else if (c == '?') //unknown option | ||||
|     { | ||||
|       //check if we know this option, but expected an argument | ||||
|       if (m_flags.find(ToString((char)optopt) + ":") != string::npos) | ||||
|       { | ||||
|         throw string("Option " + ToString((char)optopt) + "requires an argument"); | ||||
|       } | ||||
|       else | ||||
|       { | ||||
|         throw string("Unkown option " + ToString((char)optopt)); | ||||
|       } | ||||
|     } | ||||
|     else | ||||
|     { | ||||
|       ParseFlagsExtended(argc, argv, c, optarg); //pass our argument to a derived class | ||||
|     } | ||||
|   } | ||||
|  | ||||
|   PostGetopt(optind, argc, argv); //some postprocessing | ||||
| } | ||||
|  | ||||
| //go through all options and print the descriptions to stdout | ||||
| void CFlagManager::PrintBoblightOptions() | ||||
| { | ||||
|   void* boblight = boblight_init(); | ||||
|   int nroptions = boblight_getnroptions(boblight); | ||||
|  | ||||
|   for (int i = 0; i < nroptions; i++) | ||||
|   { | ||||
|     cout << boblight_getoptiondescript(boblight, i) << "\n"; | ||||
|   } | ||||
|  | ||||
|   boblight_destroy(boblight); | ||||
| } | ||||
|  | ||||
| void CFlagManager::ParseBoblightOptions(void* boblight) | ||||
| { | ||||
|   int nrlights = boblight_getnrlights(boblight); | ||||
|    | ||||
|   for (int i = 0; i < m_options.size(); i++) | ||||
|   { | ||||
|     string option = m_options[i]; | ||||
|     string lightname; | ||||
|     string optionname; | ||||
|     string optionvalue; | ||||
|     int    lightnr = -1; | ||||
|  | ||||
|     //check if we have a lightname, otherwise we use all lights | ||||
|     if (option.find(':') != string::npos) | ||||
|     { | ||||
|       lightname = option.substr(0, option.find(':')); | ||||
|       if (option.find(':') == option.size() - 1) //check if : isn't the last char in the string | ||||
|       { | ||||
|         throw string("wrong option \"" + option + "\", syntax is [light:]option=value"); | ||||
|       } | ||||
|       option = option.substr(option.find(':') + 1); //shave off the lightname | ||||
|  | ||||
|       //check which light this is | ||||
|       bool lightfound = false; | ||||
|       for (int j = 0; j < nrlights; j++) | ||||
|       { | ||||
|         if (lightname == boblight_getlightname(boblight, j)) | ||||
|         { | ||||
|           lightfound = true; | ||||
|           lightnr = j; | ||||
|           break; | ||||
|         } | ||||
|       } | ||||
|       if (!lightfound) | ||||
|       { | ||||
|         throw string("light \"" + lightname + "\" used in option \"" + m_options[i] + "\" doesn't exist"); | ||||
|       } | ||||
|     } | ||||
|  | ||||
|     //check if '=' exists and it's not at the end of the string | ||||
|     if (option.find('=') == string::npos || option.find('=') == option.size() - 1) | ||||
|     { | ||||
|       throw string("wrong option \"" + option + "\", syntax is [light:]option=value"); | ||||
|     } | ||||
|  | ||||
|     optionname = option.substr(0, option.find('='));   //option name is everything before = (already shaved off the lightname here) | ||||
|     optionvalue = option.substr(option.find('=') + 1); //value is everything after = | ||||
|  | ||||
|     option = optionname + " " + optionvalue;           //libboblight wants syntax without = | ||||
|  | ||||
|     //bitch if we can't set this option | ||||
|     if (!boblight_setoption(boblight, lightnr, option.c_str())) | ||||
|     { | ||||
|       throw string(boblight_geterror(boblight)); | ||||
|     } | ||||
|   } | ||||
| } | ||||
|  | ||||
| bool CFlagManager::SetVideoGamma() | ||||
| { | ||||
|   for (int i = 0; i < m_options.size(); i++) | ||||
|   { | ||||
|     string option = m_options[i]; | ||||
|     if (option.find(':') != string::npos) | ||||
|       option = option.substr(option.find(':') + 1); //shave off the lightname | ||||
|  | ||||
|     if (option.find('=') != string::npos) | ||||
|     { | ||||
|       if (option.substr(0, option.find('=')) == "gamma") | ||||
|         return false; //gamma set by user, don't override | ||||
|     } | ||||
|   } | ||||
|  | ||||
|   m_options.push_back("gamma=" + ToString(VIDEOGAMMA)); | ||||
|  | ||||
|   cout << "Gamma not set, using " << VIDEOGAMMA << " since this is default for video\n"; | ||||
|  | ||||
|   return true; | ||||
| } | ||||
|  | ||||
							
								
								
									
										72
									
								
								src/flagmanager.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										72
									
								
								src/flagmanager.h
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,72 @@ | ||||
| /* | ||||
|  * boblight | ||||
|  * Copyright (C) Bob  2009  | ||||
|  *  | ||||
|  * boblight is free software: you can redistribute it and/or modify it | ||||
|  * under the terms of the GNU General Public License as published by the | ||||
|  * Free Software Foundation, either version 3 of the License, or | ||||
|  * (at your option) any later version. | ||||
|  *  | ||||
|  * boblight is distributed in the hope that it will be useful, but | ||||
|  * WITHOUT ANY WARRANTY; without even the implied warranty of | ||||
|  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. | ||||
|  * See the GNU General Public License for more details. | ||||
|  *  | ||||
|  * You should have received a copy of the GNU General Public License along | ||||
|  * with this program.  If not, see <http://www.gnu.org/licenses/>. | ||||
|  */ | ||||
|  | ||||
| #ifndef FLAGMANAGER | ||||
| #define FLAGMANAGER | ||||
|  | ||||
| #define VIDEOGAMMA 2.2 | ||||
|  | ||||
| #include <string> | ||||
| #include <vector> | ||||
|  | ||||
| //class for making a copy of argc and argv | ||||
| class CArguments | ||||
| { | ||||
|   public: | ||||
|     CArguments(int argc, char** argv); | ||||
|     ~CArguments(); | ||||
|  | ||||
|     int    m_argc; | ||||
|     char** m_argv; | ||||
| }; | ||||
|  | ||||
| class CFlagManager | ||||
| { | ||||
|   public: | ||||
|     CFlagManager(); | ||||
|  | ||||
|     bool         m_printhelp;                               //if we need to print the help message | ||||
|     bool         m_printboblightoptions;                    //if we need to print the boblight options | ||||
|  | ||||
|     const char*  m_address;                                 //address to connect to, set to NULL if none given for default | ||||
|     int          m_port;                                    //port to connect to, set to -1 if none given for default | ||||
|     int          m_priority;                                //priority, set to 128 if none given for default | ||||
|     bool         m_fork;                                    //if we should fork | ||||
|     bool         m_sync;                                    //if sync mode is enabled | ||||
|  | ||||
|     void         ParseFlags(int tempargc, char** tempargv); //parsing commandline flags | ||||
|     virtual void PrintHelpMessage() {}; | ||||
|  | ||||
|     void         PrintBoblightOptions();                    //printing of boblight options (-o [light:]option=value) | ||||
|     void         ParseBoblightOptions(void* boblight);      //parsing of boblight options | ||||
|     bool         SetVideoGamma();                           //set gamma to 2.2 if not given, returns true if done | ||||
|  | ||||
|   protected: | ||||
|  | ||||
|     std::string  m_flags;                                   //string to pass to getopt, for example "c:r:a:p" | ||||
|     std::string  m_straddress;                              //place to store address to connect to, because CArguments deletes argv | ||||
|  | ||||
|     std::vector<std::string> m_options;                     //place to store boblight options | ||||
|  | ||||
|     //gets called from ParseFlags, for derived classes | ||||
|     virtual void ParseFlagsExtended(int& argc, char**& argv, int& c, char*& optarg){}; | ||||
|     //gets called after getopt | ||||
|     virtual void PostGetopt(int optind, int argc, char** argv) {}; | ||||
| }; | ||||
|  | ||||
| #endif //FLAGMANAGER | ||||
							
								
								
									
										165
									
								
								src/grabber-dispmanx.cpp
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										165
									
								
								src/grabber-dispmanx.cpp
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,165 @@ | ||||
| /* | ||||
|  * boblight | ||||
|  * Copyright (C) Bob  2009  | ||||
|  *  | ||||
|  * boblight is free software: you can redistribute it and/or modify it | ||||
|  * under the terms of the GNU General Public License as published by the | ||||
|  * Free Software Foundation, either version 3 of the License, or | ||||
|  * (at your option) any later version. | ||||
|  *  | ||||
|  * boblight is distributed in the hope that it will be useful, but | ||||
|  * WITHOUT ANY WARRANTY; without even the implied warranty of | ||||
|  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. | ||||
|  * See the GNU General Public License for more details. | ||||
|  *  | ||||
|  * You should have received a copy of the GNU General Public License along | ||||
|  * with this program.  If not, see <http://www.gnu.org/licenses/>. | ||||
|  */ | ||||
|  | ||||
| #include "stdint.h" | ||||
|  | ||||
| #include "grabber-dispmanx.h" | ||||
|  | ||||
| #include <string.h> | ||||
| #include <assert.h> | ||||
|  | ||||
| #include "misc.h" | ||||
|  | ||||
| //#define BOBLIGHT_DLOPEN_EXTERN | ||||
| #include "boblight.h" | ||||
|  | ||||
| using namespace std; | ||||
|  | ||||
| CGrabberDispmanX::CGrabberDispmanX(void* boblight, volatile bool& stop, bool sync) : m_stop(stop), m_timer(&stop) | ||||
| { | ||||
| 	int ret; | ||||
|  | ||||
| 	bcm_host_init(); | ||||
|  | ||||
| 	m_boblight = boblight; | ||||
| 	m_debug = false; | ||||
| 	m_sync = sync; | ||||
|  | ||||
| 	type = VC_IMAGE_RGB888; | ||||
|  | ||||
| 	display  = vc_dispmanx_display_open(0); | ||||
|  | ||||
| 	ret = vc_dispmanx_display_get_info(display, &info); | ||||
| 	assert(ret == 0); | ||||
| } | ||||
|  | ||||
| CGrabberDispmanX::~CGrabberDispmanX() | ||||
| { | ||||
| 	int ret; | ||||
|  | ||||
| 	free(image); | ||||
|  | ||||
| 	ret = vc_dispmanx_resource_delete(resource); | ||||
| 	assert( ret == 0 ); | ||||
| 	ret = vc_dispmanx_display_close(display); | ||||
| 	assert( ret == 0 ); | ||||
|  | ||||
| 	bcm_host_deinit(); | ||||
| } | ||||
|  | ||||
| bool CGrabberDispmanX::Setup() | ||||
| { | ||||
| 	if (m_interval > 0.0) //set up timer | ||||
| 	{ | ||||
| 		m_timer.SetInterval(Round64(m_interval * 1000000.0)); | ||||
| 	} | ||||
|  | ||||
| 	pitch = ALIGN_UP(m_size*3, 32); | ||||
|  | ||||
| 	image = new char[m_size * m_size * 3]; | ||||
|  | ||||
| 	resource = vc_dispmanx_resource_create(type, | ||||
|                                            m_size, | ||||
|                                            m_size, | ||||
|                                            &vc_image_ptr ); | ||||
| 	assert(resource); | ||||
|  | ||||
| 	m_error.clear(); | ||||
|  | ||||
| 	return ExtendedSetup(); //run stuff from derived classes | ||||
| } | ||||
|  | ||||
| bool CGrabberDispmanX::ExtendedSetup() | ||||
| { | ||||
| 	if (!CheckExtensions()) | ||||
| 		return false; | ||||
|  | ||||
| 	return true; | ||||
| } | ||||
|  | ||||
| bool CGrabberDispmanX::CheckExtensions() | ||||
| { | ||||
| 	return true; | ||||
| } | ||||
|  | ||||
| bool CGrabberDispmanX::Run() | ||||
| { | ||||
| 	int rgb[3]; | ||||
| 	VC_RECT_T rectangle; | ||||
| 	char* image_ptr; | ||||
|  | ||||
| 	boblight_setscanrange(m_boblight, m_size, m_size); | ||||
|  | ||||
| 	while(!m_stop) | ||||
| 	{ | ||||
| 		vc_dispmanx_snapshot(display,resource, VC_IMAGE_ROT0); | ||||
|  | ||||
| 		vc_dispmanx_rect_set(&rectangle, 0, 0, m_size, m_size); | ||||
|  | ||||
| 		vc_dispmanx_resource_read_data(resource, &rectangle, image, m_size*3); | ||||
|  | ||||
| 		image_ptr = (char *)image; | ||||
| 		//read out the pixels | ||||
| 		for (int y = 0; y < m_size && !m_stop; y++) | ||||
| 		{ | ||||
| //			image_ptr += y*m_size*3; | ||||
| 			for (int x = 0; x < m_size && !m_stop; x++) | ||||
| 			{ | ||||
| 				rgb[0] = image_ptr[y*m_size*3+x*3]; | ||||
| 				rgb[1] = image_ptr[y*m_size*3+x*3 + 1]; | ||||
| 				rgb[2] = image_ptr[y*m_size*3+x*3 + 2]; | ||||
|  | ||||
| 				boblight_addpixelxy(m_boblight, x, y, rgb); | ||||
| 			} | ||||
| 		} | ||||
|  | ||||
|  | ||||
| 		//send pixeldata to boblight | ||||
| 		if (!boblight_sendrgb(m_boblight, m_sync, NULL)) | ||||
| 		{ | ||||
| 			m_error = boblight_geterror(m_boblight); | ||||
| 			return true; //recoverable error | ||||
| 		} | ||||
|  | ||||
| 		//when in debug mode, put the captured image on the debug window | ||||
| 		if (m_debug) | ||||
| 		{ | ||||
| 			printf("Debug not supproted!\n"); | ||||
| 			m_debug = false; | ||||
| 		} | ||||
|  | ||||
| 		if (!Wait()) | ||||
| 		{ | ||||
| 			return false; //unrecoverable error | ||||
| 		} | ||||
| 	} | ||||
|  | ||||
| 	m_error.clear(); | ||||
|  | ||||
| 	return true; | ||||
| } | ||||
|  | ||||
| bool CGrabberDispmanX::Wait() | ||||
| { | ||||
| 	if (m_interval > 0.0) //wait for timer | ||||
| 	{ | ||||
| 		m_timer.Wait(); | ||||
| 	} | ||||
| 	return true; | ||||
| } | ||||
|  | ||||
							
								
								
									
										90
									
								
								src/grabber-dispmanx.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										90
									
								
								src/grabber-dispmanx.h
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,90 @@ | ||||
| /* | ||||
|  * boblight | ||||
|  * Copyright (C) Bob  2009  | ||||
|  *  | ||||
|  * boblight is free software: you can redistribute it and/or modify it | ||||
|  * under the terms of the GNU General Public License as published by the | ||||
|  * Free Software Foundation, either version 3 of the License, or | ||||
|  * (at your option) any later version. | ||||
|  *  | ||||
|  * boblight is distributed in the hope that it will be useful, but | ||||
|  * WITHOUT ANY WARRANTY; without even the implied warranty of | ||||
|  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. | ||||
|  * See the GNU General Public License for more details. | ||||
|  *  | ||||
|  * You should have received a copy of the GNU General Public License along | ||||
|  * with this program.  If not, see <http://www.gnu.org/licenses/>. | ||||
|  */ | ||||
|  | ||||
| #ifndef GRABBERDISPMANX | ||||
| #define GRABBERDISPMANX | ||||
|  | ||||
| #include "bcm_host.h" | ||||
|  | ||||
| #include <string> | ||||
|  | ||||
| //#include "config.h" | ||||
| #include "timer.h" | ||||
|  | ||||
| #ifndef ALIGN_UP | ||||
| #define ALIGN_UP(x,y)  ((x + (y)-1) & ~((y)-1)) | ||||
| #endif | ||||
|  | ||||
| //class for grabbing with DispmanX | ||||
| class CGrabberDispmanX | ||||
| { | ||||
|   public: | ||||
| 	CGrabberDispmanX(void* boblight, volatile bool& stop, bool sync); | ||||
|     ~CGrabberDispmanX(); | ||||
|  | ||||
|     bool ExtendedSetup(); | ||||
|     bool Run(); | ||||
|  | ||||
|     std::string& GetError()           { return m_error; }        //retrieves the latest error | ||||
|  | ||||
|     void SetInterval(double interval) { m_interval = interval; } //sets interval, negative means vblanks | ||||
|     void SetSize(int size)            { m_size = size; }         //sets how many pixels we want to grab | ||||
|  | ||||
|     bool Setup();                                                //base setup function | ||||
|  | ||||
|     void SetDebug(const char* display);                          //turn on debug window | ||||
|  | ||||
|   protected: | ||||
|  | ||||
|     bool              Wait();                                    //wait for the timer or on the vblank | ||||
|     volatile bool&    m_stop; | ||||
|  | ||||
|     std::string       m_error;                                   //latest error | ||||
|  | ||||
|     void*             m_boblight;                                //our handle from libboblight | ||||
|  | ||||
|     int               m_size;                                    //nr of pixels on lines to grab | ||||
|  | ||||
|     bool              m_debug;                                   //if we have debug mode on | ||||
|  | ||||
|     long double       m_lastupdate; | ||||
|     long double       m_lastmeasurement; | ||||
|     long double       m_measurements; | ||||
|     int               m_nrmeasurements; | ||||
|  | ||||
|     double            m_interval;                                //interval in seconds, or negative for vblanks | ||||
|     CTimer            m_timer;                                   //our timer | ||||
|     bool              m_sync;                                    //sync mode for libboblight | ||||
|  | ||||
|  | ||||
|   private: | ||||
|  | ||||
|     bool CheckExtensions(); | ||||
|  | ||||
|     DISPMANX_DISPLAY_HANDLE_T   display; | ||||
|     DISPMANX_MODEINFO_T         info; | ||||
|     void                       *image; | ||||
|     DISPMANX_UPDATE_HANDLE_T    update; | ||||
|     DISPMANX_RESOURCE_HANDLE_T  resource; | ||||
|     DISPMANX_ELEMENT_HANDLE_T   element; | ||||
|     uint32_t                    vc_image_ptr; | ||||
|     VC_IMAGE_TYPE_T             type; | ||||
|     int 						pitch; | ||||
| }; | ||||
|  | ||||
| #endif //GRABBEROPENMAX | ||||
							
								
								
									
										81
									
								
								src/misc.cpp
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										81
									
								
								src/misc.cpp
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,81 @@ | ||||
| /* | ||||
|  * boblight | ||||
|  * Copyright (C) Bob  2009  | ||||
|  *  | ||||
|  * boblight is free software: you can redistribute it and/or modify it | ||||
|  * under the terms of the GNU General Public License as published by the | ||||
|  * Free Software Foundation, either version 3 of the License, or | ||||
|  * (at your option) any later version. | ||||
|  *  | ||||
|  * boblight is distributed in the hope that it will be useful, but | ||||
|  * WITHOUT ANY WARRANTY; without even the implied warranty of | ||||
|  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. | ||||
|  * See the GNU General Public License for more details. | ||||
|  *  | ||||
|  * You should have received a copy of the GNU General Public License along | ||||
|  * with this program.  If not, see <http://www.gnu.org/licenses/>. | ||||
|  */ | ||||
|  | ||||
| #include <iostream> | ||||
| #include <locale.h> | ||||
| #include "misc.h" | ||||
|  | ||||
| using namespace std; | ||||
|  | ||||
| void PrintError(const std::string& error) | ||||
| { | ||||
|   std::cerr << "ERROR: " << error << "\n"; | ||||
| } | ||||
|  | ||||
| //get the first word (separated by whitespace) from string data and place that in word | ||||
| //then remove that word from string data | ||||
| bool GetWord(string& data, string& word) | ||||
| { | ||||
|   stringstream datastream(data); | ||||
|   string end; | ||||
|  | ||||
|   datastream >> word; | ||||
|   if (datastream.fail()) | ||||
|   { | ||||
|     data.clear(); | ||||
|     return false; | ||||
|   } | ||||
|  | ||||
|   size_t pos = data.find(word) + word.length(); | ||||
|  | ||||
|   if (pos >= data.length()) | ||||
|   { | ||||
|     data.clear(); | ||||
|     return true; | ||||
|   } | ||||
|  | ||||
|   data = data.substr(pos); | ||||
|    | ||||
|   datastream.clear(); | ||||
|   datastream.str(data); | ||||
|  | ||||
|   datastream >> end; | ||||
|   if (datastream.fail()) | ||||
|     data.clear(); | ||||
|  | ||||
|   return true; | ||||
| } | ||||
|  | ||||
| //convert . or , to the current locale for correct conversion of ascii float | ||||
| void ConvertFloatLocale(std::string& strfloat) | ||||
| { | ||||
|   static struct lconv* locale = localeconv(); | ||||
|    | ||||
|   size_t pos = strfloat.find_first_of(",."); | ||||
|  | ||||
|   while (pos != string::npos) | ||||
|   { | ||||
|     strfloat.replace(pos, 1, 1, *locale->decimal_point); | ||||
|     pos++; | ||||
|  | ||||
|     if (pos >= strfloat.size()) | ||||
|       break; | ||||
|  | ||||
|     pos = strfloat.find_first_of(",.", pos); | ||||
|   } | ||||
| } | ||||
							
								
								
									
										191
									
								
								src/misc.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										191
									
								
								src/misc.h
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,191 @@ | ||||
| /* | ||||
|  * boblight | ||||
|  * Copyright (C) Bob  2009  | ||||
|  *  | ||||
|  * boblight is free software: you can redistribute it and/or modify it | ||||
|  * under the terms of the GNU General Public License as published by the | ||||
|  * Free Software Foundation, either version 3 of the License, or | ||||
|  * (at your option) any later version. | ||||
|  *  | ||||
|  * boblight is distributed in the hope that it will be useful, but | ||||
|  * WITHOUT ANY WARRANTY; without even the implied warranty of | ||||
|  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. | ||||
|  * See the GNU General Public License for more details. | ||||
|  *  | ||||
|  * You should have received a copy of the GNU General Public License along | ||||
|  * with this program.  If not, see <http://www.gnu.org/licenses/>. | ||||
|  */ | ||||
|  | ||||
| #ifndef MISCUTIL | ||||
| #define MISCUTIL | ||||
|  | ||||
| #include "stdint.h" | ||||
|  | ||||
| #include <string> | ||||
| #include <sstream> | ||||
| #include <exception> | ||||
| #include <stdexcept> | ||||
|  | ||||
| #include <errno.h> | ||||
| #include <string.h> | ||||
| #include <stdio.h> | ||||
| #include <math.h> | ||||
|  | ||||
| void PrintError(const std::string& error); | ||||
| bool GetWord(std::string& data, std::string& word); | ||||
| void ConvertFloatLocale(std::string& strfloat); | ||||
|  | ||||
| template <class Value> | ||||
| inline std::string ToString(Value value) | ||||
| { | ||||
|   std::string data; | ||||
|   std::stringstream valuestream; | ||||
|   valuestream << value; | ||||
|   valuestream >> data; | ||||
|   return data; | ||||
| } | ||||
|  | ||||
| inline std::string GetErrno() | ||||
| { | ||||
|   return strerror(errno); | ||||
| } | ||||
|  | ||||
| inline std::string GetErrno(int err) | ||||
| { | ||||
|   return strerror(err); | ||||
| } | ||||
|  | ||||
| template <class A, class B, class C> | ||||
| inline A Clamp(A value, B min, C max) | ||||
| { | ||||
|   return value < max ? (value > min ? value : min) : max; | ||||
| } | ||||
|  | ||||
| template <class A, class B> | ||||
| inline A Max(A value1, B value2) | ||||
| { | ||||
|   return value1 > value2 ? value1 : value2; | ||||
| } | ||||
|  | ||||
| template <class A, class B, class C> | ||||
| inline A Max(A value1, B value2, C value3) | ||||
| { | ||||
|   return (value1 > value2) ? (value1 > value3 ? value1 : value3) : (value2 > value3 ? value2 : value3); | ||||
| } | ||||
|  | ||||
| template <class A, class B> | ||||
| inline A Min(A value1, B value2) | ||||
| { | ||||
|   return value1 < value2 ? value1 : value2; | ||||
| } | ||||
|  | ||||
| template <class A, class B, class C> | ||||
| inline A Min(A value1, B value2, C value3) | ||||
| { | ||||
|   return (value1 < value2) ? (value1 < value3 ? value1 : value3) : (value2 < value3 ? value2 : value3); | ||||
| } | ||||
|  | ||||
| template <class T> | ||||
| inline T Abs(T value) | ||||
| { | ||||
|   return value > 0 ? value : -value; | ||||
| } | ||||
|  | ||||
| template <class A, class B> | ||||
| inline A Round(B value) | ||||
| { | ||||
|   if (value == 0.0) | ||||
|   { | ||||
|     return 0; | ||||
|   } | ||||
|   else if (value > 0.0) | ||||
|   { | ||||
|     return (A)(value + 0.5); | ||||
|   } | ||||
|   else | ||||
|   { | ||||
|     return (A)(value - 0.5); | ||||
|   } | ||||
| } | ||||
|  | ||||
| inline int32_t Round32(float value) | ||||
| { | ||||
|   return lroundf(value); | ||||
| } | ||||
|  | ||||
| inline int32_t Round32(double value) | ||||
| { | ||||
|   return lround(value); | ||||
| } | ||||
|  | ||||
| inline int64_t Round64(float value) | ||||
| { | ||||
|   return llroundf(value); | ||||
| } | ||||
|  | ||||
| inline int64_t Round64(double value) | ||||
| { | ||||
|   return llround(value); | ||||
| } | ||||
|  | ||||
| inline bool StrToInt(const std::string& data, int& value) | ||||
| { | ||||
|   return sscanf(data.c_str(), "%i", &value) == 1; | ||||
| } | ||||
|  | ||||
| inline bool StrToInt(const std::string& data, int64_t& value) | ||||
| { | ||||
|   return sscanf(data.c_str(), "%ld", &value) == 1; | ||||
| } | ||||
|  | ||||
| inline bool HexStrToInt(const std::string& data, int& value) | ||||
| { | ||||
|   return sscanf(data.c_str(), "%x", &value) == 1; | ||||
| } | ||||
|  | ||||
| inline bool HexStrToInt(const std::string& data, int64_t& value) | ||||
| { | ||||
|   return sscanf(data.c_str(), "%x", &value) == 1; | ||||
| } | ||||
|  | ||||
| inline bool StrToFloat(const std::string& data, float& value) | ||||
| { | ||||
|   return sscanf(data.c_str(), "%f", &value) == 1; | ||||
| } | ||||
|  | ||||
| inline bool StrToFloat(const std::string& data, double& value) | ||||
| { | ||||
|   return sscanf(data.c_str(), "%lf", &value) == 1; | ||||
| } | ||||
|  | ||||
| inline bool StrToBool(const std::string& data, bool& value) | ||||
| { | ||||
|   std::string data2 = data; | ||||
|   std::string word; | ||||
|   if (!GetWord(data2, word)) | ||||
|     return false; | ||||
|    | ||||
|   if (word == "1" || word == "true" || word == "on" || word == "yes") | ||||
|   { | ||||
|     value = true; | ||||
|     return true; | ||||
|   } | ||||
|   else if (word == "0" || word == "false" || word == "off" || word == "no") | ||||
|   { | ||||
|     value = false; | ||||
|     return true; | ||||
|   } | ||||
|   else | ||||
|   { | ||||
|     int ivalue; | ||||
|     if (StrToInt(word, ivalue)) | ||||
|     { | ||||
|       value = ivalue != 0; | ||||
|       return true; | ||||
|     } | ||||
|   } | ||||
|  | ||||
|   return false; | ||||
| } | ||||
|  | ||||
| #endif //MISCUTIL | ||||
							
								
								
									
										69
									
								
								src/timer.cpp
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										69
									
								
								src/timer.cpp
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,69 @@ | ||||
| /* | ||||
|  * boblight | ||||
|  * Copyright (C) Bob  2009  | ||||
|  *  | ||||
|  * boblight is free software: you can redistribute it and/or modify it | ||||
|  * under the terms of the GNU General Public License as published by the | ||||
|  * Free Software Foundation, either version 3 of the License, or | ||||
|  * (at your option) any later version. | ||||
|  *  | ||||
|  * boblight is distributed in the hope that it will be useful, but | ||||
|  * WITHOUT ANY WARRANTY; without even the implied warranty of | ||||
|  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. | ||||
|  * See the GNU General Public License for more details. | ||||
|  *  | ||||
|  * You should have received a copy of the GNU General Public License along | ||||
|  * with this program.  If not, see <http://www.gnu.org/licenses/>. | ||||
|  */ | ||||
|  | ||||
| #include "timer.h" | ||||
| #include "misc.h" | ||||
| #include "timeutils.h" | ||||
|  | ||||
| #include <iostream> | ||||
| using namespace std; | ||||
|  | ||||
| CTimer::CTimer(volatile bool* stop /*=NULL*/) | ||||
| { | ||||
|   m_interval = -1; | ||||
|   m_timerstop = stop; | ||||
| } | ||||
|  | ||||
| void CTimer::SetInterval(int64_t usecs) | ||||
| { | ||||
|   m_interval = usecs; | ||||
|   Reset(); | ||||
| } | ||||
|  | ||||
| int64_t CTimer::GetInterval() | ||||
| { | ||||
|   return m_interval; | ||||
| } | ||||
|  | ||||
| void CTimer::Reset() | ||||
| { | ||||
|   m_time = GetTimeUs(); | ||||
| } | ||||
|  | ||||
| void CTimer::Wait() | ||||
| { | ||||
|   int64_t sleeptime; | ||||
|  | ||||
|   //keep looping until we have a timestamp that's not too old | ||||
|   int64_t now = GetTimeUs(); | ||||
|   do | ||||
|   { | ||||
|     m_time += m_interval; | ||||
|     sleeptime = m_time - now; | ||||
|   } | ||||
|   while(sleeptime <= m_interval * -2LL); | ||||
|    | ||||
|   if (sleeptime > m_interval * 2LL) //failsafe, m_time must be bork if we get here | ||||
|   { | ||||
|     sleeptime = m_interval * 2LL; | ||||
|     Reset(); | ||||
|   } | ||||
|  | ||||
|   USleep(sleeptime, m_timerstop); | ||||
| } | ||||
|  | ||||
							
								
								
									
										42
									
								
								src/timer.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										42
									
								
								src/timer.h
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,42 @@ | ||||
| /* | ||||
|  * boblight | ||||
|  * Copyright (C) Bob  2009  | ||||
|  *  | ||||
|  * boblight is free software: you can redistribute it and/or modify it | ||||
|  * under the terms of the GNU General Public License as published by the | ||||
|  * Free Software Foundation, either version 3 of the License, or | ||||
|  * (at your option) any later version. | ||||
|  *  | ||||
|  * boblight is distributed in the hope that it will be useful, but | ||||
|  * WITHOUT ANY WARRANTY; without even the implied warranty of | ||||
|  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. | ||||
|  * See the GNU General Public License for more details. | ||||
|  *  | ||||
|  * You should have received a copy of the GNU General Public License along | ||||
|  * with this program.  If not, see <http://www.gnu.org/licenses/>. | ||||
|  */ | ||||
|  | ||||
| #ifndef CTIMER | ||||
| #define CTIMER | ||||
|  | ||||
| #include "stdint.h" | ||||
|  | ||||
| #include <unistd.h> | ||||
|  | ||||
| class CTimer | ||||
| { | ||||
|   public: | ||||
|     CTimer(volatile bool* stop = NULL); | ||||
|     void SetInterval(int64_t usecs); | ||||
|     virtual void Wait(); | ||||
|     void Reset(); | ||||
|  | ||||
|     int64_t GetInterval(); | ||||
|  | ||||
|   protected: | ||||
|     int64_t        m_time; | ||||
|     int64_t        m_interval; | ||||
|     volatile bool* m_timerstop; | ||||
| }; | ||||
|  | ||||
| #endif | ||||
							
								
								
									
										56
									
								
								src/timeutils.cpp
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										56
									
								
								src/timeutils.cpp
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,56 @@ | ||||
| /* | ||||
|  * boblight | ||||
|  * Copyright (C) Bob  2009  | ||||
|  *  | ||||
|  * boblight is free software: you can redistribute it and/or modify it | ||||
|  * under the terms of the GNU General Public License as published by the | ||||
|  * Free Software Foundation, either version 3 of the License, or | ||||
|  * (at your option) any later version. | ||||
|  *  | ||||
|  * boblight is distributed in the hope that it will be useful, but | ||||
|  * WITHOUT ANY WARRANTY; without even the implied warranty of | ||||
|  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. | ||||
|  * See the GNU General Public License for more details. | ||||
|  *  | ||||
|  * You should have received a copy of the GNU General Public License along | ||||
|  * with this program.  If not, see <http://www.gnu.org/licenses/>. | ||||
|  */ | ||||
|  | ||||
| #include "timeutils.h" | ||||
|  | ||||
| void USleep(int64_t usecs, volatile bool* stop /*= NULL*/) | ||||
| { | ||||
|   if (usecs <= 0) | ||||
|   { | ||||
|     return; | ||||
|   } | ||||
|   else if (stop && usecs > 1000000) //when a pointer to a bool is passed, check it every second and stop when it's true | ||||
|   { | ||||
|     int64_t now = GetTimeUs(); | ||||
|     int64_t end = now + usecs; | ||||
|  | ||||
|     while (now < end) | ||||
|     { | ||||
|       struct timespec sleeptime = {}; | ||||
|  | ||||
|       if (*stop) | ||||
|         return; | ||||
|       else if (end - now >= 1000000) | ||||
|         sleeptime.tv_sec = 1; | ||||
|       else | ||||
|         sleeptime.tv_nsec = ((end - now) % 1000000) * 1000; | ||||
|  | ||||
|       nanosleep(&sleeptime, NULL); | ||||
|       now = GetTimeUs(); | ||||
|     } | ||||
|   } | ||||
|   else | ||||
|   { | ||||
|     struct timespec sleeptime; | ||||
|     sleeptime.tv_sec = usecs / 1000000; | ||||
|     sleeptime.tv_nsec = (usecs % 1000000) * 1000; | ||||
|  | ||||
|     nanosleep(&sleeptime, NULL); | ||||
|   } | ||||
| } | ||||
|  | ||||
							
								
								
									
										49
									
								
								src/timeutils.h
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										49
									
								
								src/timeutils.h
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,49 @@ | ||||
| /* | ||||
|  * boblight | ||||
|  * Copyright (C) Bob  2009  | ||||
|  *  | ||||
|  * boblight is free software: you can redistribute it and/or modify it | ||||
|  * under the terms of the GNU General Public License as published by the | ||||
|  * Free Software Foundation, either version 3 of the License, or | ||||
|  * (at your option) any later version. | ||||
|  *  | ||||
|  * boblight is distributed in the hope that it will be useful, but | ||||
|  * WITHOUT ANY WARRANTY; without even the implied warranty of | ||||
|  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. | ||||
|  * See the GNU General Public License for more details. | ||||
|  *  | ||||
|  * You should have received a copy of the GNU General Public License along | ||||
|  * with this program.  If not, see <http://www.gnu.org/licenses/>. | ||||
|  */ | ||||
|  | ||||
| #ifndef TIMEUTILS | ||||
| #define TIMEUTILS | ||||
|  | ||||
| #include "stdint.h" | ||||
| //#include "config.h" | ||||
|  | ||||
| #include <time.h> | ||||
| #include <sys/time.h> | ||||
|  | ||||
| inline int64_t GetTimeUs() | ||||
| { | ||||
| #if defined(HAVE_CLOCK_GETTIME) && defined(CLOCK_MONOTONIC) | ||||
|   struct timespec time; | ||||
|   clock_gettime(CLOCK_MONOTONIC, &time); | ||||
|   return ((int64_t)time.tv_sec * 1000000LL) + (int64_t)(time.tv_nsec + 500) / 1000LL; | ||||
| #else | ||||
|   struct timeval time; | ||||
|   gettimeofday(&time, NULL); | ||||
|   return ((int64_t)time.tv_sec * 1000000LL) + (int64_t)time.tv_usec; | ||||
| #endif | ||||
| } | ||||
|  | ||||
| template <class T>  | ||||
| inline T GetTimeSec() | ||||
| { | ||||
|   return (T)GetTimeUs() / (T)1000000.0; | ||||
| } | ||||
|  | ||||
| void USleep(int64_t usecs, volatile bool* stop = NULL); | ||||
|  | ||||
| #endif //TIMEUTILS | ||||
		Reference in New Issue
	
	Block a user