diff options
Diffstat (limited to 'mwe/events/src')
| -rw-r--r-- | mwe/events/src/event.cpp | 21 | ||||
| -rw-r--r-- | mwe/events/src/iKeyListener.cpp | 19 | ||||
| -rw-r--r-- | mwe/events/src/iMouseListener.cpp | 28 | ||||
| -rw-r--r-- | mwe/events/src/inputSystem.cpp | 95 | ||||
| -rw-r--r-- | mwe/events/src/keyListenerTest.cpp | 15 | ||||
| -rw-r--r-- | mwe/events/src/loopManager.cpp | 67 | ||||
| -rw-r--r-- | mwe/events/src/main.cpp | 11 | ||||
| -rw-r--r-- | mwe/events/src/mouseListenerTest.cpp | 27 | ||||
| -rw-r--r-- | mwe/events/src/uiObject.cpp | 24 | ||||
| -rw-r--r-- | mwe/events/src/uiRenderer.cpp | 107 | ||||
| -rw-r--r-- | mwe/events/src/window.cpp | 31 | 
11 files changed, 410 insertions, 35 deletions
| diff --git a/mwe/events/src/event.cpp b/mwe/events/src/event.cpp index c9201d0..0c9f3ed 100644 --- a/mwe/events/src/event.cpp +++ b/mwe/events/src/event.cpp @@ -50,3 +50,24 @@ CollisionEvent::CollisionEvent(Collision collision)  Collision CollisionEvent::getCollisionData() const {  	return this->collisionData;  } + +TextSubmitEvent::TextSubmitEvent(std::string text) +	: text(text), Event("TextSubmitEvent") {} + +std::string TextSubmitEvent::getText() const { return this->text; } + +MouseReleasedEvent::MouseReleasedEvent(int x, int y, MouseButton button) +	: mouseX(x), mouseY(y), button(button), Event("MouseReleased") {} +std::pair<int, int> MouseReleasedEvent::getMousePosition() const { +	return {mouseX, mouseY}; +} +MouseClickEvent::MouseClickEvent(int x, int y, MouseButton button) +	: mouseX(x), mouseY(y), button(button), Event("MouseClickEvent") {} +MouseMovedEvent::MouseMovedEvent(int x, int y) +	: mouseX(x), mouseY(y), Event("MouseMovedEvent") {} +std::pair<int, int> MouseClickEvent::getMousePosition() const { +	return {mouseX, mouseY}; +} +std::pair<int, int> MouseMovedEvent::getMousePosition() const { +	return {mouseX, mouseY}; +} diff --git a/mwe/events/src/iKeyListener.cpp b/mwe/events/src/iKeyListener.cpp new file mode 100644 index 0000000..0235fab --- /dev/null +++ b/mwe/events/src/iKeyListener.cpp @@ -0,0 +1,19 @@ +#include "iKeyListener.h" + +IKeyListener::~IKeyListener() { unsubscribeEvents(); } + +void IKeyListener::subscribeEvents(int listenerId) { +	keyPressedHandler +		= [this](const KeyPressedEvent & event) { this->onKeyPressed(event); }; +	keyReleasedHandler = [this](const KeyReleasedEvent & event) { +		this->onKeyReleased(event); +	}; + +	subscribe<KeyPressedEvent>(keyPressedHandler, listenerId); +	subscribe<KeyReleasedEvent>(keyReleasedHandler, listenerId); +} + +void IKeyListener::unsubscribeEvents(int listenerId) { +	unsubscribe<KeyPressedEvent>(keyPressedHandler, listenerId); +	unsubscribe<KeyReleasedEvent>(keyReleasedHandler, listenerId); +} diff --git a/mwe/events/src/iMouseListener.cpp b/mwe/events/src/iMouseListener.cpp new file mode 100644 index 0000000..69d8c9f --- /dev/null +++ b/mwe/events/src/iMouseListener.cpp @@ -0,0 +1,28 @@ +#include "iMouseListener.h" +IMouseListener::~IMouseListener() { unsubscribeEvents(); } + +void IMouseListener::subscribeEvents(int listenerId) { +	mouseClickHandler = [this](const MouseClickEvent & event) { +		this->onMouseClicked(event); +	}; +	mousePressHandler = [this](const MousePressedEvent & event) { +		this->onMousePressed(event); +	}; +	mouseReleaseHandler = [this](const MouseReleasedEvent & event) { +		this->onMouseReleased(event); +	}; +	mouseMoveHandler +		= [this](const MouseMovedEvent & event) { this->onMouseMoved(event); }; + +	subscribe<MouseClickEvent>(mouseClickHandler, listenerId); +	subscribe<MousePressedEvent>(mousePressHandler, listenerId); +	subscribe<MouseReleasedEvent>(mouseReleaseHandler, listenerId); +	subscribe<MouseMovedEvent>(mouseMoveHandler, listenerId); +} + +void IMouseListener::unsubscribeEvents(int listenerId) { +	unsubscribe<MouseClickEvent>(mouseClickHandler, listenerId); +	unsubscribe<MousePressedEvent>(mousePressHandler, listenerId); +	unsubscribe<MouseReleasedEvent>(mouseReleaseHandler, listenerId); +	unsubscribe<MouseMovedEvent>(mouseMoveHandler, listenerId); +} diff --git a/mwe/events/src/inputSystem.cpp b/mwe/events/src/inputSystem.cpp new file mode 100644 index 0000000..b87b12e --- /dev/null +++ b/mwe/events/src/inputSystem.cpp @@ -0,0 +1,95 @@ +#include "inputSystem.h" + +InputSystem::InputSystem() {} + +void InputSystem::registerButton(Button * button) { buttons.push_back(button); } +void InputSystem::registerTextInput(TextInput * input) { +	textInputs.push_back(input); +} +void InputSystem::registerText(Text * label) { texts.push_back(label); } + +void InputSystem::processInput() { +	SDL_Event event; +	while (SDL_PollEvent(&event)) { +		switch (event.type) { +			case SDL_QUIT: +				triggerEvent(ShutDownEvent()); +				break; +			case SDL_KEYDOWN: +				triggerEvent( +					KeyPressedEvent(getCustomKey(event.key.keysym.sym))); +				processKeyPress(event.key.keysym.sym); +				break; +			case SDL_TEXTINPUT: +				// Process typed characters +				processTextInput(event.text.text); +				break; +			case SDL_MOUSEBUTTONDOWN: { +				int mouseX, mouseY; +				SDL_GetMouseState(&mouseX, &mouseY); +				processMouseClick(mouseX, mouseY); +				triggerEvent(MousePressedEvent(mouseX, mouseY)); +				break; +			} +		} +	} +} + +void InputSystem::processMouseClick(int mouseX, int mouseY) { +	for (auto * button : buttons) { +		if (mouseX >= button->x && mouseX <= (button->x + button->width) +			&& mouseY >= button->y && mouseY <= (button->y + button->height)) { +			button->onClick(); +		} +	} +	for (auto * textInput : textInputs) { +		if (mouseX >= textInput->x && mouseX <= textInput->x + textInput->width +			&& mouseY >= textInput->y +			&& mouseY <= textInput->y + textInput->height) { +			textInput->isActive = true; +		} else { +			textInput->isActive = false; +		} +	} +} +void InputSystem::processKeyPress(Keycode key) { +	// for (auto* textInput : textInputs) { +	//     if (textInput->isActive) { +	//         if (key == SDLK_RETURN || key == SDLK_KP_ENTER) { +	//             // Submit the text +	//             if (textInput->onSubmit) { +	//                 textInput->onSubmit(); +	//             } +	//         } +	//         else if (key == SDLK_BACKSPACE) { +	//             // Handle backspace +	//             if (!textInput->textBuffer.empty() && textInput->caretPosition > 0) { +	//                 textInput->textBuffer.erase(textInput->caretPosition - 1, 1); +	//                 textInput->caretPosition--; +	//             } +	//         } +	//         else if (key == SDLK_LEFT) { +	//             // Move caret left +	//             if (textInput->caretPosition > 0) { +	//                 textInput->caretPosition--; +	//             } +	//         } +	//         else if (key == SDLK_RIGHT) { +	//             // Move caret right +	//             if (textInput->caretPosition < textInput->textBuffer.size()) { +	//                 textInput->caretPosition++; +	//             } +	//         } +	//     } +	// } +} + +void InputSystem::processTextInput(const std::string & text) { +	// for (auto* textInput : textInputs) { +	//     if (textInput->isActive) { +	//         // Insert text at caret position +	//         textInput->textBuffer.insert(textInput->caretPosition, text); +	//         textInput->caretPosition += text.length(); +	//     } +	// } +} diff --git a/mwe/events/src/keyListenerTest.cpp b/mwe/events/src/keyListenerTest.cpp new file mode 100644 index 0000000..8446dfa --- /dev/null +++ b/mwe/events/src/keyListenerTest.cpp @@ -0,0 +1,15 @@ +#include "keyListenerTest.h" + +KeyListenerTest::KeyListenerTest(int listenerId) { +	subscribeEvents(listenerId); +} + +KeyListenerTest::~KeyListenerTest() { unsubscribeEvents(); } + +void KeyListenerTest::onKeyPressed(const KeyPressedEvent & event) { +	std::cout << "Key pressed: " << event.getKeyCode() << std::endl; +} + +void KeyListenerTest::onKeyReleased(const KeyReleasedEvent & event) { +	std::cout << "Key released: " << event.getKeyCode() << std::endl; +} diff --git a/mwe/events/src/loopManager.cpp b/mwe/events/src/loopManager.cpp index 8ecb932..0b7d888 100644 --- a/mwe/events/src/loopManager.cpp +++ b/mwe/events/src/loopManager.cpp @@ -1,22 +1,27 @@  #include "loopManager.h" -LoopManager::LoopManager() {} +LoopManager::LoopManager() : inputSystem(std::make_unique<InputSystem>()) { +	shutdownHandler +		= [this](const ShutDownEvent & event) { this->onShutdown(event); }; +	subscribe(shutdownHandler); +}  void LoopManager::processInput() { -	SDL_Event event; -	SDL_PollEvent(&event); -	switch (event.type) { -		case SDL_QUIT: -			gameRunning = false; -			break; -		case SDL_KEYDOWN: -			triggerEvent(KeyPressedEvent(getCustomKey(event.key.keysym.sym))); -			break; -		case SDL_MOUSEBUTTONDOWN: -			int x, y; -			SDL_GetMouseState(&x, &y); -			triggerEvent(MousePressedEvent(x, y)); -			break; -	} +	inputSystem->processInput(); +	// SDL_Event event; +	// SDL_PollEvent(&event); +	// switch (event.type) { +	// 	case SDL_QUIT: +	// 		gameRunning = false; +	// 		break; +	// 	case SDL_KEYDOWN: +	// 		triggerEvent(KeyPressedEvent(getCustomKey(event.key.keysym.sym))); +	// 		break; +	// 	case SDL_MOUSEBUTTONDOWN: +	// 		int x, y; +	// 		SDL_GetMouseState(&x, &y); +	// 		triggerEvent(MousePressedEvent(x, y)); +	// 		break; +	// }  }  void LoopManager::setRunning(bool running) { this->gameRunning = running; }  void LoopManager::fixedUpdate() { @@ -28,9 +33,8 @@ void LoopManager::loop() {  	while (gameRunning) {  		timer.update(); - +		processInput();  		while (timer.getLag() >= timer.getFixedDeltaTime()) { -			processInput();  			fixedUpdate();  			timer.advanceFixedUpdate();  		} @@ -66,22 +70,35 @@ void LoopManager::setup() {  			  }  		  };  	subscribe<KeyPressedEvent>(closeWindowCallback, false); +	Button * testButton = new Button(200, 200); +	testButton->color = {100, 0, 100}; +	testButton->onClick +		= []() { std::cout << "Button was clicked" << std::endl; }; +	testButton->x = 200; +	testButton->y = 200; +	inputSystem->registerButton(testButton); + +	window.addUIObject(testButton); + +	TextInput * testInput = new TextInput(200, 200); +	testInput->x = 100; +	testInput->y = 100; +	testInput->backgroundColor = {20, 50, 80}; +	inputSystem->registerTextInput(testInput); +	window.addUIObject(testInput);  }  void LoopManager::render() {  	//fprintf(stderr, "**********render********** \n");  	if (gameRunning) { -		//window.render(objectList); +		window.renderUIObjects();  	}  } - +void LoopManager::onShutdown(const ShutDownEvent & e) { +	this->gameRunning = false; +}  void LoopManager::update() {  	//fprintf(stderr, "**********normal update********** \n");  	LoopTimer & timer = LoopTimer::getInstance();  	float delta = timer.getDeltaTime(); - -	// for (int i = 0; i < objectList.size(); i++) { -	// 	objectList[i]->setX(objectList[i]->getX() + 50 * delta); -	// 	objectList[i]->setY(objectList[i]->getY() + 50 * delta); -	// }  } diff --git a/mwe/events/src/main.cpp b/mwe/events/src/main.cpp index f7e0766..d49cf74 100644 --- a/mwe/events/src/main.cpp +++ b/mwe/events/src/main.cpp @@ -1,6 +1,10 @@  #include "customTypes.h"  #include "event.h" +#include "iKeyListener.h" +#include "iMouseListener.h" +#include "keyListenerTest.h"  #include "loopManager.h" +#include "mouseListenerTest.h"  #include <SDL2/SDL.h>  #include <iostream>  #include <memory> @@ -44,10 +48,9 @@ void testCollisionEvent() {  }  int main(int argc, char * args[]) {  	LoopManager gameLoop; -	// Create an event handler for KeyPressedEvent -	// EventHandler<KeyPressedEvent> callback = [](const KeyPressedEvent& e) { -	//     onKeyPressed(e); -	// }; +	int testListenerId = 0; +	KeyListenerTest keyListener(testListenerId); +	MouseListenerTest mouseListener(testListenerId);  	// custom event class poc  	subscribe<PlayerDamagedEvent>(onPlayerDamaged);  	triggerEvent(PlayerDamagedEvent(50, 1)); diff --git a/mwe/events/src/mouseListenerTest.cpp b/mwe/events/src/mouseListenerTest.cpp new file mode 100644 index 0000000..a2a7e6d --- /dev/null +++ b/mwe/events/src/mouseListenerTest.cpp @@ -0,0 +1,27 @@ +#include "mouseListenerTest.h" + +MouseListenerTest::MouseListenerTest(int listenerId) { +	subscribeEvents(listenerId); +} + +MouseListenerTest::~MouseListenerTest() { unsubscribeEvents(); } + +void MouseListenerTest::onMouseClicked(const MouseClickEvent & event) { +	std::cout << "Mouse clicked at: (" << event.getMousePosition().first << ", " +			  << event.getMousePosition().second << ")" << std::endl; +} + +void MouseListenerTest::onMousePressed(const MousePressedEvent & event) { +	std::cout << "Mouse button pressed at: (" << event.getMousePosition().first +			  << ", " << event.getMousePosition().second << ")" << std::endl; +} + +void MouseListenerTest::onMouseReleased(const MouseReleasedEvent & event) { +	std::cout << "Mouse button released at: (" << event.getMousePosition().first +			  << ", " << event.getMousePosition().second << ")" << std::endl; +} + +void MouseListenerTest::onMouseMoved(const MouseMovedEvent & event) { +	std::cout << "Mouse moved to: (" << event.getMousePosition().first << ", " +			  << event.getMousePosition().second << ")" << std::endl; +} diff --git a/mwe/events/src/uiObject.cpp b/mwe/events/src/uiObject.cpp new file mode 100644 index 0000000..8405469 --- /dev/null +++ b/mwe/events/src/uiObject.cpp @@ -0,0 +1,24 @@ +#include "uiObject.h" + +// Constructor for UIObject +UIObject::UIObject(int width, int height) : width(width), height(height) {} + +// Constructor for Button +Button::Button(int width, int height) : UIObject(width, height) {} + +Text::Text(int width, int height) +	: UIObject(width, height), size(12), font(nullptr), +	  color{255, 255, 255} { // Default size and color +	alignment.horizontal = Alignment::Horizontal::CENTER; +	alignment.vertical = Alignment::Vertical::MIDDLE; +	alignment.mode = Alignment::PositioningMode::RELATIVE; +} + +TextInput::TextInput(int width, int height) +	: UIObject(width, height), textBuffer(""), placeholder(""), isActive(false), +	  textColor{255, 255, 255}, backgroundColor{0, 0, 0}, maxLength(100), +	  font(nullptr) { +	alignment.horizontal = Alignment::Horizontal::LEFT; +	alignment.vertical = Alignment::Vertical::TOP; +	alignment.mode = Alignment::PositioningMode::RELATIVE; +} diff --git a/mwe/events/src/uiRenderer.cpp b/mwe/events/src/uiRenderer.cpp new file mode 100644 index 0000000..9fec272 --- /dev/null +++ b/mwe/events/src/uiRenderer.cpp @@ -0,0 +1,107 @@ +#include "uiRenderer.h" + +// Constructor +UIRenderer::UIRenderer(SDL_Renderer * renderer) : renderer(renderer) {} + +// Render function +void UIRenderer::render(UIObject * uiObject) { +	if (Button * button = dynamic_cast<Button *>(uiObject)) { +		renderButton(button); +	} else if (Text * text = dynamic_cast<Text *>(uiObject)) { +		renderText(text); +	} else if (TextInput * textInput = dynamic_cast<TextInput *>(uiObject)) { +		renderTextInput(textInput); +	} +} + +// Private helper function to render a Button +void UIRenderer::renderButton(Button * button) { +	SDL_Rect buttonRect = {button->x, button->y, button->width, button->height}; +	SDL_SetRenderDrawColor(renderer, 100, 100, 255, 255); // Button color +	SDL_RenderFillRect(renderer, &buttonRect); +} + +// Private helper function to render a Text +void UIRenderer::renderText(Text * text) { +	if (text->font != nullptr) { +		SDL_Color sdlColor +			= {text->color.red, text->color.green, text->color.blue, 255}; +		SDL_Surface * textSurface +			= TTF_RenderText_Blended(text->font, text->text.c_str(), sdlColor); +		if (!textSurface) { +			std::cerr << "Error creating text surface: " << TTF_GetError() +					  << std::endl; +			return; +		} + +		SDL_Texture * textTexture +			= SDL_CreateTextureFromSurface(renderer, textSurface); +		if (!textTexture) { +			std::cerr << "Error creating texture from surface: " +					  << SDL_GetError() << std::endl; +			SDL_FreeSurface(textSurface); +			return; +		} + +		SDL_Rect textRect = {text->x, text->y, textSurface->w, textSurface->h}; +		SDL_RenderCopy(renderer, textTexture, nullptr, &textRect); +		SDL_FreeSurface(textSurface); +		SDL_DestroyTexture(textTexture); +	} +} + +void UIRenderer::renderTextInput(TextInput * textInput) { +	// // Check if textInput or renderer is null to avoid segmentation faults +	// if (!textInput || !renderer) { +	//     std::cerr << "Error: Null pointer detected for textInput or renderer." << std::endl; +	//     return; +	// } + +	// // Render the background rectangle for the text input +	// SDL_Rect inputRect = {textInput->x, textInput->y, textInput->width, textInput->height}; +	// SDL_SetRenderDrawColor(renderer, textInput->backgroundColor.red, textInput->backgroundColor.green, textInput->backgroundColor.blue, 255); +	// SDL_RenderFillRect(renderer, &inputRect); + +	// // Check if font is valid +	// if (!textInput->font) { +	//     std::cerr << "Error: Font is not loaded for textInput." << std::endl; +	//     return; +	// } + +	// SDL_Color sdlColor = {textInput->textColor.red, textInput->textColor.green, textInput->textColor.blue, 255}; + +	// if (!textInput->textBuffer.empty()) { +	//     // Render the text in the input field +	//     SDL_Surface* textSurface = TTF_RenderText_Blended(textInput->font, textInput->textBuffer.c_str(), sdlColor); +	//     if (textSurface) { +	//         SDL_Texture* textTexture = SDL_CreateTextureFromSurface(renderer, textSurface); +	//         if (textTexture) { +	//             SDL_Rect textRect = {textInput->x + 5, textInput->y + 5, textSurface->w, textSurface->h}; +	//             SDL_RenderCopy(renderer, textTexture, nullptr, &textRect); +	//             SDL_DestroyTexture(textTexture); +	//         } else { +	//             std::cerr << "Error: Unable to create texture from text surface." << std::endl; +	//         } +	//         SDL_FreeSurface(textSurface); +	//     } else { +	//         std::cerr << "Error: Unable to create text surface." << std::endl; +	//     } +	// } else if (!textInput->placeholder.empty()) { +	//     // Render the placeholder text +	//     SDL_Color placeholderColor = {128, 128, 128, 255}; // Light gray for placeholder +	//     SDL_Surface* placeholderSurface = TTF_RenderText_Blended(textInput->font, textInput->placeholder.c_str(), placeholderColor); +	//     if (placeholderSurface) { +	//         SDL_Texture* placeholderTexture = SDL_CreateTextureFromSurface(renderer, placeholderSurface); +	//         if (placeholderTexture) { +	//             SDL_Rect placeholderRect = {textInput->x + 5, textInput->y + 5, placeholderSurface->w, placeholderSurface->h}; +	//             SDL_RenderCopy(renderer, placeholderTexture, nullptr, &placeholderRect); +	//             SDL_DestroyTexture(placeholderTexture); +	//         } else { +	//             std::cerr << "Error: Unable to create texture from placeholder surface." << std::endl; +	//         } +	//         SDL_FreeSurface(placeholderSurface); +	//     } else { +	//         std::cerr << "Error: Unable to create placeholder surface." << std::endl; +	//     } +	// } +} diff --git a/mwe/events/src/window.cpp b/mwe/events/src/window.cpp index 41eb85f..f482b7f 100644 --- a/mwe/events/src/window.cpp +++ b/mwe/events/src/window.cpp @@ -1,29 +1,48 @@  #include "window.h" -WindowManager::WindowManager() {} +#include <iostream> + +WindowManager::WindowManager() { this->uiRenderer = nullptr; } +  WindowManager::~WindowManager() { destroyWindow(); } -SDL_Renderer * WindowManager::getRenderer() { return renderer; }  bool WindowManager::initWindow() {  	if (SDL_Init(SDL_INIT_EVERYTHING) != 0) { -		fprintf(stderr, "Error inititalising SDL.\n"); +		std::cerr << "Error initializing SDL.\n";  		return false;  	} +  	window = SDL_CreateWindow("SDL Tutorial", SDL_WINDOWPOS_UNDEFINED,  							  SDL_WINDOWPOS_UNDEFINED, SCREEN_WIDTH,  							  SCREEN_HEIGHT, SDL_WINDOW_SHOWN);  	if (!window) { -		fprintf(stderr, "Error creating SDL Window. \n"); +		std::cerr << "Error creating SDL Window.\n";  		return false;  	} -	renderer = SDL_CreateRenderer(window, -1, 0); + +	renderer = SDL_CreateRenderer(window, -1, SDL_RENDERER_ACCELERATED);  	if (!renderer) { -		fprintf(stderr, "Error creating SDL renderer. \n"); +		std::cerr << "Error creating SDL renderer.\n";  		return false;  	} + +	uiRenderer = new UIRenderer(renderer);  	return true;  } +  void WindowManager::destroyWindow() {  	SDL_DestroyRenderer(renderer);  	SDL_DestroyWindow(window);  	SDL_Quit();  } + +SDL_Renderer * WindowManager::getRenderer() { return renderer; } +void WindowManager::addUIObject(UIObject * uiObject) { +	uiObjects.push_back(uiObject); +} + +void WindowManager::renderUIObjects() { +	for (UIObject * obj : uiObjects) { +		uiRenderer->render(obj); +	} +	SDL_RenderPresent(this->renderer); +} |