blackedpi
blackedpi

Reputation: 21

GTK3 C program push button in GTKScrolled Window with GTKTreeView with GTKListStore to scroll row into view

I ported a program to GTK3 in C language and everything works perfect except one thing. Say the TreeView that only shows 10 rows at a time, but is populated with 100 rows, the other rows out of view of course with tree view set to Single select rows with multple colums.

I use a button callback function to highlight and then select row 0, then increment a static index++ at end of call. Next button press highlights and selects row 1, and so forth.

When highlighted and selected row gets to the 11th row, which is out of view, I can't figure out how to scroll the tree view so that the next 11th row comes into view. The rows keep getting highlighted, cause I have printf statements for feedback. I googled for weeks, seen examples and everything, but not so much for C, although I had to translate some other code to C that I used to figure out how to select and highlight the rows, but in C couldn't figure out the scrolling part.

Using Glade, I have a main window with a child GtkFixed, with a button, progress bar, and in the GtkFixed is a GtkScrolledWindow, which contains a GtkViewPort, in which inside that is the GtkTreeView with string based columns.

Thanks for any feedback and or links. Not sure if the TreeView needs to be inside a GtkViewPort, but might have looked at older code during development and research.

my callback function

void single_button_clicked_cb(GtkWidget *widget, gpointer data)
{
    static int         index = 0;
    GtkTreeIter iter;
    char buf[9];
    GtkTreeModel *model;
    GtkAdjustment *vadjustment;
    int i;

    printf("\nScroll Active test row to %d\n",index);

    sprintf(buf,"%d",index);

    gtk_widget_grab_focus (GTK_WIDGET(gtk_tree_view));

    GtkTreePath *path = gtk_tree_path_new_from_string(buf);

    gtk_tree_view_scroll_to_cell(GTK_TREE_VIEW (gtk_tree_view),path, NULL,FALSE, 0.0, 0.0);

    gtk_tree_view_set_cursor (gtk_tree_view,path,NULL,FALSE); // works but doesn't scroll

    gtk_tree_path_free(path);

    index++;
}

Glade File

<?xml version="1.0" encoding="UTF-8"?>
<interface>
  <!-- interface-requires gtk+ 3.0 -->
  <!-- interface-naming-policy toplevel-contextual -->
  <object class="GtkAdjustment" id="adjustment1">
    <property name="upper">100</property>
    <property name="step_increment">1</property>
    <property name="page_increment">10</property>
  </object>
  <object class="GtkListStore" id="gtk_list_store">
    <columns>
      <!-- column-name Test -->
      <column type="gchararray"/>
      <!-- column-name Test1 -->
      <column type="gchararray"/>
      <!-- column-name Test2 -->
      <column type="gchararray"/>
      <!-- column-name Test3 -->
      <column type="gchararray"/>
      <!-- column-name Test4 -->
      <column type="gchararray"/>
      <!-- column-name Pass -->
      <column type="gchararray"/>
    </columns>
  </object>
  <object class="GtkWindow" id="main_window">
    <property name="width_request">1050</property>
    <property name="height_request">810</property>
    <property name="can_focus">False</property>
    <property name="border_width">3</property>
    <property name="resizable">False</property>
    <property name="window_position">center</property>
    <property name="gravity">center</property>
    <signal name="destroy" handler="on_main_window_destroy" swapped="no"/>
    <child>
      <object class="GtkFixed" id="gtk_fixed">
        <property name="visible">True</property>
        <property name="can_focus">False</property>
        <child>
          <object class="GtkButton" id="start_button">
            <property name="label" translatable="yes">Start</property>
            <property name="width_request">100</property>
            <property name="height_request">48</property>
            <property name="visible">True</property>
            <property name="can_focus">True</property>
            <property name="receives_default">True</property>
            <signal name="clicked" handler="start_button_clicked_cb" swapped="no"/>
          </object>
          <packing>
            <property name="x">935</property>
            <property name="y">605</property>
          </packing>
        </child>
        <child>
          <object class="GtkButton" id="single_button">
            <property name="label" translatable="yes">Single</property>
            <property name="width_request">100</property>
            <property name="height_request">48</property>
            <property name="visible">True</property>
            <property name="can_focus">True</property>
            <property name="receives_default">True</property>
            <signal name="clicked" handler="single_button_clicked_cb" swapped="no"/>
          </object>
          <packing>
            <property name="x">6</property>
            <property name="y">605</property>
          </packing>
        </child>
        <child>
          <object class="GtkProgressBar" id="progress_bar">
            <property name="width_request">1030</property>
            <property name="height_request">25</property>
            <property name="visible">True</property>
            <property name="can_focus">False</property>
          </object>
          <packing>
            <property name="x">1</property>
            <property name="y">100</property>
          </packing>
        </child>
        <child>
          <object class="GtkScrolledWindow" id="scrolled_window">
            <property name="width_request">1030</property>
            <property name="height_request">465</property>
            <property name="visible">True</property>
            <property name="can_focus">True</property>
            <property name="vadjustment">adjustment1</property>
            <property name="hscrollbar_policy">never</property>
            <property name="vscrollbar_policy">automatic</property>
            <child>
              <object class="GtkViewport" id="gtk_viewport">
                <property name="visible">True</property>
                <property name="can_focus">False</property>
                <child>
                  <object class="GtkTreeView" id="gtk_tree_view">
                    <property name="visible">True</property>
                    <property name="can_focus">True</property>
                    <property name="model">gtk_list_store</property>
                    <property name="headers_clickable">False</property>
                    <property name="enable_grid_lines">both</property>
                    <signal name="cursor-changed" handler="selected_row_index_cb" swapped="no"/>
                    <child>
                      <object class="GtkTreeViewColumn" id="col_test_description">
                        <property name="resizable">True</property>
                        <property name="title" translatable="yes">Test Description</property>
                        <child>
                          <object class="GtkCellRendererText" id="col_renderer_description"/>
                        </child>
                      </object>
                    </child>
                    <child>
                      <object class="GtkTreeViewColumn" id="col_test_number">
                        <property name="resizable">True</property>
                        <property name="title" translatable="yes">Test Number</property>
                        <property name="alignment">0.5</property>
                        <child>
                          <object class="GtkCellRendererText" id="col_renderer_number"/>
                        </child>
                      </object>
                    </child>
                    <child>
                      <object class="GtkTreeViewColumn" id="col_test_limits">
                        <property name="resizable">True</property>
                        <property name="title" translatable="yes">Test Limits</property>
                        <property name="alignment">0.5</property>
                        <child>
                          <object class="GtkCellRendererText" id="col_renderer_limits"/>
                        </child>
                      </object>
                    </child>
                    <child>
                      <object class="GtkTreeViewColumn" id="col_test_measurement">
                        <property name="resizable">True</property>
                        <property name="title" translatable="yes">Test Measurement</property>
                        <property name="alignment">0.5</property>
                        <child>
                          <object class="GtkCellRendererText" id="col_renderer_measurement"/>
                        </child>
                      </object>
                    </child>
                    <child>
                      <object class="GtkTreeViewColumn" id="col_test_units">
                        <property name="resizable">True</property>
                        <property name="title" translatable="yes">Test Units</property>
                        <child>
                          <object class="GtkCellRendererText" id="col_renderer_units"/>
                        </child>
                      </object>
                    </child>
                    <child>
                      <object class="GtkTreeViewColumn" id="col_test_pass_fail">
                        <property name="resizable">True</property>
                        <property name="title" translatable="yes">Pass / Fail</property>
                        <property name="alignment">0.5</property>
                        <child>
                          <object class="GtkCellRendererText" id="col_renderer_pass_fail"/>
                        </child>
                      </object>
                    </child>
                  </object>
                </child>
              </object>
            </child>
          </object>
          <packing>
            <property name="x">3</property>
            <property name="y">132</property>
          </packing>
        </child>
        <child>
          <object class="GtkMenuBar" id="menu">
            <property name="width_request">180</property>
            <property name="height_request">30</property>
            <property name="visible">True</property>
            <property name="can_focus">False</property>
            <child>
              <object class="GtkMenuItem" id="gtk_file_menu_item">
                <property name="visible">True</property>
                <property name="can_focus">False</property>
                <property name="label" translatable="yes">_File</property>
                <property name="use_underline">True</property>
                <child type="submenu">
                  <object class="GtkMenu" id="gtk_file_menu">
                    <property name="visible">True</property>
                    <property name="can_focus">False</property>
                    <child>
                      <object class="GtkImageMenuItem" id="gtk_new">
                        <property name="label">gtk-new</property>
                        <property name="visible">True</property>
                        <property name="can_focus">False</property>
                        <property name="use_underline">True</property>
                        <property name="use_stock">True</property>
                      </object>
                    </child>
                    <child>
                      <object class="GtkImageMenuItem" id="gtk_open">
                        <property name="label">gtk-open</property>
                        <property name="visible">True</property>
                        <property name="can_focus">False</property>
                        <property name="use_underline">True</property>
                        <property name="use_stock">True</property>
                        <signal name="activate" handler="open_limits_file" swapped="no"/>
                      </object>
                    </child>
                    <child>
                      <object class="GtkImageMenuItem" id="gtk_save">
                        <property name="label">gtk-save</property>
                        <property name="visible">True</property>
                        <property name="can_focus">False</property>
                        <property name="use_underline">True</property>
                        <property name="use_stock">True</property>
                      </object>
                    </child>
                    <child>
                      <object class="GtkImageMenuItem" id="gtk_save_as">
                        <property name="label">gtk-save-as</property>
                        <property name="visible">True</property>
                        <property name="can_focus">False</property>
                        <property name="use_underline">True</property>
                        <property name="use_stock">True</property>
                      </object>
                    </child>
                    <child>
                      <object class="GtkSeparatorMenuItem" id="separatormenuitem1">
                        <property name="visible">True</property>
                        <property name="can_focus">False</property>
                      </object>
                    </child>
                    <child>
                      <object class="GtkImageMenuItem" id="gtk_quit">
                        <property name="label">gtk-quit</property>
                        <property name="visible">True</property>
                        <property name="can_focus">False</property>
                        <property name="use_underline">True</property>
                        <property name="use_stock">True</property>
                        <signal name="activate" handler="on_main_window_destroy" swapped="no"/>
                      </object>
                    </child>
                  </object>
                </child>
              </object>
            </child>
            <child>
              <object class="GtkMenuItem" id="gtk_edit_menu_item">
                <property name="visible">True</property>
                <property name="can_focus">False</property>
                <property name="label" translatable="yes">_Edit</property>
                <property name="use_underline">True</property>
                <child type="submenu">
                  <object class="GtkMenu" id="gtk_edit_menu">
                    <property name="visible">True</property>
                    <property name="can_focus">False</property>
                    <child>
                      <object class="GtkImageMenuItem" id="imagemenuitem6">
                        <property name="label">gtk-cut</property>
                        <property name="visible">True</property>
                        <property name="can_focus">False</property>
                        <property name="use_underline">True</property>
                        <property name="use_stock">True</property>
                      </object>
                    </child>
                    <child>
                      <object class="GtkImageMenuItem" id="imagemenuitem7">
                        <property name="label">gtk-copy</property>
                        <property name="visible">True</property>
                        <property name="can_focus">False</property>
                        <property name="use_underline">True</property>
                        <property name="use_stock">True</property>
                      </object>
                    </child>
                    <child>
                      <object class="GtkImageMenuItem" id="imagemenuitem8">
                        <property name="label">gtk-paste</property>
                        <property name="visible">True</property>
                        <property name="can_focus">False</property>
                        <property name="use_underline">True</property>
                        <property name="use_stock">True</property>
                      </object>
                    </child>
                    <child>
                      <object class="GtkImageMenuItem" id="imagemenuitem9">
                        <property name="label">gtk-delete</property>
                        <property name="visible">True</property>
                        <property name="can_focus">False</property>
                        <property name="use_underline">True</property>
                        <property name="use_stock">True</property>
                      </object>
                    </child>
                  </object>
                </child>
              </object>
            </child>
            <child>
              <object class="GtkMenuItem" id="gtk_view_menu_item">
                <property name="visible">True</property>
                <property name="can_focus">False</property>
                <property name="label" translatable="yes">_View</property>
                <property name="use_underline">True</property>
              </object>
            </child>
            <child>
              <object class="GtkMenuItem" id="gtk_help_menu_item">
                <property name="visible">True</property>
                <property name="can_focus">False</property>
                <property name="label" translatable="yes">_Help</property>
                <property name="use_underline">True</property>
                <child type="submenu">
                  <object class="GtkMenu" id="gtk_help_menu">
                    <property name="visible">True</property>
                    <property name="can_focus">False</property>
                    <child>
                      <object class="GtkImageMenuItem" id="imagemenuitem10">
                        <property name="label">gtk-about</property>
                        <property name="visible">True</property>
                        <property name="can_focus">False</property>
                        <property name="use_underline">True</property>
                        <property name="use_stock">True</property>
                      </object>
                    </child>
                  </object>
                </child>
              </object>
            </child>
          </object>
          <packing>
            <property name="x">-1</property>
            <property name="y">-1</property>
          </packing>
        </child>
        <child>
          <object class="GtkLabel" id="test_name">
            <property name="width_request">1030</property>
            <property name="height_request">80</property>
            <property name="visible">True</property>
            <property name="can_focus">False</property>
            <property name="use_markup">True</property>
            <property name="justify">center</property>
            <property name="single_line_mode">True</property>
          </object>
          <packing>
            <property name="x">3</property>
            <property name="y">667</property>
          </packing>
        </child>
        <child>
          <object class="GtkLabel" id="test_command">
            <property name="width_request">1030</property>
            <property name="height_request">80</property>
            <property name="visible">True</property>
            <property name="can_focus">False</property>
            <property name="use_markup">True</property>
            <property name="justify">center</property>
            <property name="single_line_mode">True</property>
          </object>
          <packing>
            <property name="x">3</property>
            <property name="y">32</property>
          </packing>
        </child>
      </object>
    </child>
  </object>
</interface>

Upvotes: 1

Views: 447

Answers (1)

blackedpi
blackedpi

Reputation: 21

I finally found the issue. Another example I found had the treeview as a child of a view port. Maybe from a previous version of GTK.

From Documentation Gnome Developer Documentation for GtkScrolledWindow

The scrolled window can work in two ways. Some widgets have native scrolling support; these widgets implement the GtkScrollable interface. Widgets with native scroll support include GtkTreeView, GtkTextView, and GtkLayout.

For widgets that lack native scrolling support, the GtkViewport widget acts as an adaptor class, implementing scrollability for child widgets that lack their own scrolling capabilities. Use GtkViewport to scroll child widgets such as GtkGrid, GtkBox, and so on.

Upvotes: 1

Related Questions