# HG changeset patch # User Jacob Dawid # Date 1313693100 -7200 # Node ID b31663fb7e8ac8196e4d7c4c425c989cd6fe8b83 # Parent cc90c62ada215a091fefd7a139dedd6f2c4c5527 Further removed files. diff -r cc90c62ada21 -r b31663fb7e8a gui/octave-gui.pro --- a/gui/octave-gui.pro Thu Aug 18 19:20:10 2011 +0200 +++ b/gui/octave-gui.pro Thu Aug 18 20:45:00 2011 +0200 @@ -58,8 +58,6 @@ # Files associated with the project: SOURCES +=\ src/lexer/lexeroctavegui.cpp \ - src/terminal/KeyboardTranslator.cpp \ - src/terminal/History.cpp \ src/terminal/konsole_wcwidth.cpp \ src/terminal/Pty.cpp \ src/terminal/kpty.cpp \ @@ -88,11 +86,6 @@ HEADERS += \ src/lexer/lexeroctavegui.h \ - src/terminal/Character.h \ - src/terminal/CharacterColor.h \ - src/terminal/ColorTables.h \ - src/terminal/KeyboardTranslator.h \ - src/terminal/History.h \ src/terminal/konsole_wcwidth.h \ src/terminal/konsole_export.h \ src/terminal/Pty.h \ diff -r cc90c62ada21 -r b31663fb7e8a gui/src/terminal/Character.h --- a/gui/src/terminal/Character.h Thu Aug 18 19:20:10 2011 +0200 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,228 +0,0 @@ -/* - This file is part of Konsole, KDE's terminal. - - Copyright 2007-2008 by Robert Knight - Copyright 1997,1998 by Lars Doelle - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA - 02110-1301 USA. -*/ - -#ifndef CHARACTER_H -#define CHARACTER_H - -// Qt -#include - -// Local -#include "CharacterColor.h" - -typedef unsigned char LineProperty; - -static const int LINE_DEFAULT = 0; -static const int LINE_WRAPPED = (1 << 0); -static const int LINE_DOUBLEWIDTH = (1 << 1); -static const int LINE_DOUBLEHEIGHT = (1 << 2); - -#define DEFAULT_RENDITION 0 -#define RE_BOLD (1 << 0) -#define RE_BLINK (1 << 1) -#define RE_UNDERLINE (1 << 2) -#define RE_REVERSE (1 << 3) // Screen only -#define RE_INTENSIVE (1 << 3) // Widget only -#define RE_CURSOR (1 << 4) -#define RE_EXTENDED_CHAR (1 << 5) - -/** - * A single character in the terminal which consists of a unicode character - * value, foreground and background colors and a set of rendition attributes - * which specify how it should be drawn. - */ -class Character -{ -public: - /** - * Constructs a new character. - * - * @param _c The unicode character value of this character. - * @param _f The foreground color used to draw the character. - * @param _b The color used to draw the character's background. - * @param _r A set of rendition flags which specify how this character is to be drawn. - */ -inline Character (quint16 _c = ' ', CharacterColor _f = CharacterColor (COLOR_SPACE_DEFAULT, DEFAULT_FORE_COLOR), CharacterColor _b = CharacterColor (COLOR_SPACE_DEFAULT, DEFAULT_BACK_COLOR), quint8 _r = DEFAULT_RENDITION):character (_c), rendition (_r), foregroundColor (_f), - backgroundColor - (_b) - { - } - - union - { - /** The unicode character value for this character. */ - quint16 character; - /** - * Experimental addition which allows a single Character instance to contain more than - * one unicode character. - * - * charSequence is a hash code which can be used to look up the unicode - * character sequence in the ExtendedCharTable used to create the sequence. - */ - quint16 charSequence; - }; - - /** A combination of RENDITION flags which specify options for drawing the character. */ - quint8 rendition; - - /** The foreground color used to draw this character. */ - CharacterColor foregroundColor; - /** The color used to draw this character's background. */ - CharacterColor backgroundColor; - - /** - * Returns true if this character has a transparent background when - * it is drawn with the specified @p palette. - */ - bool isTransparent (const ColorEntry * palette) const; - /** - * Returns true if this character should always be drawn in bold when - * it is drawn with the specified @p palette, independent of whether - * or not the character has the RE_BOLD rendition flag. - */ - ColorEntry::FontWeight fontWeight (const ColorEntry * base) const; - - /** - * returns true if the format (color, rendition flag) of the compared characters is equal - */ - bool equalsFormat (const Character & other) const; - - /** - * Compares two characters and returns true if they have the same unicode character value, - * rendition and colors. - */ - friend bool operator == (const Character & a, const Character & b); - /** - * Compares two characters and returns true if they have different unicode character values, - * renditions or colors. - */ - friend bool operator != (const Character & a, const Character & b); -}; - -inline bool -operator == (const Character & a, const Character & b) -{ - return a.character == b.character && - a.rendition == b.rendition && - a.foregroundColor == b.foregroundColor && - a.backgroundColor == b.backgroundColor; -} - -inline bool -operator != (const Character & a, const Character & b) -{ - return a.character != b.character || - a.rendition != b.rendition || - a.foregroundColor != b.foregroundColor || - a.backgroundColor != b.backgroundColor; -} - -inline bool -Character::isTransparent (const ColorEntry * base) const -{ - return ((backgroundColor._colorSpace == COLOR_SPACE_DEFAULT) && - base[backgroundColor._u + 0 + - (backgroundColor._v ? BASE_COLORS : 0)].transparent) - || ((backgroundColor._colorSpace == COLOR_SPACE_SYSTEM) - && base[backgroundColor._u + 2 + - (backgroundColor._v ? BASE_COLORS : 0)].transparent); -} - -inline bool -Character::equalsFormat (const Character & other) const -{ - return - backgroundColor == other.backgroundColor && - foregroundColor == other.foregroundColor && rendition == other.rendition; -} - -inline ColorEntry::FontWeight -Character::fontWeight (const ColorEntry * base) const -{ - if (backgroundColor._colorSpace == COLOR_SPACE_DEFAULT) - return base[backgroundColor._u + 0 + - (backgroundColor._v ? BASE_COLORS : 0)].fontWeight; - else if (backgroundColor._colorSpace == COLOR_SPACE_SYSTEM) - return base[backgroundColor._u + 2 + - (backgroundColor._v ? BASE_COLORS : 0)].fontWeight; - else - return ColorEntry::UseCurrentFormat; -} - -extern unsigned short vt100_graphics[32]; - - -/** - * A table which stores sequences of unicode characters, referenced - * by hash keys. The hash key itself is the same size as a unicode - * character ( ushort ) so that it can occupy the same space in - * a structure. - */ -class ExtendedCharTable -{ -public: - /** Constructs a new character table. */ - ExtendedCharTable (); - ~ExtendedCharTable (); - - /** - * Adds a sequences of unicode characters to the table and returns - * a hash code which can be used later to look up the sequence - * using lookupExtendedChar() - * - * If the same sequence already exists in the table, the hash - * of the existing sequence will be returned. - * - * @param unicodePoints An array of unicode character points - * @param length Length of @p unicodePoints - */ - ushort createExtendedChar (ushort * unicodePoints, ushort length); - /** - * Looks up and returns a pointer to a sequence of unicode characters - * which was added to the table using createExtendedChar(). - * - * @param hash The hash key returned by createExtendedChar() - * @param length This variable is set to the length of the - * character sequence. - * - * @return A unicode character sequence of size @p length. - */ - ushort *lookupExtendedChar (ushort hash, ushort & length) const; - - /** The global ExtendedCharTable instance. */ - static ExtendedCharTable instance; -private: - // calculates the hash key of a sequence of unicode points of size 'length' - ushort extendedCharHash (ushort * unicodePoints, ushort length) const; - // tests whether the entry in the table specified by 'hash' matches the - // character sequence 'unicodePoints' of size 'length' - bool extendedCharMatch (ushort hash, ushort * unicodePoints, - ushort length) const; - // internal, maps hash keys to character sequence buffers. The first ushort - // in each value is the length of the buffer, followed by the ushorts in the buffer - // themselves. - QHash < ushort, ushort * >extendedCharTable; -}; - -Q_DECLARE_TYPEINFO (Character, Q_MOVABLE_TYPE); - -#endif // CHARACTER_H diff -r cc90c62ada21 -r b31663fb7e8a gui/src/terminal/CharacterColor.h --- a/gui/src/terminal/CharacterColor.h Thu Aug 18 19:20:10 2011 +0200 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,307 +0,0 @@ -/* - This file is part of Konsole, KDE's terminal. - - Copyright 2007-2008 by Robert Knight - Copyright 1997,1998 by Lars Doelle - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA - 02110-1301 USA. -*/ - -#ifndef CHARACTERCOLOR_H -#define CHARACTERCOLOR_H - -// Qt -#include - -/** - * An entry in a terminal display's color palette. - * - * A color palette is an array of 16 ColorEntry instances which map - * system color indexes (from 0 to 15) into actual colors. - * - * Each entry can be set as bold, in which case any text - * drawn using the color should be drawn in bold. - * - * Each entry can also be transparent, in which case the terminal - * display should avoid drawing the background for any characters - * using the entry as a background. - */ -class ColorEntry -{ -public: - /** Specifies the weight to use when drawing text with this color. */ - enum FontWeight - { - /** Always draw text in this color with a bold weight. */ - Bold, - /** Always draw text in this color with a normal weight. */ - Normal, - /** - * Use the current font weight set by the terminal application. - * This is the default behavior. - */ - UseCurrentFormat - }; - - /** - * Constructs a new color palette entry. - * - * @param c The color value for this entry. - * @param tr Specifies that the color should be transparent when used as a background color. - * @param weight Specifies the font weight to use when drawing text with this color. - */ - ColorEntry (QColor c, bool tr, FontWeight weight = UseCurrentFormat):color (c), transparent (tr), - fontWeight - (weight) - { - } - - /** - * Constructs a new color palette entry with an undefined color, and - * with the transparent and bold flags set to false. - */ - ColorEntry ():transparent (false), fontWeight (UseCurrentFormat) - { - } - - /** - * Sets the color, transparency and boldness of this color to those of @p rhs. - */ - void operator= (const ColorEntry & rhs) - { - color = rhs.color; - transparent = rhs.transparent; - fontWeight = rhs.fontWeight; - } - - /** The color value of this entry for display. */ - QColor color; - - /** - * If true character backgrounds using this color should be transparent. - * This is not applicable when the color is used to render text. - */ - bool transparent; - /** - * Specifies the font weight to use when drawing text with this color. - * This is not applicable when the color is used to draw a character's background. - */ - FontWeight fontWeight; -}; - - -// Attributed Character Representations /////////////////////////////// - -// Colors - -#define BASE_COLORS (2+8) -#define INTENSITIES 2 -#define TABLE_COLORS (INTENSITIES*BASE_COLORS) - -#define DEFAULT_FORE_COLOR 0 -#define DEFAULT_BACK_COLOR 1 - -//a standard set of colors using black text on a white background. -//defined in TerminalDisplay.cpp - -//extern const ColorEntry base_color_table[TABLE_COLORS]; - -/* CharacterColor is a union of the various color spaces. - - Assignment is as follows: - - Type - Space - Values - - 0 - Undefined - u: 0, v:0 w:0 - 1 - Default - u: 0..1 v:intense w:0 - 2 - System - u: 0..7 v:intense w:0 - 3 - Index(256) - u: 16..255 v:0 w:0 - 4 - RGB - u: 0..255 v:0..256 w:0..256 - - Default colour space has two separate colours, namely - default foreground and default background colour. -*/ - -#define COLOR_SPACE_UNDEFINED 0 -#define COLOR_SPACE_DEFAULT 1 -#define COLOR_SPACE_SYSTEM 2 -#define COLOR_SPACE_256 3 -#define COLOR_SPACE_RGB 4 - -/** - * Describes the color of a single character in the terminal. - */ -class CharacterColor -{ - friend class Character; - -public: - /** Constructs a new CharacterColor whoose color and color space are undefined. */ - CharacterColor ():_colorSpace (COLOR_SPACE_UNDEFINED), - _u (0), _v (0), _w (0) - { - } - - /** - * Constructs a new CharacterColor using the specified @p colorSpace and with - * color value @p co - * - * The meaning of @p co depends on the @p colorSpace used. - * - * TODO : Document how @p co relates to @p colorSpace - * - * TODO : Add documentation about available color spaces. - */ - CharacterColor (quint8 colorSpace, int co):_colorSpace (colorSpace), - _u (0), _v (0), _w (0) - { - switch (colorSpace) - { - case COLOR_SPACE_DEFAULT: - _u = co & 1; - break; - case COLOR_SPACE_SYSTEM: - _u = co & 7; - _v = (co >> 3) & 1; - break; - case COLOR_SPACE_256: - _u = co & 255; - break; - case COLOR_SPACE_RGB: - _u = co >> 16; - _v = co >> 8; - _w = co; - break; - default: - _colorSpace = COLOR_SPACE_UNDEFINED; - } - } - - /** - * Returns true if this character color entry is valid. - */ - bool isValid () - { - return _colorSpace != COLOR_SPACE_UNDEFINED; - } - - /** - * Toggles the value of this color between a normal system color and the corresponding intensive - * system color. - * - * This is only applicable if the color is using the COLOR_SPACE_DEFAULT or COLOR_SPACE_SYSTEM - * color spaces. - */ - void toggleIntensive (); - - /** - * Returns the color within the specified color @p palette - * - * The @p palette is only used if this color is one of the 16 system colors, otherwise - * it is ignored. - */ - QColor color (const ColorEntry * palette) const; - - /** - * Compares two colors and returns true if they represent the same color value and - * use the same color space. - */ - friend bool operator == (const CharacterColor & a, - const CharacterColor & b); - /** - * Compares two colors and returns true if they represent different color values - * or use different color spaces. - */ - friend bool operator != (const CharacterColor & a, - const CharacterColor & b); - -private: - quint8 _colorSpace; - - // bytes storing the character color - quint8 _u; - quint8 _v; - quint8 _w; -}; - -inline bool -operator == (const CharacterColor & a, const CharacterColor & b) -{ - return a._colorSpace == b._colorSpace && - a._u == b._u && a._v == b._v && a._w == b._w; -} - -inline bool -operator != (const CharacterColor & a, const CharacterColor & b) -{ - return !operator== (a, b); -} - -inline const QColor -color256 (quint8 u, const ColorEntry * base) -{ - // 0.. 16: system colors - if (u < 8) - return base[u + 2].color; - u -= 8; - if (u < 8) - return base[u + 2 + BASE_COLORS].color; - u -= 8; - - // 16..231: 6x6x6 rgb color cube - if (u < 216) - return QColor (((u / 36) % 6) ? (40 * ((u / 36) % 6) + 55) : 0, - ((u / 6) % 6) ? (40 * ((u / 6) % 6) + 55) : 0, - ((u / 1) % 6) ? (40 * ((u / 1) % 6) + 55) : 0); - u -= 216; - - // 232..255: gray, leaving out black and white - int gray = u * 10 + 8; - return QColor (gray, gray, gray); -} - -inline QColor -CharacterColor::color (const ColorEntry * base) const -{ - switch (_colorSpace) - { - case COLOR_SPACE_DEFAULT: - return base[_u + 0 + (_v ? BASE_COLORS : 0)].color; - case COLOR_SPACE_SYSTEM: - return base[_u + 2 + (_v ? BASE_COLORS : 0)].color; - case COLOR_SPACE_256: - return color256 (_u, base); - case COLOR_SPACE_RGB: - return QColor (_u, _v, _w); - case COLOR_SPACE_UNDEFINED: - return QColor (); - } - - Q_ASSERT (false); // invalid color space - - return QColor (); -} - -inline void -CharacterColor::toggleIntensive () -{ - if (_colorSpace == COLOR_SPACE_SYSTEM || _colorSpace == COLOR_SPACE_DEFAULT) - { - _v = !_v; - } -} - -#endif // CHARACTERCOLOR_H diff -r cc90c62ada21 -r b31663fb7e8a gui/src/terminal/ColorTables.h --- a/gui/src/terminal/ColorTables.h Thu Aug 18 19:20:10 2011 +0200 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,97 +0,0 @@ -/* OctaveGUI - A graphical user interface for Octave - * Copyright (C) 2011 Jacob Dawid - * jacob.dawid@googlemail.com - * - * This file was autogenerated for the Konsole project. - * - * This program is free software: you can redistribute it and/or modify - * it under the terms of the GNU General Public License as published by - * the Free Software Foundation, either version 3 of the License, or - * (at your option) any later version. - * - * This program is distributed in the hope that it will be useful, - * but WITHOUT ANY WARRANTY; without even the implied warranty of - * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - * GNU General Public License for more details. - * - * You should have received a copy of the GNU General Public License - * along with this program. If not, see . - */ - -#ifndef _COLOR_TABLE_H -#define _COLOR_TABLE_H - -#include "CharacterColor.h" - -static const ColorEntry whiteonblack_color_table[TABLE_COLORS] = { - // normal - ColorEntry (QColor (0xFF, 0xFF, 0xFF), 0, 0), ColorEntry (QColor (0x00, 0x00, 0x00), 1, 0), // Dfore, Dback - ColorEntry (QColor (0x00, 0x00, 0x00), 0, 0), ColorEntry (QColor (0xB2, 0x18, 0x18), 0, 0), // Black, Red - ColorEntry (QColor (0x18, 0xB2, 0x18), 0, 0), ColorEntry (QColor (0xB2, 0x68, 0x18), 0, 0), // Green, Yellow - ColorEntry (QColor (0x18, 0x18, 0xB2), 0, 0), ColorEntry (QColor (0xB2, 0x18, 0xB2), 0, 0), // Blue, Magenta - ColorEntry (QColor (0x18, 0xB2, 0xB2), 0, 0), ColorEntry (QColor (0xB2, 0xB2, 0xB2), 0, 0), // Cyan, White - // intensiv - ColorEntry (QColor (0x00, 0x00, 0x00), 0, 1), - ColorEntry (QColor (0xFF, 0xFF, 0xFF), 1, 0), - ColorEntry (QColor (0x68, 0x68, 0x68), 0, 0), - ColorEntry (QColor (0xFF, 0x54, 0x54), 0, 0), - ColorEntry (QColor (0x54, 0xFF, 0x54), 0, 0), - ColorEntry (QColor (0xFF, 0xFF, 0x54), 0, 0), - ColorEntry (QColor (0x54, 0x54, 0xFF), 0, 0), - ColorEntry (QColor (0xFF, 0x54, 0xFF), 0, 0), - ColorEntry (QColor (0x54, 0xFF, 0xFF), 0, 0), - ColorEntry (QColor (0xFF, 0xFF, 0xFF), 0, 0) -}; - -static const ColorEntry greenonblack_color_table[TABLE_COLORS] = { - ColorEntry (QColor (24, 240, 24), 0, 0), ColorEntry (QColor (0, 0, 0), 1, - 0), - ColorEntry (QColor (0, 0, 0), 0, 0), ColorEntry (QColor (178, 24, 24), 0, - 0), - ColorEntry (QColor (24, 178, 24), 0, 0), ColorEntry (QColor (178, 104, 24), - 0, 0), - ColorEntry (QColor (24, 24, 178), 0, 0), ColorEntry (QColor (178, 24, 178), - 0, 0), - ColorEntry (QColor (24, 178, 178), 0, 0), - ColorEntry (QColor (178, 178, 178), 0, 0), - // intensive colors - ColorEntry (QColor (24, 240, 24), 0, 1), ColorEntry (QColor (0, 0, 0), 1, - 0), - ColorEntry (QColor (104, 104, 104), 0, 0), ColorEntry (QColor (255, 84, 84), - 0, 0), - ColorEntry (QColor (84, 255, 84), 0, 0), ColorEntry (QColor (255, 255, 84), - 0, 0), - ColorEntry (QColor (84, 84, 255), 0, 0), ColorEntry (QColor (255, 84, 255), - 0, 0), - ColorEntry (QColor (84, 255, 255), 0, 0), - ColorEntry (QColor (255, 255, 255), 0, 0) -}; - -static const ColorEntry blackonlightyellow_color_table[TABLE_COLORS] = { - ColorEntry (QColor (0, 0, 0), 0, 0), ColorEntry (QColor (255, 255, 221), 1, - 0), - ColorEntry (QColor (0, 0, 0), 0, 0), ColorEntry (QColor (178, 24, 24), 0, - 0), - ColorEntry (QColor (24, 178, 24), 0, 0), ColorEntry (QColor (178, 104, 24), - 0, 0), - ColorEntry (QColor (24, 24, 178), 0, 0), ColorEntry (QColor (178, 24, 178), - 0, 0), - ColorEntry (QColor (24, 178, 178), 0, 0), - ColorEntry (QColor (178, 178, 178), 0, 0), - ColorEntry (QColor (0, 0, 0), 0, 1), ColorEntry (QColor (255, 255, 221), 1, - 0), - ColorEntry (QColor (104, 104, 104), 0, 0), ColorEntry (QColor (255, 84, 84), - 0, 0), - ColorEntry (QColor (84, 255, 84), 0, 0), ColorEntry (QColor (255, 255, 84), - 0, 0), - ColorEntry (QColor (84, 84, 255), 0, 0), ColorEntry (QColor (255, 84, 255), - 0, 0), - ColorEntry (QColor (84, 255, 255), 0, 0), - ColorEntry (QColor (255, 255, 255), 0, 0) -}; - - - - - -#endif diff -r cc90c62ada21 -r b31663fb7e8a gui/src/terminal/History.cpp --- a/gui/src/terminal/History.cpp Thu Aug 18 19:20:10 2011 +0200 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,749 +0,0 @@ -/* - This file is part of Konsole, an X terminal. - Copyright (C) 1997,1998 by Lars Doelle - - Rewritten for QT4 by e_k , Copyright (C)2008 - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA - 02110-1301 USA. -*/ - -// Own -#include "History.h" - -// System -#include -#include -#include -#include -#include -#include -#include -#include - - -// Reasonable line size -#define LINE_SIZE 1024 - -/* - An arbitrary long scroll. - - One can modify the scroll only by adding either cells - or newlines, but access it randomly. - - The model is that of an arbitrary wide typewriter scroll - in that the scroll is a serie of lines and each line is - a serie of cells with no overwriting permitted. - - The implementation provides arbitrary length and numbers - of cells and line/column indexed read access to the scroll - at constant costs. - -KDE4: Can we use QTemporaryFile here, instead of KTempFile? - -FIXME: some complain about the history buffer comsuming the - memory of their machines. This problem is critical - since the history does not behave gracefully in cases - where the memory is used up completely. - - I put in a workaround that should handle it problem - now gracefully. I'm not satisfied with the solution. - -FIXME: Terminating the history is not properly indicated - in the menu. We should throw a signal. - -FIXME: There is noticeable decrease in speed, also. Perhaps, - there whole feature needs to be revisited therefore. - Disadvantage of a more elaborated, say block-oriented - scheme with wrap around would be it's complexity. -*/ - -//FIXME: tempory replacement for tmpfile -// this is here one for debugging purpose. - -//#define tmpfile xTmpFile - -// History File /////////////////////////////////////////// - -/* - A Row(X) data type which allows adding elements to the end. -*/ - -HistoryFile::HistoryFile ():ion (-1), length (0), fileMap (0) -{ - if (tmpFile.open ()) - { - tmpFile.setAutoRemove (true); - ion = tmpFile.handle (); - } -} - -HistoryFile::~HistoryFile () -{ - if (fileMap) - unmap (); -} - -//TODO: Mapping the entire file in will cause problems if the history file becomes exceedingly large, -//(ie. larger than available memory). HistoryFile::map() should only map in sections of the file at a time, -//to avoid this. -void -HistoryFile::map () -{ - assert (fileMap == 0); - - fileMap = (char *) mmap (0, length, PROT_READ, MAP_PRIVATE, ion, 0); - - //if mmap'ing fails, fall back to the read-lseek combination - if (fileMap == MAP_FAILED) - { - readWriteBalance = 0; - fileMap = 0; - qDebug () << ": mmap'ing history failed. errno = " << errno; - } -} - -void -HistoryFile::unmap () -{ - int result = munmap (fileMap, length); - assert (result == 0); - - fileMap = 0; -} - -bool -HistoryFile::isMapped () -{ - return (fileMap != 0); -} - -void -HistoryFile::add (const unsigned char *bytes, int len) -{ - if (fileMap) - unmap (); - - readWriteBalance++; - - int rc = 0; - - rc = lseek (ion, length, SEEK_SET); - if (rc < 0) - { - perror ("HistoryFile::add.seek"); - return; - } - rc = write (ion, bytes, len); - if (rc < 0) - { - perror ("HistoryFile::add.write"); - return; - } - length += rc; -} - -void -HistoryFile::get (unsigned char *bytes, int len, int loc) -{ - //count number of get() calls vs. number of add() calls. - //If there are many more get() calls compared with add() - //calls (decided by using MAP_THRESHOLD) then mmap the log - //file to improve performance. - readWriteBalance--; - if (!fileMap && readWriteBalance < MAP_THRESHOLD) - map (); - - if (fileMap) - { - for (int i = 0; i < len; i++) - bytes[i] = fileMap[loc + i]; - } - else - { - int rc = 0; - - if (loc < 0 || len < 0 || loc + len > length) - fprintf (stderr, "getHist(...,%d,%d): invalid args.\n", len, loc); - rc = lseek (ion, loc, SEEK_SET); - if (rc < 0) - { - perror ("HistoryFile::get.seek"); - return; - } - rc = read (ion, bytes, len); - if (rc < 0) - { - perror ("HistoryFile::get.read"); - return; - } - } -} - -int -HistoryFile::len () -{ - return length; -} - - -// History Scroll abstract base class ////////////////////////////////////// - - -HistoryScroll::HistoryScroll (HistoryType * t):m_histType (t) -{ -} - -HistoryScroll::~HistoryScroll () -{ - delete m_histType; -} - -bool -HistoryScroll::hasScroll () -{ - return true; -} - -// History Scroll File ////////////////////////////////////// - -/* - The history scroll makes a Row(Row(Cell)) from - two history buffers. The index buffer contains - start of line positions which refere to the cells - buffer. - - Note that index[0] addresses the second line - (line #1), while the first line (line #0) starts - at 0 in cells. -*/ - -HistoryScrollFile::HistoryScrollFile (const QString & logFileName):HistoryScroll (new HistoryTypeFile (logFileName)), -m_logFileName -(logFileName) -{ -} - -HistoryScrollFile::~HistoryScrollFile () -{ -} - -int -HistoryScrollFile::getLines () -{ - return index.len () / sizeof (int); -} - -int -HistoryScrollFile::getLineLen (int lineno) -{ - return (startOfLine (lineno + 1) - - startOfLine (lineno)) / sizeof (Character); -} - -bool -HistoryScrollFile::isWrappedLine (int lineno) -{ - if (lineno >= 0 && lineno <= getLines ()) - { - unsigned char flag; - lineflags.get ((unsigned char *) &flag, sizeof (unsigned char), - (lineno) * sizeof (unsigned char)); - return flag; - } - return false; -} - -int -HistoryScrollFile::startOfLine (int lineno) -{ - if (lineno <= 0) - return 0; - if (lineno <= getLines ()) - { - - if (!index.isMapped ()) - index.map (); - - int res; - index.get ((unsigned char *) &res, sizeof (int), - (lineno - 1) * sizeof (int)); - return res; - } - return cells.len (); -} - -void -HistoryScrollFile::getCells (int lineno, int colno, int count, - Character res[]) -{ - cells.get ((unsigned char *) res, count * sizeof (Character), - startOfLine (lineno) + colno * sizeof (Character)); -} - -void -HistoryScrollFile::addCells (const Character text[], int count) -{ - cells.add ((unsigned char *) text, count * sizeof (Character)); -} - -void -HistoryScrollFile::addLine (bool previousWrapped) -{ - if (index.isMapped ()) - index.unmap (); - - int locn = cells.len (); - index.add ((unsigned char *) &locn, sizeof (int)); - unsigned char flags = previousWrapped ? 0x01 : 0x00; - lineflags.add ((unsigned char *) &flags, sizeof (unsigned char)); -} - - -// History Scroll Buffer ////////////////////////////////////// -HistoryScrollBuffer::HistoryScrollBuffer (unsigned int maxLineCount): -HistoryScroll (new HistoryTypeBuffer (maxLineCount)), -_historyBuffer (), -_maxLineCount (0), -_usedLines (0), -_head (0) -{ - setMaxNbLines (maxLineCount); -} - -HistoryScrollBuffer::~HistoryScrollBuffer () -{ - delete[]_historyBuffer; -} - -void -HistoryScrollBuffer::addCellsVector (const QVector < Character > &cells) -{ - _head++; - if (_usedLines < _maxLineCount) - _usedLines++; - - if (_head >= _maxLineCount) - { - _head = 0; - } - - _historyBuffer[bufferIndex (_usedLines - 1)] = cells; - _wrappedLine[bufferIndex (_usedLines - 1)] = false; -} - -void -HistoryScrollBuffer::addCells (const Character a[], int count) -{ - HistoryLine newLine (count); - qCopy (a, a + count, newLine.begin ()); - - addCellsVector (newLine); -} - -void -HistoryScrollBuffer::addLine (bool previousWrapped) -{ - _wrappedLine[bufferIndex (_usedLines - 1)] = previousWrapped; -} - -int -HistoryScrollBuffer::getLines () -{ - return _usedLines; -} - -int -HistoryScrollBuffer::getLineLen (int lineNumber) -{ - Q_ASSERT (lineNumber >= 0 && lineNumber < _maxLineCount); - - if (lineNumber < _usedLines) - { - return _historyBuffer[bufferIndex (lineNumber)].size (); - } - else - { - return 0; - } -} - -bool -HistoryScrollBuffer::isWrappedLine (int lineNumber) -{ - Q_ASSERT (lineNumber >= 0 && lineNumber < _maxLineCount); - - if (lineNumber < _usedLines) - { - //kDebug() << "Line" << lineNumber << "wrapped is" << _wrappedLine[bufferIndex(lineNumber)]; - return _wrappedLine[bufferIndex (lineNumber)]; - } - else - return false; -} - -void -HistoryScrollBuffer::getCells (int lineNumber, int startColumn, int count, - Character * buffer) -{ - if (count == 0) - return; - - Q_ASSERT (lineNumber < _maxLineCount); - - if (lineNumber >= _usedLines) - { - memset (buffer, 0, count * sizeof (Character)); - return; - } - - const HistoryLine & line = _historyBuffer[bufferIndex (lineNumber)]; - - //kDebug() << "startCol " << startColumn; - //kDebug() << "line.size() " << line.size(); - //kDebug() << "count " << count; - - Q_ASSERT (startColumn <= line.size () - count); - - memcpy (buffer, line.constData () + startColumn, - count * sizeof (Character)); -} - -void -HistoryScrollBuffer::setMaxNbLines (unsigned int lineCount) -{ - HistoryLine *oldBuffer = _historyBuffer; - HistoryLine *newBuffer = new HistoryLine[lineCount]; - - for (int i = 0; i < qMin (_usedLines, (int) lineCount); i++) - { - newBuffer[i] = oldBuffer[bufferIndex (i)]; - } - - _usedLines = qMin (_usedLines, (int) lineCount); - _maxLineCount = lineCount; - _head = (_usedLines == _maxLineCount) ? 0 : _usedLines - 1; - - _historyBuffer = newBuffer; - delete[]oldBuffer; - - _wrappedLine.resize (lineCount); -} - -int -HistoryScrollBuffer::bufferIndex (int lineNumber) -{ - Q_ASSERT (lineNumber >= 0); - Q_ASSERT (lineNumber < _maxLineCount); - Q_ASSERT ((_usedLines == _maxLineCount) || lineNumber <= _head); - - if (_usedLines == _maxLineCount) - { - return (_head + lineNumber + 1) % _maxLineCount; - } - else - { - return lineNumber; - } -} - - -// History Scroll None ////////////////////////////////////// - -HistoryScrollNone::HistoryScrollNone ():HistoryScroll (new HistoryTypeNone ()) -{ -} - -HistoryScrollNone::~HistoryScrollNone () -{ -} - -bool -HistoryScrollNone::hasScroll () -{ - return false; -} - -int -HistoryScrollNone::getLines () -{ - return 0; -} - -int -HistoryScrollNone::getLineLen (int) -{ - return 0; -} - -bool -HistoryScrollNone::isWrappedLine (int /*lineno */ ) -{ - return false; -} - -void -HistoryScrollNone::getCells (int, int, int, Character[]) -{ -} - -void -HistoryScrollNone::addCells (const Character[], int) -{ -} - -void -HistoryScrollNone::addLine (bool) -{ -} - -// History Scroll BlockArray ////////////////////////////////////// - -HistoryScrollBlockArray::HistoryScrollBlockArray (size_t size):HistoryScroll (new - HistoryTypeBlockArray - (size)) -{ - //m_blockArray.setHistorySize (size); // nb. of lines. -} - -HistoryScrollBlockArray::~HistoryScrollBlockArray () -{ -} - -int -HistoryScrollBlockArray::getLines () -{ - return m_lineLengths.count (); -} - -int -HistoryScrollBlockArray::getLineLen (int lineno) -{ - if (m_lineLengths.contains (lineno)) - return m_lineLengths[lineno]; - else - return 0; -} - -bool -HistoryScrollBlockArray::isWrappedLine (int /*lineno */ ) -{ - return false; -} - -void -HistoryScrollBlockArray::getCells (int lineno, int colno, - int count, Character res[]) -{ - Q_UNUSED(lineno); - Q_UNUSED(colno); - Q_UNUSED(count); - Q_UNUSED(res); -} - -void -HistoryScrollBlockArray::addCells (const Character a[], int count) -{ - Q_UNUSED(a); - Q_UNUSED(count); -} - -void -HistoryScrollBlockArray::addLine (bool) -{ -} - -////////////////////////////////////////////////////////////////////// -// History Types -////////////////////////////////////////////////////////////////////// - -HistoryType::HistoryType () -{ -} - -HistoryType::~HistoryType () -{ -} - -////////////////////////////// - -HistoryTypeNone::HistoryTypeNone () -{ -} - -bool -HistoryTypeNone::isEnabled () const -{ - return false; -} - -HistoryScroll * -HistoryTypeNone::scroll (HistoryScroll * old) const -{ - delete old; - return new HistoryScrollNone (); -} - -int -HistoryTypeNone::maximumLineCount () const -{ - return 0; -} - -////////////////////////////// - -HistoryTypeBlockArray::HistoryTypeBlockArray (size_t size):m_size (size) -{ -} - -bool -HistoryTypeBlockArray::isEnabled () const -{ - return true; -} - -int -HistoryTypeBlockArray::maximumLineCount () const -{ - return m_size; -} - -HistoryScroll * -HistoryTypeBlockArray::scroll (HistoryScroll * old) const -{ - delete old; - return new HistoryScrollBlockArray (m_size); -} - - -////////////////////////////// - -HistoryTypeBuffer::HistoryTypeBuffer (unsigned int nbLines):m_nbLines (nbLines) -{ -} - -bool -HistoryTypeBuffer::isEnabled () const -{ - return true; -} - -int -HistoryTypeBuffer::maximumLineCount () const -{ - return m_nbLines; -} - -HistoryScroll * -HistoryTypeBuffer::scroll (HistoryScroll * old) const -{ - if (old) - { - HistoryScrollBuffer *oldBuffer = - dynamic_cast < HistoryScrollBuffer * >(old); - if (oldBuffer) - { - oldBuffer->setMaxNbLines (m_nbLines); - return oldBuffer; - } - - HistoryScroll *newScroll = new HistoryScrollBuffer (m_nbLines); - int lines = old->getLines (); - int startLine = 0; - if (lines > (int) m_nbLines) - startLine = lines - m_nbLines; - - Character line[LINE_SIZE]; - for (int i = startLine; i < lines; i++) - { - int size = old->getLineLen (i); - if (size > LINE_SIZE) - { - Character *tmp_line = new Character[size]; - old->getCells (i, 0, size, tmp_line); - newScroll->addCells (tmp_line, size); - newScroll->addLine (old->isWrappedLine (i)); - delete[]tmp_line; - } - else - { - old->getCells (i, 0, size, line); - newScroll->addCells (line, size); - newScroll->addLine (old->isWrappedLine (i)); - } - } - delete old; - return newScroll; - } - return new HistoryScrollBuffer (m_nbLines); -} - -////////////////////////////// - -HistoryTypeFile::HistoryTypeFile (const QString & fileName):m_fileName - (fileName) -{ -} - -bool -HistoryTypeFile::isEnabled () const -{ - return true; -} - -const QString & -HistoryTypeFile::getFileName () const -{ - return m_fileName; -} - -HistoryScroll * -HistoryTypeFile::scroll (HistoryScroll * old) const -{ - if (dynamic_cast < HistoryFile * >(old)) - return old; // Unchanged. - - HistoryScroll *newScroll = new HistoryScrollFile (m_fileName); - - Character line[LINE_SIZE]; - int lines = (old != 0) ? old->getLines () : 0; - for (int i = 0; i < lines; i++) - { - int size = old->getLineLen (i); - if (size > LINE_SIZE) - { - Character *tmp_line = new Character[size]; - old->getCells (i, 0, size, tmp_line); - newScroll->addCells (tmp_line, size); - newScroll->addLine (old->isWrappedLine (i)); - delete[]tmp_line; - } - else - { - old->getCells (i, 0, size, line); - newScroll->addCells (line, size); - newScroll->addLine (old->isWrappedLine (i)); - } - } - - delete old; - return newScroll; -} - -int -HistoryTypeFile::maximumLineCount () const -{ - return 0; -} diff -r cc90c62ada21 -r b31663fb7e8a gui/src/terminal/History.h --- a/gui/src/terminal/History.h Thu Aug 18 19:20:10 2011 +0200 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,321 +0,0 @@ -/* - This file is part of Konsole, an X terminal. - Copyright (C) 1997,1998 by Lars Doelle - - Rewritten for QT4 by e_k , Copyright (C)2008 - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA - 02110-1301 USA. -*/ - -#ifndef HISTORY_H -#define HISTORY_H - -// Qt -#include -#include -#include - -// Konsole -#include "Character.h" - -class HistoryFile -{ -public: - HistoryFile (); - virtual ~ HistoryFile (); - - virtual void add (const unsigned char *bytes, int len); - virtual void get (unsigned char *bytes, int len, int loc); - virtual int len (); - - //mmaps the file in read-only mode - void map (); - //un-mmaps the file - void unmap (); - //returns true if the file is mmap'ed - bool isMapped (); - - -private: - int ion; - int length; - QTemporaryFile tmpFile; - - //pointer to start of mmap'ed file data, or 0 if the file is not mmap'ed - char *fileMap; - - //incremented whenver 'add' is called and decremented whenever - //'get' is called. - //this is used to detect when a large number of lines are being read and processed from the history - //and automatically mmap the file for better performance (saves the overhead of many lseek-read calls). - int readWriteBalance; - - //when readWriteBalance goes below this threshold, the file will be mmap'ed automatically - static const int MAP_THRESHOLD = -1000; -}; - -////////////////////////////////////////////////////////////////////// - -////////////////////////////////////////////////////////////////////// -// Abstract base class for file and buffer versions -////////////////////////////////////////////////////////////////////// -class HistoryType; - -class HistoryScroll -{ -public: - HistoryScroll (HistoryType *); - virtual ~ HistoryScroll (); - - virtual bool hasScroll (); - - // access to history - virtual int getLines () = 0; - virtual int getLineLen (int lineno) = 0; - virtual void getCells (int lineno, int colno, int count, Character res[]) = - 0; - virtual bool isWrappedLine (int lineno) = 0; - - // backward compatibility (obsolete) - Character getCell (int lineno, int colno) - { - Character res; - getCells (lineno, colno, 1, &res); - return res; - } - - // adding lines. - virtual void addCells (const Character a[], int count) = 0; - // convenience method - this is virtual so that subclasses can take advantage - // of QVector's implicit copying - virtual void addCellsVector (const QVector < Character > &cells) - { - addCells (cells.data (), cells.size ()); - } - - virtual void addLine (bool previousWrapped = false) = 0; - - // - // FIXME: Passing around constant references to HistoryType instances - // is very unsafe, because those references will no longer - // be valid if the history scroll is deleted. - // - const HistoryType & getType () - { - return *m_histType; - } - -protected: - HistoryType * m_histType; - -}; - - - -////////////////////////////////////////////////////////////////////// -// File-based history (e.g. file log, no limitation in length) -////////////////////////////////////////////////////////////////////// - -class HistoryScrollFile:public HistoryScroll -{ -public: - HistoryScrollFile (const QString & logFileName); - virtual ~ HistoryScrollFile (); - - virtual int getLines (); - virtual int getLineLen (int lineno); - virtual void getCells (int lineno, int colno, int count, Character res[]); - virtual bool isWrappedLine (int lineno); - - virtual void addCells (const Character a[], int count); - virtual void addLine (bool previousWrapped = false); - -private: - int startOfLine (int lineno); - - QString m_logFileName; - HistoryFile index; // lines Row(int) - HistoryFile cells; // text Row(Character) - HistoryFile lineflags; // flags Row(unsigned char) -}; - - -////////////////////////////////////////////////////////////////////// -// Buffer-based history (limited to a fixed nb of lines) -////////////////////////////////////////////////////////////////////// -class HistoryScrollBuffer:public HistoryScroll -{ -public: - typedef QVector < Character > HistoryLine; - - HistoryScrollBuffer (unsigned int maxNbLines = 1000); - virtual ~ HistoryScrollBuffer (); - - virtual int getLines (); - virtual int getLineLen (int lineno); - virtual void getCells (int lineno, int colno, int count, Character res[]); - virtual bool isWrappedLine (int lineno); - - virtual void addCells (const Character a[], int count); - virtual void addCellsVector (const QVector < Character > &cells); - virtual void addLine (bool previousWrapped = false); - - void setMaxNbLines (unsigned int nbLines); - unsigned int maxNbLines () - { - return _maxLineCount; - } - - -private: - int bufferIndex (int lineNumber); - - HistoryLine *_historyBuffer; - QBitArray _wrappedLine; - int _maxLineCount; - int _usedLines; - int _head; -}; - -////////////////////////////////////////////////////////////////////// -// Nothing-based history (no history :-) -////////////////////////////////////////////////////////////////////// -class HistoryScrollNone:public HistoryScroll -{ -public: - HistoryScrollNone (); - virtual ~ HistoryScrollNone (); - - virtual bool hasScroll (); - - virtual int getLines (); - virtual int getLineLen (int lineno); - virtual void getCells (int lineno, int colno, int count, Character res[]); - virtual bool isWrappedLine (int lineno); - - virtual void addCells (const Character a[], int count); - virtual void addLine (bool previousWrapped = false); -}; - -////////////////////////////////////////////////////////////////////// -// BlockArray-based history -////////////////////////////////////////////////////////////////////// -class HistoryScrollBlockArray:public HistoryScroll -{ -public: - HistoryScrollBlockArray (size_t size); - virtual ~ HistoryScrollBlockArray (); - - virtual int getLines (); - virtual int getLineLen (int lineno); - virtual void getCells (int lineno, int colno, int count, Character res[]); - virtual bool isWrappedLine (int lineno); - - virtual void addCells (const Character a[], int count); - virtual void addLine (bool previousWrapped = false); - -protected: - //BlockArray m_blockArray; - QHash < int, size_t > m_lineLengths; -}; - -////////////////////////////////////////////////////////////////////// -// History type -////////////////////////////////////////////////////////////////////// - -class HistoryType -{ -public: - HistoryType (); - virtual ~ HistoryType (); - - /** - * Returns true if the history is enabled ( can store lines of output ) - * or false otherwise. - */ - virtual bool isEnabled () const = 0; - /** - * Returns true if the history size is unlimited. - */ - bool isUnlimited () const - { - return maximumLineCount () == 0; - } - /** - * Returns the maximum number of lines which this history type - * can store or 0 if the history can store an unlimited number of lines. - */ - virtual int maximumLineCount () const = 0; - - virtual HistoryScroll *scroll (HistoryScroll *) const = 0; -}; - -class HistoryTypeNone:public HistoryType -{ -public: - HistoryTypeNone (); - - virtual bool isEnabled () const; - virtual int maximumLineCount () const; - - virtual HistoryScroll *scroll (HistoryScroll *) const; -}; - -class HistoryTypeBlockArray:public HistoryType -{ -public: - HistoryTypeBlockArray (size_t size); - - virtual bool isEnabled () const; - virtual int maximumLineCount () const; - - virtual HistoryScroll *scroll (HistoryScroll *) const; - -protected: - size_t m_size; -}; - -class HistoryTypeFile:public HistoryType -{ -public: - HistoryTypeFile (const QString & fileName = QString ()); - - virtual bool isEnabled () const; - virtual const QString & getFileName () const; - virtual int maximumLineCount () const; - - virtual HistoryScroll *scroll (HistoryScroll *) const; - -protected: - QString m_fileName; -}; - - -class HistoryTypeBuffer:public HistoryType -{ -public: - HistoryTypeBuffer (unsigned int nbLines); - - virtual bool isEnabled () const; - virtual int maximumLineCount () const; - - virtual HistoryScroll *scroll (HistoryScroll *) const; - -protected: - unsigned int m_nbLines; -}; - -#endif // HISTORY_H diff -r cc90c62ada21 -r b31663fb7e8a gui/src/terminal/KeyboardTranslator.cpp --- a/gui/src/terminal/KeyboardTranslator.cpp Thu Aug 18 19:20:10 2011 +0200 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,1091 +0,0 @@ -/* - This source file is part of Konsole, a terminal emulator. - - Copyright 2007-2008 by Robert Knight - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA - 02110-1301 USA. -*/ - -// Own -#include "KeyboardTranslator.h" - -// System -#include -#include - -// Qt -#include -#include -#include -#include -#include -#include -#include -#include -#include - -const QByteArray -KeyboardTranslatorManager:: - -defaultTranslatorText ("keyboard \"Fallback Key Translator\"\n" - "key Tab : \"\\t\""); - -KeyboardTranslatorManager::KeyboardTranslatorManager ():_haveLoadedAll (false) -{ -} - -KeyboardTranslatorManager::~KeyboardTranslatorManager () -{ - qDeleteAll (_translators); -} - -QString -KeyboardTranslatorManager::findTranslatorPath (const QString & name) -{ - QString translatorFile = QString ("../kb-layouts/" + name + ".keytab"); - if (QFile::exists (translatorFile)) - return translatorFile; - return QString ("/usr/share/octave/quint/kb-layouts/" + name + ".keytab"); -} - -void -KeyboardTranslatorManager::findTranslators () -{ - //QStringList list = KGlobal::dirs()->findAllResources("data", - // "konsole/*.keytab", - // KStandardDirs::NoDuplicates); - - QDir dir ("../kb-layouts/"); - QStringList filters; - filters << "*.keytab"; - dir.setNameFilters (filters); - QStringList list = dir.entryList (filters); - - // add the name of each translator to the list and associated - // the name with a null pointer to indicate that the translator - // has not yet been loaded from disk - QStringListIterator listIter (list); - while (listIter.hasNext ()) - { - QString translatorPath = listIter.next (); - - QString name = QFileInfo (translatorPath).baseName (); - - if (!_translators.contains (name)) - _translators.insert (name, 0); - } - - _haveLoadedAll = true; -} - -const KeyboardTranslator * -KeyboardTranslatorManager::findTranslator (const QString & name) -{ - if (name.isEmpty ()) - return defaultTranslator (); - - if (_translators.contains (name) && _translators[name] != 0) - return _translators[name]; - - KeyboardTranslator *translator = loadTranslator (name); - - if (translator != 0) - _translators[name] = translator; - //else if ( !name.isEmpty() ) - // kWarning() << "Unable to load translator" << name; - - return translator; -} - -bool -KeyboardTranslatorManager::saveTranslator (const KeyboardTranslator * - translator) -{ - //const QString path = KGlobal::dirs()->saveLocation("data","konsole/")+translator->name() - // +".keytab"; - const QString path = ".keytab"; - - //kDebug() << "Saving translator to" << path; - - QFile destination (path); - if (!destination.open (QIODevice::WriteOnly | QIODevice::Text)) - { - //kWarning() << "Unable to save keyboard translation:" - // << destination.errorString(); - return false; - } - - { - KeyboardTranslatorWriter writer (&destination); - writer.writeHeader (translator->description ()); - - QListIterator < KeyboardTranslator::Entry > iter (translator->entries ()); - while (iter.hasNext ()) - writer.writeEntry (iter.next ()); - } - - destination.close (); - - return true; -} - -KeyboardTranslator * -KeyboardTranslatorManager::loadTranslator (const QString & name) -{ - const QString & path = findTranslatorPath (name); - - QFile source (path); - if (name.isEmpty () || !source.open (QIODevice::ReadOnly | QIODevice::Text)) - return 0; - - return loadTranslator (&source, name); -} - -const KeyboardTranslator * -KeyboardTranslatorManager::defaultTranslator () -{ - // Try to find the default.keytab file if it exists, otherwise - // fall back to the hard-coded one - const KeyboardTranslator *translator = findTranslator ("default"); - if (!translator) - { - QBuffer textBuffer; - textBuffer.setData (defaultTranslatorText); - textBuffer.open (QIODevice::ReadOnly); - translator = loadTranslator (&textBuffer, "fallback"); - } - return translator; -} - -KeyboardTranslator * -KeyboardTranslatorManager::loadTranslator (QIODevice * source, - const QString & name) -{ - KeyboardTranslator *translator = new KeyboardTranslator (name); - KeyboardTranslatorReader reader (source); - translator->setDescription (reader.description ()); - while (reader.hasNextEntry ()) - translator->addEntry (reader.nextEntry ()); - - source->close (); - - if (!reader.parseError ()) - { - return translator; - } - else - { - delete translator; - return 0; - } -} - -KeyboardTranslatorWriter::KeyboardTranslatorWriter (QIODevice * destination):_destination - (destination) -{ - Q_ASSERT (destination && destination->isWritable ()); - - _writer = new QTextStream (_destination); -} - -KeyboardTranslatorWriter::~KeyboardTranslatorWriter () -{ - delete _writer; -} - -void -KeyboardTranslatorWriter::writeHeader (const QString & description) -{ - *_writer << "keyboard \"" << description << '\"' << '\n'; -} - -void -KeyboardTranslatorWriter::writeEntry (const KeyboardTranslator::Entry & entry) -{ - QString result; - if (entry.command () != KeyboardTranslator::NoCommand) - result = entry.resultToString (); - else - result = '\"' + entry.resultToString () + '\"'; - - *_writer << "key " << entry.conditionToString () << " : " << result << '\n'; -} - - -// each line of the keyboard translation file is one of: -// -// - keyboard "name" -// - key KeySequence : "characters" -// - key KeySequence : CommandName -// -// KeySequence begins with the name of the key ( taken from the Qt::Key enum ) -// and is followed by the keyboard modifiers and state flags ( with + or - in front -// of each modifier or flag to indicate whether it is required ). All keyboard modifiers -// and flags are optional, if a particular modifier or state is not specified it is -// assumed not to be a part of the sequence. The key sequence may contain whitespace -// -// eg: "key Up+Shift : scrollLineUp" -// "key Next-Shift : "\E[6~" -// -// (lines containing only whitespace are ignored, parseLine assumes that comments have -// already been removed) -// - -KeyboardTranslatorReader::KeyboardTranslatorReader (QIODevice * source):_source (source), -_hasNext -(false) -{ - // read input until we find the description - while (_description.isEmpty () && !source->atEnd ()) - { - QList < Token > tokens = tokenize (QString (source->readLine ())); - if (!tokens.isEmpty () && tokens.first ().type == Token::TitleKeyword) - _description = QString (tokens[1].text.toLatin1 ().data ()); - } - // read first entry (if any) - readNext (); -} - -void -KeyboardTranslatorReader::readNext () -{ - // find next entry - while (!_source->atEnd ()) - { - const QList < Token > &tokens = - tokenize (QString (_source->readLine ())); - if (!tokens.isEmpty () && tokens.first ().type == Token::KeyKeyword) - { - KeyboardTranslator::States flags = KeyboardTranslator::NoState; - KeyboardTranslator::States flagMask = KeyboardTranslator::NoState; - Qt::KeyboardModifiers modifiers = Qt::NoModifier; - Qt::KeyboardModifiers modifierMask = Qt::NoModifier; - - int keyCode = Qt::Key_unknown; - - decodeSequence (tokens[1].text.toLower (), - keyCode, modifiers, modifierMask, flags, flagMask); - - KeyboardTranslator::Command command = KeyboardTranslator::NoCommand; - QByteArray text; - - // get text or command - if (tokens[2].type == Token::OutputText) - { - text = tokens[2].text.toLocal8Bit (); - } - else if (tokens[2].type == Token::Command) - { - // identify command - // if (!parseAsCommand(tokens[2].text,command)) - // kWarning() << "Command" << tokens[2].text << "not understood."; - } - - KeyboardTranslator::Entry newEntry; - newEntry.setKeyCode (keyCode); - newEntry.setState (flags); - newEntry.setStateMask (flagMask); - newEntry.setModifiers (modifiers); - newEntry.setModifierMask (modifierMask); - newEntry.setText (text); - newEntry.setCommand (command); - - _nextEntry = newEntry; - - _hasNext = true; - - return; - } - } - - _hasNext = false; -} - -bool -KeyboardTranslatorReader::parseAsCommand (const QString & text, - KeyboardTranslator:: - Command & command) -{ - if (text.compare ("erase", Qt::CaseInsensitive) == 0) - command = KeyboardTranslator::EraseCommand; - else if (text.compare ("scrollpageup", Qt::CaseInsensitive) == 0) - command = KeyboardTranslator::ScrollPageUpCommand; - else if (text.compare ("scrollpagedown", Qt::CaseInsensitive) == 0) - command = KeyboardTranslator::ScrollPageDownCommand; - else if (text.compare ("scrolllineup", Qt::CaseInsensitive) == 0) - command = KeyboardTranslator::ScrollLineUpCommand; - else if (text.compare ("scrolllinedown", Qt::CaseInsensitive) == 0) - command = KeyboardTranslator::ScrollLineDownCommand; - else if (text.compare ("scrolllock", Qt::CaseInsensitive) == 0) - command = KeyboardTranslator::ScrollLockCommand; - else - return false; - - return true; -} - -bool -KeyboardTranslatorReader::decodeSequence (const QString & text, - int &keyCode, - Qt::KeyboardModifiers & modifiers, - Qt:: - KeyboardModifiers & modifierMask, - KeyboardTranslator::States & flags, - KeyboardTranslator:: - States & flagMask) -{ - bool isWanted = true; - bool endOfItem = false; - QString buffer; - - Qt::KeyboardModifiers tempModifiers = modifiers; - Qt::KeyboardModifiers tempModifierMask = modifierMask; - KeyboardTranslator::States tempFlags = flags; - KeyboardTranslator::States tempFlagMask = flagMask; - - for (int i = 0; i < text.count (); i++) - { - const QChar & ch = text[i]; - bool isFirstLetter = i == 0; - bool isLastLetter = (i == text.count () - 1); - endOfItem = true; - if (ch.isLetterOrNumber ()) - { - endOfItem = false; - buffer.append (ch); - } - else if (isFirstLetter) - { - buffer.append (ch); - } - - if ((endOfItem || isLastLetter) && !buffer.isEmpty ()) - { - Qt::KeyboardModifier itemModifier = Qt::NoModifier; - int itemKeyCode = 0; - KeyboardTranslator::State itemFlag = KeyboardTranslator::NoState; - - if (parseAsModifier (buffer, itemModifier)) - { - tempModifierMask |= itemModifier; - - if (isWanted) - tempModifiers |= itemModifier; - } - else if (parseAsStateFlag (buffer, itemFlag)) - { - tempFlagMask |= itemFlag; - - if (isWanted) - tempFlags |= itemFlag; - } - else if (parseAsKeyCode (buffer, itemKeyCode)) - keyCode = itemKeyCode; - //else - // kWarning() << "Unable to parse key binding item:" << buffer; - - buffer.clear (); - } - - // check if this is a wanted / not-wanted flag and update the - // state ready for the next item - if (ch == '+') - isWanted = true; - else if (ch == '-') - isWanted = false; - } - - modifiers = tempModifiers; - modifierMask = tempModifierMask; - flags = tempFlags; - flagMask = tempFlagMask; - - return true; -} - -bool -KeyboardTranslatorReader::parseAsModifier (const QString & item, - Qt::KeyboardModifier & modifier) -{ - if (item == "shift") - modifier = Qt::ShiftModifier; - else if (item == "ctrl" || item == "control") - modifier = Qt::ControlModifier; - else if (item == "alt") - modifier = Qt::AltModifier; - else if (item == "meta") - modifier = Qt::MetaModifier; - else if (item == "keypad") - modifier = Qt::KeypadModifier; - else - return false; - - return true; -} - -bool -KeyboardTranslatorReader::parseAsStateFlag (const QString & item, - KeyboardTranslator::State & flag) -{ - if (item == "appcukeys" || item == "appcursorkeys") - flag = KeyboardTranslator::CursorKeysState; - else if (item == "ansi") - flag = KeyboardTranslator::AnsiState; - else if (item == "newline") - flag = KeyboardTranslator::NewLineState; - else if (item == "appscreen") - flag = KeyboardTranslator::AlternateScreenState; - else if (item == "anymod" || item == "anymodifier") - flag = KeyboardTranslator::AnyModifierState; - else if (item == "appkeypad") - flag = KeyboardTranslator::ApplicationKeypadState; - else - return false; - - return true; -} - -bool -KeyboardTranslatorReader::parseAsKeyCode (const QString & item, int &keyCode) -{ - QKeySequence sequence = QKeySequence::fromString (item); - if (!sequence.isEmpty ()) - { - keyCode = sequence[0]; - - if (sequence.count () > 1) - { - //kWarning() << "Unhandled key codes in sequence: " << item; - } - } - // additional cases implemented for backwards compatibility with KDE 3 - else if (item == "prior") - keyCode = Qt::Key_PageUp; - else if (item == "next") - keyCode = Qt::Key_PageDown; - else - return false; - - return true; -} - -QString -KeyboardTranslatorReader::description () const -{ - return _description; -} - -bool -KeyboardTranslatorReader::hasNextEntry () -{ - return _hasNext; -} - -KeyboardTranslator::Entry KeyboardTranslatorReader:: -createEntry (const QString & condition, const QString & result) -{ - QString - entryString ("keyboard \"temporary\"\nkey "); - entryString.append (condition); - entryString.append (" : "); - - // if 'result' is the name of a command then the entry result will be that command, - // otherwise the result will be treated as a string to echo when the key sequence - // specified by 'condition' is pressed - KeyboardTranslator::Command command; - if (parseAsCommand (result, command)) - entryString.append (result); - else - entryString.append ('\"' + result + '\"'); - - QByteArray - array = entryString.toUtf8 (); - QBuffer - buffer (&array); - buffer.open (QIODevice::ReadOnly); - KeyboardTranslatorReader - reader (&buffer); - - KeyboardTranslator::Entry entry; - if (reader.hasNextEntry ()) - entry = reader.nextEntry (); - - return entry; -} - -KeyboardTranslator::Entry KeyboardTranslatorReader::nextEntry () -{ - Q_ASSERT (_hasNext); - KeyboardTranslator::Entry entry = _nextEntry; - readNext (); - return entry; -} - -bool -KeyboardTranslatorReader::parseError () -{ - return false; -} - -QList < KeyboardTranslatorReader::Token > - KeyboardTranslatorReader::tokenize (const QString & line) -{ - QString text = line; - - // remove comments - bool inQuotes = false; - int commentPos = -1; - for (int i = text.length () - 1; i >= 0; i--) - { - QChar ch = text[i]; - if (ch == '\"') - inQuotes = !inQuotes; - else if (ch == '#' && !inQuotes) - commentPos = i; - } - if (commentPos != -1) - text.remove (commentPos, text.length ()); - - text = text.simplified (); - - // title line: keyboard "title" - static QRegExp title ("keyboard\\s+\"(.*)\""); - // key line: key KeySequence : "output" - // key line: key KeySequence : command - static QRegExp - key ("key\\s+([\\w\\+\\s\\-\\*\\.]+)\\s*:\\s*(\"(.*)\"|\\w+)"); - - QList < Token > list; - if (text.isEmpty ()) - { - return list; - } - - if (title.exactMatch (text)) - { - Token titleToken = { Token::TitleKeyword, QString () }; - Token textToken = { Token::TitleText, title.capturedTexts ()[1] }; - - list << titleToken << textToken; - } - else if (key.exactMatch (text)) - { - Token keyToken = { Token::KeyKeyword, QString () }; - Token sequenceToken = - { Token::KeySequence, key.capturedTexts ()[1].remove (' ') }; - - list << keyToken << sequenceToken; - - if (key.capturedTexts ()[3].isEmpty ()) - { - // capturedTexts()[2] is a command - Token commandToken = { Token::Command, key.capturedTexts ()[2] }; - list << commandToken; - } - else - { - // capturedTexts()[3] is the output string - Token outputToken = { Token::OutputText, key.capturedTexts ()[3] }; - list << outputToken; - } - } - else - { - //kWarning() << "Line in keyboard translator file could not be understood:" << text; - } - - return list; -} - -QList < QString > KeyboardTranslatorManager::allTranslators () -{ - if (!_haveLoadedAll) - { - findTranslators (); - } - - return _translators.keys (); -} - -KeyboardTranslator::Entry::Entry ():_keyCode (0), _modifiers (Qt::NoModifier), _modifierMask (Qt::NoModifier), -_state (NoState), _stateMask (NoState), -_command (NoCommand) -{ -} - -bool -KeyboardTranslator::Entry::operator== (const Entry & rhs) const -{ - return _keyCode == rhs._keyCode && - _modifiers == rhs._modifiers && - _modifierMask == rhs._modifierMask && - _state == rhs._state && - _stateMask == rhs._stateMask && - _command == rhs._command && _text == rhs._text; -} - -bool -KeyboardTranslator::Entry::matches (int keyCode, - Qt::KeyboardModifiers modifiers, - States testState) const -{ - if (_keyCode != keyCode) - return false; - - if ((modifiers & _modifierMask) != (_modifiers & _modifierMask)) - return false; - - // if modifiers is non-zero, the 'any modifier' state is implicit - if (modifiers != 0) - testState |= AnyModifierState; - - if ((testState & _stateMask) != (_state & _stateMask)) - return false; - - // special handling for the 'Any Modifier' state, which checks for the presence of - // any or no modifiers. In this context, the 'keypad' modifier does not count. - bool - anyModifiersSet = modifiers != 0 && modifiers != Qt::KeypadModifier; - bool - wantAnyModifier = _state & KeyboardTranslator::AnyModifierState; - if (_stateMask & KeyboardTranslator::AnyModifierState) - { - if (wantAnyModifier != anyModifiersSet) - return false; - } - - return true; -} - -QByteArray -KeyboardTranslator::Entry::escapedText (bool expandWildCards, - Qt:: - KeyboardModifiers modifiers) const -{ - QByteArray - result (text (expandWildCards, modifiers)); - - for (int i = 0; i < result.count (); i++) - { - char - ch = result[i]; - char - replacement = 0; - - switch (ch) - { - case 27: - replacement = 'E'; - break; - case 8: - replacement = 'b'; - break; - case 12: - replacement = 'f'; - break; - case 9: - replacement = 't'; - break; - case 13: - replacement = 'r'; - break; - case 10: - replacement = 'n'; - break; - default: - // any character which is not printable is replaced by an equivalent - // \xhh escape sequence (where 'hh' are the corresponding hex digits) - if (!QChar (ch).isPrint ()) - replacement = 'x'; - } - - if (replacement == 'x') - { - result.replace (i, 1, "\\x" + QByteArray (1, ch).toHex ()); - } - else if (replacement != 0) - { - result.remove (i, 1); - result.insert (i, '\\'); - result.insert (i + 1, replacement); - } - } - - return result; -} - -QByteArray -KeyboardTranslator::Entry::unescape (const QByteArray & input) const -{ - QByteArray - result (input); - - for (int i = 0; i < result.count () - 1; i++) - { - - QByteRef - ch = result[i]; - if (ch == '\\') - { - char - replacement[2] = { 0, 0 }; - int - charsToRemove = 2; - bool - escapedChar = true; - - switch (result[i + 1]) - { - case 'E': - replacement[0] = 27; - break; - case 'b': - replacement[0] = 8; - break; - case 'f': - replacement[0] = 12; - break; - case 't': - replacement[0] = 9; - break; - case 'r': - replacement[0] = 13; - break; - case 'n': - replacement[0] = 10; - break; - case 'x': - { - // format is \xh or \xhh where 'h' is a hexadecimal - // digit from 0-9 or A-F which should be replaced - // with the corresponding character value - char - hexDigits[3] = { 0 }; - - if ((i < result.count () - 2) && isxdigit (result[i + 2])) - hexDigits[0] = result[i + 2]; - if ((i < result.count () - 3) && isxdigit (result[i + 3])) - hexDigits[1] = result[i + 3]; - - unsigned - charValue = 0; - sscanf (hexDigits, "%x", &charValue); - - replacement[0] = (char) charValue; - charsToRemove = 2 + strlen (hexDigits); - } - break; - default: - escapedChar = false; - } - - if (escapedChar) - result.replace (i, charsToRemove, replacement); - } - } - - return result; -} - -void -KeyboardTranslator::Entry::insertModifier (QString & item, int modifier) const -{ - if (!(modifier & _modifierMask)) - return; - - if (modifier & _modifiers) - item += '+'; - else - item += '-'; - - if (modifier == Qt::ShiftModifier) - item += "Shift"; - else if (modifier == Qt::ControlModifier) - item += "Ctrl"; - else if (modifier == Qt::AltModifier) - item += "Alt"; - else if (modifier == Qt::MetaModifier) - item += "Meta"; - else if (modifier == Qt::KeypadModifier) - item += "KeyPad"; -} - -void -KeyboardTranslator::Entry::insertState (QString & item, int state) const -{ - if (!(state & _stateMask)) - return; - - if (state & _state) - item += '+'; - else - item += '-'; - - if (state == KeyboardTranslator::AlternateScreenState) - item += "AppScreen"; - else if (state == KeyboardTranslator::NewLineState) - item += "NewLine"; - else if (state == KeyboardTranslator::AnsiState) - item += "Ansi"; - else if (state == KeyboardTranslator::CursorKeysState) - item += "AppCursorKeys"; - else if (state == KeyboardTranslator::AnyModifierState) - item += "AnyModifier"; - else if (state == KeyboardTranslator::ApplicationKeypadState) - item += "AppKeypad"; -} - -QString -KeyboardTranslator::Entry::resultToString (bool expandWildCards, - Qt:: - KeyboardModifiers modifiers) const -{ - if (!_text.isEmpty ()) - return escapedText (expandWildCards, modifiers); - else if (_command == EraseCommand) - return "Erase"; - else if (_command == ScrollPageUpCommand) - return "ScrollPageUp"; - else if (_command == ScrollPageDownCommand) - return "ScrollPageDown"; - else if (_command == ScrollLineUpCommand) - return "ScrollLineUp"; - else if (_command == ScrollLineDownCommand) - return "ScrollLineDown"; - else if (_command == ScrollLockCommand) - return "ScrollLock"; - - return QString (); -} - -QString -KeyboardTranslator::Entry::conditionToString () const -{ - QString - result = QKeySequence (_keyCode).toString (); - - insertModifier (result, Qt::ShiftModifier); - insertModifier (result, Qt::ControlModifier); - insertModifier (result, Qt::AltModifier); - insertModifier (result, Qt::MetaModifier); - insertModifier (result, Qt::KeypadModifier); - - insertState (result, KeyboardTranslator::AlternateScreenState); - insertState (result, KeyboardTranslator::NewLineState); - insertState (result, KeyboardTranslator::AnsiState); - insertState (result, KeyboardTranslator::CursorKeysState); - insertState (result, KeyboardTranslator::AnyModifierState); - insertState (result, KeyboardTranslator::ApplicationKeypadState); - - return result; -} - -KeyboardTranslator::KeyboardTranslator (const QString & name):_name (name) -{ -} - -void -KeyboardTranslator::setDescription (const QString & description) -{ - _description = description; -} - -QString -KeyboardTranslator::description () const -{ - return _description; -} - -void -KeyboardTranslator::setName (const QString & name) -{ - _name = name; -} - -QString -KeyboardTranslator::name () const -{ - return _name; -} - -QList < KeyboardTranslator::Entry > -KeyboardTranslator::entries () const -{ - return _entries.values (); -} - -void -KeyboardTranslator::addEntry (const Entry & entry) -{ - const int keyCode = entry.keyCode (); - _entries.insert (keyCode, entry); -} - -void -KeyboardTranslator::replaceEntry (const Entry & existing, - const Entry & replacement) -{ - if (!existing.isNull ()) - _entries.remove (existing.keyCode (), existing); - _entries.insert (replacement.keyCode (), replacement); -} - -void -KeyboardTranslator::removeEntry (const Entry & entry) -{ - _entries.remove (entry.keyCode (), entry); -} - -KeyboardTranslator::Entry KeyboardTranslator::findEntry (int keyCode, - Qt:: - KeyboardModifiers - modifiers, - States state) const -{ - foreach (const Entry & entry, _entries.values (keyCode)) - { - if (entry.matches (keyCode, modifiers, state)) - return entry; - } - return Entry (); // entry not found -} - -void -KeyboardTranslatorManager::addTranslator (KeyboardTranslator * translator) -{ - _translators.insert (translator->name (), translator); - - // if ( !saveTranslator(translator) ) - // kWarning() << "Unable to save translator" << translator->name() - // << "to disk."; -} - -bool -KeyboardTranslatorManager::deleteTranslator (const QString & name) -{ - Q_ASSERT (_translators.contains (name)); - - // locate and delete - QString path = findTranslatorPath (name); - if (QFile::remove (path)) - { - _translators.remove (name); - return true; - } - else - { - //kWarning() << "Failed to remove translator - " << path; - return false; - } -} - -/** - * @internal - */ -typedef void (*KdeCleanUpFunction) (); - -/** - * @internal - * - * Helper class for K_GLOBAL_STATIC to clean up the object on library unload or application - * shutdown. - */ -class KCleanUpGlobalStatic -{ -public: - KdeCleanUpFunction func; - - inline ~ KCleanUpGlobalStatic () - { - func (); - } -}; - - - -#ifdef Q_CC_MSVC -/** - * @internal - * - * MSVC seems to give anonymous structs the same name which fails at link time. So instead we name - * the struct and hope that by adding the line number to the name it's unique enough to never clash. - */ -#define K_GLOBAL_STATIC_STRUCT_NAME(NAME) _k_##NAME##__LINE__ -#else -/** - * @internal - * - * Make the struct of the K_GLOBAL_STATIC anonymous. - */ -#define K_GLOBAL_STATIC_STRUCT_NAME(NAME) -#endif - - - -#define K_GLOBAL_STATIC_WITH_ARGS(TYPE, NAME, ARGS) \ -static QBasicAtomicPointer _k_static_##NAME = Q_BASIC_ATOMIC_INITIALIZER(0); \ -static bool _k_static_##NAME##_destroyed; \ -static struct K_GLOBAL_STATIC_STRUCT_NAME(NAME) \ -{ \ - inline bool isDestroyed() const \ - { \ - return _k_static_##NAME##_destroyed; \ - } \ - inline bool exists() const \ - { \ - return _k_static_##NAME != 0; \ - } \ - inline operator TYPE*() \ - { \ - return operator->(); \ - } \ - inline TYPE *operator->() \ - { \ - if (!_k_static_##NAME) { \ - if (isDestroyed()) { \ - qFatal("Fatal Error: Accessed global static '%s *%s()' after destruction. " \ - "Defined at %s:%d", #TYPE, #NAME, __FILE__, __LINE__); \ - } \ - TYPE *x = new TYPE ARGS; \ - if (!_k_static_##NAME.testAndSetOrdered(0, x) \ - && _k_static_##NAME != x ) { \ - delete x; \ - } else { \ - static KCleanUpGlobalStatic cleanUpObject = { destroy }; \ - } \ - } \ - return _k_static_##NAME; \ - } \ - inline TYPE &operator*() \ - { \ - return *operator->(); \ - } \ - static void destroy() \ - { \ - _k_static_##NAME##_destroyed = true; \ - TYPE *x = _k_static_##NAME; \ - _k_static_##NAME = 0; \ - delete x; \ - } \ -} NAME; - -#define K_GLOBAL_STATIC(TYPE, NAME) K_GLOBAL_STATIC_WITH_ARGS(TYPE, NAME, ()) - -K_GLOBAL_STATIC (KeyboardTranslatorManager, theKeyboardTranslatorManager) - KeyboardTranslatorManager *KeyboardTranslatorManager::instance () -{ - return theKeyboardTranslatorManager; -} diff -r cc90c62ada21 -r b31663fb7e8a gui/src/terminal/KeyboardTranslator.h --- a/gui/src/terminal/KeyboardTranslator.h Thu Aug 18 19:20:10 2011 +0200 +++ /dev/null Thu Jan 01 00:00:00 1970 +0000 @@ -1,626 +0,0 @@ -/* - This source file is part of Konsole, a terminal emulator. - - Copyright 2007-2008 by Robert Knight - - This program is free software; you can redistribute it and/or modify - it under the terms of the GNU General Public License as published by - the Free Software Foundation; either version 2 of the License, or - (at your option) any later version. - - This program is distributed in the hope that it will be useful, - but WITHOUT ANY WARRANTY; without even the implied warranty of - MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the - GNU General Public License for more details. - - You should have received a copy of the GNU General Public License - along with this program; if not, write to the Free Software - Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA - 02110-1301 USA. -*/ - -#ifndef KEYBOARDTRANSLATOR_H -#define KEYBOARDTRANSLATOR_H - -// Qt -#include -#include -#include -#include -#include - -class QIODevice; -class QTextStream; - -/** - * A convertor which maps between key sequences pressed by the user and the - * character strings which should be sent to the terminal and commands - * which should be invoked when those character sequences are pressed. - * - * Konsole supports multiple keyboard translators, allowing the user to - * specify the character sequences which are sent to the terminal - * when particular key sequences are pressed. - * - * A key sequence is defined as a key code, associated keyboard modifiers - * (Shift,Ctrl,Alt,Meta etc.) and state flags which indicate the state - * which the terminal must be in for the key sequence to apply. - */ -class KeyboardTranslator -{ -public: - /** - * The meaning of a particular key sequence may depend upon the state which - * the terminal emulation is in. Therefore findEntry() may return a different - * Entry depending upon the state flags supplied. - * - * This enum describes the states which may be associated with with a particular - * entry in the keyboard translation entry. - */ - enum State - { - /** Indicates that no special state is active */ - NoState = 0, - /** - * TODO More documentation - */ - NewLineState = 1, - /** - * Indicates that the terminal is in 'Ansi' mode. - * TODO: More documentation - */ - AnsiState = 2, - /** - * TODO More documentation - */ - CursorKeysState = 4, - /** - * Indicates that the alternate screen ( typically used by interactive programs - * such as screen or vim ) is active - */ - AlternateScreenState = 8, - /** Indicates that any of the modifier keys is active. */ - AnyModifierState = 16, - /** Indicates that the numpad is in application mode. */ - ApplicationKeypadState = 32 - }; - Q_DECLARE_FLAGS (States, State) - /** - * This enum describes commands which are associated with particular key sequences. - */ - enum Command - { - /** Indicates that no command is associated with this command sequence */ - NoCommand = 0, - /** TODO Document me */ - SendCommand = 1, - /** Scroll the terminal display up one page */ - ScrollPageUpCommand = 2, - /** Scroll the terminal display down one page */ - ScrollPageDownCommand = 4, - /** Scroll the terminal display up one line */ - ScrollLineUpCommand = 8, - /** Scroll the terminal display down one line */ - ScrollLineDownCommand = 16, - /** Toggles scroll lock mode */ - ScrollLockCommand = 32, - /** Echos the operating system specific erase character. */ - EraseCommand = 64 - }; - Q_DECLARE_FLAGS (Commands, Command) - /** - * Represents an association between a key sequence pressed by the user - * and the character sequence and commands associated with it for a particular - * KeyboardTranslator. - */ - class Entry - { - public: - /** - * Constructs a new entry for a keyboard translator. - */ - Entry (); - - /** - * Returns true if this entry is null. - * This is true for newly constructed entries which have no properties set. - */ - bool isNull () const; - - /** Returns the commands associated with this entry */ - Command command () const; - /** Sets the command associated with this entry. */ - void setCommand (Command command); - - /** - * Returns the character sequence associated with this entry, optionally replacing - * wildcard '*' characters with numbers to indicate the keyboard modifiers being pressed. - * - * TODO: The numbers used to replace '*' characters are taken from the Konsole/KDE 3 code. - * Document them. - * - * @param expandWildCards Specifies whether wild cards (occurrences of the '*' character) in - * the entry should be replaced with a number to indicate the modifier keys being pressed. - * - * @param modifiers The keyboard modifiers being pressed. - */ - QByteArray text (bool expandWildCards = false, - Qt::KeyboardModifiers modifiers = Qt::NoModifier) const; - - /** Sets the character sequence associated with this entry */ - void setText (const QByteArray & text); - - /** - * Returns the character sequence associated with this entry, - * with any non-printable characters replaced with escape sequences. - * - * eg. \\E for Escape, \\t for tab, \\n for new line. - * - * @param expandWildCards See text() - * @param modifiers See text() - */ - QByteArray escapedText (bool expandWildCards = false, - Qt::KeyboardModifiers modifiers = - Qt::NoModifier) const; - - /** Returns the character code ( from the Qt::Key enum ) associated with this entry */ - int keyCode () const; - /** Sets the character code associated with this entry */ - void setKeyCode (int keyCode); - - /** - * Returns a bitwise-OR of the enabled keyboard modifiers associated with this entry. - * If a modifier is set in modifierMask() but not in modifiers(), this means that the entry - * only matches when that modifier is NOT pressed. - * - * If a modifier is not set in modifierMask() then the entry matches whether the modifier - * is pressed or not. - */ - Qt::KeyboardModifiers modifiers () const; - - /** Returns the keyboard modifiers which are valid in this entry. See modifiers() */ - Qt::KeyboardModifiers modifierMask () const; - - /** See modifiers() */ - void setModifiers (Qt::KeyboardModifiers modifiers); - /** See modifierMask() and modifiers() */ - void setModifierMask (Qt::KeyboardModifiers modifiers); - - /** - * Returns a bitwise-OR of the enabled state flags associated with this entry. - * If flag is set in stateMask() but not in state(), this means that the entry only - * matches when the terminal is NOT in that state. - * - * If a state is not set in stateMask() then the entry matches whether the terminal - * is in that state or not. - */ - States state () const; - - /** Returns the state flags which are valid in this entry. See state() */ - States stateMask () const; - - /** See state() */ - void setState (States state); - /** See stateMask() */ - void setStateMask (States mask); - - /** - * Returns the key code and modifiers associated with this entry - * as a QKeySequence - */ - //QKeySequence keySequence() const; - - /** - * Returns this entry's conditions ( ie. its key code, modifier and state criteria ) - * as a string. - */ - QString conditionToString () const; - - /** - * Returns this entry's result ( ie. its command or character sequence ) - * as a string. - * - * @param expandWildCards See text() - * @param modifiers See text() - */ - QString resultToString (bool expandWildCards = false, - Qt::KeyboardModifiers modifiers = - Qt::NoModifier) const; - - /** - * Returns true if this entry matches the given key sequence, specified - * as a combination of @p keyCode , @p modifiers and @p state. - */ - bool matches (int keyCode, - Qt::KeyboardModifiers modifiers, States flags) const; - - bool operator== (const Entry & rhs) const; - - private: - void insertModifier (QString & item, int modifier) const; - void insertState (QString & item, int state) const; - QByteArray unescape (const QByteArray & text) const; - - int _keyCode; - Qt::KeyboardModifiers _modifiers; - Qt::KeyboardModifiers _modifierMask; - States _state; - States _stateMask; - - Command _command; - QByteArray _text; - }; - - /** Constructs a new keyboard translator with the given @p name */ - KeyboardTranslator (const QString & name); - - //KeyboardTranslator(const KeyboardTranslator& other); - - /** Returns the name of this keyboard translator */ - QString name () const; - - /** Sets the name of this keyboard translator */ - void setName (const QString & name); - - /** Returns the descriptive name of this keyboard translator */ - QString description () const; - - /** Sets the descriptive name of this keyboard translator */ - void setDescription (const QString & description); - - /** - * Looks for an entry in this keyboard translator which matches the given - * key code, keyboard modifiers and state flags. - * - * Returns the matching entry if found or a null Entry otherwise ( ie. - * entry.isNull() will return true ) - * - * @param keyCode A key code from the Qt::Key enum - * @param modifiers A combination of modifiers - * @param state Optional flags which specify the current state of the terminal - */ - Entry findEntry (int keyCode, - Qt::KeyboardModifiers modifiers, - States state = NoState) const; - - /** - * Adds an entry to this keyboard translator's table. Entries can be looked up according - * to their key sequence using findEntry() - */ - void addEntry (const Entry & entry); - - /** - * Replaces an entry in the translator. If the @p existing entry is null, - * then this is equivalent to calling addEntry(@p replacement) - */ - void replaceEntry (const Entry & existing, const Entry & replacement); - - /** - * Removes an entry from the table. - */ - void removeEntry (const Entry & entry); - - /** Returns a list of all entries in the translator. */ - QList < Entry > entries () const; - -private: - - QMultiHash < int, Entry > _entries; // entries in this keyboard translation, - // entries are indexed according to - // their keycode - QString _name; - QString _description; -}; -Q_DECLARE_OPERATORS_FOR_FLAGS (KeyboardTranslator::States) -Q_DECLARE_OPERATORS_FOR_FLAGS (KeyboardTranslator::Commands) -/** - * Parses the contents of a Keyboard Translator (.keytab) file and - * returns the entries found in it. - * - * Usage example: - * - * @code - * QFile source( "/path/to/keytab" ); - * source.open( QIODevice::ReadOnly ); - * - * KeyboardTranslator* translator = new KeyboardTranslator( "name-of-translator" ); - * - * KeyboardTranslatorReader reader(source); - * while ( reader.hasNextEntry() ) - * translator->addEntry(reader.nextEntry()); - * - * source.close(); - * - * if ( !reader.parseError() ) - * { - * // parsing succeeded, do something with the translator - * } - * else - * { - * // parsing failed - * } - * @endcode - */ - class KeyboardTranslatorReader - { - public: - /** Constructs a new reader which parses the given @p source */ - KeyboardTranslatorReader (QIODevice * source); - - /** - * Returns the description text. - * TODO: More documentation - */ - QString description () const; - - /** Returns true if there is another entry in the source stream */ - bool hasNextEntry (); - /** Returns the next entry found in the source stream */ - KeyboardTranslator::Entry nextEntry (); - - /** - * Returns true if an error occurred whilst parsing the input or - * false if no error occurred. - */ - bool parseError (); - - /** - * Parses a condition and result string for a translator entry - * and produces a keyboard translator entry. - * - * The condition and result strings are in the same format as in - */ - static KeyboardTranslator:: - Entry createEntry (const QString & condition, - const QString & result); - private: - struct Token - { - enum Type - { - TitleKeyword, - TitleText, - KeyKeyword, - KeySequence, - Command, - OutputText - }; - Type type; - QString text; - }; - QList < Token > tokenize (const QString &); - void readNext (); - bool decodeSequence (const QString &, - int &keyCode, - Qt::KeyboardModifiers & modifiers, - Qt::KeyboardModifiers & modifierMask, - KeyboardTranslator::States & state, - KeyboardTranslator::States & stateFlags); - - static bool parseAsModifier (const QString & item, - Qt::KeyboardModifier & modifier); - static bool parseAsStateFlag (const QString & item, - KeyboardTranslator::State & state); - static bool parseAsKeyCode (const QString & item, int &keyCode); - static bool parseAsCommand (const QString & text, - KeyboardTranslator::Command & command); - - QIODevice *_source; - QString _description; - KeyboardTranslator::Entry _nextEntry; - bool _hasNext; - }; - -/** Writes a keyboard translation to disk. */ - class KeyboardTranslatorWriter - { - public: - /** - * Constructs a new writer which saves data into @p destination. - * The caller is responsible for closing the device when writing is complete. - */ - KeyboardTranslatorWriter (QIODevice * destination); - ~KeyboardTranslatorWriter (); - - /** - * Writes the header for the keyboard translator. - * @param description Description of the keyboard translator. - */ - void writeHeader (const QString & description); - /** Writes a translator entry. */ - void writeEntry (const KeyboardTranslator::Entry & entry); - - private: - QIODevice * _destination; - QTextStream *_writer; - }; - -/** - * Manages the keyboard translations available for use by terminal sessions, - * see KeyboardTranslator. - */ - class KeyboardTranslatorManager - { - public: - /** - * Constructs a new KeyboardTranslatorManager and loads the list of - * available keyboard translations. - * - * The keyboard translations themselves are not loaded until they are - * first requested via a call to findTranslator() - */ - KeyboardTranslatorManager (); - ~KeyboardTranslatorManager (); - - /** - * Adds a new translator. If a translator with the same name - * already exists, it will be replaced by the new translator. - * - * TODO: More documentation. - */ - void addTranslator (KeyboardTranslator * translator); - - /** - * Deletes a translator. Returns true on successful deletion or false otherwise. - * - * TODO: More documentation - */ - bool deleteTranslator (const QString & name); - - /** Returns the default translator for Konsole. */ - const KeyboardTranslator *defaultTranslator (); - - /** - * Returns the keyboard translator with the given name or 0 if no translator - * with that name exists. - * - * The first time that a translator with a particular name is requested, - * the on-disk .keyboard file is loaded and parsed. - */ - const KeyboardTranslator *findTranslator (const QString & name); - /** - * Returns a list of the names of available keyboard translators. - * - * The first time this is called, a search for available - * translators is started. - */ - QList < QString > allTranslators (); - - /** Returns the global KeyboardTranslatorManager instance. */ - static KeyboardTranslatorManager *instance (); - - private: - static const QByteArray defaultTranslatorText; - - void findTranslators (); // locate the available translators - KeyboardTranslator *loadTranslator (const QString & name); // loads the translator - // with the given name - KeyboardTranslator *loadTranslator (QIODevice * device, - const QString & name); - - bool saveTranslator (const KeyboardTranslator * translator); - QString findTranslatorPath (const QString & name); - - QHash < QString, KeyboardTranslator * >_translators; // maps translator-name -> KeyboardTranslator - // instance - bool _haveLoadedAll; - }; - -inline int -KeyboardTranslator::Entry::keyCode () const -{ - return _keyCode; -} - -inline void -KeyboardTranslator::Entry::setKeyCode (int keyCode) -{ - _keyCode = keyCode; -} - -inline void -KeyboardTranslator::Entry::setModifiers (Qt::KeyboardModifiers modifier) -{ - _modifiers = modifier; -} - -inline Qt::KeyboardModifiers -KeyboardTranslator::Entry::modifiers () const -{ - return _modifiers; -} - -inline void -KeyboardTranslator::Entry::setModifierMask (Qt::KeyboardModifiers mask) -{ - _modifierMask = mask; -} - -inline Qt::KeyboardModifiers -KeyboardTranslator::Entry::modifierMask () const -{ - return _modifierMask; -} - -inline bool -KeyboardTranslator::Entry::isNull () const -{ - return (*this == Entry ()); -} - -inline void -KeyboardTranslator::Entry::setCommand (Command command) -{ - _command = command; -} - -inline KeyboardTranslator::Command -KeyboardTranslator::Entry::command () const -{ - return _command; -} - -inline void -KeyboardTranslator::Entry::setText (const QByteArray & text) -{ - _text = unescape (text); -} - -inline int -oneOrZero (int value) -{ - return value ? 1 : 0; -} - -inline QByteArray -KeyboardTranslator::Entry::text (bool expandWildCards, - Qt::KeyboardModifiers modifiers) const -{ - QByteArray - expandedText = _text; - - if (expandWildCards) - { - int - modifierValue = 1; - modifierValue += oneOrZero (modifiers & Qt::ShiftModifier); - modifierValue += oneOrZero (modifiers & Qt::AltModifier) << 1; - modifierValue += oneOrZero (modifiers & Qt::ControlModifier) << 2; - - for (int i = 0; i < _text.length (); i++) - { - if (expandedText[i] == '*') - expandedText[i] = '0' + modifierValue; - } - } - - return expandedText; -} - -inline void -KeyboardTranslator::Entry::setState (States state) -{ - _state = state; -} - -inline KeyboardTranslator::States -KeyboardTranslator::Entry::state () const -{ - return _state; -} - -inline void -KeyboardTranslator::Entry::setStateMask (States stateMask) -{ - _stateMask = stateMask; -} - -inline KeyboardTranslator::States -KeyboardTranslator::Entry::stateMask () const -{ - return _stateMask; -} - - -Q_DECLARE_METATYPE (KeyboardTranslator::Entry) -Q_DECLARE_METATYPE (const KeyboardTranslator *) -#endif // KEYBOARDTRANSLATOR_H diff -r cc90c62ada21 -r b31663fb7e8a gui/src/terminal/Session.cpp --- a/gui/src/terminal/Session.cpp Thu Aug 18 19:20:10 2011 +0200 +++ b/gui/src/terminal/Session.cpp Thu Aug 18 20:45:00 2011 +0200 @@ -37,6 +37,8 @@ #include #include #include +#include +#include #include "kprocess.h" #include "kptydevice.h" diff -r cc90c62ada21 -r b31663fb7e8a gui/src/terminal/Session.h --- a/gui/src/terminal/Session.h Thu Aug 18 19:20:10 2011 +0200 +++ b/gui/src/terminal/Session.h Thu Aug 18 20:45:00 2011 +0200 @@ -30,9 +30,8 @@ #include #include #include - -// Konsole -#include "History.h" +#include +#include class KProcess; class Pty;