PHP-GTK2 Newsletter

PHP-GTK2 Tips & Techniques
FREE Newsletter
by kksou



Sample Code 153: How to highlight matching brackets in GtkTextView - Part 2?
Written by kksou   
Sunday, 28 January 2007
Problem

In Part 1, you have highlighted enclosing curly brackets in a GtkTextView.

However, pressing the button when the cursor is at "else" should not highlight anything. We'll fix this in this article as shown below:

How to highlight matching brackets in GtkTextView - Part 2?


Solution
  • On the left, we need to make sure that there's no "}" after the "{" by using the method.
  • Similarly, on the right, we need to make sure that there's no "{" before the "}".
  • GtkTextiter::compare() is the method that allows us to compare the position of two iters.

Sample Code
1   
2   
3   
4   
5   
6   
7   
8   
9   
10   
11   
12   
13   
14   
15   
16   
17   
18   
19   
20   
21   
22   
23   
24   
25   
26   
27   
28   
29   
30   
31   
32   
33   
34   
35   
36   
37   
38   
39   
40   
41   
42   
43   
44   
45   
46   
47   
48   
49   
50   
51   
52   
53   
54   
55   
56   
57   
58   
59   
60   
61   
62   
63   
64   
65   
66   
67   
68   
69   
70   
71   
72   
73   
74   
75   
76   
77   
78   
79   
80   
81   
82   
83   
84   
85   
86   
87   
88   
89   
90   
91   
<?php
$window = new GtkWindow();
$window->set_size_request(400, 240);
$window->connect_simple('destroy', array('Gtk','main_quit'));
$window->add($vbox = new GtkVBox());

// display title
$title = new GtkLabel("Find matching curly bracket - Part 2\n".
"Place the cursor on 'else' and press the button.\n".
"Nothing will be highlighted.");
$title->modify_font(new PangoFontDescription("Times New Roman Italic 10"));
$title->modify_fg(Gtk::STATE_NORMAL, GdkColor::parse("#0000ff"));
$title->set_size_request(-1, 60);
$title->set_justify(Gtk::JUSTIFY_CENTER);
$alignment = new GtkAlignment(0.5, 0.5, 0, 0);
$alignment->add($title);
$vbox->pack_start($alignment);

$left_start_iter = $left_end_iter = null;
$right_start_iter = $right_end_iter = null;

// Create a new buffer and a new view to show the buffer.
$buffer = new GtkTextBuffer();
$buffer->set_text('if ($i==1) {
    test();
} else {
    test2();
}');
$view = new GtkTextView();
$view->set_buffer($buffer);
$view->modify_font(new PangoFontDescription("Arial 10"));
$view->set_wrap_mode(Gtk::WRAP_WORD);

$hbox = new GtkHBox();
$hbox->pack_start($button = new GtkButton('Find enclosing bracket'), 0);
$vbox->pack_start($hbox, 0);
$button->connect('clicked', 'on_button', $buffer);

$scrolled_win = new GtkScrolledWindow();
$scrolled_win->set_policy( Gtk::POLICY_AUTOMATIC, Gtk::POLICY_AUTOMATIC);
$vbox->pack_start($scrolled_win);
$scrolled_win->add($view);

$tag_table = $buffer->get_tag_table();
$tag['highlight'] = new GtkTextTag();
$tag['highlight']->set_property('background', "#ffff00");
$tag_table->add($tag['highlight']);

$window->show_all();
Gtk::main();

function find_left_bracket($iter, $buffer) {
    global $tag;
    $iter2 = $iter->copy();

    $match_start = $iter->copy();
    $match_end = $iter->copy();

    // check left { first
    $found = $iter->backward_search('{', 0, $match_start,
        $match_end, null);
    if (!$found) return null;

    // check if there's a } on the left
    $match_start2 = $iter->copy();
    $match_end2 = $iter->copy();

    $found2 = $iter2->backward_search('}', 0, $match_start2, // note 1
        $match_end2, null); 

    if ($found2 && $match_start->compare($match_start2)!=1) // note 2
        return null; 

    $buffer->apply_tag($tag['highlight'], $match_start, $match_end);
    return array($match_start, $match_end);
}

function find_right_bracket($iter, $buffer) {
    global $tag;
    $iter2 = $iter->copy();
    $match_start = $iter->copy();
    $match_end = $iter->copy();

    // check right } first
    $found = $iter->forward_search('}', 0, $match_start,
        $match_end, null);
    if (!$found) return null;

    // check if there's a { on the right
    $match_start2 = $iter->copy();
    $match_end2 = $iter->copy();
  • Note that this is only 70% of the sample code. You have to be a registered member to see the entire sample code. Please login or register.
  • Registration is free and immediate.
  • Have some doubt about the registration? Please read this forum article.
Explanation
  1. Check if there's a "}" on the left.
  2. If the } comes after the {, we do not highlight the curly bracket.
  3. Check if there's a "{" on the right.
  4. If the { comes after the }, we do not highlight the curly bracket.

Note

There is one more thing we need to improve:

  • When the user moves the cursor (by mouse or keyboard), the highlight should disappear.

We will fix this in the next article.


Related Links
 

Add comment


Security code
Refresh

< Prev   Next >

Blog - Forum - Privacy Policy - Contact Us
Copyright © 2006-2012. kksou.com. All Rights Reserved