mirror of
https://github.com/SFML/SFML.git
synced 2024-11-28 22:31:09 +08:00
Add sf::WindowBase::set{Min|Max}imumSize()
Co-authored-by: Shane Whitmire <dogunbound5@gmail.com> Co-authored-by: michael.david.howard@outlook.com <michael.david.howard@outlook.com>
This commit is contained in:
parent
c45f6378d6
commit
27249d42ed
@ -50,6 +50,8 @@ int main()
|
|||||||
// Create the main window
|
// Create the main window
|
||||||
sf::RenderWindow window(sf::VideoMode({800, 600}), "SFML graphics with OpenGL", sf::Style::Default, contextSettings);
|
sf::RenderWindow window(sf::VideoMode({800, 600}), "SFML graphics with OpenGL", sf::Style::Default, contextSettings);
|
||||||
window.setVerticalSyncEnabled(true);
|
window.setVerticalSyncEnabled(true);
|
||||||
|
window.setMinimumSize(sf::Vector2u(400, 300));
|
||||||
|
window.setMaximumSize(sf::Vector2u(1200, 900));
|
||||||
|
|
||||||
// Create a sprite for the background
|
// Create a sprite for the background
|
||||||
sf::Texture backgroundTexture;
|
sf::Texture backgroundTexture;
|
||||||
|
@ -36,6 +36,7 @@
|
|||||||
#include <SFML/System/Vector2.hpp>
|
#include <SFML/System/Vector2.hpp>
|
||||||
|
|
||||||
#include <memory>
|
#include <memory>
|
||||||
|
#include <optional>
|
||||||
|
|
||||||
|
|
||||||
namespace sf
|
namespace sf
|
||||||
@ -255,6 +256,26 @@ public:
|
|||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
void setSize(const Vector2u& size);
|
void setSize(const Vector2u& size);
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
/// \brief Set the minimum window rendering region size
|
||||||
|
///
|
||||||
|
/// Pass std::nullopt to unset the minimum size
|
||||||
|
///
|
||||||
|
/// \param minimumSize New minimum size, in pixels
|
||||||
|
///
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void setMinimumSize(const std::optional<Vector2u>& minimumSize);
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
/// \brief Set the maximum window rendering region size
|
||||||
|
///
|
||||||
|
/// Pass std::nullopt to unset the maximum size
|
||||||
|
///
|
||||||
|
/// \param maximumSize New maximum size, in pixels
|
||||||
|
///
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void setMaximumSize(const std::optional<Vector2u>& maximumSize);
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
/// \brief Change the title of the window
|
/// \brief Change the title of the window
|
||||||
///
|
///
|
||||||
|
@ -149,6 +149,20 @@ void WindowImplAndroid::setSize(const Vector2u& /* size */)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void WindowImplAndroid::setMinimumSize(const std::optional<Vector2u>& /* minimumSize */)
|
||||||
|
{
|
||||||
|
// Not applicable
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void WindowImplAndroid::setMaximumSize(const std::optional<Vector2u>& /* maximumSize */)
|
||||||
|
{
|
||||||
|
// Not applicable
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
void WindowImplAndroid::setTitle(const String& /* title */)
|
void WindowImplAndroid::setTitle(const String& /* title */)
|
||||||
{
|
{
|
||||||
|
@ -110,6 +110,26 @@ public:
|
|||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
void setSize(const Vector2u& size) override;
|
void setSize(const Vector2u& size) override;
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
/// \brief Set the minimum window rendering region size
|
||||||
|
///
|
||||||
|
/// Pass std::nullopt to unset the minimum size
|
||||||
|
///
|
||||||
|
/// \param minimumSize New minimum size, in pixels
|
||||||
|
///
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void setMinimumSize(const std::optional<Vector2u>& minimumSize) override;
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
/// \brief Set the maximum window rendering region size
|
||||||
|
///
|
||||||
|
/// Pass std::nullopt to unset the maximum size
|
||||||
|
///
|
||||||
|
/// \param maximumSize New maximum size, in pixels
|
||||||
|
///
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void setMaximumSize(const std::optional<Vector2u>& maximumSize) override;
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
/// \brief Change the title of the window
|
/// \brief Change the title of the window
|
||||||
///
|
///
|
||||||
|
@ -91,6 +91,18 @@ void WindowImplDRM::setSize(const Vector2u& /*size*/)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void WindowImplDRM::setMinimumSize(const std::optional<Vector2u>& /* minimumSize */)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void WindowImplDRM::setMaximumSize(const std::optional<Vector2u>& /* maximumSize */)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
void WindowImplDRM::setTitle(const String& /*title*/)
|
void WindowImplDRM::setTitle(const String& /*title*/)
|
||||||
{
|
{
|
||||||
|
@ -104,6 +104,26 @@ public:
|
|||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
void setSize(const Vector2u& size) override;
|
void setSize(const Vector2u& size) override;
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
/// \brief Set the minimum window rendering region size
|
||||||
|
///
|
||||||
|
/// Pass std::nullopt to unset the minimum size
|
||||||
|
///
|
||||||
|
/// \param minimumSize New minimum size, in pixels
|
||||||
|
///
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void setMinimumSize(const std::optional<Vector2u>& minimumSize) override;
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
/// \brief Set the maximum window rendering region size
|
||||||
|
///
|
||||||
|
/// Pass std::nullopt to unset the maximum size
|
||||||
|
///
|
||||||
|
/// \param maximumSize New maximum size, in pixels
|
||||||
|
///
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void setMaximumSize(const std::optional<Vector2u>& maximumSize) override;
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
/// \brief Change the title of the window
|
/// \brief Change the title of the window
|
||||||
///
|
///
|
||||||
|
@ -173,6 +173,18 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////
|
||||||
|
- (void)setMinimumSize:(NSSize)size
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////
|
||||||
|
- (void)setMaximumSize:(NSSize)size
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////
|
||||||
- (void)changeTitle:(NSString*)title
|
- (void)changeTitle:(NSString*)title
|
||||||
{
|
{
|
||||||
|
@ -471,6 +471,20 @@
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////
|
||||||
|
- (void)setMinimumSize:(NSSize)size
|
||||||
|
{
|
||||||
|
[m_window setContentMinSize:size];
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////
|
||||||
|
- (void)setMaximumSize:(NSSize)size
|
||||||
|
{
|
||||||
|
[m_window setContentMaxSize:size];
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////
|
||||||
- (void)changeTitle:(NSString*)title
|
- (void)changeTitle:(NSString*)title
|
||||||
{
|
{
|
||||||
|
@ -279,6 +279,26 @@ public:
|
|||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
void setSize(const Vector2u& size) override;
|
void setSize(const Vector2u& size) override;
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
/// \brief Set the minimum window rendering region size
|
||||||
|
///
|
||||||
|
/// Pass std::nullopt to unset the minimum size
|
||||||
|
///
|
||||||
|
/// \param minimumSize New minimum size, in pixels
|
||||||
|
///
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void setMinimumSize(const std::optional<Vector2u>& minimumSize) override;
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
/// \brief Set the maximum window rendering region size
|
||||||
|
///
|
||||||
|
/// Pass std::nullopt to unset the maximum size
|
||||||
|
///
|
||||||
|
/// \param maximumSize New maximum size, in pixels
|
||||||
|
///
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void setMaximumSize(const std::optional<Vector2u>& maximumSize) override;
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
/// \brief Change the title of the window
|
/// \brief Change the title of the window
|
||||||
///
|
///
|
||||||
|
@ -39,6 +39,7 @@
|
|||||||
#include <SFML/System/Err.hpp>
|
#include <SFML/System/Err.hpp>
|
||||||
#include <SFML/System/String.hpp>
|
#include <SFML/System/String.hpp>
|
||||||
|
|
||||||
|
#include <limits>
|
||||||
#include <ostream>
|
#include <ostream>
|
||||||
|
|
||||||
namespace sf::priv
|
namespace sf::priv
|
||||||
@ -437,6 +438,27 @@ void WindowImplCocoa::setSize(const Vector2u& size)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void WindowImplCocoa::setMinimumSize(const std::optional<Vector2u>& minimumSize)
|
||||||
|
{
|
||||||
|
WindowImpl::setMinimumSize(minimumSize);
|
||||||
|
const AutoreleasePool pool;
|
||||||
|
const NSSize size = minimumSize ? NSMakeSize(minimumSize->x, minimumSize->y) : NSMakeSize(0, 0);
|
||||||
|
[m_delegate setMinimumSize:size];
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void WindowImplCocoa::setMaximumSize(const std::optional<Vector2u>& maximumSize)
|
||||||
|
{
|
||||||
|
WindowImpl::setMaximumSize(maximumSize);
|
||||||
|
const AutoreleasePool pool;
|
||||||
|
const NSSize size = maximumSize ? NSMakeSize(maximumSize->x, maximumSize->y)
|
||||||
|
: NSMakeSize(std::numeric_limits<CGFloat>::max(), std::numeric_limits<CGFloat>::max());
|
||||||
|
[m_delegate setMaximumSize:size];
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
void WindowImplCocoa::setTitle(const String& title)
|
void WindowImplCocoa::setTitle(const String& title)
|
||||||
{
|
{
|
||||||
|
@ -151,6 +151,22 @@ class WindowImplCocoa;
|
|||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
- (void)resizeTo:(unsigned int)width by:(unsigned int)height;
|
- (void)resizeTo:(unsigned int)width by:(unsigned int)height;
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
/// \brief Set the minimize window/view size
|
||||||
|
///
|
||||||
|
/// \param size minimum size
|
||||||
|
///
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
- (void)setMinimumSize:(NSSize)size;
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
/// \brief Set the maximum window/view size
|
||||||
|
///
|
||||||
|
/// \param size maximum size
|
||||||
|
///
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
- (void)setMaximumSize:(NSSize)size;
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
/// \brief Set the window's title
|
/// \brief Set the window's title
|
||||||
///
|
///
|
||||||
|
@ -843,6 +843,22 @@ void WindowImplX11::setSize(const Vector2u& size)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void WindowImplX11::setMinimumSize(const std::optional<Vector2u>& minimumSize)
|
||||||
|
{
|
||||||
|
WindowImpl::setMinimumSize(minimumSize);
|
||||||
|
setWindowSizeConstraints();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void WindowImplX11::setMaximumSize(const std::optional<Vector2u>& maximumSize)
|
||||||
|
{
|
||||||
|
WindowImpl::setMaximumSize(maximumSize);
|
||||||
|
setWindowSizeConstraints();
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
void WindowImplX11::setTitle(const String& title)
|
void WindowImplX11::setTitle(const String& title)
|
||||||
{
|
{
|
||||||
@ -2139,4 +2155,28 @@ Vector2i WindowImplX11::getPrimaryMonitorPosition()
|
|||||||
return monitorPosition;
|
return monitorPosition;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void WindowImplX11::setWindowSizeConstraints() const
|
||||||
|
{
|
||||||
|
// Do nothing if resizing is disabled
|
||||||
|
if (m_useSizeHints)
|
||||||
|
return;
|
||||||
|
|
||||||
|
XSizeHints sizeHints{};
|
||||||
|
if (const auto minimumSize = getMinimumSize())
|
||||||
|
{
|
||||||
|
sizeHints.flags |= PMinSize;
|
||||||
|
sizeHints.min_width = static_cast<int>(minimumSize->x);
|
||||||
|
sizeHints.min_height = static_cast<int>(minimumSize->y);
|
||||||
|
}
|
||||||
|
if (const auto maximumSize = getMaximumSize())
|
||||||
|
{
|
||||||
|
sizeHints.flags |= PMaxSize;
|
||||||
|
sizeHints.max_width = static_cast<int>(maximumSize->x);
|
||||||
|
sizeHints.max_height = static_cast<int>(maximumSize->y);
|
||||||
|
}
|
||||||
|
XSetWMNormalHints(m_display, m_window, &sizeHints);
|
||||||
|
}
|
||||||
|
|
||||||
} // namespace sf::priv
|
} // namespace sf::priv
|
||||||
|
@ -111,6 +111,26 @@ public:
|
|||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
void setSize(const Vector2u& size) override;
|
void setSize(const Vector2u& size) override;
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
/// \brief Set the minimum window rendering region size
|
||||||
|
///
|
||||||
|
/// Pass std::nullopt to unset the minimum size
|
||||||
|
///
|
||||||
|
/// \param minimumSize New minimum size, in pixels
|
||||||
|
///
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void setMinimumSize(const std::optional<Vector2u>& minimumSize) override;
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
/// \brief Set the maximum window rendering region size
|
||||||
|
///
|
||||||
|
/// Pass std::nullopt to unset the maximum size
|
||||||
|
///
|
||||||
|
/// \param maximumSize New maximum size, in pixels
|
||||||
|
///
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void setMaximumSize(const std::optional<Vector2u>& maximumSize) override;
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
/// \brief Change the title of the window
|
/// \brief Change the title of the window
|
||||||
///
|
///
|
||||||
@ -291,6 +311,12 @@ private:
|
|||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
Vector2i getPrimaryMonitorPosition();
|
Vector2i getPrimaryMonitorPosition();
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
/// \brief Set min/max window size
|
||||||
|
///
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void setWindowSizeConstraints() const;
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
// Member data
|
// Member data
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
|
@ -329,13 +329,7 @@ Vector2u WindowImplWin32::getSize() const
|
|||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
void WindowImplWin32::setSize(const Vector2u& size)
|
void WindowImplWin32::setSize(const Vector2u& size)
|
||||||
{
|
{
|
||||||
// SetWindowPos wants the total size of the window (including title bar and borders),
|
const auto [width, height] = contentSizeToWindowSize(size);
|
||||||
// so we have to compute it
|
|
||||||
RECT rectangle = {0, 0, static_cast<long>(size.x), static_cast<long>(size.y)};
|
|
||||||
AdjustWindowRect(&rectangle, static_cast<DWORD>(GetWindowLongPtr(m_handle, GWL_STYLE)), false);
|
|
||||||
const int width = rectangle.right - rectangle.left;
|
|
||||||
const int height = rectangle.bottom - rectangle.top;
|
|
||||||
|
|
||||||
SetWindowPos(m_handle, nullptr, 0, 0, width, height, SWP_NOMOVE | SWP_NOZORDER);
|
SetWindowPos(m_handle, nullptr, 0, 0, width, height, SWP_NOMOVE | SWP_NOZORDER);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -560,6 +554,20 @@ void WindowImplWin32::grabCursor(bool grabbed)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
Vector2i WindowImplWin32::contentSizeToWindowSize(const Vector2u& size)
|
||||||
|
{
|
||||||
|
// SetWindowPos wants the total size of the window (including title bar and borders) so we have to compute it
|
||||||
|
RECT rectangle = {0, 0, static_cast<long>(size.x), static_cast<long>(size.y)};
|
||||||
|
AdjustWindowRect(&rectangle, static_cast<DWORD>(GetWindowLongPtr(m_handle, GWL_STYLE)), false);
|
||||||
|
const auto width = rectangle.right - rectangle.left;
|
||||||
|
const auto height = rectangle.bottom - rectangle.top;
|
||||||
|
|
||||||
|
return {width, height};
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
Keyboard::Scancode WindowImplWin32::toScancode(WPARAM wParam, LPARAM lParam)
|
Keyboard::Scancode WindowImplWin32::toScancode(WPARAM wParam, LPARAM lParam)
|
||||||
{
|
{
|
||||||
@ -780,14 +788,28 @@ void WindowImplWin32::processEvent(UINT message, WPARAM wParam, LPARAM lParam)
|
|||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
// The system request the min/max window size and position
|
// Fix violations of minimum or maximum size
|
||||||
case WM_GETMINMAXINFO:
|
case WM_GETMINMAXINFO:
|
||||||
{
|
{
|
||||||
// We override the returned information to remove the default limit
|
// We override the returned information to remove the default limit
|
||||||
// (the OS doesn't allow windows bigger than the desktop by default)
|
// (the OS doesn't allow windows bigger than the desktop by default)
|
||||||
auto* info = reinterpret_cast<MINMAXINFO*>(lParam);
|
|
||||||
info->ptMaxTrackSize.x = 50000;
|
const auto maximumSize = contentSizeToWindowSize(getMaximumSize().value_or(Vector2u(50'000, 50'000)));
|
||||||
info->ptMaxTrackSize.y = 50000;
|
|
||||||
|
MINMAXINFO& minMaxInfo = *reinterpret_cast<PMINMAXINFO>(lParam);
|
||||||
|
minMaxInfo.ptMaxTrackSize.x = maximumSize.x;
|
||||||
|
minMaxInfo.ptMaxTrackSize.y = maximumSize.y;
|
||||||
|
if (getMaximumSize().has_value())
|
||||||
|
{
|
||||||
|
minMaxInfo.ptMaxSize.x = maximumSize.x;
|
||||||
|
minMaxInfo.ptMaxSize.y = maximumSize.y;
|
||||||
|
}
|
||||||
|
if (getMinimumSize().has_value())
|
||||||
|
{
|
||||||
|
const auto minimumSize = contentSizeToWindowSize(getMinimumSize().value());
|
||||||
|
minMaxInfo.ptMinTrackSize.x = minimumSize.x;
|
||||||
|
minMaxInfo.ptMinTrackSize.y = minimumSize.y;
|
||||||
|
}
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1122,6 +1144,36 @@ void WindowImplWin32::processEvent(UINT message, WPARAM wParam, LPARAM lParam)
|
|||||||
|
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Work around Windows 10 bug
|
||||||
|
// When a maximum size is specified and the window is snapped to the edge of the display the window size is subtly too big
|
||||||
|
case WM_WINDOWPOSCHANGED:
|
||||||
|
{
|
||||||
|
WINDOWPOS& pos = *reinterpret_cast<PWINDOWPOS>(lParam);
|
||||||
|
if (pos.flags & SWP_NOSIZE)
|
||||||
|
break;
|
||||||
|
|
||||||
|
if (!getMaximumSize().has_value())
|
||||||
|
break;
|
||||||
|
const auto maximumSize = contentSizeToWindowSize(getMaximumSize().value());
|
||||||
|
|
||||||
|
bool shouldResize = false;
|
||||||
|
if (pos.cx > maximumSize.x)
|
||||||
|
{
|
||||||
|
pos.cx = maximumSize.x;
|
||||||
|
shouldResize = true;
|
||||||
|
}
|
||||||
|
if (pos.cy > maximumSize.y)
|
||||||
|
{
|
||||||
|
pos.cy = maximumSize.y;
|
||||||
|
shouldResize = true;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (shouldResize)
|
||||||
|
SetWindowPos(m_handle, pos.hwndInsertAfter, pos.x, pos.y, pos.cx, pos.cy, 0);
|
||||||
|
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -242,6 +242,16 @@ private:
|
|||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
void grabCursor(bool grabbed);
|
void grabCursor(bool grabbed);
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
/// \brief Convert content size to window size including window chrome
|
||||||
|
///
|
||||||
|
/// \param size Size to convert
|
||||||
|
///
|
||||||
|
/// \return Converted size including window chrome
|
||||||
|
///
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
Vector2i contentSizeToWindowSize(const Vector2u& size);
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
/// \brief Convert a Win32 virtual key code to a SFML key code
|
/// \brief Convert a Win32 virtual key code to a SFML key code
|
||||||
///
|
///
|
||||||
|
@ -31,8 +31,12 @@
|
|||||||
|
|
||||||
#include <SFML/System/Err.hpp>
|
#include <SFML/System/Err.hpp>
|
||||||
|
|
||||||
|
#include <algorithm>
|
||||||
|
#include <limits>
|
||||||
#include <ostream>
|
#include <ostream>
|
||||||
|
|
||||||
|
#include <cassert>
|
||||||
|
|
||||||
|
|
||||||
namespace
|
namespace
|
||||||
{
|
{
|
||||||
@ -207,11 +211,22 @@ void WindowBase::setSize(const Vector2u& size)
|
|||||||
{
|
{
|
||||||
if (m_impl)
|
if (m_impl)
|
||||||
{
|
{
|
||||||
m_impl->setSize(size);
|
// Constrain requested size within minimum and maximum bounds
|
||||||
|
const auto minimumSize = m_impl->getMinimumSize().value_or(Vector2u());
|
||||||
|
const auto maximumSize = m_impl->getMaximumSize().value_or(
|
||||||
|
Vector2u(std::numeric_limits<unsigned int>::max(), std::numeric_limits<unsigned int>::max()));
|
||||||
|
const auto width = std::clamp(size.x, minimumSize.x, maximumSize.x);
|
||||||
|
const auto height = std::clamp(size.y, minimumSize.y, maximumSize.y);
|
||||||
|
|
||||||
|
// Do nothing if requested size matches current size
|
||||||
|
const Vector2u clampedSize(width, height);
|
||||||
|
if (clampedSize == m_size)
|
||||||
|
return;
|
||||||
|
|
||||||
|
m_impl->setSize(clampedSize);
|
||||||
|
|
||||||
// Cache the new size
|
// Cache the new size
|
||||||
m_size.x = size.x;
|
m_size = clampedSize;
|
||||||
m_size.y = size.y;
|
|
||||||
|
|
||||||
// Notify the derived class
|
// Notify the derived class
|
||||||
onResize();
|
onResize();
|
||||||
@ -219,6 +234,44 @@ void WindowBase::setSize(const Vector2u& size)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void WindowBase::setMinimumSize(const std::optional<Vector2u>& minimumSize)
|
||||||
|
{
|
||||||
|
if (m_impl)
|
||||||
|
{
|
||||||
|
[[maybe_unused]] const auto validateMinimumSize = [this, minimumSize]()
|
||||||
|
{
|
||||||
|
if (!minimumSize.has_value() || !m_impl->getMaximumSize().has_value())
|
||||||
|
return true;
|
||||||
|
return minimumSize->x <= m_impl->getMaximumSize()->x && minimumSize->y <= m_impl->getMaximumSize()->y;
|
||||||
|
};
|
||||||
|
assert(validateMinimumSize() && "Minimum size cannot be bigger than the maximum size along either axis");
|
||||||
|
|
||||||
|
m_impl->setMinimumSize(minimumSize);
|
||||||
|
setSize(getSize());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void WindowBase::setMaximumSize(const std::optional<Vector2u>& maximumSize)
|
||||||
|
{
|
||||||
|
if (m_impl)
|
||||||
|
{
|
||||||
|
[[maybe_unused]] const auto validateMaxiumSize = [this, maximumSize]()
|
||||||
|
{
|
||||||
|
if (!maximumSize.has_value() || !m_impl->getMinimumSize().has_value())
|
||||||
|
return true;
|
||||||
|
return maximumSize->x >= m_impl->getMinimumSize()->x && maximumSize->y >= m_impl->getMinimumSize()->y;
|
||||||
|
};
|
||||||
|
assert(validateMaxiumSize() && "Maximum size cannot be smaller than the minimum size along either axis");
|
||||||
|
|
||||||
|
m_impl->setMaximumSize(maximumSize);
|
||||||
|
setSize(getSize());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
void WindowBase::setTitle(const String& title)
|
void WindowBase::setTitle(const String& title)
|
||||||
{
|
{
|
||||||
|
@ -135,6 +135,20 @@ WindowImpl::WindowImpl() : m_joystickStatesImpl(std::make_unique<JoystickStatesI
|
|||||||
WindowImpl::~WindowImpl() = default;
|
WindowImpl::~WindowImpl() = default;
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
std::optional<Vector2u> WindowImpl::getMinimumSize() const
|
||||||
|
{
|
||||||
|
return m_minimumSize;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
std::optional<Vector2u> WindowImpl::getMaximumSize() const
|
||||||
|
{
|
||||||
|
return m_maximumSize;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
void WindowImpl::setJoystickThreshold(float threshold)
|
void WindowImpl::setJoystickThreshold(float threshold)
|
||||||
{
|
{
|
||||||
@ -142,6 +156,20 @@ void WindowImpl::setJoystickThreshold(float threshold)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void WindowImpl::setMinimumSize(const std::optional<Vector2u>& minimumSize)
|
||||||
|
{
|
||||||
|
m_minimumSize = minimumSize;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void WindowImpl::setMaximumSize(const std::optional<Vector2u>& maximumSize)
|
||||||
|
{
|
||||||
|
m_maximumSize = maximumSize;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
bool WindowImpl::popEvent(Event& event, bool block)
|
bool WindowImpl::popEvent(Event& event, bool block)
|
||||||
{
|
{
|
||||||
|
@ -40,6 +40,7 @@
|
|||||||
#include <SFML/Window/WindowHandle.hpp>
|
#include <SFML/Window/WindowHandle.hpp>
|
||||||
|
|
||||||
#include <memory>
|
#include <memory>
|
||||||
|
#include <optional>
|
||||||
#include <queue>
|
#include <queue>
|
||||||
#include <set>
|
#include <set>
|
||||||
|
|
||||||
@ -142,6 +143,22 @@ public:
|
|||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
virtual Vector2i getPosition() const = 0;
|
virtual Vector2i getPosition() const = 0;
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
/// \brief Get the minimum window rendering region size
|
||||||
|
///
|
||||||
|
/// \return Minimum size
|
||||||
|
///
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
std::optional<Vector2u> getMinimumSize() const;
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
/// \brief Get the maximum window rendering region size
|
||||||
|
///
|
||||||
|
/// \return Maximum size
|
||||||
|
///
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
std::optional<Vector2u> getMaximumSize() const;
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
/// \brief Change the position of the window on screen
|
/// \brief Change the position of the window on screen
|
||||||
///
|
///
|
||||||
@ -166,6 +183,26 @@ public:
|
|||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
virtual void setSize(const Vector2u& size) = 0;
|
virtual void setSize(const Vector2u& size) = 0;
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
/// \brief Set the minimum window rendering region size
|
||||||
|
///
|
||||||
|
/// Pass std::nullopt to unset the minimum size
|
||||||
|
///
|
||||||
|
/// \param minimumSize New minimum size, in pixels
|
||||||
|
///
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
virtual void setMinimumSize(const std::optional<Vector2u>& minimumSize);
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
/// \brief Set the maximum window rendering region size
|
||||||
|
///
|
||||||
|
/// Pass std::nullopt to unset the maximum size
|
||||||
|
///
|
||||||
|
/// \param maximumSize New maximum size, in pixels
|
||||||
|
///
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
virtual void setMaximumSize(const std::optional<Vector2u>& maximumSize);
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
/// \brief Change the title of the window
|
/// \brief Change the title of the window
|
||||||
///
|
///
|
||||||
@ -298,6 +335,8 @@ private:
|
|||||||
Vector3f m_sensorValue[Sensor::Count]; //!< Previous value of the sensors
|
Vector3f m_sensorValue[Sensor::Count]; //!< Previous value of the sensors
|
||||||
float m_joystickThreshold{0.1f}; //!< Joystick threshold (minimum motion for "move" event to be generated)
|
float m_joystickThreshold{0.1f}; //!< Joystick threshold (minimum motion for "move" event to be generated)
|
||||||
float m_previousAxes[Joystick::Count][Joystick::AxisCount]; //!< Position of each axis last time a move event triggered, in range [-100, 100]
|
float m_previousAxes[Joystick::Count][Joystick::AxisCount]; //!< Position of each axis last time a move event triggered, in range [-100, 100]
|
||||||
|
std::optional<Vector2u> m_minimumSize; //!< Minimum window size
|
||||||
|
std::optional<Vector2u> m_maximumSize; //!< Maximum window size
|
||||||
};
|
};
|
||||||
|
|
||||||
} // namespace priv
|
} // namespace priv
|
||||||
|
@ -105,6 +105,26 @@ public:
|
|||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
void setSize(const Vector2u& size) override;
|
void setSize(const Vector2u& size) override;
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
/// \brief Set the minimum window rendering region size
|
||||||
|
///
|
||||||
|
/// Pass std::nullopt to unset the minimum size
|
||||||
|
///
|
||||||
|
/// \param minimumSize New minimum size, in pixels
|
||||||
|
///
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void setMinimumSize(const std::optional<Vector2u>& minimumSize) override;
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
/// \brief Set the maximum window rendering region size
|
||||||
|
///
|
||||||
|
/// Pass std::nullopt to unset the maximum size
|
||||||
|
///
|
||||||
|
/// \param maximumSize New maximum size, in pixels
|
||||||
|
///
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void setMaximumSize(const std::optional<Vector2u>& maximumSize) override;
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
/// \brief Change the title of the window
|
/// \brief Change the title of the window
|
||||||
///
|
///
|
||||||
|
@ -146,6 +146,20 @@ void WindowImplUIKit::setSize(const Vector2u& size)
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void WindowImplUIKit::setMinimumSize(const std::optional<Vector2u>& /* minimumSize */)
|
||||||
|
{
|
||||||
|
// Not applicable
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////
|
||||||
|
void WindowImplUIKit::setMaximumSize(const std::optional<Vector2u>& /* maximumSize */)
|
||||||
|
{
|
||||||
|
// Not applicable
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////
|
||||||
void WindowImplUIKit::setTitle(const String& /* title */)
|
void WindowImplUIKit::setTitle(const String& /* title */)
|
||||||
{
|
{
|
||||||
|
@ -89,7 +89,7 @@ TEST_CASE("[Window] sf::WindowBase" * doctest::skip(skipDisplayTests))
|
|||||||
CHECK(!windowBase.waitEvent(event));
|
CHECK(!windowBase.waitEvent(event));
|
||||||
}
|
}
|
||||||
|
|
||||||
SUBCASE("Get/set position")
|
SUBCASE("Set/get position")
|
||||||
{
|
{
|
||||||
sf::WindowBase windowBase;
|
sf::WindowBase windowBase;
|
||||||
windowBase.setPosition({12, 34});
|
windowBase.setPosition({12, 34});
|
||||||
@ -111,5 +111,37 @@ TEST_CASE("[Window] sf::WindowBase" * doctest::skip(skipDisplayTests))
|
|||||||
windowBase.setSize({128, 256});
|
windowBase.setSize({128, 256});
|
||||||
CHECK(windowBase.getSize() == sf::Vector2u(128, 256));
|
CHECK(windowBase.getSize() == sf::Vector2u(128, 256));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
SUBCASE("Minimum size")
|
||||||
|
{
|
||||||
|
sf::WindowBase windowBase(sf::VideoMode({360, 240}), "WindowBase Tests");
|
||||||
|
windowBase.setMinimumSize(sf::Vector2u(128, 256));
|
||||||
|
windowBase.setSize({100, 100});
|
||||||
|
CHECK(windowBase.getSize() == sf::Vector2u(128, 256));
|
||||||
|
}
|
||||||
|
|
||||||
|
SUBCASE("Maximum size")
|
||||||
|
{
|
||||||
|
sf::WindowBase windowBase(sf::VideoMode({360, 240}), "WindowBase Tests");
|
||||||
|
windowBase.setMaximumSize(sf::Vector2u(128, 256));
|
||||||
|
windowBase.setSize({400, 400});
|
||||||
|
CHECK(windowBase.getSize() == sf::Vector2u(128, 256));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
SUBCASE("setMinimumSize()")
|
||||||
|
{
|
||||||
|
sf::WindowBase windowBase(sf::VideoMode({100, 100}), "WindowBase Tests", sf::Style::Default ^ sf::Style::Resize);
|
||||||
|
windowBase.setMinimumSize(sf::Vector2u(200, 300));
|
||||||
|
CHECK(windowBase.getSize() == sf::Vector2u(200, 300));
|
||||||
|
windowBase.setMaximumSize(sf::Vector2u(200, 300));
|
||||||
|
}
|
||||||
|
|
||||||
|
SUBCASE("setMinimumSize()")
|
||||||
|
{
|
||||||
|
sf::WindowBase windowBase(sf::VideoMode({400, 400}), "WindowBase Tests", sf::Style::Default ^ sf::Style::Resize);
|
||||||
|
windowBase.setMaximumSize(sf::Vector2u(200, 300));
|
||||||
|
CHECK(windowBase.getSize() == sf::Vector2u(200, 300));
|
||||||
|
windowBase.setMinimumSize(sf::Vector2u(200, 300));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user