#ifndef _LAYOUT_H
#define _LAYOUT_H
+/**
+ * Gets the unoccupied space (= space which is available for windows which were resized by the user)
+ * for the given row. This is necessary to render both, customly resized windows and never touched
+ * windows correctly, meaning that the aspect ratio will be maintained when opening new windows.
+ *
+ */
+int get_unoccupied_x(Workspace *workspace, int row);
+
/**
* (Re-)draws window decorations for a given Client onto the given drawable/graphic context.
* When in stacking mode, the window decorations are drawn onto an own window.
return 1;
}
+ /* Save the old unoccupied space to re-evaluate the other containers (not first or second) later */
+ int old_unoccupied_x = get_unoccupied_x(ws, first->row);
+
/* Convert 0 (for default width_factor) to actual numbers */
if (first->width_factor == 0)
first->width_factor = ((float)ws->rect.width / ws->cols) / ws->rect.width;
+ else first->width_factor = ((first->width_factor * old_unoccupied_x) / ws->rect.width);
+
if (second->width_factor == 0)
second->width_factor = ((float)ws->rect.width / ws->cols) / ws->rect.width;
+ else second->width_factor = ((second->width_factor * old_unoccupied_x) / ws->rect.width);
+
+ LOG("\n\n\n");
+
+ LOG("old_unoccupied_x = %d\n", old_unoccupied_x);
+
+ LOG("Old first->width_factor = %f\n", first->width_factor);
+ LOG("Old second->width_factor = %f\n", second->width_factor);
first->width_factor *= (float)(first->width + (new_position - event->root_x)) / first->width;
second->width_factor *= (float)(second->width - (new_position - event->root_x)) / second->width;
+
+ LOG("new unoccupied_x = %d\n", get_unoccupied_x(ws, first->row));
+ LOG("old_unoccupied_x = %d\n", old_unoccupied_x);
+
+ for (int col = 0; col < ws->cols; col++) {
+ Container *con = ws->table[col][first->row];
+ if (con == first || con == second)
+ continue;
+
+ LOG("Updating other container (current width_factor = %f)\n", con->width_factor);
+ con->width_factor = ((con->width_factor * old_unoccupied_x) / get_unoccupied_x(ws, first->row));
+ LOG("to %f\n", con->width_factor);
+ }
+
+ LOG("New first->width_factor = %f\n", first->width_factor);
+ LOG("New second->width_factor = %f\n", second->width_factor);
+
+ LOG("\n\n\n");
} else {
LOG("Resize was from Y = %d to Y = %d\n", event->root_y, new_position);
if (event->root_y == new_position) {
for (int cols = 0; cols < workspace->cols;) {
Container *con = workspace->table[cols][row];
LOG("width_factor[%d][%d] = %f, colspan = %d\n", cols, row, con->width_factor, con->colspan);
- if (con->width_factor == 0)
+ if (con->width_factor == 0) {
+ LOG("- %d * %f * %d = %f\n", workspace->rect.width, default_factor, con->colspan, workspace->rect.width * default_factor * con->colspan);
unoccupied -= workspace->rect.width * default_factor * con->colspan;
+ }
cols += con->colspan;
}
- assert(unoccupied != 0);
-
LOG("unoccupied space: %d\n", unoccupied);
return unoccupied;
}
rows += con->rowspan;
}
- assert(unoccupied != 0);
-
LOG("unoccupied space: %d\n", unoccupied);
return unoccupied;
}
if (old_container->mode == MODE_STACK)
leave_stack_mode(conn, old_container);
+ /* We need to distribute the space which will now be freed to other containers */
+ if (old_container->width_factor > 0) {
+ Container *dest_container = NULL;
+ /* Check if we got a container to the left… */
+ if (col > 0)
+ dest_container = workspace->table[col-1][row];
+ /* …or to the right */
+ else if ((col+1) < workspace->cols)
+ dest_container = workspace->table[col+1][row];
+
+ if (dest_container != NULL) {
+ if (dest_container->width_factor == 0)
+ dest_container->width_factor = ((float)workspace->rect.width / workspace->cols) / workspace->rect.width;
+ LOG("dest_container->width_factor = %f\n", dest_container->width_factor);
+ dest_container->width_factor += old_container->width_factor;
+ LOG("afterwards it's %f\n", dest_container->width_factor);
+ }
+ }
+
free(old_container);
}