Help! Custom cell renderers blowing up ...



Hi again :)

I've made steady progress today, but now I'm stumped again. I've been used bits of pieces of code borrowed from Odot and other examples I've found. Hence, I don't *quite* understand what they're doing completely :) Anyway, I'm getting into START_EDITING() fine. But when this exits, I get the error:

Can't locate object method "EDITING_STARTED" via package "Gtk3::Ex::Datasheet::DBI::CellRendererText" at /usr/lib64/perl5/site_perl/5.12.4/Gtk3.pm line 228.

>From my searching around, 'editing_started' is a signal, not a method. What's going on?

Dan

---

package Gtk3::Ex::Datasheet::DBI::CellEditableText;

# Copied and pasted from Odot

use strict;
use warnings;

use Glib qw(TRUE FALSE);
use Glib::Object::Subclass
  Gtk3::TextView::,
  interfaces => [ Gtk3::CellEditable:: ];

sub set_text {
   
    my ( $editable, $text ) = @_;
   
    $text = "" unless ( defined( $text ) );
   
    $editable->get_buffer()->set_text( $text, length( $text ) );
   
}

sub get_text {
   
    my ( $editable ) = @_;
    my $buffer = $editable->get_buffer();
   
    return $buffer->get_text( $buffer->get_bounds(), TRUE );
   
}

sub select_all {
   
    my ( $editable ) = @_;
    my $buffer = $editable->get_buffer();
   
    my ( $start, $end ) = $buffer->get_bounds();
    $buffer->move_mark_by_name( insert => $start );
    $buffer->move_mark_by_name( selection_bound => $end );
   
}

1;

package Gtk3::Ex::Datasheet::DBI::CellRendererText;

# Originally from Odot, with bits and pieces from the CellRendererSpinButton example,
# and even some of my own stuff worked in :)

use constant x_padding => 2;
use constant y_padding => 3;

use strict;
use warnings;

#use Gtk3::Gdk;
use Glib qw(TRUE FALSE);

use Glib::Object::Subclass
  Gtk3::CellRendererText::,
  properties => [
                    Glib::ParamSpec->object(
                                                    "editable-widget",
                                                    "Editable widget",
                                                    "The editable that's used for cell editing.",
                                                    Gtk3::Ex::Datasheet::DBI::CellEditableText::,
                                                    [ qw( readable writable ) ]
                                           ),
                    Glib::ParamSpec->boolean(
                                                    "number",
                                                    "Number",
                                                    "Should I apply number formatting to the data?",
                                                    0,
                                                    [ qw( readable writable ) ]
                                            ),
                    Glib::ParamSpec->string(
                                                    "decimals",
                                                    "Decimals",
                                                    "How many decimal places should be displayed?",
                                                    -1,
                                                    [ qw( readable writable ) ]
                                           ),
                    Glib::ParamSpec->boolean(
                                                    "currency",
                                                    "Currency",
                                                    "Should I prepend a dollar sign to the data?",
                                                    0,
                                                    [ qw( readable writable ) ]
                                            )
                ];

sub INIT_INSTANCE {
   
    my ( $cell ) = @_;
   
    my $editable = Gtk3::Ex::Datasheet::DBI::CellEditableText->new();
   
    $editable->set( border_width => $cell->get( "ypad" ) );
   
    $editable->signal_connect( key_press_event => sub {
       
        my ( $editable, $event ) = @_;
       
        #if (
        #    $event -> keyval == $Gtk2::Gdk::Keysyms{ Return } ||
        #    $event -> keyval == $Gtk2::Gdk::Keysyms{ KP_Enter }
        #    and not $event -> state & qw(control-mask)
        #   )
       
        # TODO: Find these constants ...
        if (
            $event->keyval == $Gtk3::Gdk::KEY_RETURN ||
            $event->keyval == $Gtk3::Gdk::KEY_KP_ENTER
            and not $event-> state & qw(control-mask)
           )
        {
           
            # Grab parent
            my $parent = $editable->get_parent;
           
            $editable->{ _editing_canceled } = FALSE;
            $editable->editing_done();
            $editable->remove_widget();
           
            my ( $path, $focus_column ) = $parent->get_cursor;
            my @cols = $parent->get_columns;
            my $next_col = undef;
           
            foreach my $i (0..$#cols) {
                if ( $cols[$i] == $focus_column ) {
                    if ( $event->state >= 'shift-mask' ) {
                        # go backwards
                        $next_col = $cols[$i-1] if $i > 0;
                    } else {
                        # Go forwards
                        # First check whether the next column is read_only
                        while ( $i-1 < $#cols ) {
                            $i++;
                            if ( ! $cols[$i]->{definition}->{read_only} ) {
                                last;
                            }
                        }
                        $next_col = $cols[$i];
                    }
                    last;
                }
            }
           
            # For some reason, the last item returned by the above call to
            # $parent->get_columns isn't a Gtk3::TreeViewColumn, and therefore
            # the $parent_set_cursor line fails. Avoid this.
            if ( ref $next_col eq 'Gtk3::TreeViewColumn' ) {
                $parent->set_cursor ( $path, $next_col, 1 )
                    if $next_col;
            }
           
            return TRUE;
           
        }
       
        return FALSE;
       
    });
   
    $editable->signal_connect( editing_done => sub {
       
        my ( $editable ) = @_;
       
        # TODO: figure out what used to be going on here, and what is now appropriate
       
        # gtk+ changed semantics in 2.6.  you now need to call stop_editing().
        #if ( Gtk2->CHECK_VERSION( 2, 6, 0 ) ) {
            $cell->stop_editing( $editable->{ _editing_canceled } );
        #}
       
        # if gtk+ < 2.4.0, emit the signal regardless of whether editing was
        # canceled to make undo/redo work.
       
        #my $new = Gtk2->CHECK_VERSION( 2, 4, 0 );
        #
        #if ( ! $new || ( $new && ! $editable->{ _editing_canceled } ) ) {
        #    $cell->signal_emit( edited => $editable->{ _path }, $editable -> get_text() );
        #} else {
            $cell->editing_canceled();
        #}
    });
   
    $cell->set( editable_widget => $editable );
   
}

sub GET_SIZE {
   
    my ( $self, $widget, $cell_area ) = @_;
   
    return $self->SUPER::GET_SIZE ( $widget, $cell_area );
   
}

sub START_EDITING {
   
    my ( $cell, $event, $view, $path, $background_area, $cell_area, $flags ) = @_;
   
    if ( $event ) {
        return unless ( $event->button == 1 );
    }
   
    my $editable = $cell->get( "editable-widget" );
   
    #$editable->modify_font( Gtk2::Pango::FontDescription->from_string( "Arial " . $cell->get( "font" ) ) );
    $editable->modify_font( Pango::FontDescription->from_string( "Arial " . $cell->get( "font" ) ) );
   
    $editable->{ _editing_canceled } = FALSE;
    $editable->{ _path } = $path;
    $editable->set( height_request => $cell_area->{height} );
   
    $editable->set_text( $cell->get( "text" ) );
    $editable->select_all();
    $editable->show();
   
    $editable -> signal_connect_after(
            'focus-out-event'       => sub {
                                                my ( $event_box, $event ) = @_;
                                                $cell->signal_emit( edited => $editable->{ _path }, $editable->get_text );
                                                return $event;
            }
                               );
   
    return $editable;
   
}

sub get_layout {
   
    my ( $cell, $widget ) = @_;
   
    return $widget->create_pango_layout( "" );
   
}

1;

[Date Prev][Date Next]   [Thread Prev][Thread Next]   [Thread Index] [Date Index] [Author Index]