diff --git a/config.def.h b/config.def.h
index 6eb617b..e8ce95f 100644
--- a/config.def.h
+++ b/config.def.h
@@ -38,10 +38,12 @@ static const Key keys[] = {
 	{ MODKEY,                    XKB_KEY_k,          focusstack,     {.i = -1} },
 	{ MODKEY,                    XKB_KEY_t,          setlayout,      {.v = &layouts[0]} },
 	{ MODKEY,                    XKB_KEY_f,          setlayout,      {.v = &layouts[1]} },
+	{ MODKEY|WLR_MODIFIER_SHIFT, XKB_KEY_space,      togglefloating, {0} },
 	{ MODKEY|WLR_MODIFIER_SHIFT, XKB_KEY_Q,          quit,           {0} },
 };
 
 static const Button buttons[] = {
-	{ MODKEY, BTN_LEFT,  movemouse,   {0} },
-	{ MODKEY, BTN_RIGHT, resizemouse, {0} },
+	{ MODKEY, BTN_LEFT,   movemouse,      {0} },
+	{ MODKEY, BTN_MIDDLE, togglefloating, {0} },
+	{ MODKEY, BTN_RIGHT,  resizemouse,    {0} },
 };
diff --git a/dwl.c b/dwl.c
index 58dd523..316d29b 100644
--- a/dwl.c
+++ b/dwl.c
@@ -64,6 +64,7 @@ typedef struct {
 	struct wl_listener request_resize;
 	Monitor *mon;
 	int x, y; /* layout-relative */
+	int isfloating;
 } Client;
 
 typedef struct {
@@ -147,6 +148,7 @@ static void setlayout(const Arg *arg);
 static void setup(void);
 static void spawn(const Arg *arg);
 static void tile(Monitor *m);
+static void togglefloating(const Arg *arg);
 static void unmapnotify(struct wl_listener *listener, void *data);
 static Client *xytoclient(double x, double y,
 		struct wlr_surface **surface, double *sx, double *sy);
@@ -649,6 +651,9 @@ movemouse(const Arg *arg)
 	cursor_mode = CurMove;
 	grabsx = cursor->x - c->x;
 	grabsy = cursor->y - c->y;
+	/* Float the window */
+	if (!grabc->isfloating && selmon->lt[selmon->sellt]->arrange)
+		grabc->isfloating = 1;
 }
 
 void
@@ -804,6 +809,9 @@ resizemouse(const Arg *arg)
 	/* Prepare for resizing client in motionnotify */
 	grabc = c;
 	cursor_mode = CurResize;
+	/* Float the window */
+	if (!grabc->isfloating && selmon->lt[selmon->sellt]->arrange)
+		grabc->isfloating = 1;
 }
 
 void
@@ -1025,7 +1033,7 @@ tile(Monitor *m)
 	struct wlr_box ca;
 
 	wl_list_for_each(c, &clients, link) {
-		if (VISIBLEON(c, m))
+		if (VISIBLEON(c, m) && !c->isfloating)
 			n++;
 	}
 	if (n == 0)
@@ -1037,7 +1045,7 @@ tile(Monitor *m)
 		mw = m->ww;
 	i = my = ty = 0;
 	wl_list_for_each(c, &clients, link) {
-		if (!VISIBLEON(c, m))
+		if (!VISIBLEON(c, m) || c->isfloating)
 			continue;
 		wlr_xdg_surface_get_geometry(c->xdg_surface, &ca);
 		if (i < m->nmaster) {
@@ -1053,6 +1061,16 @@ tile(Monitor *m)
 	}
 }
 
+void
+togglefloating(const Arg *arg)
+{
+	Client *sel = selclient();
+	if (!sel)
+		return;
+	/* return if fullscreen */
+	sel->isfloating = !sel->isfloating /* || sel->isfixed */;
+}
+
 void
 unmapnotify(struct wl_listener *listener, void *data)
 {