diff --git a/src/PuzzleSingleImageState.cpp b/src/PuzzleSingleImageState.cpp index 2438494..d87ce0a 100644 --- a/src/PuzzleSingleImageState.cpp +++ b/src/PuzzleSingleImageState.cpp @@ -34,6 +34,7 @@ https://github.com/sago007/saland PuzzleSingleImageState::PuzzleSingleImageState() { std::map config = LoadConfigMap(); flipMode = GetConfigBool(config, "flipMode", false); + rectangularMode = GetConfigBool(config, "rectangularMode", false); } PuzzleSingleImageState::~PuzzleSingleImageState() { @@ -104,7 +105,8 @@ void PuzzleSingleImageState::Draw(SDL_Renderer* target) { Uint8 alpha = 255; alpha = static_cast(255 * ((swapAnimationTime - swapAnimationDuration) / swapAnimationDuration)); SDL_SetTextureAlphaMod(this->pictureTex, alpha); - } else { + } + else { SDL_SetTextureAlphaMod(this->pictureTex, 255); } @@ -147,6 +149,14 @@ void PuzzleSingleImageState::Draw(SDL_Renderer* target) { SaveConfigMap(config); Shuffle(); } + if (ImGui::MenuItem("Rectangular Mode", nullptr, rectangularMode)) { + rectangularMode = !rectangularMode; + // Save the updated configuration + std::map config = LoadConfigMap(); + SetConfigBool(config, "rectangularMode", rectangularMode); + SaveConfigMap(config); + // Note: Need to reload the image to apply the new piece generation mode + } ImGui::EndMenu(); } ImGui::EndMainMenuBar(); @@ -270,15 +280,24 @@ void PuzzleSingleImageState::LoadPictureFromFile(const std::string& filename, SD SDL_FreeSurface(bitmapSurface); SDL_SetTextureBlendMode(this->pictureTex, SDL_BLENDMODE_BLEND); pieces_logical.clear(); - SDL_Rect piece; - piece.x = 0; - piece.y = 0; - piece.h = resized_image_logical_height; - piece.w = resized_image_logical_width; - pieces_logical.push_back(piece); - for (int i = 0; i<10; ++i) { - SplitPiece(); + + if (rectangularMode) { + // Create a 4x4 grid of rectangular pieces + CreateRectangularPieces(4, 4); + } + else { + // Use the original splitting algorithm + SDL_Rect piece; + piece.x = 0; + piece.y = 0; + piece.h = resized_image_logical_height; + piece.w = resized_image_logical_width; + pieces_logical.push_back(piece); + for (int i = 0; i<10; ++i) { + SplitPiece(); + } } + ResizeImagePhysical(); Shuffle(); } @@ -332,6 +351,69 @@ void PuzzleSingleImageState::SplitPiece() { } } +void PuzzleSingleImageState::CreateRectangularPieces(int rows, int cols) { + pieces_logical.clear(); + srand(time(NULL)); + + int num_pieces = rows * cols; + int attempts = 0; + const int max_attempts = num_pieces * 100; + + // Try to place non-overlapping rectangles + while (pieces_logical.size() < num_pieces && attempts < max_attempts) { + attempts++; + + // Random size within reasonable bounds + int piece_width = min_piece_size + rand() % (resized_image_logical_width / 3); + int piece_height = min_piece_size + rand() % (resized_image_logical_height / 3); + + // Ensure pieces aren't too large + if (piece_width > resized_image_logical_width / 2) { + piece_width = resized_image_logical_width / 2; + } + if (piece_height > resized_image_logical_height / 2) { + piece_height = resized_image_logical_height / 2; + } + + // Random position + int max_x = resized_image_logical_width - piece_width; + int max_y = resized_image_logical_height - piece_height; + if (max_x < 0) { + max_x = 0; + } + if (max_y < 0) { + max_y = 0; + } + + int piece_x = rand() % (max_x + 1); + int piece_y = rand() % (max_y + 1); + + SDL_Rect candidate; + candidate.x = piece_x; + candidate.y = piece_y; + candidate.w = piece_width; + candidate.h = piece_height; + + // Check for overlaps with existing pieces + bool overlaps = false; + for (const SDL_Rect& existing : pieces_logical) { + if (SDL_HasIntersection(&candidate, &existing)) { + overlaps = true; + break; + } + } + + if (!overlaps) { + pieces_logical.push_back(candidate); + } + } + + // If we couldn't place enough pieces, fill remaining space with grid pieces + if (pieces_logical.size() < num_pieces) { + std::cerr << "Warning: Could only place " << pieces_logical.size() << " non-overlapping pieces out of " << num_pieces << " requested\n"; + } +} + void PuzzleSingleImageState::ClearPicture() { if (this->pictureTex) { SDL_DestroyTexture(this->pictureTex); diff --git a/src/PuzzleSingleImageState.hpp b/src/PuzzleSingleImageState.hpp index 5a2b8fd..25d8fe1 100644 --- a/src/PuzzleSingleImageState.hpp +++ b/src/PuzzleSingleImageState.hpp @@ -45,6 +45,7 @@ public: void SplitPiece(size_t piece_number); void SplitPieceVertical(size_t piece_number); void SplitPieceHorisontal(size_t piece_number); + void CreateRectangularPieces(int rows, int cols); void Shuffle(); void CheckSolved(); @@ -53,6 +54,7 @@ public: void CreatePhysicalPieces(); bool flipMode = false; + bool rectangularMode = false; private: void ClearPicture();