Implementing a selection rectangle involves tracking the start and current positions of a drag operation to define the rectangle's bounds. Here's how to create one:
#include <SDL.h>
#include <iostream>
#include "Window.h"
class SelectionBox {
public:
void Tick() {
int MouseX, MouseY;
Uint32 Buttons = SDL_GetMouseState(
&MouseX, &MouseY);
if (Buttons & SDL_BUTTON_LMASK) {
if (!IsSelecting) {
// Start new selection
StartX = MouseX;
StartY = MouseY;
IsSelecting = true;
}
// Calculate rectangle bounds
CurrentX = MouseX;
CurrentY = MouseY;
int Left = std::min(StartX, CurrentX);
int Right = std::max(StartX, CurrentX);
int Top = std::min(StartY, CurrentY);
int Bottom = std::max(StartY, CurrentY);
int Width = Right - Left;
int Height = Bottom - Top;
std::cout << "Selection: Position("
<< Left << ", " << Top << ") "
<< "Size(" << Width << ", "
<< Height << ")\n";
} else if (IsSelecting) {
// Selection complete
IsSelecting = false;
PrintFinalSelection();
}
}
private:
bool IsSelecting{false};
int StartX{0}, StartY{0};
int CurrentX{0}, CurrentY{0};
void PrintFinalSelection() {
int Left = std::min(StartX, CurrentX);
int Right = std::max(StartX, CurrentX);
int Top = std::min(StartY, CurrentY);
int Bottom = std::max(StartY, CurrentY);
std::cout << "Final selection area: ("
<< Left << ", " << Top << ") to ("
<< Right << ", " << Bottom << ")\n";
}
};
int main(int argc, char** argv) {
SDL_Init(SDL_INIT_VIDEO);
Window GameWindow;
SelectionBox Selection;
SDL_Event E;
while (true) {
while (SDL_PollEvent(&E)) {
// Handle other events...
}
Selection.Tick();
GameWindow.Update();
}
SDL_Quit();
return 0;
}
Selection: Position(100, 150) Size(5, 3)
Selection: Position(100, 150) Size(10, 8)
Selection: Position(100, 150) Size(15, 12)
Final selection area: (100, 150) to (115, 162)
The selection rectangle system works by:
Here's an enhanced version that includes minimum size and snapping:
#include <SDL.h>
class AdvancedSelectionBox {
public:
void Tick() {
int MouseX, MouseY;
Uint32 Buttons = SDL_GetMouseState(
&MouseX, &MouseY);
if (Buttons & SDL_BUTTON_LMASK) {
if (!IsSelecting) {
StartX = MouseX;
StartY = MouseY;
IsSelecting = true;
}
CurrentX = MouseX;
CurrentY = MouseY;
// Add minimum size requirement
int Width = std::abs(CurrentX - StartX);
int Height = std::abs(CurrentY - StartY);
if (Width < MinimumSize) {
CurrentX = StartX + (CurrentX > StartX
? MinimumSize : -MinimumSize);
}
if (Height < MinimumSize) {
CurrentY = StartY + (CurrentY > StartY
? MinimumSize : -MinimumSize);
}
// Snap to grid
CurrentX = (CurrentX / GridSize) * GridSize;
CurrentY = (CurrentY / GridSize) * GridSize;
PrintSelection();
} else if (IsSelecting) {
IsSelecting = false;
PrintFinalSelection();
}
}
private:
static const int MinimumSize = 10;
static const int GridSize = 8;
bool IsSelecting{false};
int StartX{0}, StartY{0};
int CurrentX{0}, CurrentY{0};
};
This enhanced version includes:
The system is flexible enough to be used for many purposes:
Answers to questions are automatically generated and may not have been reviewed.
Learn how to monitor mouse position and button states in real-time using SDL's state query functions