summaryrefslogtreecommitdiff
path: root/core/apps/embeddedkonsole/konsole.cpp
Unidiff
Diffstat (limited to 'core/apps/embeddedkonsole/konsole.cpp') (more/less context) (ignore whitespace changes)
-rw-r--r--core/apps/embeddedkonsole/konsole.cpp512
1 files changed, 512 insertions, 0 deletions
diff --git a/core/apps/embeddedkonsole/konsole.cpp b/core/apps/embeddedkonsole/konsole.cpp
new file mode 100644
index 0000000..7253baf
--- a/dev/null
+++ b/core/apps/embeddedkonsole/konsole.cpp
@@ -0,0 +1,512 @@
1/* ---------------------------------------------------------------------- */
2/* */
3/* [main.C] Konsole */
4/* */
5/* ---------------------------------------------------------------------- */
6/* */
7/* Copyright (c) 1997,1998 by Lars Doelle <lars.doelle@on-line.de> */
8/* */
9/* This file is part of Konsole, an X terminal. */
10/* */
11/* The material contained in here more or less directly orginates from */
12/* kvt, which is copyright (c) 1996 by Matthias Ettrich <ettrich@kde.org> */
13/* */
14/* ---------------------------------------------------------------------- */
15 /* */
16/* Ported Konsole to Qt/Embedded */
17 /* */
18/* Copyright (C) 2000 by John Ryland <jryland@trolltech.com> */
19 /* */
20/* -------------------------------------------------------------------------- */
21
22#include <qpe/resource.h>
23
24#include <qdir.h>
25#include <qevent.h>
26#include <qdragobject.h>
27#include <qobjectlist.h>
28#include <qtoolbutton.h>
29#include <qpe/qpetoolbar.h>
30#include <qpushbutton.h>
31#include <qfontdialog.h>
32#include <qglobal.h>
33#include <qpainter.h>
34#include <qpe/qpemenubar.h>
35#include <qmessagebox.h>
36#include <qaction.h>
37#include <qapplication.h>
38#include <qfontmetrics.h>
39#include <qcombobox.h>
40#include <qevent.h>
41#include <qtabwidget.h>
42#include <qtabbar.h>
43#include <qpe/config.h>
44
45#include <sys/wait.h>
46#include <stdio.h>
47#include <stdlib.h>
48#include <assert.h>
49
50#include "konsole.h"
51#include "keytrans.h"
52
53class EKNumTabBar : public QTabBar {
54public:
55 void numberTabs()
56 {
57 // Yes, it really is this messy. QTabWidget needs functions
58 // that provide acces to tabs in a sequential way.
59 int m=INT_MIN;
60 for (int i=0; i<count(); i++) {
61 QTab* left=0;
62 QListIterator<QTab> it(*tabList());
63 int x=INT_MAX;
64 for( QTab* t; (t=it.current()); ++it ) {
65 int tx = t->rect().x();
66 if ( tx<x && tx>m ) {
67 x = tx;
68 left = t;
69 }
70 }
71 if ( left ) {
72 left->setText(QString::number(i+1));
73 m = left->rect().x();
74 }
75 }
76 }
77};
78
79class EKNumTabWidget : public QTabWidget {
80public:
81 EKNumTabWidget(QWidget* parent) : QTabWidget(parent)
82 {
83 }
84
85 void addTab(QWidget* w)
86 {
87 QTab* t = new QTab(QString::number(tabBar()->count()+1));
88 QTabWidget::addTab(w,t);
89 }
90
91 void removeTab(QWidget* w)
92 {
93 removePage(w);
94 ((EKNumTabBar*)tabBar())->numberTabs();
95 }
96};
97
98// This could be configurable or dynamicly generated from the bash history
99// file of the user
100static const char *commonCmds[] =
101{
102 "ls ",
103 //"ls -la ",
104 "cd ",
105 "pwd",
106 //"cat",
107 //"less ",
108 //"vi ",
109 //"man ",
110 "echo ",
111 "set ",
112 //"ps",
113 "ps aux",
114 //"tar",
115 //"tar -zxf",
116 "grep ",
117 //"grep -i",
118 //"mkdir",
119 "cp ",
120 "mv ",
121 "rm ",
122 "rmdir ",
123 //"chmod",
124 //"su",
125// "top",
126 //"find",
127 //"make",
128 //"tail",
129 "cardctl eject",
130 "ifconfig ",
131// "iwconfig eth0 ",
132 "nc localhost 7777",
133 "nc localhost 7776",
134 //"mount /dev/hda1",
135
136/*
137 "gzip",
138 "gunzip",
139 "chgrp",
140 "chown",
141 "date",
142 "dd",
143 "df",
144 "dmesg",
145 "fuser",
146 "hostname",
147 "kill",
148 "killall",
149 "ln",
150 "ping",
151 "mount",
152 "more",
153 "sort",
154 "touch",
155 "umount",
156 "mknod",
157 "netstat",
158*/
159
160 "exit",
161 NULL
162};
163
164
165Konsole::Konsole(QWidget* parent, const char* name, WFlags fl) :
166 QMainWindow(parent, name, fl)
167{
168 QStrList args;
169 init("/bin/sh",args);
170}
171
172Konsole::Konsole(const char* name, const char* _pgm, QStrList & _args, int)
173 : QMainWindow(0, name)
174{
175 init(_pgm,_args);
176}
177
178void Konsole::init(const char* _pgm, QStrList & _args)
179{
180 b_scroll = TRUE; // histon;
181 n_keytab = 0;
182 n_render = 0;
183
184 setCaption( tr("Terminal") );
185 setIcon( Resource::loadPixmap( "konsole" ) );
186
187 Config cfg("Konsole");
188 cfg.setGroup("Konsole");
189
190 // initialize the list of allowed fonts ///////////////////////////////////
191 cfont = cfg.readNumEntry("FontID", 1);
192 QFont f = QFont("Micro", 4, QFont::Normal);
193 f.setFixedPitch(TRUE);
194 fonts.append(new VTFont(tr("Micro"), f));
195
196 f = QFont("Fixed", 7, QFont::Normal);
197 f.setFixedPitch(TRUE);
198 fonts.append(new VTFont(tr("Small Fixed"), f));
199
200 f = QFont("Fixed", 12, QFont::Normal);
201 f.setFixedPitch(TRUE);
202 fonts.append(new VTFont(tr("Medium Fixed"), f));
203
204 // create terminal emulation framework ////////////////////////////////////
205 nsessions = 0;
206 tab = new EKNumTabWidget(this);
207 tab->setTabPosition(QTabWidget::Bottom);
208 connect(tab, SIGNAL(currentChanged(QWidget*)), this, SLOT(switchSession(QWidget*)));
209
210 // create terminal toolbar ////////////////////////////////////////////////
211 setToolBarsMovable( FALSE );
212 QPEToolBar *menuToolBar = new QPEToolBar( this );
213 menuToolBar->setHorizontalStretchable( TRUE );
214
215 QPEMenuBar *menuBar = new QPEMenuBar( menuToolBar );
216
217 fontList = new QPopupMenu( this );
218 for(uint i = 0; i < fonts.count(); i++) {
219 VTFont *fnt = fonts.at(i);
220 fontList->insertItem(fnt->getName(), i);
221 }
222 fontChanged(cfont);
223
224 connect( fontList, SIGNAL( activated(int) ), this, SLOT( fontChanged(int) ));
225
226 menuBar->insertItem( tr("Font"), fontList );
227
228 QPEToolBar *toolbar = new QPEToolBar( this );
229
230 QAction *a;
231
232 // Button Commands
233 a = new QAction( tr("New"), Resource::loadPixmap( "konsole" ), QString::null, 0, this, 0 );
234 connect( a, SIGNAL( activated() ), this, SLOT( newSession() ) ); a->addTo( toolbar );
235 a = new QAction( tr("Enter"), Resource::loadPixmap( "konsole/enter" ), QString::null, 0, this, 0 );
236 connect( a, SIGNAL( activated() ), this, SLOT( hitEnter() ) ); a->addTo( toolbar );
237 a = new QAction( tr("Space"), Resource::loadPixmap( "konsole/space" ), QString::null, 0, this, 0 );
238 connect( a, SIGNAL( activated() ), this, SLOT( hitSpace() ) ); a->addTo( toolbar );
239 a = new QAction( tr("Tab"), Resource::loadPixmap( "konsole/tab" ), QString::null, 0, this, 0 );
240 connect( a, SIGNAL( activated() ), this, SLOT( hitTab() ) ); a->addTo( toolbar );
241 a = new QAction( tr("Up"), Resource::loadPixmap( "konsole/up" ), QString::null, 0, this, 0 );
242 connect( a, SIGNAL( activated() ), this, SLOT( hitUp() ) ); a->addTo( toolbar );
243 a = new QAction( tr("Down"), Resource::loadPixmap( "konsole/down" ), QString::null, 0, this, 0 );
244 connect( a, SIGNAL( activated() ), this, SLOT( hitDown() ) ); a->addTo( toolbar );
245 a = new QAction( tr("Paste"), Resource::loadPixmap( "paste" ), QString::null, 0, this, 0 );
246 connect( a, SIGNAL( activated() ), this, SLOT( hitPaste() ) ); a->addTo( toolbar );
247/*
248 a = new QAction( tr("Up"), Resource::loadPixmap( "up" ), QString::null, 0, this, 0 );
249 connect( a, SIGNAL( activated() ), this, SLOT( hitUp() ) ); a->addTo( toolbar );
250 a = new QAction( tr("Down"), Resource::loadPixmap( "down" ), QString::null, 0, this, 0 );
251 connect( a, SIGNAL( activated() ), this, SLOT( hitDown() ) ); a->addTo( toolbar );
252*/
253
254 QPEToolBar *secondToolBar = new QPEToolBar( this );
255 secondToolBar->setHorizontalStretchable( TRUE );
256
257 QComboBox *commonCombo = new QComboBox( secondToolBar );
258// commonCombo->setEditable( TRUE );
259 for (int i = 0; commonCmds[i] != NULL; i++)
260 commonCombo->insertItem( commonCmds[i], i );
261 connect( commonCombo, SIGNAL( activated(int) ), this, SLOT( enterCommand(int) ));
262
263 // create applications /////////////////////////////////////////////////////
264 setCentralWidget(tab);
265
266 // load keymaps ////////////////////////////////////////////////////////////
267 KeyTrans::loadAll();
268 for (int i = 0; i < KeyTrans::count(); i++)
269 { KeyTrans* s = KeyTrans::find(i);
270 assert( s );
271 }
272
273 se_pgm = _pgm;
274 se_args = _args;
275
276 // read and apply default values ///////////////////////////////////////////
277 resize(321, 321); // Dummy.
278 QSize currentSize = size();
279 if (currentSize != size())
280 defaultSize = size();
281}
282
283void Konsole::show()
284{
285 if ( !nsessions ) {
286 newSession();
287 }
288 QMainWindow::show();
289}
290
291void Konsole::initSession(const char*, QStrList &)
292{
293 QMainWindow::show();
294}
295
296Konsole::~Konsole()
297{
298 while (nsessions > 0) {
299 doneSession(getTe()->currentSession, 0);
300 }
301
302 Config cfg("Konsole");
303 cfg.setGroup("Konsole");
304 cfg.writeEntry("FontID", cfont);
305}
306
307void Konsole::fontChanged(int f)
308{
309 VTFont* font = fonts.at(f);
310 if (font != 0) {
311 for(uint i = 0; i < fonts.count(); i++) {
312 fontList->setItemChecked(i, (i == (uint) f) ? TRUE : FALSE);
313 }
314
315 cfont = f;
316
317 TEWidget* te = getTe();
318 if (te != 0) {
319 te->setVTFont(font->getFont());
320 }
321 }
322}
323
324void Konsole::enterCommand(int c)
325{
326 TEWidget* te = getTe();
327 if (te != 0) {
328 QString text = commonCmds[c];
329 te->emitText(text);
330 }
331}
332
333void Konsole::hitEnter()
334{
335 TEWidget* te = getTe();
336 if (te != 0) {
337 te->emitText(QString("\r"));
338 }
339}
340
341void Konsole::hitSpace()
342{
343 TEWidget* te = getTe();
344 if (te != 0) {
345 te->emitText(QString(" "));
346 }
347}
348
349void Konsole::hitTab()
350{
351 TEWidget* te = getTe();
352 if (te != 0) {
353 te->emitText(QString("\t"));
354 }
355}
356
357void Konsole::hitPaste()
358{
359 TEWidget* te = getTe();
360 if (te != 0) {
361 te->pasteClipboard();
362 }
363}
364
365void Konsole::hitUp()
366{
367 TEWidget* te = getTe();
368 if (te != 0) {
369 QKeyEvent ke( QKeyEvent::KeyPress, Qt::Key_Up, 0, 0);
370 QApplication::sendEvent( te, &ke );
371 }
372}
373
374void Konsole::hitDown()
375{
376 TEWidget* te = getTe();
377 if (te != 0) {
378 QKeyEvent ke( QKeyEvent::KeyPress, Qt::Key_Down, 0, 0);
379 QApplication::sendEvent( te, &ke );
380 }
381}
382
383/**
384 This function calculates the size of the external widget
385 needed for the internal widget to be
386 */
387QSize Konsole::calcSize(int columns, int lines) {
388 TEWidget* te = getTe();
389 if (te != 0) {
390 QSize size = te->calcSize(columns, lines);
391 return size;
392 } else {
393 QSize size;
394 return size;
395 }
396}
397
398/**
399 sets application window to a size based on columns X lines of the te
400 guest widget. Call with (0,0) for setting default size.
401*/
402
403void Konsole::setColLin(int columns, int lines)
404{
405 if ((columns==0) || (lines==0))
406 {
407 if (defaultSize.isEmpty()) // not in config file : set default value
408 {
409 defaultSize = calcSize(80,24);
410 // notifySize(24,80); // set menu items (strange arg order !)
411 }
412 resize(defaultSize);
413 } else {
414 resize(calcSize(columns, lines));
415 // notifySize(lines,columns); // set menu items (strange arg order !)
416 }
417}
418
419/*
420void Konsole::setFont(int fontno)
421{
422 QFont f;
423 if (fontno == 0)
424 f = defaultFont = QFont( "Helvetica", 12 );
425 else
426 if (fonts[fontno][0] == '-')
427 f.setRawName( fonts[fontno] );
428 else
429 {
430 f.setFamily(fonts[fontno]);
431 f.setRawMode( TRUE );
432 }
433 if ( !f.exactMatch() && fontno != 0)
434 {
435 QString msg = i18n("Font `%1' not found.\nCheck README.linux.console for help.").arg(fonts[fontno]);
436 QMessageBox(this, msg);
437 return;
438 }
439 if (se) se->setFontNo(fontno);
440 te->setVTFont(f);
441 n_font = fontno;
442}
443*/
444
445// --| color selection |-------------------------------------------------------
446
447void Konsole::changeColumns(int columns)
448{
449 TEWidget* te = getTe();
450 if (te != 0) {
451 setColLin(columns,te->Lines());
452 te->update();
453 }
454}
455
456//FIXME: If a child dies during session swap,
457// this routine might be called before
458// session swap is completed.
459
460void Konsole::doneSession(TESession*, int )
461{
462 TEWidget *te = getTe();
463 if (te != 0) {
464 te->currentSession->setConnect(FALSE);
465 tab->removeTab(te);
466 delete te->currentSession;
467 delete te;
468 nsessions--;
469 }
470
471 if (nsessions == 0) {
472 close();
473 }
474}
475
476
477void Konsole::newSession() {
478 TEWidget* te = new TEWidget(tab);
479 te->setBackgroundMode(PaletteBase);
480 te->setVTFont(fonts.at(cfont)->getFont());
481 tab->addTab(te);
482 TESession* se = new TESession(this, te, se_pgm, se_args, "xterm");
483 te->currentSession = se;
484 connect( se, SIGNAL(done(TESession*,int)), this, SLOT(doneSession(TESession*,int)) );
485 se->run();
486 se->setConnect(TRUE);
487 se->setHistory(b_scroll);
488 tab->setCurrentPage(nsessions);
489 nsessions++;
490}
491
492TEWidget* Konsole::getTe() {
493 if (nsessions) {
494 return (TEWidget *) tab->currentPage();
495 } else {
496 return 0;
497 }
498 }
499
500void Konsole::switchSession(QWidget* w) {
501 TEWidget* te = (TEWidget *) w;
502
503 QFont teFnt = te->getVTFont();
504 for(uint i = 0; i < fonts.count(); i++) {
505 VTFont *fnt = fonts.at(i);
506 bool cf = fnt->getFont() == teFnt;
507 fontList->setItemChecked(i, cf);
508 if (cf) {
509 cfont = i;
510 }
511 }
512}