implement moveWindowUp/Down/Left/Right
authorDana Jansens <danakj@orodu.net>
Sat, 20 Jul 2002 18:16:52 +0000 (18:16 +0000)
committerDana Jansens <danakj@orodu.net>
Sat, 20 Jul 2002 18:16:52 +0000 (18:16 +0000)
util/epist/actions.hh
util/epist/epist.cc
util/epist/screen.cc
util/epist/window.cc
util/epist/window.hh

index 5d57e0d..b13149a 100644 (file)
@@ -42,10 +42,10 @@ public:
     close, //done
     toggleshade, //done
     toggleomnipresent, //done
-    moveWindowUp,
-    moveWindowDown,
-    moveWindowLeft,
-    moveWindowRight,
+    moveWindowUp, //done
+    moveWindowDown, //done
+    moveWindowLeft, //done
+    moveWindowRight, //done
 
     toggleMaximizeFull,
     toggleMaximizeVertical,
index eea8502..76a64ae 100644 (file)
@@ -118,6 +118,22 @@ epist::epist(char **argv, char *dpy_name, char *rc_file)
                            XKeysymToKeycode(getXDisplay(),
                                              XStringToKeysym("Down")),
                            Mod1Mask));
+  _actions.push_back(Action(Action::moveWindowUp,
+                           XKeysymToKeycode(getXDisplay(),
+                                             XStringToKeysym("Up")),
+                           Mod1Mask | ControlMask, 1));
+  _actions.push_back(Action(Action::moveWindowDown,
+                           XKeysymToKeycode(getXDisplay(),
+                                             XStringToKeysym("Down")),
+                           Mod1Mask | ControlMask, 1));
+  _actions.push_back(Action(Action::moveWindowLeft,
+                           XKeysymToKeycode(getXDisplay(),
+                                             XStringToKeysym("Left")),
+                           Mod1Mask | ControlMask, 1));
+  _actions.push_back(Action(Action::moveWindowRight,
+                           XKeysymToKeycode(getXDisplay(),
+                                             XStringToKeysym("Right")),
+                           Mod1Mask | ControlMask, 1));
   _actions.push_back(Action(Action::iconify,
                            XKeysymToKeycode(getXDisplay(),
                                              XStringToKeysym("I")),
index 3f78c51..cd749ae 100644 (file)
@@ -245,6 +245,22 @@ void screen::handleKeypress(const XEvent &e) {
             window->sendTo(0xffffffff);
           return;
 
+        case Action::moveWindowUp:
+          window->move(0, -it->number());
+          return;
+      
+        case Action::moveWindowDown:
+          window->move(0, it->number());
+          return;
+      
+        case Action::moveWindowLeft:
+          window->move(-it->number(), 0);
+          return;
+      
+        case Action::moveWindowRight:
+          window->move(it->number(), 0);
+          return;
+      
         case Action::toggleshade:
           window->shade(! window->shaded());
           return;
index cbd60f3..fd951aa 100644 (file)
@@ -141,7 +141,106 @@ void XWindow::processEvent(const XEvent &e) {
     break;
   }
 }
+
+
+void XWindow::findFramePosition(int &x, int &y) const {
+  Window win = _window, parent, root, last = None;
+  Window *children = 0;
+  unsigned int nchildren;
+  int gravity, top, bottom, left, right;
+  XWindowAttributes wattr;
+  XSizeHints size;
+  long ret;
+  unsigned int cwidth, cheight;
   
+  // get the location, size and gravity of the client window
+  if (! XGetWindowAttributes(_epist->getXDisplay(), _window, &wattr)) return;
+  cwidth = wattr.width;
+  cheight = wattr.height;
+  if (! XGetWMNormalHints(_epist->getXDisplay(), _window, &size, &ret)) return;
+  if (size.flags & PWinGravity)
+    gravity = size.win_gravity;
+  else
+    gravity = NorthWestGravity;
+    
+  while (XQueryTree(_epist->getXDisplay(), win, &root, &parent, &children,
+                    &nchildren)) {
+    if (children && nchildren > 0)
+      XFree(children); // don't care about the children
+
+    if (! parent) // no parent!?
+      return;
+
+    // if the parent window is the root window, stop here
+    if (parent == root)
+      break;
+
+    last = win;
+    win = parent;
+  }
+
+  if (! (XTranslateCoordinates(_epist->getXDisplay(), last, win, 0, 0,
+                               &left, &top, &parent) &&
+         XGetWindowAttributes(_epist->getXDisplay(), win, &wattr)))
+    return;
+
+  right = wattr.width - cwidth - left;
+  bottom = wattr.height - cheight - top;
+
+  left += wattr.border_width;
+  right += wattr.border_width;
+  top += wattr.border_width;
+  bottom += wattr.border_width;
+
+  // find the client's location
+  x = wattr.x + left;
+  y = wattr.y + top;
+
+  // this makes things work. why? i don't know. but you need them.
+  right -= 2;
+  bottom -= 2;
+
+  // find the frame's reference position based on the window's gravity
+  switch (gravity) {
+  case NorthWestGravity:
+    x -= left;
+    y -= top;
+    break;
+  case NorthGravity:
+    x += (left + right) / 2;
+    y -= top;
+    break;
+  case NorthEastGravity:
+    x += right;
+    y -= top;
+  case WestGravity:
+    x -= left;
+    y += (top + bottom) / 2;
+    break;
+  case CenterGravity:
+    x += (left + right) / 2;
+    y += (top + bottom) / 2;
+    break;
+  case EastGravity:
+    x += right;
+    y += (top + bottom) / 2;
+  case SouthWestGravity:
+    x -= left;
+    y += bottom;
+    break;
+  case SouthGravity:
+    x += (left + right) / 2;
+    y += bottom;
+    break;
+  case SouthEastGravity:
+    x += right;
+    y += bottom;
+    break;
+  default:
+    break;
+  }
+}
+
 
 void XWindow::shade(const bool sh) const {
   _xatom->sendClientMessage(_screen->rootWindow(), XAtom::net_wm_state,
@@ -183,3 +282,10 @@ void XWindow::sendTo(unsigned int dest) const {
   _xatom->sendClientMessage(_screen->rootWindow(), XAtom::net_wm_desktop,
                             _window, dest);
 }
+
+
+void XWindow::move(int x, int y) const {
+  int fx, fy;
+  findFramePosition(fx, fy);
+  XMoveWindow(_epist->getXDisplay(), _window, fx + x, fy + y);
+}
index 91cd834..5ba0435 100644 (file)
@@ -62,6 +62,8 @@ private:
   void updateTitle();
   void updateClass();
 
+  void findFramePosition(int &x, int &y) const;
+
 public:
   XWindow(epist *epist, screen *screen, Window window);
   virtual ~XWindow();
@@ -87,6 +89,7 @@ public:
   void iconify() const;
   void focus() const;
   void sendTo(unsigned int dest) const;
+  void move(int x, int y) const;
 
   bool operator == (const XWindow &w) const { return w._window == _window; }
   bool operator == (const Window &w) const { return w == _window; }