00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00068
00069
00070
00071
00072 #include "TEmulation.h"
00073 #include <stdio.h>
00074 #include <stdlib.h>
00075 #include <unistd.h>
00076
00077
00078
00079
00080
00081
00082
00083
00084 #define CNTL(c) ((c)-'@')
00085
00089 TEmulation::TEmulation(TEWidget* gui)
00090 : decoder((QTextDecoder*)NULL)
00091 {
00092 this->gui = gui;
00093
00094 screen[0] = new TEScreen(gui->Lines(),gui->Columns());
00095 screen[1] = new TEScreen(gui->Lines(),gui->Columns());
00096 scr = screen[0];
00097
00098 bulk_nlcnt = 0;
00099 bulk_incnt = 0;
00100 connected = FALSE;
00101
00102 QObject::connect(&bulk_timer, SIGNAL(timeout()), this, SLOT(showBulk()) );
00103
00104 QObject::connect(gui,SIGNAL(changedImageSizeSignal(int,int)),
00105 this,SLOT(onImageSizeChange(int,int)));
00106
00107 QObject::connect(gui,SIGNAL(changedHistoryCursor(int)),
00108 this,SLOT(onHistoryCursorChange(int)));
00109
00110 QObject::connect(gui,SIGNAL(changedHorzCursor(int)),
00111 this,SLOT(onHorzCursorChange(int)));
00112
00113 QObject::connect(gui,SIGNAL(keyPressedSignal(QKeyEvent*)),
00114 this,SLOT(onKeyPress(QKeyEvent*)));
00115
00116 QObject::connect(gui,SIGNAL(beginSelectionSignal(const int,const int)),
00117 this,SLOT(onSelectionBegin(const int,const int)) );
00118
00119 QObject::connect(gui,SIGNAL(extendSelectionSignal(const int,const int)),
00120 this,SLOT(onSelectionExtend(const int,const int)) );
00121
00122 QObject::connect(gui,SIGNAL(endSelectionSignal(const BOOL)),
00123 this,SLOT(setSelection(const BOOL)) );
00124
00125 QObject::connect(gui,SIGNAL(clearSelectionSignal()),
00126 this,SLOT(clearSelection()) );
00127 }
00128
00132 TEmulation::~TEmulation()
00133 {
00134 delete screen[0];
00135 delete screen[1];
00136 bulk_timer.stop();
00137 }
00138
00142 void TEmulation::setScreen(int n)
00143 {
00144 scr = screen[n&1];
00145 }
00146
00147 void TEmulation::setHistory(bool on)
00148 {
00149 screen[0]->setScroll(on);
00150 if (!connected) return;
00151 showBulk();
00152 }
00153
00154 bool TEmulation::history()
00155 {
00156 return screen[0]->hasScroll();
00157 }
00158
00159 void TEmulation::setCodec(int c)
00160 {
00161
00162 codec = c ? QTextCodec::codecForName("utf8")
00163 : QTextCodec::codecForLocale();
00164 if (decoder) delete decoder;
00165 decoder = codec->makeDecoder();
00166 }
00167
00168 void TEmulation::setKeytrans(int no)
00169 {
00170 keytrans = KeyTrans::find(no);
00171 }
00172
00173 void TEmulation::setKeytrans(const char * no)
00174 {
00175 keytrans = KeyTrans::find(no);
00176 }
00177
00178
00179
00180
00181
00182
00183
00184
00185
00186
00190 void TEmulation::onRcvChar(int c)
00191
00192
00193 {
00194 c &= 0xff;
00195
00196 switch (c)
00197 {
00198 case '\b' : scr->BackSpace(); break;
00199 case '\t' : scr->Tabulate(); break;
00200 case '\n' : scr->NewLine(); break;
00201 case '\r' : scr->Return(); break;
00202 case 0x07 : gui->Bell(); break;
00203 default : scr->ShowCharacter(c); break;
00204 };
00205 }
00206
00207
00208
00209
00210
00211
00212
00216 void TEmulation::onKeyPress( QKeyEvent* ev )
00217 {
00218 if (!connected) return;
00219 if (scr->getHistCursor() != scr->getHistLines());
00220 scr->setHistCursor(scr->getHistLines());
00221 if (!ev->text().isEmpty())
00222 {
00223
00224
00225
00226 emit sndBlock(ev->text().ascii(),ev->text().length());
00227 }
00228 else if (ev->ascii()>0)
00229 { unsigned char c[1];
00230 c[0] = ev->ascii();
00231 emit sndBlock((char*)c,1);
00232 }
00233 }
00234
00235
00236
00237
00238
00239
00240
00241 void TEmulation::onRcvBlock(const char *s, int len)
00242 {
00243 bulkStart();
00244 bulk_incnt += 1;
00245 for (int i = 0; i < len; i++)
00246 {
00247 QString result = decoder->toUnicode(&s[i],1);
00248 int reslen = result.length();
00249 for (int j = 0; j < reslen; j++)
00250 onRcvChar(result[j].unicode());
00251 if (s[i] == '\n') bulkNewline();
00252 }
00253 bulkEnd();
00254 }
00255
00256
00257
00258 void TEmulation::onSelectionBegin(const int x, const int y) {
00259 if (!connected) return;
00260 scr->setSelBeginXY(x,y);
00261 showBulk();
00262 }
00263
00264 void TEmulation::onSelectionExtend(const int x, const int y) {
00265 if (!connected) return;
00266 scr->setSelExtentXY(x,y);
00267 showBulk();
00268 }
00269
00270 void TEmulation::setSelection(const BOOL preserve_line_breaks) {
00271 if (!connected) return;
00272 QString t = scr->getSelText(preserve_line_breaks);
00273 if (!t.isNull()) gui->setSelection(t);
00274 }
00275
00276 void TEmulation::clearSelection() {
00277 if (!connected) return;
00278 scr->clearSelection();
00279 showBulk();
00280 }
00281
00282
00283
00284 #define BULK_TIMEOUT 20
00285
00290 void TEmulation::bulkNewline()
00291 {
00292 bulk_nlcnt += 1;
00293 bulk_incnt = 0;
00294 }
00295
00299 void TEmulation::showBulk()
00300 {
00301 bulk_nlcnt = 0;
00302 bulk_incnt = 0;
00303 if (connected)
00304 {
00305 ca* image = scr->getCookedImage();
00306 gui->setImage(image,
00307 scr->getLines(),
00308 scr->getColumns());
00309 free(image);
00310
00311
00312 gui->setScroll(scr->getHistCursor(),scr->getHistLines());
00313
00314 }
00315 }
00316
00317 void TEmulation::bulkStart()
00318 {
00319 if (bulk_timer.isActive()) bulk_timer.stop();
00320 }
00321
00322 void TEmulation::bulkEnd()
00323 {
00324 if ( bulk_nlcnt > gui->Lines() || bulk_incnt > 20 )
00325 showBulk();
00326 else
00327 bulk_timer.start(BULK_TIMEOUT,TRUE);
00328 }
00329
00330 void TEmulation::setConnect(bool c)
00331 {
00332 connected = c;
00333 if ( connected)
00334 {
00335 onImageSizeChange(gui->Lines(), gui->Columns());
00336 showBulk();
00337 }
00338 else
00339 {
00340 scr->clearSelection();
00341 }
00342 }
00343
00344
00345
00352 void TEmulation::onImageSizeChange(int lines, int columns) {
00353 if (!connected) return;
00354 screen[0]->resizeImage(lines,columns);
00355 screen[1]->resizeImage(lines,columns);
00356 showBulk();
00357 emit ImageSizeChanged(lines,columns);
00358 }
00359
00360 void TEmulation::onHistoryCursorChange(int cursor) {
00361 if (!connected) return;
00362 scr->setHistCursor(cursor);
00363 showBulk();
00364 }
00365
00366 void TEmulation::onHorzCursorChange(int cursor) {
00367 if (!connected) return;
00368 scr->setHorzCursor(cursor);
00369 showBulk();
00370 }
00371
00372 void TEmulation::setColumns(int columns) {
00373
00374
00375 emit changeColumns(columns);
00376 }