Merge pull request #1367 from psychon/resizes
Fix some possible errors with resizes. Fixes https://github.com/awesomeWM/awesome/issues/1368.
This commit is contained in:
commit
162685bf30
|
@ -1176,12 +1176,33 @@ client_geometry_refresh(void)
|
||||||
area_t real_geometry = c->geometry;
|
area_t real_geometry = c->geometry;
|
||||||
if (!c->fullscreen)
|
if (!c->fullscreen)
|
||||||
{
|
{
|
||||||
|
if ((real_geometry.width < c->titlebar[CLIENT_TITLEBAR_LEFT].size
|
||||||
|
+ c->titlebar[CLIENT_TITLEBAR_RIGHT].size) ||
|
||||||
|
(real_geometry.height < c->titlebar[CLIENT_TITLEBAR_TOP].size
|
||||||
|
+ c->titlebar[CLIENT_TITLEBAR_BOTTOM].size))
|
||||||
|
warn("Resizing a window to a negative size!? Have width %d-%d-%d=%d"
|
||||||
|
" and height %d-%d-%d=%d", real_geometry.width,
|
||||||
|
c->titlebar[CLIENT_TITLEBAR_LEFT].size,
|
||||||
|
c->titlebar[CLIENT_TITLEBAR_RIGHT].size,
|
||||||
|
real_geometry.width -
|
||||||
|
c->titlebar[CLIENT_TITLEBAR_LEFT].size -
|
||||||
|
c->titlebar[CLIENT_TITLEBAR_RIGHT].size,
|
||||||
|
real_geometry.height,
|
||||||
|
c->titlebar[CLIENT_TITLEBAR_TOP].size,
|
||||||
|
c->titlebar[CLIENT_TITLEBAR_BOTTOM].size,
|
||||||
|
real_geometry.height -
|
||||||
|
c->titlebar[CLIENT_TITLEBAR_TOP].size -
|
||||||
|
c->titlebar[CLIENT_TITLEBAR_BOTTOM].size);
|
||||||
|
|
||||||
real_geometry.x = c->titlebar[CLIENT_TITLEBAR_LEFT].size;
|
real_geometry.x = c->titlebar[CLIENT_TITLEBAR_LEFT].size;
|
||||||
real_geometry.y = c->titlebar[CLIENT_TITLEBAR_TOP].size;
|
real_geometry.y = c->titlebar[CLIENT_TITLEBAR_TOP].size;
|
||||||
real_geometry.width -= c->titlebar[CLIENT_TITLEBAR_LEFT].size;
|
real_geometry.width -= c->titlebar[CLIENT_TITLEBAR_LEFT].size;
|
||||||
real_geometry.width -= c->titlebar[CLIENT_TITLEBAR_RIGHT].size;
|
real_geometry.width -= c->titlebar[CLIENT_TITLEBAR_RIGHT].size;
|
||||||
real_geometry.height -= c->titlebar[CLIENT_TITLEBAR_TOP].size;
|
real_geometry.height -= c->titlebar[CLIENT_TITLEBAR_TOP].size;
|
||||||
real_geometry.height -= c->titlebar[CLIENT_TITLEBAR_BOTTOM].size;
|
real_geometry.height -= c->titlebar[CLIENT_TITLEBAR_BOTTOM].size;
|
||||||
|
|
||||||
|
if (real_geometry.width == 0 || real_geometry.height == 0)
|
||||||
|
warn("Resizing a window to size zero!?");
|
||||||
} else {
|
} else {
|
||||||
real_geometry.x = 0;
|
real_geometry.x = 0;
|
||||||
real_geometry.y = 0;
|
real_geometry.y = 0;
|
||||||
|
@ -1678,6 +1699,17 @@ client_resize(client_t *c, area_t geometry, bool honor_hints)
|
||||||
if(geometry.y + geometry.height < 0)
|
if(geometry.y + geometry.height < 0)
|
||||||
geometry.y = 0;
|
geometry.y = 0;
|
||||||
|
|
||||||
|
if (honor_hints) {
|
||||||
|
/* We could get integer underflows in client_remove_titlebar_geometry()
|
||||||
|
* without these checks here.
|
||||||
|
*/
|
||||||
|
if(geometry.width < c->titlebar[CLIENT_TITLEBAR_LEFT].size + c->titlebar[CLIENT_TITLEBAR_RIGHT].size)
|
||||||
|
return false;
|
||||||
|
if(geometry.height < c->titlebar[CLIENT_TITLEBAR_TOP].size + c->titlebar[CLIENT_TITLEBAR_BOTTOM].size)
|
||||||
|
return false;
|
||||||
|
geometry = client_apply_size_hints(c, geometry);
|
||||||
|
}
|
||||||
|
|
||||||
if(geometry.width < c->titlebar[CLIENT_TITLEBAR_LEFT].size + c->titlebar[CLIENT_TITLEBAR_RIGHT].size)
|
if(geometry.width < c->titlebar[CLIENT_TITLEBAR_LEFT].size + c->titlebar[CLIENT_TITLEBAR_RIGHT].size)
|
||||||
return false;
|
return false;
|
||||||
if(geometry.height < c->titlebar[CLIENT_TITLEBAR_TOP].size + c->titlebar[CLIENT_TITLEBAR_BOTTOM].size)
|
if(geometry.height < c->titlebar[CLIENT_TITLEBAR_TOP].size + c->titlebar[CLIENT_TITLEBAR_BOTTOM].size)
|
||||||
|
@ -1686,9 +1718,6 @@ client_resize(client_t *c, area_t geometry, bool honor_hints)
|
||||||
if(geometry.width == 0 || geometry.height == 0)
|
if(geometry.width == 0 || geometry.height == 0)
|
||||||
return false;
|
return false;
|
||||||
|
|
||||||
if (honor_hints)
|
|
||||||
geometry = client_apply_size_hints(c, geometry);
|
|
||||||
|
|
||||||
if(!AREA_EQUAL(c->geometry, geometry))
|
if(!AREA_EQUAL(c->geometry, geometry))
|
||||||
{
|
{
|
||||||
client_resize_do(c, geometry);
|
client_resize_do(c, geometry);
|
||||||
|
|
|
@ -5,30 +5,47 @@ local spawn = require("awful.spawn")
|
||||||
|
|
||||||
local test_client_source = [[
|
local test_client_source = [[
|
||||||
local lgi = require 'lgi'
|
local lgi = require 'lgi'
|
||||||
|
local Gdk = lgi.require('Gdk')
|
||||||
local Gtk = lgi.require('Gtk')
|
local Gtk = lgi.require('Gtk')
|
||||||
local Gio = lgi.require('Gio')
|
local Gio = lgi.require('Gio')
|
||||||
Gtk.init()
|
Gtk.init()
|
||||||
|
|
||||||
local function open_window(class, title, snid)
|
local function open_window(class, title, options)
|
||||||
local window = Gtk.Window {
|
local window = Gtk.Window {
|
||||||
default_width = 100,
|
default_width = 100,
|
||||||
default_height = 100,
|
default_height = 100,
|
||||||
title = title
|
title = title
|
||||||
}
|
}
|
||||||
if snid ~= "" then
|
if options.snid and options.snid ~= "" then
|
||||||
window:set_startup_id(snid)
|
window:set_startup_id(options.snid)
|
||||||
|
end
|
||||||
|
if options.resize_increment then
|
||||||
|
local geom = Gdk.Geometry {
|
||||||
|
width_inc = 200,
|
||||||
|
height_inc = 200,
|
||||||
|
}
|
||||||
|
window:set_geometry_hints(nil, geom, Gdk.WindowHints.RESIZE_INC)
|
||||||
end
|
end
|
||||||
window:set_wmclass(class, class)
|
window:set_wmclass(class, class)
|
||||||
window:show_all()
|
window:show_all()
|
||||||
end
|
end
|
||||||
|
|
||||||
|
local function parse_options(options)
|
||||||
|
local result = {}
|
||||||
|
for word in string.gmatch(options, "([^,]+)") do
|
||||||
|
local key, value = string.match(word, "([^=]+)=?(.*)")
|
||||||
|
result[key] = value
|
||||||
|
end
|
||||||
|
return result
|
||||||
|
end
|
||||||
|
|
||||||
-- Start a coroutine for nicer input handling
|
-- Start a coroutine for nicer input handling
|
||||||
local coro = coroutine.wrap(function()
|
local coro = coroutine.wrap(function()
|
||||||
while true do
|
while true do
|
||||||
local class = coroutine.yield()
|
local class = coroutine.yield()
|
||||||
local title = coroutine.yield()
|
local title = coroutine.yield()
|
||||||
local snid = coroutine.yield()
|
local options = coroutine.yield()
|
||||||
open_window(class, title, snid)
|
open_window(class, title, parse_options(options))
|
||||||
end
|
end
|
||||||
end)
|
end)
|
||||||
coro()
|
coro()
|
||||||
|
@ -86,13 +103,21 @@ local function get_snid(sn_rules, callback)
|
||||||
return snid
|
return snid
|
||||||
end
|
end
|
||||||
|
|
||||||
return function(class, title, sn_rules, callback)
|
return function(class, title, sn_rules, callback, resize_increment)
|
||||||
class = class or "test_app"
|
class = class or "test_app"
|
||||||
title = title or "Awesome test client"
|
title = title or "Awesome test client"
|
||||||
|
|
||||||
init()
|
init()
|
||||||
local snid = (sn_rules or callback) and get_snid(sn_rules, callback) or ""
|
local options = ""
|
||||||
local data = class .. "\n" .. title .. "\n" .. snid .. "\n"
|
local snid
|
||||||
|
if sn_rules or callback then
|
||||||
|
snid = get_snid(sn_rules, callback)
|
||||||
|
options = options .. "snid=" .. snid .. ","
|
||||||
|
end
|
||||||
|
if resize_increment then
|
||||||
|
options = options .. "resize_increment,"
|
||||||
|
end
|
||||||
|
local data = class .. "\n" .. title .. "\n" .. options .. "\n"
|
||||||
local success, msg = pipe:write_all(data)
|
local success, msg = pipe:write_all(data)
|
||||||
assert(success, tostring(msg))
|
assert(success, tostring(msg))
|
||||||
|
|
||||||
|
|
|
@ -439,6 +439,37 @@ table.insert(steps, function()
|
||||||
return true
|
return true
|
||||||
end)
|
end)
|
||||||
|
|
||||||
|
table.insert(steps, function()
|
||||||
|
for _, c in pairs(client.get()) do
|
||||||
|
c:kill()
|
||||||
|
end
|
||||||
|
if #client.get() == 0 then
|
||||||
|
test_client(nil, nil, nil, nil, true)
|
||||||
|
return true
|
||||||
|
end
|
||||||
|
end)
|
||||||
|
|
||||||
|
table.insert(steps, function()
|
||||||
|
if #client.get() ~= 1 then
|
||||||
|
return
|
||||||
|
end
|
||||||
|
|
||||||
|
local c = client.get()[1]
|
||||||
|
local geo = c:geometry()
|
||||||
|
local hints = c.size_hints
|
||||||
|
assert(hints.height_inc == 200)
|
||||||
|
assert(hints.width_inc == 200)
|
||||||
|
assert(c:apply_size_hints(1, 1) == 0)
|
||||||
|
|
||||||
|
c:geometry { width = 1, height = 50 }
|
||||||
|
|
||||||
|
-- The above should be rejected, because it would make us resize the
|
||||||
|
-- window size 0x0.
|
||||||
|
assert(c:geometry().width == geo.width)
|
||||||
|
assert(c:geometry().height == geo.height)
|
||||||
|
return true
|
||||||
|
end)
|
||||||
|
|
||||||
require("_runner").run_steps(steps)
|
require("_runner").run_steps(steps)
|
||||||
|
|
||||||
-- vim: filetype=lua:expandtab:shiftwidth=4:tabstop=8:softtabstop=4:textwidth=80
|
-- vim: filetype=lua:expandtab:shiftwidth=4:tabstop=8:softtabstop=4:textwidth=80
|
||||||
|
|
Loading…
Reference in New Issue