|
Problem You want to highlight enclosing html tags in a GtkTextView as shown below:

Solution
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 92 93 94 95 96 97 98 99 100 101
| <?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("Highlight matching HTML tags"); $title->modify_font(new PangoFontDescription("Times New Roman Italic 10")); $title->modify_fg(Gtk::STATE_NORMAL, GdkColor::parse("#0000ff")); $title->set_size_request(-1, 20); $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('<p>This is a test</p> <ul> <li>item 1</li> <li>item 2</li> <li>item 3</li> </ul>'); $view = new GtkTextView(); $view->set_buffer($buffer); $view->modify_font(new PangoFontDescription("Arial 10")); $view->set_wrap_mode(Gtk::WRAP_WORD); $view->connect('button-press-event', 'on_button_press_in_textview'); $view->connect('key-press-event', 'on_key_press_in_textview');
$hbox = new GtkHBox(); $hbox->pack_start($button = new GtkButton('Find enclosing tags'), 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_tag($iter, $buffer) { global $tag;
$match_start = $iter->copy(); $match_end = $iter->copy();
// check left { first
$found = $iter->backward_search('<', 0, $match_start, // note 1
$match_end, null); if (!$found) return null;
// check if there's a } on the left
$iter2 = $match_end->copy(); $match_start2 = $iter2->copy(); $match_end2 = $iter2->copy();
$found2 = $iter2->forward_search('>', 0, $match_start2, // note 2
$match_end2, null);
if ($found2 && $match_start->compare($match_start2)!=-1) return null;
$buffer->apply_tag($tag['highlight'], $match_start, $match_end2); // note 3
return array($match_start, $match_end2); }
function find_right_tag($current_iter, $buffer) { global $tag; $iter = $current_iter->copy(); $match_start = $iter->copy(); $match_end = $iter->copy();
// check right } first
$found = $iter->forward_search('<', 0, $match_start, // note 4
$match_end, null); if (!$found) return null;
// check if there's a { on the left
$iter2 = $match_end->copy(); $match_start2 = $iter2->copy(); $match_end2 = $iter2->copy();
$found2 = $iter2->forward_search('>', 0, $match_start2, // note 5
$match_end2, null);
if ($found2 && $match_start->compare($match_start2)!=-1) return null;
$buffer->apply_tag($tag['highlight'], $match_start, $match_end2); // note 6
return array($match_start, $match_end2); }
|
- 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
- Search for start of left tag.
- Search for end of left tag.
- Highlight the left tag.
- Search for start of right tag.
- Search for end of right tag.
- Highlight the right tag.
Note
To make the code easier to understand, I did not put in any error checking here. In your actual implementation, you should check that the start and end tags are matching, otherwise the following might occur:

Related Links
User reviews There are no user reviews yet. Note: You have to be a registered member to leave a comment. Free registration here. |