📄 scintillagtk.cxx
字号:
sciThis->UnRealizeThis(widget);
}
static void MapWidget(GtkWidget *widget) {
if (widget &&
GTK_WIDGET_VISIBLE(widget) &&
!GTK_WIDGET_MAPPED(widget)) {
gtk_widget_map(widget);
}
}
void ScintillaGTK::MapThis() {
//Platform::DebugPrintf("ScintillaGTK::map this\n");
GTK_WIDGET_SET_FLAGS(PWidget(wMain), GTK_MAPPED);
MapWidget(PWidget(wText));
MapWidget(PWidget(scrollbarh));
MapWidget(PWidget(scrollbarv));
wMain.SetCursor(Window::cursorArrow);
scrollbarv.SetCursor(Window::cursorArrow);
scrollbarh.SetCursor(Window::cursorArrow);
gdk_window_show(PWidget(wMain)->window);
}
void ScintillaGTK::Map(GtkWidget *widget) {
ScintillaGTK *sciThis = ScintillaFromWidget(widget);
sciThis->MapThis();
}
void ScintillaGTK::UnMapThis() {
//Platform::DebugPrintf("ScintillaGTK::unmap this\n");
GTK_WIDGET_UNSET_FLAGS(PWidget(wMain), GTK_MAPPED);
gdk_window_hide(PWidget(wMain)->window);
gtk_widget_unmap(PWidget(wText));
gtk_widget_unmap(PWidget(scrollbarh));
gtk_widget_unmap(PWidget(scrollbarv));
}
void ScintillaGTK::UnMap(GtkWidget *widget) {
ScintillaGTK *sciThis = ScintillaFromWidget(widget);
sciThis->UnMapThis();
}
#ifdef INTERNATIONAL_INPUT
gint ScintillaGTK::CursorMoved(GtkWidget *widget, int xoffset, int yoffset, ScintillaGTK *sciThis) {
if (GTK_WIDGET_HAS_FOCUS(widget) && gdk_im_ready() && sciThis->ic &&
(gdk_ic_get_style (sciThis->ic) & GDK_IM_PREEDIT_POSITION)) {
sciThis->ic_attr->spot_location.x = xoffset;
sciThis->ic_attr->spot_location.y = yoffset;
gdk_ic_set_attr (sciThis->ic, sciThis->ic_attr, GDK_IC_SPOT_LOCATION);
}
return FALSE;
}
#else
gint ScintillaGTK::CursorMoved(GtkWidget *, int, int, ScintillaGTK *) {
return FALSE;
}
#endif
gint ScintillaGTK::FocusIn(GtkWidget *widget, GdkEventFocus * /*event*/) {
ScintillaGTK *sciThis = ScintillaFromWidget(widget);
//Platform::DebugPrintf("ScintillaGTK::focus in %x\n", sciThis);
GTK_WIDGET_SET_FLAGS(widget, GTK_HAS_FOCUS);
sciThis->SetFocusState(true);
#ifdef INTERNATIONAL_INPUT
if (sciThis->ic)
gdk_im_begin(sciThis->ic, widget->window);
#endif
return FALSE;
}
gint ScintillaGTK::FocusOut(GtkWidget *widget, GdkEventFocus * /*event*/) {
ScintillaGTK *sciThis = ScintillaFromWidget(widget);
//Platform::DebugPrintf("ScintillaGTK::focus out %x\n", sciThis);
GTK_WIDGET_UNSET_FLAGS(widget, GTK_HAS_FOCUS);
sciThis->SetFocusState(false);
#ifdef INTERNATIONAL_INPUT
gdk_im_end();
#endif
return FALSE;
}
void ScintillaGTK::SizeRequest(GtkWidget *widget, GtkRequisition *requisition) {
requisition->width = 600;
requisition->height = 2000;
ScintillaGTK *sciThis = ScintillaFromWidget(widget);
GtkRequisition child_requisition;
gtk_widget_size_request(PWidget(sciThis->scrollbarh), &child_requisition);
gtk_widget_size_request(PWidget(sciThis->scrollbarv), &child_requisition);
}
void ScintillaGTK::SizeAllocate(GtkWidget *widget, GtkAllocation *allocation) {
widget->allocation = *allocation;
ScintillaGTK *sciThis = ScintillaFromWidget(widget);
if (GTK_WIDGET_REALIZED(widget))
gdk_window_move_resize(widget->window,
widget->allocation.x,
widget->allocation.y,
widget->allocation.width,
widget->allocation.height);
sciThis->Resize(allocation->width, allocation->height);
#ifdef INTERNATIONAL_INPUT
if (sciThis->ic && (gdk_ic_get_style (sciThis->ic) & GDK_IM_PREEDIT_POSITION)) {
gint width, height;
gdk_window_get_size(widget->window, &width, &height);
sciThis->ic_attr->preedit_area.width = width;
sciThis->ic_attr->preedit_area.height = height;
gdk_ic_set_attr(sciThis->ic, sciThis->ic_attr, GDK_IC_PREEDIT_AREA);
}
#endif
}
void ScintillaGTK::Initialise() {
//Platform::DebugPrintf("ScintillaGTK::Initialise\n");
parentClass = reinterpret_cast<GtkWidgetClass *>(
gtk_type_class(gtk_container_get_type()));
GTK_WIDGET_SET_FLAGS(PWidget(wMain), GTK_CAN_FOCUS);
GTK_WIDGET_SET_FLAGS(GTK_WIDGET(PWidget(wMain)), GTK_SENSITIVE);
gtk_widget_set_events(PWidget(wMain),
GDK_EXPOSURE_MASK
| GDK_STRUCTURE_MASK
| GDK_KEY_PRESS_MASK
| GDK_KEY_RELEASE_MASK
| GDK_FOCUS_CHANGE_MASK
| GDK_LEAVE_NOTIFY_MASK
| GDK_BUTTON_PRESS_MASK
| GDK_BUTTON_RELEASE_MASK
| GDK_POINTER_MOTION_MASK
| GDK_POINTER_MOTION_HINT_MASK);
wText = gtk_drawing_area_new();
gtk_widget_set_parent(PWidget(wText), PWidget(wMain));
gtk_widget_show(PWidget(wText));
gtk_signal_connect(GTK_OBJECT(PWidget(wText)), "expose_event",
GtkSignalFunc(ScintillaGTK::ExposeText), this);
gtk_widget_set_events(PWidget(wText), GDK_EXPOSURE_MASK);
#if GTK_MAJOR_VERSION >= 2
// Avoid background drawing flash
gtk_widget_set_double_buffered(PWidget(wText), FALSE);
#endif
gtk_drawing_area_size(GTK_DRAWING_AREA(PWidget(wText)),
100,100);
adjustmentv = gtk_adjustment_new(0.0, 0.0, 201.0, 1.0, 20.0, 20.0);
scrollbarv = gtk_vscrollbar_new(GTK_ADJUSTMENT(adjustmentv));
GTK_WIDGET_UNSET_FLAGS(PWidget(scrollbarv), GTK_CAN_FOCUS);
gtk_signal_connect(GTK_OBJECT(adjustmentv), "value_changed",
GTK_SIGNAL_FUNC(ScrollSignal), this);
gtk_widget_set_parent(PWidget(scrollbarv), PWidget(wMain));
gtk_widget_show(PWidget(scrollbarv));
adjustmenth = gtk_adjustment_new(0.0, 0.0, 101.0, 1.0, 20.0, 20.0);
scrollbarh = gtk_hscrollbar_new(GTK_ADJUSTMENT(adjustmenth));
GTK_WIDGET_UNSET_FLAGS(PWidget(scrollbarh), GTK_CAN_FOCUS);
gtk_signal_connect(GTK_OBJECT(adjustmenth), "value_changed",
GTK_SIGNAL_FUNC(ScrollHSignal), this);
gtk_widget_set_parent(PWidget(scrollbarh), PWidget(wMain));
gtk_widget_show(PWidget(scrollbarh));
gtk_widget_grab_focus(PWidget(wMain));
static const GtkTargetEntry targets[] = {
{ "STRING", 0, TARGET_STRING },
{ "TEXT", 0, TARGET_TEXT },
{ "COMPOUND_TEXT", 0, TARGET_COMPOUND_TEXT },
{ "text/uri-list", 0, 0 },
};
static const gint n_targets = sizeof(targets) / sizeof(targets[0]);
gtk_selection_add_targets(GTK_WIDGET(PWidget(wMain)), GDK_SELECTION_PRIMARY,
targets, n_targets);
if (!clipboard_atom)
clipboard_atom = gdk_atom_intern("CLIPBOARD", FALSE);
gtk_selection_add_targets(GTK_WIDGET(PWidget(wMain)), clipboard_atom,
targets, n_targets);
gtk_drag_dest_set(GTK_WIDGET(PWidget(wMain)),
GTK_DEST_DEFAULT_ALL, targets, n_targets,
static_cast<GdkDragAction>(GDK_ACTION_COPY | GDK_ACTION_MOVE));
SetTicking(true);
}
void ScintillaGTK::Finalise() {
SetTicking(false);
ScintillaBase::Finalise();
}
void ScintillaGTK::DisplayCursor(Window::Cursor c) {
if (cursorMode == SC_CURSORNORMAL)
wText.SetCursor(c);
else
wText.SetCursor(static_cast<Window::Cursor>(cursorMode));
}
void ScintillaGTK::StartDrag() {
dragWasDropped = false;
static const GtkTargetEntry targets[] = {
{ "STRING", 0, TARGET_STRING },
{ "TEXT", 0, TARGET_TEXT },
{ "COMPOUND_TEXT", 0, TARGET_COMPOUND_TEXT },
};
static const gint n_targets = sizeof(targets) / sizeof(targets[0]);
GtkTargetList *tl = gtk_target_list_new(targets, n_targets);
gtk_drag_begin(GTK_WIDGET(PWidget(wMain)),
tl,
static_cast<GdkDragAction>(GDK_ACTION_COPY | GDK_ACTION_MOVE),
evbtn.button,
reinterpret_cast<GdkEvent *>(&evbtn));
}
sptr_t ScintillaGTK::WndProc(unsigned int iMessage, uptr_t wParam, sptr_t lParam) {
switch (iMessage) {
case SCI_GRABFOCUS:
gtk_widget_grab_focus(PWidget(wMain));
break;
case SCI_GETDIRECTFUNCTION:
return reinterpret_cast<sptr_t>(DirectFunction);
case SCI_GETDIRECTPOINTER:
return reinterpret_cast<sptr_t>(this);
#ifdef SCI_LEXER
case SCI_LOADLEXERLIBRARY:
LexerManager::GetInstance()->Load(reinterpret_cast<const char*>( wParam ));
break;
#endif
default:
return ScintillaBase::WndProc(iMessage, wParam, lParam);
}
return 0l;
}
sptr_t ScintillaGTK::DefWndProc(unsigned int, uptr_t, sptr_t) {
return 0;
}
void ScintillaGTK::SetTicking(bool on) {
if (timer.ticking != on) {
timer.ticking = on;
if (timer.ticking) {
timer.tickerID = reinterpret_cast<TickerID>(gtk_timeout_add(timer.tickSize, (GtkFunction)TimeOut, this));
} else {
gtk_timeout_remove(GPOINTER_TO_UINT(timer.tickerID));
}
}
timer.ticksToWait = caret.period;
}
void ScintillaGTK::SetMouseCapture(bool on) {
if (mouseDownCaptures) {
if (on) {
gtk_grab_add(GTK_WIDGET(PWidget(wMain)));
} else {
gtk_grab_remove(GTK_WIDGET(PWidget(wMain)));
}
}
capturedMouse = on;
}
bool ScintillaGTK::HaveMouseCapture() {
return capturedMouse;
}
// Redraw all of text area. This paint will not be abandoned.
void ScintillaGTK::FullPaint() {
#if GTK_MAJOR_VERSION < 2
paintState = painting;
rcPaint = GetClientRectangle();
//Platform::DebugPrintf("ScintillaGTK::FullPaint %0d,%0d %0d,%0d\n",
// rcPaint.left, rcPaint.top, rcPaint.right, rcPaint.bottom);
paintingAllText = true;
if ((PWidget(wText))->window) {
Surface *sw = Surface::Allocate();
if (sw) {
sw->Init(PWidget(wText)->window, PWidget(wText));
Paint(sw, rcPaint);
sw->Release();
delete sw;
}
}
paintState = notPainting;
#else
wText.InvalidateAll();
#endif
}
PRectangle ScintillaGTK::GetClientRectangle() {
PRectangle rc = wMain.GetClientPosition();
if (verticalScrollBarVisible)
rc.right -= scrollBarWidth;
if (horizontalScrollBarVisible && (wrapState == eWrapNone))
rc.bottom -= scrollBarHeight;
// Move to origin
rc.right -= rc.left;
rc.bottom -= rc.top;
rc.left = 0;
rc.top = 0;
return rc;
}
// Synchronously paint a rectangle of the window.
void ScintillaGTK::SyncPaint(PRectangle rc) {
paintState = painting;
rcPaint = rc;
PRectangle rcClient = GetClientRectangle();
paintingAllText = rcPaint.Contains(rcClient);
if ((PWidget(wText))->window) {
Surface *sw = Surface::Allocate();
if (sw) {
sw->Init(PWidget(wText)->window, PWidget(wText));
Paint(sw, rc);
sw->Release();
delete sw;
}
}
if (paintState == paintAbandoned) {
// Painting area was insufficient to cover new styling or brace highlight positions
FullPaint();
}
paintState = notPainting;
}
void ScintillaGTK::ScrollText(int linesToMove) {
int diff = vs.lineHeight * -linesToMove;
//Platform::DebugPrintf("ScintillaGTK::ScrollText %d %d %0d,%0d %0d,%0d\n", linesToMove, diff,
// rc.left, rc.top, rc.right, rc.bottom);
GtkWidget *wi = PWidget(wText);
#if GTK_MAJOR_VERSION < 2
PRectangle rc = GetClientRectangle();
GdkGC *gc = gdk_gc_new(wi->window);
// Set up gc so we get GraphicsExposures from gdk_draw_pixmap
// which calls XCopyArea
gdk_gc_set_exposures(gc, TRUE);
// Redraw exposed bit : scrolling upwards
if (diff > 0) {
gdk_draw_pixmap(wi->window,
gc, wi->window,
0, diff,
0, 0,
rc.Width()-1, rc.Height() - diff);
SyncPaint(PRectangle(0, rc.Height() - diff,
rc.Width(), rc.Height()+1));
// Redraw exposed bit : scrolling downwards
} else {
gdk_draw_pixmap(wi->window,
gc, wi->window,
0, 0,
0, -diff,
rc.Width()-1, rc.Height() + diff);
SyncPaint(PRectangle(0, 0, rc.Width(), -diff));
}
// Look for any graphics expose
GdkEvent* event;
while ((event = gdk_event_get_graphics_expose(wi->window)) != NULL) {
gtk_widget_event(wi, event);
if (event->expose.count == 0) {
gdk_event_free(event);
break;
}
gdk_event_free(event);
}
gdk_gc_unref(gc);
#else
gdk_window_scroll(wi->window, 0, -diff);
#endif
}
void ScintillaGTK::SetVerticalScrollPos() {
gtk_adjustment_set_value(GTK_ADJUSTMENT(adjustmentv), topLine);
}
void ScintillaGTK::SetHorizontalScrollPos() {
gtk_adjustment_set_value(GTK_ADJUSTMENT(adjustmenth), xOffset / 2);
}
bool ScintillaGTK::ModifyScrollBars(int nMax, int nPage) {
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -