chiark / gitweb /
bump RTP packet size a bit
[disorder] / disobedience / choose.c
index 3c086a5d9000f77e57cf8c4ce8f6babbff97fd9f..cb68bb5b67cabaf63954a18fd1733bb0066c2525 100644 (file)
@@ -91,6 +91,8 @@ struct choosenode {
 
   when_filled_callback *whenfilled;     /**< @brief called when filled or 0 */
   void *wfu;                            /**< @brief passed to @c whenfilled */
+  int ymin;                             /**< @brief least Y value */
+  int ymax;                             /**< @brief greatest Y value */
 };
 
 /** @brief One item in the popup menu */
@@ -117,6 +119,7 @@ struct choose_menuitem {
 /* Variables */
 
 static GtkWidget *chooselayout;
+static GtkAdjustment *vadjust;
 static GtkWidget *searchentry;          /**< @brief search terms */
 static struct choosenode *root;
 static GtkWidget *track_menu;           /**< @brief track popup menu */
@@ -197,7 +200,7 @@ static struct choose_menuitem dir_menuitems[] = {
 
 /* Maintaining the data structure ------------------------------------------ */
 
-static char *flags(const struct choosenode *cn) {
+static char *cnflags(const struct choosenode *cn) {
   unsigned f = cn->flags, n;
   struct dynstr d[1];
   
@@ -356,7 +359,7 @@ static void got_files(void *v, int nvec, char **vec) {
   struct choosenode *cn = cbd->u.choosenode;
   int n;
 
-  D(("got_files %d files for %s %s", nvec, cn->path, flags(cn)));
+  D(("got_files %d files for %s %s", nvec, cn->path, cnflags(cn)));
   /* Complicated by the need to resolve aliases.  We can save a bit of effort
    * by re-using cbd though. */
   cn->flags &= ~CN_GETTING_FILES;
@@ -379,7 +382,7 @@ static void got_resolved_file(void *v, const char *track) {
   struct callbackdata *cbd = v;
   struct choosenode *cn = cbd->u.choosenode, *file_cn;
 
-  D(("resolved %s %s %d left", cn->path, flags(cn), cn->pending - 1));
+  D(("resolved %s %s %d left", cn->path, cnflags(cn), cn->pending - 1));
   /* TODO as below */
   file_cn = newnode(cn, track,
                     trackname_transform("track", track, "display"),
@@ -401,7 +404,7 @@ static void got_dirs(void *v, int nvec, char **vec) {
   struct choosenode *cn = cbd->u.choosenode;
   int n;
 
-  D(("got_dirs %d dirs for %s %s", nvec, cn->path, flags(cn)));
+  D(("got_dirs %d dirs for %s %s", nvec, cn->path, cnflags(cn)));
   /* TODO this depends on local configuration for trackname_transform().
    * This will work, since the defaults are now built-in, but it'll be
    * (potentially) different to the server's configured settings.
@@ -444,7 +447,7 @@ static void fill_directory_node(struct choosenode *cn) {
 
 /** @brief Expand a node */
 static void expand_node(struct choosenode *cn, int contingent) {
-  D(("expand_node %s %d %s", cn->path, contingent, flags(cn)));
+  D(("expand_node %s %d %s", cn->path, contingent, cnflags(cn)));
   assert(cn->flags & CN_EXPANDABLE);
   /* If node is already expanded do nothing. */
   if(cn->flags & CN_EXPANDED) return;
@@ -498,6 +501,10 @@ static void expand_from(struct choosenode *cn) {
     /* This is an actual search result */
     ++nsearchvisible;
     progress_window_progress(spw, nsearchvisible, nsearchresults);
+    if(nsearchvisible == nsearchresults)
+      /* This is the last track to become visible, we'll make sure it's in
+       * range so that at least one is. */
+      gtk_adjustment_clamp_page(vadjust, cn->ymax, cn->ymin);
   }
 }
 
@@ -794,6 +801,8 @@ static struct displaydata display_tree(struct choosenode *cn, int x, int y) {
   gtk_widget_size_request(cn->container, &req);
   d.width = x + req.width;
   d.height = y + req.height;
+  cn->ymin = y;
+  cn->ymax = d.height;
   if(cn->flags & CN_EXPANDED) {
     /* We'll offset children by the size of the arrow whatever it might be. */
     assert(cn->arrow);
@@ -1268,7 +1277,8 @@ GtkWidget *choose_widget(void) {
                     0, 1, n, n + 1);
   }
   /* The layout is scrollable */
-  scrolled = scroll_widget(GTK_WIDGET(chooselayout), "choose");
+  scrolled = scroll_widget(chooselayout, "choose");
+  vadjust = gtk_layout_get_vadjustment(GTK_LAYOUT(chooselayout));
 
   /* The scrollable layout and the search hbox go together in a vbox */
   NW(vbox);