* Applied slightly changed patch by Olivier that adds basic xterm style mouse

support, thanks!
* This probably closes bug #2854, confirmation pending.


git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@30268 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
Axel Dörfler
2009-04-19 20:59:08 +00:00
parent 728c7f10e1
commit 21543141dd
6 changed files with 192 additions and 84 deletions
+1
View File
@@ -91,6 +91,7 @@ const uint32 MSG_REMOVE_RESIZE_VIEW_IF_NEEDED = 'rmrv';
const uint32 MSG_TERMINAL_BUFFER_CHANGED = 'bufc'; const uint32 MSG_TERMINAL_BUFFER_CHANGED = 'bufc';
const uint32 MSG_SET_TERMNAL_TITLE = 'sett'; const uint32 MSG_SET_TERMNAL_TITLE = 'sett';
const uint32 MSG_QUIT_TERMNAL = 'qutt'; const uint32 MSG_QUIT_TERMNAL = 'qutt';
const uint32 MSG_REPORT_ANY_MOUSE_EVENT = 'mous';
// Preference Read/Write Keys // Preference Read/Write Keys
const char* const PREF_HALF_FONT_FAMILY = "Half Font Family"; const char* const PREF_HALF_FONT_FAMILY = "Half Font Family";
+66 -39
View File
@@ -1,9 +1,12 @@
/* /*
* Copyright 2001-2007, Haiku, Inc. * Copyright 2001-2009, Haiku, Inc.
* Copyright (c) 2003-4 Kian Duffy <[email protected]> * Copyright (c) 2003-4 Kian Duffy <[email protected]>
* Parts Copyright (C) 1998,99 Kazuho Okui and Takashi Murai. * Parts Copyright (C) 1998,99 Kazuho Okui and Takashi Murai.
* Distributed under the terms of the MIT license. * Distributed under the terms of the MIT license.
*/ */
//! Escape sequence parse and character encoding.
#include "TermParse.h" #include "TermParse.h"
#include <ctype.h> #include <ctype.h>
@@ -23,25 +26,19 @@
#include "VTparse.h" #include "VTparse.h"
//////////////////////////////////////////////////////////////////////////////
// EscParse ... Escape sequence parse and character encoding.
//
//////////////////////////////////////////////////////////////////////////////
extern int gUTF8GroundTable[]; /* UTF8 Ground table */ extern int gUTF8GroundTable[]; /* UTF8 Ground table */
extern int gCS96GroundTable[]; /* CS96 Ground table */ extern int gCS96GroundTable[]; /* CS96 Ground table */
extern int gISO8859GroundTable[]; /* ISO8859 & EUC Ground table */ extern int gISO8859GroundTable[]; /* ISO8859 & EUC Ground table */
extern int gSJISGroundTable[]; /* Shift-JIS Ground table */ extern int gSJISGroundTable[]; /* Shift-JIS Ground table */
extern int gEscTable[]; /* ESC */ extern int gEscTable[]; /* ESC */
extern int gCsiTable[]; /* ESC [ */ extern int gCsiTable[]; /* ESC [ */
extern int gDecTable[]; /* ESC [ ? */ extern int gDecTable[]; /* ESC [ ? */
extern int gScrTable[]; /* ESC # */ extern int gScrTable[]; /* ESC # */
extern int gIgnoreTable[]; /* ignore table */ extern int gIgnoreTable[]; /* ignore table */
extern int gIesTable[]; /* ignore ESC table */ extern int gIesTable[]; /* ignore ESC table */
extern int gEscIgnoreTable[]; /* ESC ignore table */ extern int gEscIgnoreTable[]; /* ESC ignore table */
extern int gMbcsTable[]; /* ESC $ */ extern int gMbcsTable[]; /* ESC $ */
@@ -101,7 +98,7 @@ TermParse::StartThreads(TerminalBuffer *buffer)
status_t status = InitPtyReader(); status_t status = InitPtyReader();
if (status < B_OK) { if (status < B_OK) {
fBuffer = NULL; fBuffer = NULL;
return status; return status;
} }
@@ -109,9 +106,9 @@ TermParse::StartThreads(TerminalBuffer *buffer)
if (status < B_OK) { if (status < B_OK) {
StopPtyReader(); StopPtyReader();
fBuffer = NULL; fBuffer = NULL;
return status; return status;
} }
return B_OK; return B_OK;
} }
@@ -126,9 +123,9 @@ TermParse::StopThreads()
StopPtyReader(); StopPtyReader();
StopTermParse(); StopTermParse();
fBuffer = NULL; fBuffer = NULL;
return B_OK; return B_OK;
} }
@@ -144,7 +141,7 @@ TermParse::InitTermParse()
B_DISPLAY_PRIORITY, this); B_DISPLAY_PRIORITY, this);
resume_thread(fParseThread); resume_thread(fParseThread);
return B_OK; return B_OK;
} }
@@ -164,7 +161,7 @@ TermParse::InitPtyReader()
if (fReaderLocker < 0) { if (fReaderLocker < 0) {
delete_sem(fReaderSem); delete_sem(fReaderSem);
fReaderSem = -1; fReaderSem = -1;
return fReaderLocker; return fReaderLocker;
} }
fReaderThread = spawn_thread(_ptyreader_thread, "PtyReader", fReaderThread = spawn_thread(_ptyreader_thread, "PtyReader",
@@ -174,8 +171,8 @@ TermParse::InitPtyReader()
fReaderSem = -1; fReaderSem = -1;
delete_sem(fReaderLocker); delete_sem(fReaderLocker);
fReaderLocker = -1; fReaderLocker = -1;
return fReaderThread; return fReaderThread;
} }
resume_thread(fReaderThread); resume_thread(fReaderThread);
@@ -189,7 +186,7 @@ TermParse::StopTermParse()
if (fParseThread >= 0) { if (fParseThread >= 0) {
status_t dummy; status_t dummy;
wait_for_thread(fParseThread, &dummy); wait_for_thread(fParseThread, &dummy);
fParseThread = -1; fParseThread = -1;
} }
} }
@@ -201,7 +198,7 @@ TermParse::StopPtyReader()
delete_sem(fReaderSem); delete_sem(fReaderSem);
fReaderSem = -1; fReaderSem = -1;
} }
if (fReaderLocker >= 0) { if (fReaderLocker >= 0) {
delete_sem(fReaderLocker); delete_sem(fReaderLocker);
fReaderLocker = -1; fReaderLocker = -1;
} }
@@ -212,7 +209,7 @@ TermParse::StopPtyReader()
status_t status; status_t status;
wait_for_thread(fReaderThread, &status); wait_for_thread(fReaderThread, &status);
fReaderThread = -1; fReaderThread = -1;
} }
} }
@@ -227,11 +224,11 @@ TermParse::PtyReader()
// If Pty Buffer nearly full, snooze this thread, and continue. // If Pty Buffer nearly full, snooze this thread, and continue.
while (READ_BUF_SIZE - bufferSize < MIN_PTY_BUFFER_SPACE) { while (READ_BUF_SIZE - bufferSize < MIN_PTY_BUFFER_SPACE) {
status_t status; status_t status;
do { do {
status = acquire_sem(fReaderLocker); status = acquire_sem(fReaderLocker);
} while (status == B_INTERRUPTED); } while (status == B_INTERRUPTED);
if (status < B_OK) if (status < B_OK)
return status; return status;
bufferSize = fReadBufferSize; bufferSize = fReadBufferSize;
} }
@@ -309,7 +306,7 @@ TermParse::EscParse()
int top, bot; int top, bot;
int cs96 = 0; int cs96 = 0;
uchar curess = 0; uchar curess = 0;
char cbuf[4], dstbuf[4]; char cbuf[4], dstbuf[4];
char *ptr; char *ptr;
@@ -381,7 +378,7 @@ TermParse::EscParse()
case CASE_PRINT_GR: case CASE_PRINT_GR:
/* case iso8859 gr character, or euc */ /* case iso8859 gr character, or euc */
ptr = cbuf; ptr = cbuf;
if (now_coding == B_EUC_CONVERSION if (now_coding == B_EUC_CONVERSION
|| now_coding == B_EUC_KR_CONVERSION || now_coding == B_EUC_KR_CONVERSION
|| now_coding == B_JIS_CONVERSION || now_coding == B_JIS_CONVERSION
|| now_coding == B_GBK_CONVERSION || now_coding == B_GBK_CONVERSION
@@ -469,7 +466,7 @@ TermParse::EscParse()
break; break;
cbuf[1] = c; cbuf[1] = c;
cbuf[2] = '\0'; cbuf[2] = '\0';
fBuffer->InsertChar(cbuf, 2, attr); fBuffer->InsertChar(cbuf, 2, attr);
break; break;
@@ -502,7 +499,7 @@ TermParse::EscParse()
case CASE_SCS_STATE: case CASE_SCS_STATE:
{ {
cs96 = 0; cs96 = 0;
uchar dummy; uchar dummy;
_NextParseChar(dummy); _NextParseChar(dummy);
parsestate = groundtable; parsestate = groundtable;
break; break;
@@ -819,7 +816,7 @@ TermParse::EscParse()
// screen->max_col + 1, False); // screen->max_col + 1, False);
parsestate = groundtable; parsestate = groundtable;
break; break;
// case CASE_GSETS: // case CASE_GSETS:
// screen->gsets[scstype] = GSET(c) | cs96; // screen->gsets[scstype] = GSET(c) | cs96;
// parsestate = groundtable; // parsestate = groundtable;
@@ -879,14 +876,14 @@ TermParse::EscParse()
uchar mode_char; uchar mode_char;
_NextParseChar(mode_char); _NextParseChar(mode_char);
if (mode_char != '0' if (mode_char != '0'
&& mode_char != '1' && mode_char != '1'
&& mode_char != '2') { && mode_char != '2') {
parsestate = groundtable; parsestate = groundtable;
break; break;
} }
uchar current_char; uchar current_char;
_NextParseChar(current_char); _NextParseChar(current_char);
while (_NextParseChar(current_char) == B_OK while (_NextParseChar(current_char) == B_OK
&& current_char != 0x7) { && current_char != 0x7) {
if (!isprint(current_char & 0x7f) if (!isprint(current_char & 0x7f)
|| len+2 >= sizeof(string)) || len+2 >= sizeof(string))
@@ -987,7 +984,7 @@ TermParse::EscParse()
break; break;
} }
} }
return B_OK; return B_OK;
} }
@@ -1109,8 +1106,23 @@ TermParse::_DecPrivateModeSet(int value)
// Use Alternate Screen Buffer. // Use Alternate Screen Buffer.
fBuffer->UseAlternateScreenBuffer(false); fBuffer->UseAlternateScreenBuffer(false);
break; break;
case 1000:
// TODO: Send Mouse X & Y on button press and release.
break;
case 1003:
// Use All Motion Mouse Tracking
fBuffer->ReportAnyMouseEvent(true);
break;
case 1034: case 1034:
// Interpret "meta" key, sets eighth bit. // TODO: Interprete "meta" key, sets eighth bit.
// Not supported yet.
break;
case 1036:
// TODO: Send ESC when Meta modifies a key
// Not supported yet.
break;
case 1039:
// TODO: Send ESC when Alt modifies a key
// Not supported yet. // Not supported yet.
break; break;
case 1049: case 1049:
@@ -1155,8 +1167,23 @@ TermParse::_DecPrivateModeReset(int value)
// Use Normal Screen Buffer. // Use Normal Screen Buffer.
fBuffer->UseNormalScreenBuffer(); fBuffer->UseNormalScreenBuffer();
break; break;
case 1000:
// TODO: Don't send Mouse X & Y on button press and release.
break;
case 1003:
// Disable All Motion Mouse Tracking.
fBuffer->ReportAnyMouseEvent(false);
break;
case 1034: case 1034:
// Dont interpret "meta" key. // Don't interprete "meta" key.
// Not supported yet.
break;
case 1036:
// TODO: Don't send ESC when Meta modifies a key
// Not supported yet.
break;
case 1039:
// TODO: Don't send ESC when Alt modifies a key
// Not supported yet. // Not supported yet.
break; break;
case 1049: case 1049:
+108 -45
View File
@@ -170,7 +170,8 @@ TermView::TermView(BRect frame, int32 argc, const char** argv, int32 historySize
fColumns(COLUMNS_DEFAULT), fColumns(COLUMNS_DEFAULT),
fRows(ROWS_DEFAULT), fRows(ROWS_DEFAULT),
fEncoding(M_UTF8), fEncoding(M_UTF8),
fScrBufSize(historySize) fScrBufSize(historySize),
fReportAnyMouseEvent(false)
{ {
_InitObject(argc, argv); _InitObject(argc, argv);
} }
@@ -183,7 +184,8 @@ TermView::TermView(int rows, int columns, int32 argc, const char** argv,
fColumns(columns), fColumns(columns),
fRows(rows), fRows(rows),
fEncoding(M_UTF8), fEncoding(M_UTF8),
fScrBufSize(historySize) fScrBufSize(historySize),
fReportAnyMouseEvent(false)
{ {
_InitObject(argc, argv); _InitObject(argc, argv);
SetTermSize(fRows, fColumns, true); SetTermSize(fRows, fColumns, true);
@@ -207,7 +209,8 @@ TermView::TermView(BMessage* archive)
fColumns(COLUMNS_DEFAULT), fColumns(COLUMNS_DEFAULT),
fRows(ROWS_DEFAULT), fRows(ROWS_DEFAULT),
fEncoding(M_UTF8), fEncoding(M_UTF8),
fScrBufSize(1000) fScrBufSize(1000),
fReportAnyMouseEvent(false)
{ {
// We need this // We need this
SetFlags(Flags() | B_WILL_DRAW | B_PULSE_NEEDED); SetFlags(Flags() | B_WILL_DRAW | B_PULSE_NEEDED);
@@ -277,6 +280,7 @@ TermView::_InitObject(int32 argc, const char** argv)
fMouseTracking = false; fMouseTracking = false;
fIMflag = false; fIMflag = false;
fCheckMouseTracking = false; fCheckMouseTracking = false;
fReportAnyMouseEvent = false;
fTextBuffer = new(std::nothrow) TerminalBuffer; fTextBuffer = new(std::nothrow) TerminalBuffer;
if (fTextBuffer == NULL) if (fTextBuffer == NULL)
@@ -1333,18 +1337,18 @@ TermView::MessageReceived(BMessage *msg)
//rgb_color *color; //rgb_color *color;
int32 i = 0; int32 i = 0;
if (msg->FindRef("refs", i++, &ref) == B_OK) { if (msg->FindRef("refs", i++, &ref) == B_OK) {
// first check if secondary mouse button is pressed // first check if secondary mouse button is pressed
int32 buttons = 0; int32 buttons = 0;
msg->FindInt32("buttons", &buttons); msg->FindInt32("buttons", &buttons);
if (buttons == B_SECONDARY_MOUSE_BUTTON) { if (buttons == B_SECONDARY_MOUSE_BUTTON) {
// start popup menu // start popup menu
_SecondaryMouseButtonDropped(msg); _SecondaryMouseButtonDropped(msg);
return; return;
} }
_DoFileDrop(ref); _DoFileDrop(ref);
while (msg->FindRef("refs", i++, &ref) == B_OK) { while (msg->FindRef("refs", i++, &ref) == B_OK) {
@@ -1517,7 +1521,13 @@ TermView::MessageReceived(BMessage *msg)
SetTitle(title); SetTitle(title);
break; break;
} }
case MSG_REPORT_ANY_MOUSE_EVENT:
{
bool reportAnyMouseEvent;
if (msg->FindBool("reportAnyMouseEvent", &reportAnyMouseEvent) == B_OK)
fReportAnyMouseEvent = reportAnyMouseEvent;
break;
}
case MSG_REMOVE_RESIZE_VIEW_IF_NEEDED: case MSG_REMOVE_RESIZE_VIEW_IF_NEEDED:
{ {
BPoint point; BPoint point;
@@ -1630,30 +1640,30 @@ TermView::_SecondaryMouseButtonDropped(BMessage* msg)
BMessage* insertMessage = new BMessage(*msg); BMessage* insertMessage = new BMessage(*msg);
insertMessage->what = kSecondaryMouseDropAction; insertMessage->what = kSecondaryMouseDropAction;
insertMessage->AddInt8("action", kInsert); insertMessage->AddInt8("action", kInsert);
BMessage* cdMessage = new BMessage(*msg); BMessage* cdMessage = new BMessage(*msg);
cdMessage->what = kSecondaryMouseDropAction; cdMessage->what = kSecondaryMouseDropAction;
cdMessage->AddInt8("action", kChangeDirectory); cdMessage->AddInt8("action", kChangeDirectory);
BMessage* lnMessage = new BMessage(*msg); BMessage* lnMessage = new BMessage(*msg);
lnMessage->what = kSecondaryMouseDropAction; lnMessage->what = kSecondaryMouseDropAction;
lnMessage->AddInt8("action", kLinkFiles); lnMessage->AddInt8("action", kLinkFiles);
BMessage* mvMessage = new BMessage(*msg); BMessage* mvMessage = new BMessage(*msg);
mvMessage->what = kSecondaryMouseDropAction; mvMessage->what = kSecondaryMouseDropAction;
mvMessage->AddInt8("action", kMoveFiles); mvMessage->AddInt8("action", kMoveFiles);
BMessage* cpMessage = new BMessage(*msg); BMessage* cpMessage = new BMessage(*msg);
cpMessage->what = kSecondaryMouseDropAction; cpMessage->what = kSecondaryMouseDropAction;
cpMessage->AddInt8("action", kCopyFiles); cpMessage->AddInt8("action", kCopyFiles);
BMenuItem* insertItem = new BMenuItem("Insert Path", insertMessage); BMenuItem* insertItem = new BMenuItem("Insert Path", insertMessage);
BMenuItem* cdItem = new BMenuItem("Change Directory", cdMessage); BMenuItem* cdItem = new BMenuItem("Change Directory", cdMessage);
BMenuItem* lnItem = new BMenuItem("Create Link Here", lnMessage); BMenuItem* lnItem = new BMenuItem("Create Link Here", lnMessage);
BMenuItem* mvItem = new BMenuItem("Move Here", mvMessage); BMenuItem* mvItem = new BMenuItem("Move Here", mvMessage);
BMenuItem* cpItem = new BMenuItem("Copy Here", cpMessage); BMenuItem* cpItem = new BMenuItem("Copy Here", cpMessage);
BMenuItem* chItem = new BMenuItem("Cancel", NULL); BMenuItem* chItem = new BMenuItem("Cancel", NULL);
// if the refs point to different directorys disable the cd menu item // if the refs point to different directorys disable the cd menu item
bool differentDirs = false; bool differentDirs = false;
BDirectory firstDir; BDirectory firstDir;
@@ -1667,14 +1677,14 @@ TermView::_SecondaryMouseButtonDropped(BMessage* msg)
dir.SetTo(&ref); dir.SetTo(&ref);
else else
entry.GetParent(&dir); entry.GetParent(&dir);
if (i == 1) { if (i == 1) {
node_ref nodeRef; node_ref nodeRef;
dir.GetNodeRef(&nodeRef); dir.GetNodeRef(&nodeRef);
firstDir.SetTo(&nodeRef); firstDir.SetTo(&nodeRef);
} else if (firstDir != dir) { } else if (firstDir != dir) {
differentDirs = true; differentDirs = true;
break; break;
} }
} }
if (differentDirs) if (differentDirs)
@@ -1700,10 +1710,10 @@ TermView::_DoSecondaryMouseDropAction(BMessage* msg)
{ {
int8 action = -1; int8 action = -1;
msg->FindInt8("action", &action); msg->FindInt8("action", &action);
BString outString = ""; BString outString = "";
BString itemString = ""; BString itemString = "";
switch (action) { switch (action) {
case kInsert: case kInsert:
break; break;
@@ -1723,22 +1733,22 @@ TermView::_DoSecondaryMouseDropAction(BMessage* msg)
default: default:
return; return;
} }
bool listContainsDirectory = false; bool listContainsDirectory = false;
entry_ref ref; entry_ref ref;
int32 i = 0; int32 i = 0;
while (msg->FindRef("refs", i++, &ref) == B_OK) { while (msg->FindRef("refs", i++, &ref) == B_OK) {
BEntry ent(&ref); BEntry ent(&ref);
BNode node(&ref); BNode node(&ref);
BPath path(&ent); BPath path(&ent);
BString string(path.Path()); BString string(path.Path());
if (node.IsDirectory()) if (node.IsDirectory())
listContainsDirectory = true; listContainsDirectory = true;
if (i > 1) if (i > 1)
itemString += " "; itemString += " ";
if (action == kChangeDirectory) { if (action == kChangeDirectory) {
if (!node.IsDirectory()) { if (!node.IsDirectory()) {
int32 slash = string.FindLast("/"); int32 slash = string.FindLast("/");
@@ -1751,18 +1761,18 @@ TermView::_DoSecondaryMouseDropAction(BMessage* msg)
string.CharacterEscape(kEscapeCharacters, '\\'); string.CharacterEscape(kEscapeCharacters, '\\');
itemString += string; itemString += string;
} }
if (listContainsDirectory && action == kCopyFiles) if (listContainsDirectory && action == kCopyFiles)
outString += " -R"; outString += " -R";
outString += itemString; outString += itemString;
if (action == kLinkFiles || action == kMoveFiles || action == kCopyFiles) if (action == kLinkFiles || action == kMoveFiles || action == kCopyFiles)
outString += " ."; outString += " .";
if (action != kInsert) if (action != kInsert)
outString += "\n"; outString += "\n";
_WritePTY(outString.String(), outString.Length()); _WritePTY(outString.String(), outString.Length());
} }
@@ -2023,6 +2033,37 @@ TermView::_MouseDistanceSinceLastClick(BPoint where)
} }
void
TermView::_SendMouseEvent(int32 buttons, int32 mode, int32 x, int32 y,
bool motion)
{
char xtermButtons;
if (buttons == B_PRIMARY_MOUSE_BUTTON)
xtermButtons = 32 + 0;
else if (buttons == B_SECONDARY_MOUSE_BUTTON)
xtermButtons = 32 + 1;
else if (buttons == B_TERTIARY_MOUSE_BUTTON)
xtermButtons = 32 + 2;
else
xtermButtons = 32 + 3;
if (motion)
xtermButtons += 32;
char xtermX = x + 1 + 32;
char xtermY = y + 1 + 32;
char destBuffer[6];
destBuffer[0] = '\033';
destBuffer[1] = '[';
destBuffer[2] = 'M';
destBuffer[3] = xtermButtons;
destBuffer[4] = xtermX;
destBuffer[5] = xtermY;
fShell->Write(destBuffer, 6);
}
void void
TermView::MouseDown(BPoint where) TermView::MouseDown(BPoint where)
{ {
@@ -2030,10 +2071,19 @@ TermView::MouseDown(BPoint where)
MakeFocus(); MakeFocus();
int32 buttons; int32 buttons;
int32 modifier;
Window()->CurrentMessage()->FindInt32("buttons", &buttons); Window()->CurrentMessage()->FindInt32("buttons", &buttons);
Window()->CurrentMessage()->FindInt32("modifiers", &modifier);
fMouseButtons = buttons; fMouseButtons = buttons;
if (fReportAnyMouseEvent) {
TermPos clickPos = _ConvertToTerminal(where);
_SendMouseEvent(buttons, modifier, clickPos.x, clickPos.y, false);
return;
}
// paste button // paste button
if ((buttons & (B_SECONDARY_MOUSE_BUTTON | B_TERTIARY_MOUSE_BUTTON)) != 0) { if ((buttons & (B_SECONDARY_MOUSE_BUTTON | B_TERTIARY_MOUSE_BUTTON)) != 0) {
Paste(gMouseClipboard); Paste(gMouseClipboard);
@@ -2043,14 +2093,13 @@ TermView::MouseDown(BPoint where)
// Select Region // Select Region
if (buttons == B_PRIMARY_MOUSE_BUTTON) { if (buttons == B_PRIMARY_MOUSE_BUTTON) {
int32 mod, clicks; int32 clicks;
Window()->CurrentMessage()->FindInt32("modifiers", &mod);
Window()->CurrentMessage()->FindInt32("clicks", &clicks); Window()->CurrentMessage()->FindInt32("clicks", &clicks);
if (_HasSelection()) { if (_HasSelection()) {
TermPos inPos = _ConvertToTerminal(where); TermPos inPos = _ConvertToTerminal(where);
if (_CheckSelectedRegion(inPos)) { if (_CheckSelectedRegion(inPos)) {
if (mod & B_CONTROL_KEY) { if (modifier & B_CONTROL_KEY) {
BPoint p; BPoint p;
uint32 bt; uint32 bt;
do { do {
@@ -2081,7 +2130,7 @@ TermView::MouseDown(BPoint where)
TermPos clickPos = _ConvertToTerminal(where); TermPos clickPos = _ConvertToTerminal(where);
if (mod & B_SHIFT_KEY) { if (modifier & B_SHIFT_KEY) {
fInitialSelectionStart = clickPos; fInitialSelectionStart = clickPos;
fInitialSelectionEnd = clickPos; fInitialSelectionEnd = clickPos;
_ExtendSelection(fInitialSelectionStart, true, false); _ExtendSelection(fInitialSelectionStart, true, false);
@@ -2098,22 +2147,21 @@ TermView::MouseDown(BPoint where)
case 1: case 1:
fCheckMouseTracking = true; fCheckMouseTracking = true;
fSelectGranularity = SELECT_CHARS; fSelectGranularity = SELECT_CHARS;
break; break;
case 2: case 2:
_SelectWord(where, (mod & B_SHIFT_KEY) != 0, false); _SelectWord(where, (modifier & B_SHIFT_KEY) != 0, false);
fMouseTracking = true; fMouseTracking = true;
fSelectGranularity = SELECT_WORDS; fSelectGranularity = SELECT_WORDS;
break; break;
case 3: case 3:
_SelectLine(where, (mod & B_SHIFT_KEY) != 0, false); _SelectLine(where, (modifier & B_SHIFT_KEY) != 0, false);
fMouseTracking = true; fMouseTracking = true;
fSelectGranularity = SELECT_LINES; fSelectGranularity = SELECT_LINES;
break; break;
} }
} }
fLastClickPoint = where; fLastClickPoint = where;
} }
@@ -2121,6 +2169,15 @@ TermView::MouseDown(BPoint where)
void void
TermView::MouseMoved(BPoint where, uint32 transit, const BMessage *message) TermView::MouseMoved(BPoint where, uint32 transit, const BMessage *message)
{ {
if (fReportAnyMouseEvent) {
int32 modifier;
Window()->CurrentMessage()->FindInt32("modifiers", &modifier);
TermPos clickPos = _ConvertToTerminal(where);
_SendMouseEvent(fMouseButtons, modifier, clickPos.x, clickPos.y, true);
return;
}
if (fCheckMouseTracking) { if (fCheckMouseTracking) {
if (_MouseDistanceSinceLastClick(where) > 9) if (_MouseDistanceSinceLastClick(where) > 9)
fMouseTracking = true; fMouseTracking = true;
@@ -2169,15 +2226,15 @@ TermView::MouseMoved(BPoint where, uint32 transit, const BMessage *message)
} }
_ExtendSelection(_ConvertToTerminal(where), true, true); _ExtendSelection(_ConvertToTerminal(where), true, true);
break; break;
} }
case SELECT_WORDS: case SELECT_WORDS:
_SelectWord(where, true, true); _SelectWord(where, true, true);
break; break;
case SELECT_LINES: case SELECT_LINES:
_SelectLine(where, true, true); _SelectLine(where, true, true);
break; break;
} }
} }
@@ -2196,16 +2253,22 @@ TermView::MouseUp(BPoint where)
// clipboard. // clipboard.
int32 buttons; int32 buttons;
Window()->CurrentMessage()->FindInt32("buttons", &buttons); Window()->CurrentMessage()->FindInt32("buttons", &buttons);
if ((buttons & B_PRIMARY_MOUSE_BUTTON) == 0
&& (fMouseButtons & B_PRIMARY_MOUSE_BUTTON) != 0) {
Copy(gMouseClipboard);
}
if (fReportAnyMouseEvent) {
TermPos clickPos = _ConvertToTerminal(where);
_SendMouseEvent(0, 0, clickPos.x, clickPos.y, false);
} else {
if ((buttons & B_PRIMARY_MOUSE_BUTTON) == 0
&& (fMouseButtons & B_PRIMARY_MOUSE_BUTTON) != 0) {
Copy(gMouseClipboard);
}
}
fMouseButtons = buttons; fMouseButtons = buttons;
} }
// Select a range of text //! Select a range of text.
void void
TermView::_Select(TermPos start, TermPos end, bool inclusive, TermView::_Select(TermPos start, TermPos end, bool inclusive,
bool setInitialSelection) bool setInitialSelection)
@@ -2267,7 +2330,7 @@ TermView::_Select(TermPos start, TermPos end, bool inclusive,
} }
// extend selection (shift + mouse click) //! Extend selection (shift + mouse click).
void void
TermView::_ExtendSelection(TermPos pos, bool inclusive, TermView::_ExtendSelection(TermPos pos, bool inclusive,
bool useInitialSelection) bool useInitialSelection)
+4
View File
@@ -177,6 +177,8 @@ private:
void _ScrollTo(float y, bool scrollGfx); void _ScrollTo(float y, bool scrollGfx);
void _ScrollToRange(TermPos start, TermPos end); void _ScrollToRange(TermPos start, TermPos end);
void _SendMouseEvent(int32 button, int32 mode, int32 x,
int32 y, bool motion);
private: private:
class CharClassifier; class CharClassifier;
@@ -251,6 +253,8 @@ private:
bool fCheckMouseTracking; bool fCheckMouseTracking;
int fSelectGranularity; int fSelectGranularity;
BPoint fLastClickPoint; BPoint fLastClickPoint;
bool fReportAnyMouseEvent;
// Input Method parameter. // Input Method parameter.
int fIMViewPtr; int fIMViewPtr;
+11
View File
@@ -74,6 +74,17 @@ TerminalBuffer::Encoding() const
} }
void
TerminalBuffer::ReportAnyMouseEvent(bool reportAnyMouseEvent)
{
if (fListenerValid) {
BMessage message(MSG_REPORT_ANY_MOUSE_EVENT);
message.AddBool("reportAnyMouseEvent", reportAnyMouseEvent);
fListener.SendMessage(&message);
}
}
void void
TerminalBuffer::SetEncoding(int encoding) TerminalBuffer::SetEncoding(int encoding)
{ {
+2
View File
@@ -34,6 +34,8 @@ public:
void UseAlternateScreenBuffer(bool clear); void UseAlternateScreenBuffer(bool clear);
void UseNormalScreenBuffer(); void UseNormalScreenBuffer();
void ReportAnyMouseEvent(bool reportAnyMouseEvent);
protected: protected:
virtual void NotifyListener(); virtual void NotifyListener();