浏览代码

fixed assert dialog in VC++ CMake
multiwindow included to Demo
significantly improved EventDispatcher performance
added error handler callback to oxygine::log
added std::function ThreadMessages callback
updated to latest Marmalade and fixed build
minor fixes

dmuratshin 10 年之前
父节点
当前提交
75a6c4e3d1
共有 35 个文件被更改,包括 332 次插入142 次删除
  1. 2 2
      .hg_archival.txt
  2. 4 0
      examples/Demo/proj.cmake/CMakeLists.txt
  3. 3 2
      examples/Demo/src/TestHttp.h
  4. 33 4
      examples/Demo/src/example.cpp
  5. 5 1
      examples/DemoBox2D/proj.cmake/CMakeLists.txt
  6. 4 0
      examples/Game/part1/proj.cmake/CMakeLists.txt
  7. 4 0
      examples/Game/part2/proj.cmake/CMakeLists.txt
  8. 4 0
      examples/Game/part3/proj.cmake/CMakeLists.txt
  9. 4 0
      examples/Game/part4/proj.cmake/CMakeLists.txt
  10. 4 0
      examples/Game/part5/proj.cmake/CMakeLists.txt
  11. 4 0
      examples/HelloWorld/proj.cmake/CMakeLists.txt
  12. 4 0
      examples/Match3/proj.cmake/CMakeLists.txt
  13. 3 1
      examples/Match3/src/jewels.cpp
  14. 4 0
      examples/TutorialResources/proj.cmake/CMakeLists.txt
  15. 11 4
      oxygine/src/Actor.cpp
  16. 6 1
      oxygine/src/AsyncTask.cpp
  17. 57 56
      oxygine/src/EventDispatcher.cpp
  18. 8 3
      oxygine/src/EventDispatcher.h
  19. 5 0
      oxygine/src/HttpRequestTask.cpp
  20. 2 0
      oxygine/src/HttpRequestTask.h
  21. 1 1
      oxygine/src/TouchEvent.h
  22. 26 0
      oxygine/src/core/ThreadMessages.cpp
  23. 8 0
      oxygine/src/core/ThreadMessages.h
  24. 13 0
      oxygine/src/core/curl/HttpRequestCurlTask.cpp
  25. 22 6
      oxygine/src/core/log.cpp
  26. 5 0
      oxygine/src/core/log.h
  27. 1 1
      oxygine/src/core/oxygine.cpp
  28. 1 1
      oxygine/src/core/s3e/MyHttp.cpp
  29. 52 44
      oxygine/src/oxygine_include.h
  30. 21 0
      oxygine/src/pugixml/pugixml.cpp
  31. 3 0
      oxygine/src/pugixml/pugixml.hpp
  32. 3 10
      oxygine/src/utils/stringUtils.cpp
  33. 0 4
      oxygine/src/utils/stringUtils.h
  34. 1 1
      tools/others/gen_templates.py
  35. 4 0
      tools/templates/proj.cmake/CMakeLists.txt

+ 2 - 2
.hg_archival.txt

@@ -1,5 +1,5 @@
 repo: b6d71054df5712e643a0685bc3ba54b123db5729
-node: caf41c056e3e32240761d7398f7bdb36c64fde51
+node: 5d4d0612a4501f309960b222d6538751f41f47ca
 branch: default
 latesttag: oldrender
-latesttagdistance: 664
+latesttagdistance: 684

+ 4 - 0
examples/Demo/proj.cmake/CMakeLists.txt

@@ -9,4 +9,8 @@ link_directories(${OXYGINE_LIBRARY_DIRS})
 set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11")
 add_executable(Demo ../src/entry_point.cpp ../src/example.cpp ../src/test.cpp  ../src/TestBox9Sprite.h ../src/TestClipRect.h ../src/TestDrag.h ../src/TestHttp.h ../src/TestInputText.h ../src/TestManageRes.h ../src/TestMask.h ../src/TestPerf.h ../src/TestPolygon.h ../src/TestProgressBar.h ../src/TestRender2Texture.h ../src/TestSliding.h ../src/TestTexel2Pixel.h ../src/TestText.h ../src/TestTextureFormat.h ../src/TestTweens.h ../src/TestUserShader.h ../src/TestUserShader2.h ../src/example.h ../src/test.h )
 
+if (WIN32) #disable console mode for VC++
+	set_target_properties(Demo PROPERTIES WIN32_EXECUTABLE TRUE)
+endif(WIN32)
+
 target_link_libraries(Demo ${OXYGINE_CORE_LIBS})

+ 3 - 2
examples/Demo/src/TestHttp.h

@@ -98,9 +98,10 @@ public:
 	void dateTimeLoaded(Event* event)
 	{
 		HttpRequestTask* task = safeCast<HttpRequestTask*>(event->currentTarget.get());
-		const std::vector<unsigned char> &bf = task->getResponse();
+		const std::vector<unsigned char> &response = task->getResponse();
+
 		pugi::xml_document doc;
-		doc.load_buffer(&bf.front(), bf.size());
+		doc.load_buffer(&response.front(), response.size());
 		string time = doc.root().first_child().attribute("time").as_string();
 		notify("internet time:\n" + time, 2000);
 

+ 33 - 4
examples/Demo/src/example.cpp

@@ -34,7 +34,11 @@ spActor _tests;
 Resources resources;
 Resources resourcesUI;
 
-//extern spStage stage2;
+//#define MULTIWINDOW 1
+
+#if MULTIWINDOW
+spStage stage2;
+#endif
 
 class TestActor: public Test
 {
@@ -71,9 +75,13 @@ public:
 
 	void showTest(spActor actor)
 	{
+		spStage stage = getStage();
+#if MULTIWINDOW
+		stage = stage2;
+#else
 		setVisible(false);
-		//spStage stage = stage2;
-		getStage()->addChild(actor);
+#endif
+		stage->addChild(actor);
 	}
 
 	void clicked(string id)
@@ -220,11 +228,32 @@ void example_init()
     
     //initialize http requests
     HttpRequestTask::init();
+
+
+#if MULTIWINDOW
+	SDL_Window *window2 = SDL_CreateWindow("Second Oxygine Window", SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED, getStage()->getWidth(), getStage()->getHeight(), SDL_WINDOW_OPENGL | SDL_WINDOW_SHOWN);	
+	stage2 = new Stage(false);
+	stage2->setSize(getStage()->getSize());
+	stage2->associateWithWindow(window2);
+#endif
+
 }
 
 void example_update()
 {
-
+#if MULTIWINDOW
+	stage2->update();
+	SDL_Window *wnd = stage2->getAssociatedWindow();
+	if (core::beginRendering(wnd))
+	{
+		Color clearColor(32, 32, 32, 255);
+		Rect viewport(Point(0, 0), core::getDisplaySize());
+		//render all actors. Actor::render would be called also for all children
+		stage2->render(clearColor, viewport);
+	
+		core::swapDisplayBuffers(wnd);
+	}
+#endif
 }
 
 void example_destroy()

+ 5 - 1
examples/DemoBox2D/proj.cmake/CMakeLists.txt

@@ -16,4 +16,8 @@ add_executable(DemoBox2D ${BOX2DSRC} ../src/Box2DDebugDraw.cpp ../src/entry_poin
 source_group(box2d FILES ${BOX2DSRC})
 include_directories(../box2d)
 
-target_link_libraries(DemoBox2D ${OXYGINE_CORE_LIBS})
+target_link_libraries(DemoBox2D ${OXYGINE_CORE_LIBS})
+
+if (WIN32) #disable console mode for VC++
+	set_target_properties(DemoBox2D PROPERTIES WIN32_EXECUTABLE TRUE)
+endif(WIN32)

+ 4 - 0
examples/Game/part1/proj.cmake/CMakeLists.txt

@@ -9,4 +9,8 @@ link_directories(${OXYGINE_LIBRARY_DIRS})
 set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11")
 add_executable(GamePart1 ../src/Game.cpp ../src/Joystick.cpp ../src/Player.cpp ../src/Unit.cpp ../src/entry_point.cpp ../src/example.cpp ../src/res.cpp  ../src/Game.h ../src/Joystick.h ../src/Player.h ../src/Unit.h ../src/example.h ../src/res.h )
 
+if (WIN32) #disable console mode for VC++
+	set_target_properties(GamePart1 PROPERTIES WIN32_EXECUTABLE TRUE)
+endif(WIN32)
+
 target_link_libraries(GamePart1 ${OXYGINE_CORE_LIBS})

+ 4 - 0
examples/Game/part2/proj.cmake/CMakeLists.txt

@@ -9,4 +9,8 @@ link_directories(${OXYGINE_LIBRARY_DIRS})
 set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11")
 add_executable(GamePart2 ../src/Enemy.cpp ../src/Game.cpp ../src/Joystick.cpp ../src/Player.cpp ../src/Rocket.cpp ../src/Unit.cpp ../src/entry_point.cpp ../src/example.cpp ../src/res.cpp  ../src/Enemy.h ../src/Game.h ../src/Joystick.h ../src/Player.h ../src/Rocket.h ../src/Unit.h ../src/example.h ../src/res.h )
 
+if (WIN32) #disable console mode for VC++
+	set_target_properties(GamePart2 PROPERTIES WIN32_EXECUTABLE TRUE)
+endif(WIN32)
+
 target_link_libraries(GamePart2 ${OXYGINE_CORE_LIBS})

+ 4 - 0
examples/Game/part3/proj.cmake/CMakeLists.txt

@@ -9,4 +9,8 @@ link_directories(${OXYGINE_LIBRARY_DIRS})
 set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11")
 add_executable(GamePart3 ../src/Enemy.cpp ../src/Game.cpp ../src/GameScene.cpp ../src/Joystick.cpp ../src/MainMenuScene.cpp ../src/MyButton.cpp ../src/Player.cpp ../src/Rocket.cpp ../src/Scene.cpp ../src/Unit.cpp ../src/entry_point.cpp ../src/example.cpp ../src/res.cpp  ../src/Enemy.h ../src/Game.h ../src/GameScene.h ../src/Joystick.h ../src/MainMenuScene.h ../src/MyButton.h ../src/Player.h ../src/Rocket.h ../src/Scene.h ../src/Unit.h ../src/example.h ../src/res.h )
 
+if (WIN32) #disable console mode for VC++
+	set_target_properties(GamePart3 PROPERTIES WIN32_EXECUTABLE TRUE)
+endif(WIN32)
+
 target_link_libraries(GamePart3 ${OXYGINE_CORE_LIBS})

+ 4 - 0
examples/Game/part4/proj.cmake/CMakeLists.txt

@@ -9,4 +9,8 @@ link_directories(${OXYGINE_LIBRARY_DIRS})
 set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11")
 add_executable(GamePart4 ../src/Enemy.cpp ../src/Game.cpp ../src/GameMenu.cpp ../src/GameScene.cpp ../src/Joystick.cpp ../src/MainMenuScene.cpp ../src/MyButton.cpp ../src/Player.cpp ../src/Rocket.cpp ../src/Scene.cpp ../src/Unit.cpp ../src/entry_point.cpp ../src/example.cpp ../src/res.cpp  ../src/Enemy.h ../src/Game.h ../src/GameMenu.h ../src/GameScene.h ../src/Joystick.h ../src/MainMenuScene.h ../src/MyButton.h ../src/Player.h ../src/Rocket.h ../src/Scene.h ../src/Unit.h ../src/example.h ../src/res.h )
 
+if (WIN32) #disable console mode for VC++
+	set_target_properties(GamePart4 PROPERTIES WIN32_EXECUTABLE TRUE)
+endif(WIN32)
+
 target_link_libraries(GamePart4 ${OXYGINE_CORE_LIBS})

+ 4 - 0
examples/Game/part5/proj.cmake/CMakeLists.txt

@@ -9,4 +9,8 @@ link_directories(${OXYGINE_LIBRARY_DIRS})
 set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11")
 add_executable(GamePart5 ../src/Enemy.cpp ../src/Game.cpp ../src/GameMenu.cpp ../src/GameScene.cpp ../src/Joystick.cpp ../src/MainMenuScene.cpp ../src/MyButton.cpp ../src/Player.cpp ../src/Rocket.cpp ../src/Scene.cpp ../src/Unit.cpp ../src/entry_point.cpp ../src/example.cpp ../src/res.cpp  ../src/Enemy.h ../src/Game.h ../src/GameMenu.h ../src/GameScene.h ../src/Joystick.h ../src/MainMenuScene.h ../src/MyButton.h ../src/Player.h ../src/Rocket.h ../src/Scene.h ../src/Unit.h ../src/example.h ../src/res.h )
 
+if (WIN32) #disable console mode for VC++
+	set_target_properties(GamePart5 PROPERTIES WIN32_EXECUTABLE TRUE)
+endif(WIN32)
+
 target_link_libraries(GamePart5 ${OXYGINE_CORE_LIBS})

+ 4 - 0
examples/HelloWorld/proj.cmake/CMakeLists.txt

@@ -9,4 +9,8 @@ link_directories(${OXYGINE_LIBRARY_DIRS})
 set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11")
 add_executable(HelloWorld ../src/entry_point.cpp ../src/example.cpp  ../src/example.h )
 
+if (WIN32) #disable console mode for VC++
+	set_target_properties(HelloWorld PROPERTIES WIN32_EXECUTABLE TRUE)
+endif(WIN32)
+
 target_link_libraries(HelloWorld ${OXYGINE_CORE_LIBS})

+ 4 - 0
examples/Match3/proj.cmake/CMakeLists.txt

@@ -9,4 +9,8 @@ link_directories(${OXYGINE_LIBRARY_DIRS})
 set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11")
 add_executable(Match3 ../src/entry_point.cpp ../src/example.cpp ../src/gameframe.cpp ../src/jewels.cpp ../src/shared.cpp  ../src/example.h ../src/gameframe.h ../src/jewels.h ../src/shared.h )
 
+if (WIN32) #disable console mode for VC++
+	set_target_properties(Match3 PROPERTIES WIN32_EXECUTABLE TRUE)
+endif(WIN32)
+
 target_link_libraries(Match3 ${OXYGINE_CORE_LIBS})

+ 3 - 1
examples/Match3/src/jewels.cpp

@@ -4,6 +4,8 @@
 
 Jewel::Jewel(int jewel_id)
 {
+	locked = false;
+
 	state = jsNormal;
 	Set(jewel_id);
 	setTouchEnabled(false);
@@ -70,4 +72,4 @@ void Jewel::AnimationEnd()
 {
 	state = jsScored;
 	setVisible(false);
-}
+}

+ 4 - 0
examples/TutorialResources/proj.cmake/CMakeLists.txt

@@ -9,4 +9,8 @@ link_directories(${OXYGINE_LIBRARY_DIRS})
 set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11")
 add_executable(TutorialResources ../src/entry_point.cpp ../src/example.cpp  ../src/example.h )
 
+if (WIN32) #disable console mode for VC++
+	set_target_properties(TutorialResources PROPERTIES WIN32_EXECUTABLE TRUE)
+endif(WIN32)
+
 target_link_libraries(TutorialResources ${OXYGINE_CORE_LIBS})

+ 11 - 4
oxygine/src/Actor.cpp

@@ -126,10 +126,14 @@ namespace oxygine
 
 	void Actor::removedFromStage()
 	{
-		OX_ASSERT(_stage);
+		OX_ASSERT(_stage);		
+
 		onRemovedFromStage();
 		_stage->removeEventListeners(this);
-		_stage = 0;		
+		_stage = 0;	
+
+		_pressed = 0;
+		_overred = 0;
 
 		spActor actor = _children._first;
 		while (actor)
@@ -307,8 +311,6 @@ namespace oxygine
 		case  TouchEvent::TOUCH_DOWN:
 			if (isDescendant(act))
 			{
-				if (event->phase == Event::phase_target)
-					_getStage()->addEventListener(TouchEvent::TOUCH_UP, CLOSURE(this, &Actor::_onMouseEvent));					
 				setPressed(me->index);
 				//_pressed = me->id;
 				//setPressed(true);
@@ -345,8 +347,13 @@ namespace oxygine
 					{
 						setOverred(me->index);
 
+						/*
 						if (event->phase == Event::phase_target)
+						{
+							_getStage()->removeEventListener(TouchEvent::MOVE, CLOSURE(this, &Actor::_onMouseEvent));
 							_getStage()->addEventListener(TouchEvent::MOVE, CLOSURE(this, &Actor::_onMouseEvent));
+						}
+						*/
 					}
 				}
 				else

+ 6 - 1
oxygine/src/AsyncTask.cpp

@@ -1,6 +1,6 @@
 #include "AsyncTask.h"
 #include "core/oxygine.h"
-
+#include <typeinfo>
 namespace oxygine
 {
 	const int successID = sysEventID('s', 'c', 'm');	
@@ -21,6 +21,7 @@ namespace oxygine
 	void AsyncTask::run()
 	{
 		_prerun();
+		log::messageln("AsyncTask::run %d - %s", getObjectID(), typeid(*this).name());
 
 		OX_ASSERT(_status == status_not_started);
 		_status = status_inprogress;
@@ -58,6 +59,8 @@ namespace oxygine
 
 	void AsyncTask::_complete()
 	{
+		log::messageln("AsyncTask::_complete %d - %s", getObjectID(), typeid(*this).name());
+
 		_status = status_completed;
 		_onFinal(false);
 		_finalize(false);
@@ -69,6 +72,8 @@ namespace oxygine
 
 	void AsyncTask::_error()
 	{
+		log::messageln("AsyncTask::_error %d - %s", getObjectID(), typeid(*this).name());
+
 		_status = status_failed;
 		_onFinal(true);
 		_finalize(true);

+ 57 - 56
oxygine/src/EventDispatcher.cpp

@@ -52,16 +52,14 @@ namespace oxygine
 		if (!_listeners)
 			return;
 
-		for (listeners::iterator i = _listeners->begin(); i != _listeners->end(); )
+		for (size_t size = _listeners->size(), i = 0; i != size; ++i)
 		{
-			const listener &ls = *i;
+			const listener &ls = _listeners->at(i);
 			if (ls.id == id)
 			{
-				i = _listeners->erase(i);
+				_listeners->erase(_listeners->begin() + i);
 				break;
 			}
-			else
-				++i;
 		}
 	}
 
@@ -73,34 +71,45 @@ namespace oxygine
 		if (!_listeners)
 			return;
 
-		for (listeners::iterator i = _listeners->begin(); i != _listeners->end(); )
+		for (size_t size = _listeners->size(), i = 0; i != size; ++i)
 		{
-			listener ls = *i;
+			const listener& ls = _listeners->at(i);
 			if (ls.type == et && cb == ls.cb)
 			{
-				i = _listeners->erase(i);
+				_listeners->erase(_listeners->begin() + i);
+				break;
+				//OX_ASSERT(hasEventListeners(et, cb) == false);
+				//--i;
 			}
-			else
-				++i;
 		}
 	}
 
 	bool EventDispatcher::hasEventListeners(void *CallbackThis)
 	{
 		__doCheck();
-		//OX_ASSERT(_listeners);
 		if (!_listeners)
 			return false;
 
-		for (listeners::iterator i = _listeners->begin(); i != _listeners->end();)
+		for (size_t size = _listeners->size(), i = 0; i != size; ++i)
 		{
-			listener ls = *i;
-			if (ls.cb.p_this == CallbackThis)
-			{
+			const listener& ls = _listeners->at(i);
+			if (ls.cb.p_this == CallbackThis)			
+				return true;			
+		}
+		return false;
+	}
+
+	bool EventDispatcher::hasEventListeners(eventType et, EventCallback cb)
+	{
+		__doCheck();
+		if (!_listeners)
+			return false;
+
+		for (size_t size = _listeners->size(), i = 0; i != size; ++i)
+		{
+			const listener& ls = _listeners->at(i);
+			if (ls.type == et && cb == ls.cb)
 				return true;
-			}
-			else
-				++i;
 		}
 		return false;
 	}
@@ -108,19 +117,18 @@ namespace oxygine
 	void EventDispatcher::removeEventListeners(void *CallbackThis)
 	{
 		__doCheck();
-		//OX_ASSERT(_listeners);
 		if (!_listeners)
 			return;
 
-		for (listeners::iterator i = _listeners->begin(); i != _listeners->end(); )
+		for (size_t i = 0; i < _listeners->size(); ++i)
 		{
-			listener ls = *i;
+			const listener& ls = _listeners->at(i);
 			if (ls.cb.p_this == CallbackThis)
 			{
-				i = _listeners->erase(i);
+				_listeners->erase(_listeners->begin() + i);
+				//OX_ASSERT(hasEventListeners(CallbackThis) == false);
+				--i;
 			}
-			else
-				++i;
 		}
 	}
 
@@ -131,47 +139,40 @@ namespace oxygine
 	}
 
 	
-	void EventDispatcher::dispatchEvent(Event *event_)
+	void EventDispatcher::dispatchEvent(Event *event)
 	{
 		__doCheck();
 		if (!_listeners)
 			return;
+		
+		
+		size_t size = _listeners->size();
+		listenerbase* copy = (listenerbase*)alloca(sizeof(listenerbase) * size);
 
-		Event *ev = event_;
-		ev->currentTarget = this;
-
-		listeners copy = *_listeners;//todo, do something!
-		for (listeners::iterator i = copy.begin(); i != copy.end(); ++i)
+		size_t num = 0;
+		for (size_t i = 0; i != size; ++i)
 		{
-			listener ls = *i;
-			if (ls.type != ev->type)
-				continue;
-			//todo!
-
-			/*
-			bool found = false;
-			for (listeners::iterator n = _listeners->begin(); n != _listeners->end(); ++n)
-			{
-				const listener &ols= *n;
-				if (ols.type == ls.type && ols.id == ls.id && ols.cb == ls.cb)
-				{
-					found = true;
-					break;
-				}
-			}
-
-			if (!found)
+			listener& ls = _listeners->at(i);
+			if (ls.type != event->type)
 				continue;
 
-			*/
-
-			//OX_ASSERT(ls.type < 20);
-			//log::messageln("cb: %d %x", ls.type, ls.cb.p_this);
-			ls.cb(ev);
-			if (ev->stopsImmediatePropagation)
-			{
+			new(copy + num) listenerbase(ls);
+			++num;
+		}
+		
+		for (size_t i = 0; i != num; ++i)
+		{
+			listenerbase& ls = copy[i];
+			event->currentTarget = this;
+			ls.cb(event);
+			if (event->stopsImmediatePropagation)
 				break;
-			}
+		}
+
+		for (size_t i = 0; i != num; ++i)
+		{
+			listenerbase& ls = copy[i];
+			ls.~listenerbase();
 		}
 	}
 }

+ 8 - 3
oxygine/src/EventDispatcher.h

@@ -32,6 +32,7 @@ namespace oxygine
 		void removeEventListener(eventType, EventCallback);
 		void removeEventListener(int id);
 		bool hasEventListeners(void *CallbackThis);
+		bool hasEventListeners(eventType, EventCallback);
 		void removeEventListeners(void *CallbackThis);
 		void removeAllEventListeners();
 
@@ -41,16 +42,20 @@ namespace oxygine
 
 	protected:
 
-		struct listener
+		struct listenerbase
+		{
+			EventCallback cb;			
+		};
+
+		struct listener : public listenerbase
 		{
-			EventCallback cb;
 			eventType type;
 			int id;
 		};
 
 		int _lastID;
 		
-		typedef std::list<listener> listeners;
+		typedef std::vector<listener> listeners;
 		listeners *_listeners;
 	};
 }

+ 5 - 0
oxygine/src/HttpRequestTask.cpp

@@ -40,6 +40,11 @@ namespace oxygine
 	}
 
 
+	const std::vector<unsigned char>&	HttpRequestTask::getPostData() const
+	{
+		return _postData;
+	}
+
 	const std::vector<unsigned char> &HttpRequestTask::getResponse() const 
 	{
 		return _response; 

+ 2 - 0
oxygine/src/HttpRequestTask.h

@@ -38,8 +38,10 @@ namespace oxygine
 		~HttpRequestTask();
 
 		const std::vector<unsigned char>&	getResponse() const;
+		const std::vector<unsigned char>&	getPostData() const;
 		const std::string&					getFileName() const;
 
+		/**swap version of getResponse if you want to modify result buffer inplace*/
 		void getResponseSwap(std::vector<unsigned char> &);
 
 		void setPostData(const std::vector<unsigned char> &data);

+ 1 - 1
oxygine/src/TouchEvent.h

@@ -25,7 +25,7 @@ namespace oxygine
 		};
 
 
-		TouchEvent(eventType type, bool Bubbles = true, const Vector2 &locPosition = Vector2(0, 0)) :Event(type, Bubbles), localPosition(locPosition), position(locPosition), mouseButton(MouseButton_Touch), pressure(1.0f), index(0){}
+		TouchEvent(eventType type, bool Bubbles = true, const Vector2 &locPosition = Vector2(0, 0)) :Event(type, Bubbles), localPosition(locPosition), position(locPosition), mouseButton(MouseButton_Touch), pressure(1.0f), index(1){}
 
 		Vector2 localPosition;
 		Vector2 position;

+ 26 - 0
oxygine/src/core/ThreadMessages.cpp

@@ -151,6 +151,14 @@ namespace oxygine
 				_last.cb(_last);
 			}
 
+#ifndef __S3E__
+			if (_last.cbFunction)
+			{
+				LOGDN("ThreadMessages::running callback function");
+				_last.cbFunction();
+			}
+#endif
+
 			LOGDN("ThreadMessages::_replyLast pre _waitReplyID = %d, _last._id = %d, _last.msgid=%d", _waitReplyID, _last._id, _last.msgid);
 
 			if (_waitReplyID && _last._id == _waitReplyID)
@@ -236,4 +244,22 @@ namespace oxygine
 		_events.push_back(ev);
 		pthread_cond_signal(&_cond);
 	}
+
+#ifndef __S3E__
+	void ThreadMessages::postCallback(const std::function<void()> &f)
+	{
+		message ev;
+		ev.msgid = 0;
+		ev.arg1 = 0;
+		ev.arg2 = 0;
+		ev.cb = 0;
+		ev.cbData = 0;
+		ev.cbFunction = f;
+
+		MutexPthreadLock lock(_mutex);
+		ev._id = ++_id;
+		_events.push_back(ev);
+		pthread_cond_signal(&_cond);
+	}
+#endif
 }

+ 8 - 0
oxygine/src/core/ThreadMessages.h

@@ -2,6 +2,8 @@
 #include "oxygine_include.h"
 #include <vector>
 #include "pthread.h"
+#include <functional>
+
 namespace oxygine
 {
 	class MutexPthreadLock
@@ -30,6 +32,9 @@ namespace oxygine
 
 			callback	cb;
 			void*		cbData;
+#ifndef __S3E__
+			std::function< void() >		cbFunction;
+#endif
 
 			unsigned int _id;
 			void*	_result;
@@ -51,6 +56,9 @@ namespace oxygine
 		void*send(int msgid, void *arg1, void *arg2);
 		void post(int msgid, void *arg1, void *arg2);
 		void postCallback(int msgid, void *arg1, void *arg2, callback cb, void *cbData);
+#ifndef __S3E__
+		void postCallback(const std::function<void()> &);
+#endif
 
 		void reply(void *val);
 

+ 13 - 0
oxygine/src/core/curl/HttpRequestCurlTask.cpp

@@ -1,6 +1,7 @@
 #include "HttpRequestCurlTask.h"
 #include "core/oxygine.h"
 #include "core/ThreadMessages.h"
+#include "SDL.h"
 
 
 namespace oxygine
@@ -38,6 +39,18 @@ namespace oxygine
 				ok = response == 200;
 			}
 
+#if 0
+			const Uint8* data = SDL_GetKeyboardState(0);
+			static bool fail = false;
+
+			if (data[SDL_SCANCODE_N])
+				fail = true;
+			if (data[SDL_SCANCODE_M])
+				fail = false;
+
+			if (fail)
+				ok = false;
+#endif
 
 			if (ok)
 				task->onComplete();

+ 22 - 6
oxygine/src/core/log.cpp

@@ -51,6 +51,13 @@ namespace oxygine
 			_enabled = false;
 		}
 
+		error_handler _eh = 0;
+
+		void setErrorHandler(error_handler eh)
+		{
+			_eh = eh;
+		}
+
 		void out(const char *str)
 		{
 			if (!_enabled)
@@ -66,10 +73,13 @@ namespace oxygine
 		void out_line(char *str, int i)
 		{
 			out(str);
+#if __ANDROID__ || EMSCRIPTEN
+#else
 			out("\n");
+#endif
 		}
 
-		void out_line_prefix(const char *pref, const char* format, va_list args)
+		void out_line_prefix(error_handler eh, const char *pref, const char* format, va_list args)
 		{
 			char buff[SIZE] = {0};
 			strcpy(buff, pref);
@@ -79,9 +89,12 @@ namespace oxygine
 			if (i == -1)
 				buff[SIZE - 1] = 0;
 			out_line(buff, i + len);
+
+			if (eh)
+				eh(buff);
 		}
 
-		void out_prefix(const char *pref, const char* format, va_list args)
+		void out_prefix(error_handler eh, const char *pref, const char* format, va_list args)
 		{
 			char buff[SIZE] = {0};
 			strcpy(buff, pref);
@@ -91,6 +104,9 @@ namespace oxygine
 			if (i == -1)
 				buff[SIZE - 1] = 0;
 			out(buff);
+
+			if (eh)
+				eh(buff);
 		}
 
 		void message(const char *format, ...)
@@ -103,7 +119,7 @@ namespace oxygine
 
 		void message_va(const char *format, va_list args)
 		{
-			out_prefix("", format, args);
+			out_prefix(0, "", format, args);
 		}
 
 		void warning(const char *format, ...)
@@ -116,7 +132,7 @@ namespace oxygine
 
 		void warning_va(const char *format, va_list args)
 		{
-			out_line_prefix("warning: ", format, args);
+			out_line_prefix(0, "warning: ", format, args);
 		}
 
 		void error(const char *format, ...)
@@ -129,7 +145,7 @@ namespace oxygine
 
 		void error_va(const char *format, va_list args)
 		{
-			out_line_prefix("error: ", format, args);
+			out_line_prefix(_eh, "error: ", format, args);
 		}
 
 		void messageln(const char *format, ...)
@@ -142,7 +158,7 @@ namespace oxygine
 
 		void messageln_va(const char *format, va_list args)
 		{
-			out_line_prefix("", format, args);
+			out_line_prefix(0, "", format, args);
 		}
 	}
 }

+ 5 - 0
oxygine/src/core/log.h

@@ -11,6 +11,11 @@ namespace oxygine
 		/**Display logging*/
 		void disable();
 
+		typedef void (*error_handler)(const char *txt);
+
+		/*run your callback if log::error was called*/
+		void setErrorHandler(error_handler);
+
 		/**pure out to log*/
 		void out(const char *str);
 

+ 1 - 1
oxygine/src/core/oxygine.cpp

@@ -778,7 +778,7 @@ namespace oxygine
 		{
 		case ep_show_error:
 			log::error_va(format, args);
-			OX_ASSERT(!"handleErrorPolicy error.");
+			OX_ASSERT_NL(!"handleErrorPolicy error.");
 			break;
 		case ep_show_warning:
 			log::warning_va(format, args);

+ 1 - 1
oxygine/src/core/s3e/MyHttp.cpp

@@ -258,7 +258,7 @@ void MyHttp::gotData(int size)
 int MyHttp::_gotData (void* systemData, void* userData)
 {
 	MyHttp *http = (MyHttp *)userData;
-	http->gotData((int)systemData);
+	http->gotData((size_t)systemData);
 	return 0;
 }
 

+ 52 - 44
oxygine/src/oxygine_include.h

@@ -10,29 +10,29 @@
 //#define OXYGINE_NO_YEILD 1
 
 #if __S3E__
-	#define OXYGINE_MARMALADE 1
-	#ifdef IW_DEBUG
-		#define OX_DEBUG 1
-	#endif
+#	define OXYGINE_MARMALADE 1
+#	ifdef IW_DEBUG
+#		define OX_DEBUG 1
+#	endif
 #elif EMSCRIPTEN
-	#define OXYGINE_EMSCRIPTEN 1
-	#ifndef NDEBUG
-		#define OX_DEBUG 1
-	#endif // DEBUG	
+#	define OXYGINE_EMSCRIPTEN 1
+#	ifndef NDEBUG
+#		define OX_DEBUG 1
+#	endif // DEBUG	
 #else
-	#define OXYGINE_SDL 1
-	#ifdef WIN32
-		#ifndef _CRT_SECURE_NO_WARNINGS
-			#define _CRT_SECURE_NO_WARNINGS
-		#endif
-	#endif
+#	define OXYGINE_SDL 1
+#	ifdef WIN32
+#		ifndef _CRT_SECURE_NO_WARNINGS
+#			define _CRT_SECURE_NO_WARNINGS
+#		endif
+#	endif
 #endif
 
 
 #if _DEBUG || DEBUG
-	#ifndef OX_DEBUG
-		#define OX_DEBUG 1
-	#endif
+#	ifndef OX_DEBUG
+#		define OX_DEBUG 1
+#	endif
 #endif
 
 
@@ -40,32 +40,40 @@
 
 
 #ifndef OX_DEBUG
-	#ifndef EMSCRIPTEN
-		#define USE_MEMORY_POOL 1
-		#define OBJECT_POOL_ALLOCATOR 1
-	#endif
+#	ifndef EMSCRIPTEN
+#		define USE_MEMORY_POOL 1
+#		define OBJECT_POOL_ALLOCATOR 1
+#	endif
 #endif
 
 #if OX_DEBUG
-	#define OXYGINE_DEBUG_TRACE_LEAKS 1
-	#define OXYGINE_DEBUG_T2P 1
-	#define OXYGINE_DEBUG_SAFECAST 1
-	#define OXYGINE_TRACE_VIDEO_STATS 1
+#	define OXYGINE_DEBUG_TRACE_LEAKS 1
+#	define OXYGINE_DEBUG_T2P 1
+#	define OXYGINE_DEBUG_SAFECAST 1
+#	define OXYGINE_TRACE_VIDEO_STATS 1
 #endif
 
 #define OXYGINE_ASSERT2LOG 1
 
-#if OXYGINE_ASSERT2LOG
-namespace oxygine{namespace log{void error(const char *format, ...);}}
+namespace oxygine{ namespace log{ void error(const char *format, ...); } }
+
+#define OX_LOG_ERROR(x)		if (!(x)) {oxygine::log::error("Assert! %s in %s:%d", #x, __FILE__, __LINE__);}
+
+
+//assert without log::error
 #ifdef OXYGINE_QT
-#define OX_ASSERT(x) if (!(x)) {__asm("int3");oxygine::log::error("Assert! %d %s", __LINE__, __FILE__); }(assert(x))
+#	define OX_ASSERT_NL(x) {assert(x);}
 #elif EMSCRIPTEN
-#define OX_ASSERT(x) if (!(x)) {oxygine::log::error("Assert! %d %s", __LINE__, __FILE__);}
+#	define OX_ASSERT_NL(x) 
 #else
-#define OX_ASSERT(x) if (!(x)) {oxygine::log::error("Assert! %d %s", __LINE__, __FILE__);}(assert(x))
+#	define OX_ASSERT_NL(x) {assert(x);}
 #endif
+
+
+#if OXYGINE_ASSERT2LOG
+#	define OX_ASSERT(x) {OX_LOG_ERROR(x); OX_ASSERT_NL(x);}
 #else
-#define OX_ASSERT(x) (if (!(x)) oxygine::log::error("Assert! %d %s", __LINE__, __FILE__))
+#	define OX_ASSERT(x) {OX_ASSERT_NL(x);}
 #endif
 
 #define OXYGINE_HAS_RESTORE
@@ -73,30 +81,30 @@ namespace oxygine{namespace log{void error(const char *format, ...);}}
 #define OXYGINE_RENDERER 2
 
 #ifdef __GNUC__
-#define OXYGINE_DEPRECATED __attribute__((deprecated))
+#	define OXYGINE_DEPRECATED __attribute__((deprecated))
 #elif defined(_MSC_VER)
-#define OXYGINE_DEPRECATED __declspec(deprecated)
+#	define OXYGINE_DEPRECATED __declspec(deprecated)
 #else
-#pragma message("WARNING: You need to implement DEPRECATED for this compiler")
-#define OXYGINE_DEPRECATED
+#	pragma message("WARNING: You need to implement DEPRECATED for this compiler")
+#	define OXYGINE_DEPRECATED
 #endif
 
 
 #ifdef _MSC_VER
-#define OVERRIDE override
+#	define OVERRIDE override
 #else
-#define OVERRIDE 
+#	define OVERRIDE 
 #endif
 
 
 #ifndef __S3E__
-#if defined(_MSC_VER) || defined(__BORLANDC__)
-typedef unsigned __int64 uint64;
-typedef signed __int64 int64;
-#else
-typedef unsigned long long uint64;
-typedef signed long long int64;
-#endif
+#	if defined(_MSC_VER) || defined(__BORLANDC__)
+	typedef unsigned __int64 uint64;
+	typedef signed __int64 int64;
+#	else
+	typedef unsigned long long uint64;
+	typedef signed long long int64;
+#	endif
 #endif
 
 namespace oxygine

+ 21 - 0
oxygine/src/pugixml/pugixml.cpp

@@ -11416,6 +11416,27 @@ namespace pugi
 	{
 		return query.evaluate_node(*this);
 	}
+
+	pugi::xml_attribute find_next_attribute(const pugi::xml_node &node, pugi::xml_attribute& attr, const char *name)
+	{
+		pugi::xml_attribute current = attr;
+
+		while (!current.empty())
+		{
+			if (!strcmp(current.name(), name))
+			{
+				attr = current.next_attribute();
+				return current;
+			}
+			current = current.next_attribute();
+		}
+
+		current = node.attribute(name);
+		if (!current.empty())		
+			attr = current;
+
+		return current;
+	}
 }
 
 #endif

+ 3 - 0
oxygine/src/pugixml/pugixml.hpp

@@ -1293,6 +1293,9 @@ namespace pugi
 	std::basic_string<wchar_t, std::char_traits<wchar_t>, std::allocator<wchar_t> > PUGIXML_FUNCTION as_wide(const std::basic_string<char, std::char_traits<char>, std::allocator<char> >& str);
 #endif
 
+
+	pugi::xml_attribute PUGIXML_FUNCTION find_next_attribute(const pugi::xml_node &node, pugi::xml_attribute& attr, const char *name);
+
 	// Memory allocation function interface; returns pointer to allocated memory or NULL on failure
 	typedef void* (*allocation_function)(size_t size);
 	

+ 3 - 10
oxygine/src/utils/stringUtils.cpp

@@ -220,14 +220,7 @@ namespace oxygine
 		std::transform(data.begin(), data.end(), data.begin(), ::tolower);//todo optimize
 		return data;
 	}
-
-	std::wstring debug_s2ws(const std::string &str)
-	{
-		std::wstring wstr(str.length(), L' ');
-		std::copy(str.begin(), str.end(), wstr.begin());
-		return wstr;
-	}
-	
+		
 	std::wstring utf8tows(const char *utf8str)
 	{
 		if (!utf8str)
@@ -243,7 +236,7 @@ namespace oxygine
 		wchar_t *s = (wchar_t *)fastAlloc(4 * n);
 		s[0] = 0;
 
-		int len = IwUTF8ToWideChar(utf8str, n, (ucs2char*)s, n * 4);
+		int len = IwUTF8ToWideChar(utf8str, n, s, n * 4);
 		s[len] = 0;
 
 		std::wstring str = s;
@@ -280,7 +273,7 @@ namespace oxygine
 		char *s = (char *)fastAlloc(4 * n);
 		s[0] = 0;
 
-		int len = IwWideCharToUTF8((const ucs2char*)wstr, n, s, n * 4);
+		int len = IwWideCharToUTF8(wstr, n, s, n * 4);
 		s[len] = 0;
 
 		std::string str = s;

+ 0 - 4
oxygine/src/utils/stringUtils.h

@@ -23,10 +23,6 @@ namespace oxygine
 
 	std::string lower(const std::string &str);
 
-	/**ONLY FOR DEBUGGING!!! converts wstring to string. it supports ONLY ANSI*/
-	std::wstring debug_s2ws(const std::string &str);
-
-
 	std::wstring	utf8tows(const char *utf8str);
 	std::string		ws2utf8(const wchar_t *wstr);
 

+ 1 - 1
tools/others/gen_templates.py

@@ -12,7 +12,7 @@ def gen(path, project = ""):
 	#projs = ("win32", )
 	projs = ("cmake", )	
 	#projs = ("android", )
-	projs = ("emscripten", )
+	#projs = ("emscripten", )
 
 	for platform in projs:
 		dest = "../../examples/" + path + "/proj." + platform

+ 4 - 0
tools/templates/proj.cmake/CMakeLists.txt

@@ -9,4 +9,8 @@ link_directories(${OXYGINE_LIBRARY_DIRS})
 set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -std=c++11")
 add_executable(${PROJECT} ${SRC} ${INCLUDE})
 
+if (WIN32) #disable console mode for VC++
+	set_target_properties(${PROJECT} PROPERTIES WIN32_EXECUTABLE TRUE)
+endif(WIN32)
+
 target_link_libraries(${PROJECT} ${OXYGINE_CORE_LIBS})