first
fluxgen fluxgen
4 files changed,
472 insertions(+),
0 deletions(-)
A
util/fbrun/FbRun.cc
@@ -0,0 +1,226 @@
+// FbRun.hh +// Copyright (c) 2002 Henrik Kinnunen (fluxgen@linuxmail.org) +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. + +// $Id: FbRun.cc,v 1.1 2002/08/20 02:04:34 fluxgen Exp $ + +#include "FbRun.hh" + +#include <X11/Xlib.h> +#include <X11/keysym.h> +#include <X11/Xutil.h> + +#include <unistd.h> + +#include <iostream> + +using namespace std; +FbRun::FbRun(Display *disp, int x, int y, size_t width): +m_font(disp, "fixed"), +m_win(None), +m_display(disp), +m_bevel(4), +m_gc(None), +m_end(false) { + + createWindow(x, y, width, m_font.height() + m_bevel); + // create GC + XGCValues gcv; + + if (m_font.fontStruct()) + gcv.font = m_font.fontStruct()->fid; + + m_gc = XCreateGC(m_display, m_win, GCFont, &gcv); +} + +FbRun::~FbRun() { + hide(); + XDestroyWindow(m_display, m_win); +} + +void FbRun::run(const std::string &command) { + //fork and execute program + if (!fork()) { + setsid(); + execl("/bin/sh", "/bin/sh", "-c", command.c_str(), 0); + exit(0); //exit fork + } + + hide(); + + m_end = true; // mark end of processing +} + +bool FbRun::loadFont(const string &fontname) { + if (!m_font.load(fontname.c_str())) + return false; + + // reconfigure m_gc for the new font + XGCValues gcv; + if (m_font.fontStruct()) + gcv.font = m_font.fontStruct()->fid; + XChangeGC(m_display, m_gc, GCFont, &gcv); + + // resize to fit new font height + resize(m_width, m_font.height() + m_bevel); + return true; +} + +void FbRun::setForeground(const XColor &color) { + XSetForeground(m_display, m_gc, color.pixel); + redrawLabel(); +} + +void FbRun::setBackground(const XColor &color) { + XSetWindowBackground(m_display, m_win, color.pixel); + redrawLabel(); +} + + +void FbRun::setText(const string &text) { + m_runtext = text; + redrawLabel(); +} + +void FbRun::setTitle(const string &title) { + assert(m_win); + XStoreName(m_display, m_win, const_cast<char *>(title.c_str())); +} + +void FbRun::move(int x, int y) { + XMoveWindow(m_display, m_win, x, y); +} + +void FbRun::resize(size_t width, size_t height) { + assert(m_win); + XResizeWindow(m_display, m_win, width, height + m_bevel); + m_width = width; + m_height = height + m_bevel; + setNoMaximize(); +} + +void FbRun::show() { + assert(m_win); + XMapWindow(m_display, m_win); +} + +void FbRun::hide() { + assert(m_win); + XUnmapWindow(m_display, m_win); +} + +void FbRun::redrawLabel() { + assert(m_win); + + XClearWindow(m_display, m_win); + drawString(0, m_height - m_bevel/2, + m_runtext.c_str(), m_runtext.size()); + +} + +void FbRun::drawString(int x, int y, + const char *text, size_t len) { + assert(m_win); + assert(m_gc); + + if (FbTk::Font::multibyte()) { + XmbDrawString(m_display, m_win, m_font.fontSet(), + m_gc, x, y, + text, len); + } else { + XDrawString(m_display, m_win, + m_gc, x, y, + text, len); + } +} + + +void FbRun::createWindow(int x, int y, size_t width, size_t height) { + m_win = XCreateSimpleWindow(m_display, // display + DefaultRootWindow(m_display), // parent windows + x, y, + width, height, + 1, // border_width + 0, // border + WhitePixel(m_display, DefaultScreen(m_display))); // background + + if (m_win == None) + throw string("Failed to create FbRun window!"); + + XSelectInput(m_display, m_win, KeyPressMask|ExposureMask); + + setNoMaximize(); + + m_width = width; + m_height = height; + +} + +void FbRun::handleEvent(XEvent * const xev) { + switch (xev->type) { + case KeyPress: { + KeySym ks; + char keychar[1]; + XLookupString(&xev->xkey, keychar, 1, &ks, 0); + if (ks == XK_Escape) { + m_end = true; + hide(); + return; // no more processing + } else if (ks == XK_Return) { + run(m_runtext); + m_runtext = ""; // clear text + } else if (ks == XK_BackSpace && m_runtext.size() != 0) { + m_runtext.erase(m_runtext.size()-1); + redrawLabel(); + } else if (! IsModifierKey(ks) && !IsCursorKey(ks)) { + m_runtext+=keychar[0]; // append character + redrawLabel(); + } + } break; + case Expose: + redrawLabel(); + break; + default: + break; + } +} + +void FbRun::getSize(size_t &width, size_t &height) { + XWindowAttributes attr; + XGetWindowAttributes(m_display, m_win, &attr); + width = attr.width; + height = attr.height; +} + +void FbRun::setNoMaximize() { + + size_t width, height; + + getSize(width, height); + + // we don't need to maximize this window + XSizeHints sh; + sh.flags = PMaxSize | PMinSize; + sh.max_width = width; + sh.max_height = height; + sh.min_width = width; + sh.min_height = height; + XSetWMNormalHints(m_display, m_win, &sh); +}
A
util/fbrun/FbRun.hh
@@ -0,0 +1,76 @@
+// FbRun.hh +// Copyright (c) 2002 Henrik Kinnunen (fluxgen@linuxmail.org) +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. + +// $Id: FbRun.hh,v 1.1 2002/08/20 02:04:34 fluxgen Exp $ + +#ifndef FBRUN_HH +#define FBRUN_HH + +#include "EventHandler.hh" +#include "Font.hh" + +#include <string> + +/** + Creates and managed a run window + TODO: a command history +*/ +class FbRun: public FbTk::EventHandler<XEvent> { +public: + FbRun(Display *disp, int x = 0, int y = 0, size_t width = 200); + ~FbRun(); + void handleEvent(XEvent * const ev); + void setText(const std::string &text); + void setTitle(const std::string &title); + void move(int x, int y); + void resize(size_t width, size_t height); + /// hide window + void hide(); + /// show window + void show(); + /// load and reconfigure for new font + bool loadFont(const std::string &fontname); + void setForeground(const XColor &color); + void setBackground(const XColor &color); + const FbTk::Font &font() const { return m_font; } + /// execute command and exit + void run(const std::string &execstring); + /// is this object done? + bool end() const { return m_end; } +private: + void drawString(int x, int y, const char *text, size_t len); + void getSize(size_t &width, size_t &height); + void createWindow(int x, int y, size_t width, size_t height); + void redrawLabel(); + /// set no maximizable for this window + void setNoMaximize(); + + FbTk::Font m_font; ///< font used to draw command text + Window m_win; ///< toplevel window + Display *m_display; ///< display connection + std::string m_runtext; ///< command to execute + size_t m_width, m_height; ///< size of window + int m_bevel; ///< distance to window edge from font in pixels + GC m_gc; + bool m_end; +}; + +#endif // FBRUN_HH
A
util/fbrun/Makefile.am
@@ -0,0 +1,7 @@
+FLUXBOX_SRC_DIR=../../src/ +INCLUDES = -I${FLUXBOX_SRC_DIR} +bin_PROGRAMS = fbrun +fbrun_SOURCES = FbRun.hh FbRun.cc main.cc +fbrun_LDADD = ${FLUXBOX_SRC_DIR}Font.o + +fbrun.o: ${FLUXBOX_SRC_DIR}/Font.hh
A
util/fbrun/main.cc
@@ -0,0 +1,163 @@
+// main.cc for FbRun +// Copyright (c) 2002 Henrik Kinnunen (fluxgen@linuxmail.org) +// +// Permission is hereby granted, free of charge, to any person obtaining a +// copy of this software and associated documentation files (the "Software"), +// to deal in the Software without restriction, including without limitation +// the rights to use, copy, modify, merge, publish, distribute, sublicense, +// and/or sell copies of the Software, and to permit persons to whom the +// Software is furnished to do so, subject to the following conditions: +// +// The above copyright notice and this permission notice shall be included in +// all copies or substantial portions of the Software. +// +// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR +// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, +// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL +// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER +// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING +// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER +// DEALINGS IN THE SOFTWARE. + +// $Id: main.cc,v 1.1 2002/08/20 02:04:34 fluxgen Exp $ + +#include "FbRun.hh" + +#include <string> +#include <iostream> +using namespace std; + +void showUsage(const char *progname) { + cerr<<"fbrun 1.1.0 : (c) 2002 Henrik Kinnunen"<<endl; + cerr<<"Usage: "<< + progname<<" [arguments]"<<endl<< + "Arguments: "<<endl<< + " -font [font name] Text font"<<endl<< + " -title [title name] Set title"<<endl<< + " -text [text] Text input"<<endl<< + " -w [width] Window width in pixels"<<endl<< + " -h [height] Window height in pixels"<<endl<< + " -display [display string] Display name"<<endl<< + " -pos [x] [y] Window position in pixels"<<endl<< + " -fg [color name] Foreground text color"<<endl<< + " -bg [color name] Background color"<<endl<< + " -help Show this help"<<endl<<endl<< + "Example: fbrun -fg black -bg white -text xterm -title \"run xterm\""<<endl; +} + +int main(int argc, char **argv) { + int x = 0, y = 0; // default pos of window + size_t width = 200, height = 32; // default size of window + bool set_height = false; // use height of font by default + bool set_pos = false; // set position + string fontname; // font name + string title("Run program"); // default title + string text; // default input text + string foreground("black"); // text color + string background("white"); // text background color + string display_name; // name of the display connection + + // parse arguments + for (int i=1; i<argc; i++) { + if (strcmp(argv[i], "-font") == 0 && i+1 < argc) { + ++i; + fontname = argv[i]; + } else if (strcmp(argv[i], "-title") == 0 && i+1 < argc) { + ++i; + title = argv[i]; + } else if (strcmp(argv[i], "-text") == 0 && i+1 < argc) { + ++i; + text = argv[i]; + } else if (strcmp(argv[i], "-w") == 0 && i+1 < argc) { + ++i; + width = atoi(argv[i]); + } else if (strcmp(argv[i], "-h") == 0 && i+1 < argc) { + ++i; + height = atoi(argv[i]); + set_height = true; // mark true else the height of font will be used + } else if (strcmp(argv[i], "-display") == 0 && i+1 < argc) { + ++i; + display_name = argv[i]; + } else if (strcmp(argv[i], "-pos") == 0 && i+2 < argc) { + ++i; + x = atoi(argv[i]); + ++i; + y = atoi(argv[i]); + set_pos = true; + } else if (strcmp(argv[i], "-fg") == 0 && i+1 < argc) { + ++i; + foreground = argv[i]; + } else if (strcmp(argv[i], "-bg") == 0 && i+1 < argc) { + ++i; + background = argv[i]; + } else if (strcmp(argv[i], "-h") == 0 || strcmp(argv[i], "-help") == 0) { + showUsage(argv[0]); + exit(0); + } else { + cerr<<"Invalid argument: "<<argv[i]<<endl; + showUsage(argv[0]); + exit(0); + } + + } + + try { + + Display *disp = 0; + + // establish display connection + disp = XOpenDisplay(display_name.c_str()); + if (disp == 0) + throw string("Can't open display: " + display_name); + + FbRun fbrun(disp); + if (fontname.size() != 0) { + if (!fbrun.loadFont(fontname.c_str())) { + cerr<<"Failed to load font: "<<fontname<<endl; + cerr<<"Falling back to \"fixed\""<<endl; + } + } + + // get color + XColor xc_foreground, xc_background; + if (XParseColor(disp, DefaultColormap(disp, DefaultScreen(disp)), + foreground.c_str(), + &xc_foreground) == 0) { + cerr<<"Faild to lookup color: "<<foreground<<endl; + } + + if (XParseColor(disp, DefaultColormap(disp, DefaultScreen(disp)), + background.c_str(), + &xc_background) == 0) { + cerr<<"Faild to lookup color: "<<background<<endl; + } + + XAllocColor(disp, DefaultColormap(disp, DefaultScreen(disp)), + &xc_foreground); + XAllocColor(disp, DefaultColormap(disp, DefaultScreen(disp)), + &xc_background); + + fbrun.setForeground(xc_foreground); + fbrun.setBackground(xc_background); + + if (set_height) + fbrun.resize(width, height); + + fbrun.setTitle(title); + fbrun.setText(text); + fbrun.show(); + + if (set_pos) + fbrun.move(x, y); + + XEvent event; + // main loop + while (!fbrun.end()) { + XNextEvent(disp, &event); + fbrun.handleEvent(&event); + } + + } catch (string errstr) { + cerr<<"Error: "<<errstr<<endl; + } +}