[Aptitude-svn-commit] r3723 - in branches/aptitude-0.3/aptitude: . src/vscreen

Daniel Burrows dburrows at costa.debian.org
Sun Aug 7 03:20:20 UTC 2005


Author: dburrows
Date: Sun Aug  7 03:20:15 2005
New Revision: 3723

Added:
   branches/aptitude-0.3/aptitude/src/vscreen/ref_ptr.h
Modified:
   branches/aptitude-0.3/aptitude/ChangeLog
   branches/aptitude-0.3/aptitude/src/vscreen/testvscreen.cc
   branches/aptitude-0.3/aptitude/src/vscreen/vs_bin.cc
   branches/aptitude-0.3/aptitude/src/vscreen/vs_bin.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_button.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_center.cc
   branches/aptitude-0.3/aptitude/src/vscreen/vs_center.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_container.cc
   branches/aptitude-0.3/aptitude/src/vscreen/vs_container.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_editline.cc
   branches/aptitude-0.3/aptitude/src/vscreen/vs_editline.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_frame.cc
   branches/aptitude-0.3/aptitude/src/vscreen/vs_frame.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_label.cc
   branches/aptitude-0.3/aptitude/src/vscreen/vs_label.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_menu.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_menubar.cc
   branches/aptitude-0.3/aptitude/src/vscreen/vs_menubar.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_minibuf_win.cc
   branches/aptitude-0.3/aptitude/src/vscreen/vs_minibuf_win.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_multiplex.cc
   branches/aptitude-0.3/aptitude/src/vscreen/vs_multiplex.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_pager.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_passthrough.cc
   branches/aptitude-0.3/aptitude/src/vscreen/vs_passthrough.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_radiogroup.cc
   branches/aptitude-0.3/aptitude/src/vscreen/vs_radiogroup.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_scrollbar.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_size_box.cc
   branches/aptitude-0.3/aptitude/src/vscreen/vs_size_box.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_stacked.cc
   branches/aptitude-0.3/aptitude/src/vscreen/vs_stacked.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_statuschoice.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_table.cc
   branches/aptitude-0.3/aptitude/src/vscreen/vs_table.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_text_layout.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_togglebutton.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_transient.cc
   branches/aptitude-0.3/aptitude/src/vscreen/vs_transient.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_tree.h
   branches/aptitude-0.3/aptitude/src/vscreen/vs_util.cc
   branches/aptitude-0.3/aptitude/src/vscreen/vs_util.h
   branches/aptitude-0.3/aptitude/src/vscreen/vscreen.cc
   branches/aptitude-0.3/aptitude/src/vscreen/vscreen.h
   branches/aptitude-0.3/aptitude/src/vscreen/vscreen_widget.cc
   branches/aptitude-0.3/aptitude/src/vscreen/vscreen_widget.h
Log:
Break everything by switching to refcounting for vscreen.

Modified: branches/aptitude-0.3/aptitude/ChangeLog
==============================================================================
--- branches/aptitude-0.3/aptitude/ChangeLog	(original)
+++ branches/aptitude-0.3/aptitude/ChangeLog	Sun Aug  7 03:20:15 2005
@@ -1,5 +1,15 @@
 2005-08-06  Daniel Burrows  <dburrows at debian.org>
 
+	* src/vscreen/testvscreen.cc, src/vscreen/vs_bin.cc, src/vscreen/vs_bin.h, src/vscreen/vs_button.h, src/vscreen/vs_center.cc, src/vscreen/vs_center.h, src/vscreen/vs_container.cc, src/vscreen/vs_container.h, src/vscreen/vscreen.cc, src/vscreen/vscreen.h, src/vscreen/vscreen_widget.cc, src/vscreen/vscreen_widget.h, src/vscreen/vs_editline.cc, src/vscreen/vs_editline.h, src/vscreen/vs_frame.cc, src/vscreen/vs_frame.h, src/vscreen/vs_label.cc, src/vscreen/vs_label.h, src/vscreen/vs_menubar.cc, src/vscreen/vs_menubar.h, src/vscreen/vs_menu.h, src/vscreen/vs_minibuf_win.cc, src/vscreen/vs_minibuf_win.h, src/vscreen/vs_multiplex.cc, src/vscreen/vs_multiplex.h, src/vscreen/vs_pager.h, src/vscreen/vs_passthrough.cc, src/vscreen/vs_passthrough.h, src/vscreen/vs_radiogroup.cc, src/vscreen/vs_radiogroup.h, src/vscreen/vs_scrollbar.h, src/vscreen/vs_size_box.cc, src/vscreen/vs_size_box.h, src/vscreen/vs_stacked.cc, src/vscreen/vs_stacked.h, src/vscreen/vs_statuschoice.h, src/vscreen/vs_table.cc, src/vscreen/vs_table.h, src/vscreen/vs_text_layout.h, src/vscreen/vs_togglebutton.h, src/vscreen/vs_transient.cc, src/vscreen/vs_transient.h, src/vscreen/vs_tree.h, src/vscreen/vs_util.cc, src/vscreen/vs_util.h, src/vscreen/ref_ptr.h:
+
+	  Convert the vscreen code over to using reference-counted
+	  pointers for inter-object references.  This is a sensible thing
+	  to do since widgets form a tree -- normally you'll just see a
+	  widget's owner holding onto references to it (but in special
+	  cases some other references could exist).
+
+	  This change breaks everything.  Whee!
+
 	* src/vscreen/vscreen_widget.cc:
 
 	  Fix a gaping bug and memory leak that only just came to my

Added: branches/aptitude-0.3/aptitude/src/vscreen/ref_ptr.h
==============================================================================
--- (empty file)
+++ branches/aptitude-0.3/aptitude/src/vscreen/ref_ptr.h	Sun Aug  7 03:20:15 2005
@@ -0,0 +1,145 @@
+// ref_ptr.h                                       -*-c++-*-
+//
+// A reference-counting pointer.  The object behind the pointer should
+// implement incref() and decref(); the pointer arranges for these
+// methods to be called at the appropriate times.
+
+#ifndef REF_PTR_H
+#define REF_PTR_H
+
+template<class T>
+class ref_ptr
+{
+  T *ref;
+
+public:
+  ref_ptr(T *_ref)
+    :ref(_ref)
+  {
+    if(ref != 0)
+      ref->incref();
+  }
+
+  ref_ptr(const ref_ptr &other)
+    :ref(other.ref)
+  {
+    if(ref != 0)
+      ref->incref();
+  }
+
+  template<class S>
+  ref_ptr(const ref_ptr<S> &other)
+    :ref(other.unsafe_get_ref())
+  {
+    if(ref != 0)
+      ref->incref();
+  }
+
+  ref_ptr()
+    :ref(0)
+  {
+  }
+
+  ~ref_ptr()
+  {
+    if(ref != 0)
+      ref->decref();
+  }
+
+  ref_ptr &operator=(const ref_ptr &other)
+  {
+    if(other.ref != 0)
+      other.ref->incref();
+
+    if(ref != 0)
+      ref->decref();
+
+    ref = other.ref;
+
+    return *this;
+  }
+
+  // If S is assignment-compatible with T and both have
+  // reference-counting methods, perform this assignment.
+  //
+  // Read: upcasting pointers.
+  template<class S>
+  ref_ptr<T> &operator=(const ref_ptr<S> &other)
+  {
+    S * const other_ref = other.unsafe_get_ref();
+
+    if(other_ref != 0)
+      other_ref->incref();
+
+    if(ref != 0)
+      ref->decref();
+
+    ref = other_ref;
+
+    return *this;
+  }
+
+  template<class S>
+  bool operator==(const ref_ptr<S> &other) const
+  {
+    return ref == other.unsafe_get_ref();
+  }
+
+  template<class S>
+  bool operator!=(const ref_ptr<S> &other) const
+  {
+    return ref != other.unsafe_get_ref();
+  }
+
+  template<class S>
+  bool operator<(const ref_ptr<S> &other) const
+  {
+    return ref < other.unsafe_get_ref();
+  }
+
+  template<class S>
+  bool operator>(const ref_ptr<S> &other) const
+  {
+    return ref > other.unsafe_get_ref();
+  }
+
+  template<class S>
+  bool operator<=(const ref_ptr<S> &other) const
+  {
+    return ref <= other.unsafe_get_ref();
+  }
+
+  template<class S>
+  bool operator>=(const ref_ptr<S> &other) const
+  {
+    return ref >= other.unsafe_get_ref();
+  }
+
+  // Safe downcasting.
+  template<class S>
+  ref_ptr<S> dyn_downcast() const
+  {
+    return ref_ptr<S>(dynamic_cast<S>(ref));
+  }
+
+  bool valid() const
+  {
+    return ref != 0;
+  }
+
+  T *operator->() const
+  {
+    return ref;
+  }
+
+  /** Extract the pointer.  Should generally be used with care (but is
+   *  used in the implementation to cast/compare between differently
+   *  templated instances).
+   */
+  T *unsafe_get_ref() const
+  {
+    return ref;
+  }
+};
+
+#endif

Modified: branches/aptitude-0.3/aptitude/src/vscreen/testvscreen.cc
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/testvscreen.cc	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/testvscreen.cc	Sun Aug  7 03:20:15 2005
@@ -40,7 +40,7 @@
 using namespace std;
 
 // Er..having this be global is not so great?
-vs_stacked *stacker=new vs_stacked(0,0);
+vs_stacked_ref stacker=vs_stacked::create(0,0);
 
 class test_keyname:public vs_label
 {
@@ -117,14 +117,14 @@
   const wchar_t *label() {return txt.c_str();}
 };
 
-void do_toggle_hierarchical(vs_tree *tree)
+void do_toggle_hierarchical(const vs_tree_ref &tree)
 {
   tree->set_hierarchical(!tree->get_hierarchical());
 }
 
-vscreen_widget *make_test_treewidget()
+vs_widget_ref make_test_treewidget()
 {
-  vs_tree *tree=new vs_tree();
+  vs_tree_ref tree=vs_tree::create();
 
   silly_subtree *root=new silly_subtree(true, "The Root Of It All");
   silly_subtree *tree1=new silly_subtree(false, "Money");
@@ -227,7 +227,7 @@
   VS_MENU_END
 };
 
-void radio_button_selected(int id, vs_label *l)
+void radio_button_selected(int id, const vs_label_ref &l)
 {
   char buf[128];
 
@@ -235,10 +235,10 @@
   l->set_text(buf);
 }
 
-vscreen_widget *button_mania()
+vs_widget_ref button_mania()
 {
-  vs_table *rval=new vs_table;
-  vs_label *label=new vs_label("ERROR");
+  vs_table_ref rval=vs_table::create();
+  vs_label_ref label=vs_label::create("ERROR");
 
   rval->add_widget(label, 5, 0, 1, 4, false);
 
@@ -260,11 +260,11 @@
 	    f=fragf("Line 1%n%F%nLine 3", f);
 
 	  if(i!=3)
-	    rval->add_widget_opts(new vs_button(f), i, j, 1, 1,
+	    rval->add_widget_opts(vs_button::create(f), i, j, 1, 1,
 				  vs_table::ALIGN_CENTER, vs_table::ALIGN_CENTER);
 	  else
 	    {
-	      vs_togglebutton *b=new vs_radiobutton(f);
+	      vs_togglebutton_ref b=vs_radiobutton::create(f);
 	      rval->add_widget_opts(b, i, j, 1, 1,
 				    vs_table::ALIGN_CENTER | vs_table::EXPAND, vs_table::ALIGN_CENTER);
 	      g->add_button(b, i*4+j);
@@ -272,43 +272,43 @@
 	}
     }
 
-  rval->add_widget_opts(new vs_checkbutton("Button 16"), 4, 0, 1, 2,
+  rval->add_widget_opts(vs_checkbutton::create("Button 16"), 4, 0, 1, 2,
 			vs_table::ALIGN_CENTER,
 			vs_table::ALIGN_CENTER | vs_table::EXPAND);
-  rval->add_widget_opts(new vs_button("Button 17"), 4, 2, 1, 2,
+  rval->add_widget_opts(vs_button::create("Button 17"), 4, 2, 1, 2,
 			vs_table::ALIGN_CENTER,
 			vs_table::ALIGN_CENTER | vs_table::EXPAND);
 
   return rval;
 }
 
-static void do_load_file(wstring s, vs_editline *p)
+static void do_load_file(wstring s, const vs_editline_ref &p)
 {
   p->set_text(L"");
 }
 
-vscreen_widget *pager_test()
+vs_widget_ref pager_test()
 {
-  vs_table *tbl=new vs_table;
-  vs_editline *ln=new vs_editline("Enter a filename to load: ");
+  vs_table_ref tbl=vs_table::create();
+  vs_editline_ref ln=vs_editline::create("Enter a filename to load: ");
   const char *s="This space for rent.\n\nApply above.";
-  vs_file_pager *pager=new vs_file_pager(s, strlen(s));
-  vs_scrollbar *scrl=new vs_scrollbar(vs_scrollbar::VERTICAL, 0, 0);
+  vs_file_pager_ref pager=vs_file_pager::create(s, strlen(s));
+  vs_scrollbar_ref scrl=vs_scrollbar::create(vs_scrollbar::VERTICAL, 0, 0);
 
   tbl->add_widget_opts(ln, 0, 0, 1, 2, vs_table::EXPAND | vs_table::FILL | vs_table::SHRINK, vs_table::SHRINK);
   tbl->add_widget_opts(pager, 1, 0, 1, 1, vs_table::SHRINK, vs_table::EXPAND | vs_table::FILL);
   tbl->add_widget_opts(scrl, 1, 1, 1, 1, vs_table::ALIGN_LEFT, vs_table::EXPAND | vs_table::FILL);
 
   ln->entered.connect(sigc::bind(sigc::ptr_fun(&do_load_file), ln));
-  ln->entered.connect(sigc::mem_fun(*pager, (void (vs_file_pager::*)(const std::wstring &)) &vs_file_pager::load_file));
-  pager->line_changed.connect(sigc::mem_fun(*scrl, &vs_scrollbar::set_slider));
+  ln->entered.connect(sigc::mem_fun(*pager.unsafe_get_ref(), (void (vs_file_pager::*)(const std::wstring &)) &vs_file_pager::load_file));
+  pager->line_changed.connect(sigc::mem_fun(*scrl.unsafe_get_ref(), &vs_scrollbar::set_slider));
   pager->do_line_signal();
-  scrl->scrollbar_interaction.connect(sigc::mem_fun(*pager, &vs_pager::scroll_page));
+  scrl->scrollbar_interaction.connect(sigc::mem_fun(*pager.unsafe_get_ref(), &vs_pager::scroll_page));
 
   return tbl;
 }
 
-void update_menu_status(vs_menu_item *item, vs_label *label)
+void update_menu_status(const vs_menu_item *item, const vs_label_ref &label)
 {
   if(item)
     {
@@ -320,7 +320,7 @@
     label->hide();
 }
 
-void do_editline_history(std::wstring s, vs_editline *l)
+void do_editline_history(std::wstring s, const vs_editline_ref &l)
 {
   l->add_to_history(s);
   l->reset_history();
@@ -378,15 +378,15 @@
 }
 
 // This isn't a very comprehensive test yet.
-vscreen_widget *make_layout_test(fragment *f)
+vs_widget_ref make_layout_test(fragment *f)
 {
-  vs_table *t=new vs_table;
+  vs_table_ref t=vs_table::create();
 
 
-  vs_text_layout *l=new vs_text_layout(f);
-  vs_scrollbar *s=new vs_scrollbar(vs_scrollbar::VERTICAL);
-  l->location_changed.connect(sigc::mem_fun(*s, &vs_scrollbar::set_slider));
-  s->scrollbar_interaction.connect(sigc::mem_fun(*l, &vs_text_layout::scroll));
+  vs_text_layout_ref l=vs_text_layout::create(f);
+  vs_scrollbar_ref s=vs_scrollbar::create(vs_scrollbar::VERTICAL);
+  l->location_changed.connect(sigc::mem_fun(*s.unsafe_get_ref(), &vs_scrollbar::set_slider));
+  s->scrollbar_interaction.connect(sigc::mem_fun(*l.unsafe_get_ref(), &vs_text_layout::scroll));
 
   t->add_widget_opts(l, 0, 0, 1, 1, vs_table::EXPAND | vs_table::SHRINK, vs_table::EXPAND);
   t->add_widget_opts(s, 0, 1, 1, 1, 0, vs_table::EXPAND | vs_table::FILL);
@@ -405,73 +405,73 @@
   global_bindings.set("ToggleCellVisible", key(KEY_F(5), true));
   global_bindings.set("ToggleHier", key(L'h', false));
 
-  vs_menubar *menubar=new vs_menubar();
+  vs_menubar_ref menubar=vs_menubar::create();
 
   menubar->connect_key_post("Quit", &global_bindings, sigc::ptr_fun(&vscreen_exitmain));
 
-  vs_label *menu_display=new vs_label("", get_style("Status"));
+  vs_label_ref menu_display=vs_label::create("", get_style("Status"));
 
-  vs_menu *menu=new vs_menu(0, 0, 0, test_file_menu);
+  vs_menu_ref menu(vs_menu::create(0, 0, 0, test_file_menu));
   menubar->append_item(L"File", menu);
   menu->item_highlighted.connect(sigc::bind(sigc::ptr_fun(&update_menu_status),
 					    menu_display));
 
-  menu=new vs_menu(0, 0, 0, test_test_menu);
+  menu=vs_menu::create(0, 0, 0, test_test_menu);
   menubar->append_item(L"Test", menu);
   menu->item_highlighted.connect(sigc::bind(sigc::ptr_fun(&update_menu_status),
 					    menu_display));
 
-  menu=new vs_menu(0, 0, 0, test_help_menu);
+  menu=vs_menu::create(0, 0, 0, test_help_menu);
   menubar->append_item(L"Help", menu);
   menu->item_highlighted.connect(sigc::bind(sigc::ptr_fun(&update_menu_status),
 					    menu_display));
 
-  vs_minibuf_win *toplevel=new vs_minibuf_win();
+  vs_minibuf_win_ref toplevel=vs_minibuf_win::create();
 
   toplevel->add_widget(menu_display);
 
   menubar->set_subwidget(toplevel);
 
-  vs_multiplex *switcher=new vs_multiplex(true);
+  vs_multiplex_ref switcher=vs_multiplex::create(true);
   switcher->connect_key("CycleScreen",
 			&global_bindings,
-			sigc::mem_fun(*switcher, &vs_multiplex::cycle_forward));
+			sigc::mem_fun(*switcher.unsafe_get_ref(), &vs_multiplex::cycle_forward));
   switcher->connect_key("CycleScreenBack",
 			&global_bindings,
-			sigc::mem_fun(*switcher, &vs_multiplex::cycle_backward));
+			sigc::mem_fun(*switcher.unsafe_get_ref(), &vs_multiplex::cycle_backward));
 
   switcher->add_visible_widget(pager_test(), true);
   switcher->add_visible_widget(button_mania(), true);
 
-  switcher->add_visible_widget(new vs_center(new vs_size_box(size(20, 8), new vs_frame(new vs_center(new vs_label(flowbox(fragf("This is another screen.%nNotice that this label is properly word-wrapped."))))))), true);
-  switcher->add_visible_widget(new vs_label("This is one screen."), true);
+  switcher->add_visible_widget(vs_center::create(vs_size_box::create(size(20, 8), vs_frame::create(vs_center::create(vs_label::create(flowbox(fragf("This is another screen.%nNotice that this label is properly word-wrapped."))))))), true);
+  switcher->add_visible_widget(vs_label::create("This is one screen."), true);
   switcher->add_visible_widget(vs_dialog_ok(transcode("Press any key to hide this widget")), true);
   switcher->add_visible_widget(make_test_treewidget(), true);
 
-  vs_table *ttable=new vs_table;
-  ttable->add_widget(new vs_frame(new vs_label("Press a key:")));
-  ttable->add_widget(new vs_frame(new test_keyname));
+  vs_table_ref ttable=vs_table::create();
+  ttable->add_widget(vs_frame::create(vs_label::create("Press a key:")));
+  ttable->add_widget(vs_frame::create(new test_keyname));
   ttable->show_all();
   switcher->add_widget(ttable);
 
-  vs_table *table=new vs_table;
+  vs_table_ref table=vs_table::create();
   table->set_colsep(3);
-  vscreen_widget *w=new vs_frame(new vs_center(new vs_label("Pane 1")));
+  vs_widget_ref w=vs_frame::create(vs_center::create(vs_label::create("Pane 1")));
   table->add_widget(w, 0, 0, 2, 1, false);
-  w=new vs_frame(new vs_center(new vs_label("Pane 2")));
+  w=vs_frame::create(vs_center::create(vs_label::create("Pane 2")));
   table->add_widget_opts(w, 0, 1, 1, 1, vs_table::EXPAND | vs_table::FILL, 0);
 
   vs_editline::history_list h;
-  vs_editline *l=new vs_editline(20, "Input: ", "Pane 3", &h);
+  vs_editline_ref l=vs_editline::create(20, "Input: ", "Pane 3", &h);
   l->entered.connect(sigc::bind(sigc::ptr_fun(&do_editline_history),
 				l));
 
-  w=new vs_frame(new vs_center(l));
+  w=vs_frame::create(vs_center::create(l));
   table->add_widget(w, 1, 1);
-  w=new vs_frame(new vs_center(new vs_label("Pane 4 - a pane with a very long label in it\nwhich should crowd out the other table cells")));
+  w=vs_frame::create(vs_center::create(vs_label::create("Pane 4 - a pane with a very long label in it\nwhich should crowd out the other table cells")));
   table->connect_key("ToggleCellVisible",
 		     &global_bindings,
-		     sigc::mem_fun(*w, &vscreen_widget::toggle_visible));
+		     sigc::mem_fun(*w.unsafe_get_ref(), &vscreen_widget::toggle_visible));
   table->add_widget(w, 0, 2, 2);
   table->show_all();
   switcher->add_widget(table);

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_bin.cc
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_bin.cc	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_bin.cc	Sun Aug  7 03:20:15 2005
@@ -14,21 +14,21 @@
 
 vs_bin::~vs_bin()
 {
-  if(subwidget)
+  if(subwidget.valid())
     set_subwidget(NULL);
 }
 
-vscreen_widget *vs_bin::get_focus()
+vs_widget_ref vs_bin::get_focus()
 {
-  if(subwidget && subwidget->get_visible())
+  if(subwidget.valid() && subwidget->get_visible())
     return subwidget;
   else
     return NULL;
 }
 
-void vs_bin::set_subwidget(vscreen_widget *w)
+void vs_bin::set_subwidget(const vs_widget_ref &w)
 {
-  if(subwidget)
+  if(subwidget.valid())
     {
       subwidget->set_owner(NULL);
       subwidget->unfocussed();
@@ -37,12 +37,12 @@
       hide_conn.disconnect();
     }
 
-  subwidget=w;
+  subwidget = w;
 
-  if(w)
+  if(w.valid())
     {
-      show_conn=w->shown_sig.connect(sigc::bind(sigc::mem_fun(*this, &vs_bin::show_widget), w));
-      hide_conn=w->hidden_sig.connect(sigc::bind(sigc::mem_fun(*this, &vs_bin::hide_widget), w));
+      show_conn = w->shown_sig.connect(sigc::bind(sigc::mem_fun(*this, &vs_bin::show_widget), w));
+      hide_conn = w->hidden_sig.connect(sigc::bind(sigc::mem_fun(*this, &vs_bin::hide_widget), w));
       w->set_owner(this);
       if(get_isfocussed())
 	w->focussed();
@@ -51,10 +51,11 @@
   vscreen_queuelayout();
 }
 
-void vs_bin::add_widget(vscreen_widget *w)
+void vs_bin::add_widget(const vs_widget_ref &w)
 {
-  assert(subwidget==NULL);
-  assert(w!=NULL);
+  assert(!subwidget.valid());
+  assert(w.valid());
+
   set_subwidget(w);
 
   // I assume that we're hidden right now.
@@ -65,9 +66,9 @@
     w->focussed();
 }
 
-void vs_bin::rem_widget(vscreen_widget *w)
+void vs_bin::rem_widget(const vs_widget_ref &w)
 {
-  assert(w==subwidget);
+  assert(w == subwidget);
   set_subwidget(NULL);
 
   if(get_visible())
@@ -79,20 +80,20 @@
 
 void vs_bin::show_all()
 {
-  if(subwidget)
+  if(subwidget.valid())
     subwidget->show_all();
 
   show();
 }
 
-void vs_bin::show_widget(vscreen_widget *w)
+void vs_bin::show_widget(const vs_widget_ref &w)
 {
   assert(w==subwidget);
 
   show();
 }
 
-void vs_bin::hide_widget(vscreen_widget *w)
+void vs_bin::hide_widget(const vs_widget_ref &w)
 {
   assert(w==subwidget);
   hide();
@@ -100,6 +101,6 @@
 
 void vs_bin::paint(const style &st)
 {
-  if(get_subwidget() && get_subwidget()->get_visible())
-    get_subwidget()->display(st);
+  if(subwidget.valid() && subwidget->get_visible())
+    subwidget->display(st);
 }

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_bin.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_bin.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_bin.h	Sun Aug  7 03:20:15 2005
@@ -11,7 +11,7 @@
 
 class vs_bin:public vs_passthrough
 {
-  vscreen_widget *subwidget;
+  vs_widget_ref subwidget;
 
   // These are unfortunate necessities; when a widget is /removed/
   // (but not destroyed), it is necessary to delete the connections to
@@ -19,21 +19,24 @@
   sigc::connection show_conn, hide_conn;
 
   // right now these just show or hide the bin itself
-  void show_widget(vscreen_widget *w);
-  void hide_widget(vscreen_widget *w);
-public:
+  void show_widget(const vs_widget_ref &w);
+  void hide_widget(const vs_widget_ref &w);
+
+protected:
   vs_bin();
+
+public:
   virtual ~vs_bin();
 
-  void set_subwidget(vscreen_widget *w);
-  vscreen_widget *get_subwidget() {return subwidget;}
+  void set_subwidget(const ref_ptr<vscreen_widget> &w);
+  vs_widget_ref get_subwidget() {return subwidget;}
 
   virtual void show_all();
 
-  virtual void add_widget(vscreen_widget *w);
-  virtual void rem_widget(vscreen_widget *w);
+  virtual void add_widget(const vs_widget_ref &w);
+  virtual void rem_widget(const vs_widget_ref &w);
 
-  vscreen_widget *get_focus();
+  vs_widget_ref get_focus();
 
   void paint(const style &st);
 };

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_button.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_button.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_button.h	Sun Aug  7 03:20:15 2005
@@ -26,28 +26,44 @@
 protected:
   bool handle_key(const key &k);
   fragment_cache *get_label() const {return label;}
-public:
+
   /** Instantiate a vs_button.
    *
-   *  \param _label the new label of this button; the button is
-   *  responsible for deleting it.
+   *  \param _label the new label of this button; it will be placed
+   *  inside a simple text_fragment.
    */
+  vs_button(const std::wstring &_label);
   vs_button(fragment *_label);
+  vs_button(const std::string &_label);
+public:
+
+  ~vs_button();
+
+  static ref_ptr<vs_button>
+  create(const std::wstring &label)
+  {
+    return new vs_button(label);
+  }
 
   /** Instantiate a vs_button.
    *
-   *  \param _label the new label of this button; it will be placed
-   *  inside a simple text_fragment.
+   *  \param _label the new label of this button; the button is
+   *  responsible for deleting it.
    */
-  vs_button(const std::string &_label);
+  static ref_ptr<vs_button> create(fragment *label)
+  {
+    return new vs_button(label);
+  }
 
   /** Instantiate a vs_button.
    *
    *  \param _label the new label of this button; it will be placed
    *  inside a simple text_fragment.
    */
-  vs_button(const std::wstring &_label);
-  ~vs_button();
+  static ref_ptr<vs_button> create(const std::string &label)
+  {
+    return new vs_button(label);
+  }
 
   void paint(const style &st);
 
@@ -67,4 +83,6 @@
   sigc::signal0<void> pressed;
 };
 
+typedef ref_ptr<vs_button> vs_button_ref;
+
 #endif

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_center.cc
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_center.cc	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_center.cc	Sun Aug  7 03:20:15 2005
@@ -4,7 +4,7 @@
 
 #include <sigc++/functors/mem_fun.h>
 
-vs_center::vs_center(vscreen_widget *w)
+vs_center::vs_center(const vs_widget_ref &w)
 {
   set_subwidget(w);
   set_opaque(false);
@@ -14,25 +14,29 @@
 
 int vs_center::width_request()
 {
-  if(get_subwidget() && get_subwidget()->get_visible())
-    return get_subwidget()->width_request();
+  vs_widget_ref subwidget = get_subwidget();
+
+  if(subwidget.valid() && subwidget->get_visible())
+    return subwidget->width_request();
   else
     return 0;
 }
 
 int vs_center::height_request(int width)
 {
-  if(get_subwidget() && get_subwidget()->get_visible())
-    return get_subwidget()->height_request(width);
+  vs_widget_ref subwidget = get_subwidget();
+
+  if(subwidget.valid() && subwidget->get_visible())
+    return subwidget->height_request(width);
   else
     return 0;
 }
 
 void vs_center::layout_me()
 {
-  vscreen_widget *child=get_subwidget();
+  vs_widget_ref child=get_subwidget();
 
-  if(child)
+  if(child.valid())
     {
       if(child->get_visible())
 	{

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_center.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_center.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_center.h	Sun Aug  7 03:20:15 2005
@@ -10,11 +10,20 @@
 class vs_center:public vs_bin
 {
   void layout_me();
+
+protected:
+  vs_center(const vs_widget_ref &w = NULL);
+
 public:
-  vs_center(vscreen_widget *w=NULL);
+  static ref_ptr<vs_center> create(const vs_widget_ref &w = NULL)
+  {
+    return new vs_center(w);
+  }
 
   int width_request();
   int height_request(int width);
 };
 
+typedef ref_ptr<vs_center> vs_center_ref;
+
 #endif

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_container.cc
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_container.cc	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_container.cc	Sun Aug  7 03:20:15 2005
@@ -5,7 +5,8 @@
 {
 }
 
-void vs_container::add_visible_widget(vscreen_widget *w, bool visible)
+void vs_container::add_visible_widget(const vs_widget_ref &w,
+				      bool visible)
 {
   add_widget(w);
 

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_container.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_container.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_container.h	Sun Aug  7 03:20:15 2005
@@ -15,11 +15,11 @@
   vs_container():vscreen_widget() {}
   ~vs_container();
 
-  virtual void add_widget(vscreen_widget *)=0;
+  virtual void add_widget(const vs_widget_ref &)=0;
   // To make it easier to add anonymous widgets:
   // (NOTE: C++ is evil!!  I should be able to call this "add_widget"..grrr..)
-  void add_visible_widget(vscreen_widget *w, bool visible);
-  virtual void rem_widget(vscreen_widget *)=0;
+  void add_visible_widget(const vs_widget_ref &, bool visible);
+  virtual void rem_widget(const vs_widget_ref &)=0;
 
   // Abstract so I don't forget to implement it in a subclass..
   virtual void show_all()=0;

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_editline.cc
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_editline.cc	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_editline.cc	Sun Aug  7 03:20:15 2005
@@ -15,7 +15,7 @@
 
 keybindings *vs_editline::bindings=NULL;
 
-vs_editline::vs_editline(string _prompt, string _text,
+vs_editline::vs_editline(const string &_prompt, const string &_text,
 			 history_list *_history)
   :vscreen_widget(), curloc(_text.size()),
    startloc(0), desired_size(-1), history(_history),
@@ -32,7 +32,7 @@
   do_layout.connect(sigc::mem_fun(*this, &vs_editline::normalize_cursor));
 }
 
-vs_editline::vs_editline(wstring _prompt, wstring _text,
+vs_editline::vs_editline(const wstring &_prompt, const wstring &_text,
 			 history_list *_history)
   :vscreen_widget(), prompt(_prompt), text(_text), curloc(_text.size()),
    startloc(0), desired_size(-1), history(_history),

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_editline.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_editline.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_editline.h	Sun Aug  7 03:20:15 2005
@@ -45,20 +45,51 @@
   wchar_t get_char(size_t n);
 protected:
   bool handle_key(const key &k);
-public:
-  vs_editline(std::wstring _prompt, std::wstring _text=L"",
+
+  vs_editline(const std::wstring &_prompt,
+	      const std::wstring &_text=L"",
 	      history_list *history=NULL);
 
   /** Transcodes its input strings from the system charset. */
-  vs_editline(std::string _prompt, std::string _text="",
+  vs_editline(const std::string &_prompt,
+	      const std::string &_text="",
 	      history_list *history=NULL);
 
   vs_editline(int maxlength, const std::wstring &_prompt,
-	      const std::wstring &_text=L"", history_list *history=NULL);
+	      const std::wstring &_text, history_list *history);
 
   /** Transcodes its input strings from the system charset. */
   vs_editline(int maxlength, const std::string &_prompt,
-	      const std::string &_text="", history_list *history=NULL);
+	      const std::string &_text, history_list *history);
+
+public:
+  static ref_ptr<vs_editline>
+  create(const std::wstring &prompt, std::wstring &text = L"",
+	 history_list *history = NULL)
+  {
+    return new vs_editline(prompt, text, history);
+  }
+
+  static ref_ptr<vs_editline>
+  create(const std::string &prompt, const std::string &text = "",
+	 history_list *history = NULL)
+  {
+    return new vs_editline(prompt, text, history);
+  }
+
+  static ref_ptr<vs_editline>
+  create(int maxlength, const std::wstring &prompt,
+	 const std::wstring &text = L"", history_list *history = NULL)
+  {
+    return new vs_editline(maxlength, prompt, text, history);
+  }
+
+  static ref_ptr<vs_editline>
+  create(int maxlength, const std::string &prompt,
+	 const std::string &text = "", history_list *history = NULL)
+  {
+    return new vs_editline(maxlength, prompt, text, history);
+  }
 
   bool focus_me();
   void paint(const style &st);
@@ -94,4 +125,6 @@
   static void init_bindings();
 };
 
+typedef ref_ptr<vs_editline> vs_editline_ref;
+
 #endif

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_frame.cc
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_frame.cc	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_frame.cc	Sun Aug  7 03:20:15 2005
@@ -6,7 +6,7 @@
 
 #include <sigc++/functors/mem_fun.h>
 
-vs_frame::vs_frame(vscreen_widget *w)
+vs_frame::vs_frame(const vs_widget_ref &w)
   :vs_bin()
 {
   set_subwidget(w);
@@ -16,8 +16,10 @@
 
 int vs_frame::width_request()
 {
-  if(get_subwidget() && get_subwidget()->get_visible())
-    return get_subwidget()->width_request()+2;
+  vs_widget_ref subwidget = get_subwidget();
+
+  if(subwidget.valid() && subwidget->get_visible())
+    return subwidget->width_request()+2;
   else
     return 2;
 }
@@ -26,7 +28,7 @@
 {
   if(width<2)
     return 0;
-  else if(get_subwidget() && get_subwidget()->get_visible())
+  else if(get_subwidget().valid() && get_subwidget()->get_visible())
     return get_subwidget()->height_request(width-2)+2;
   else
     return 2;
@@ -34,12 +36,14 @@
 
 void vs_frame::layout_me()
 {
-  if(get_subwidget())
+  vs_widget_ref subwidget = get_subwidget();
+
+  if(subwidget.valid())
     {
-      if(get_subwidget()->get_visible())
-	get_subwidget()->alloc_size(1, 1, getmaxx()-2, getmaxy()-2);
+      if(subwidget->get_visible())
+	subwidget->alloc_size(1, 1, getmaxx()-2, getmaxy()-2);
       else
-	get_subwidget()->alloc_size(0, 0, 0, 0);
+	subwidget->alloc_size(0, 0, 0, 0);
     }
 }
 
@@ -47,6 +51,8 @@
 {
   border(0,0,0,0,0,0,0,0);
 
-  if(get_subwidget() && get_subwidget()->get_visible())
-    get_subwidget()->display(st);
+  vs_widget_ref subwidget = get_subwidget();
+
+  if(subwidget.valid() && subwidget->get_visible())
+    subwidget->display(st);
 }

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_frame.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_frame.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_frame.h	Sun Aug  7 03:20:15 2005
@@ -11,8 +11,15 @@
 class vs_frame:public vs_bin
 {
   void layout_me();
+
+protected:
+  vs_frame(const vs_widget_ref &w);
+
 public:
-  vs_frame(vscreen_widget *w=NULL);
+  static ref_ptr<vs_frame> create(const vs_widget_ref &w)
+  {
+    return new vs_frame(w);
+  }
 
   /** \return the desired width of the frame.  A frame is 2 larger
    *   than its contents in every direction.
@@ -30,4 +37,6 @@
   virtual void paint(const style &st);
 };
 
+typedef ref_ptr<vs_frame> vs_frame_ref;
+
 #endif

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_label.cc
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_label.cc	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_label.cc	Sun Aug  7 03:20:15 2005
@@ -12,14 +12,13 @@
 using namespace std;
 
 vs_label::vs_label(fragment *f)
+  :txt(new fragment_cache(f))
 {
-  txt=new fragment_cache(f);
 }
 
 vs_label::vs_label(const string &_txt, const style &st)
-  :txt(new fragment_cache(text_fragment(_txt)))
+  :txt(new fragment_cache(style_fragment(text_fragment(_txt), st)))
 {
-  set_bg_style(st);
 }
 
 vs_label::vs_label(const string &_txt)
@@ -28,9 +27,8 @@
 }
 
 vs_label::vs_label(const wstring &_txt, const style &st)
-  :txt(new fragment_cache(text_fragment(_txt)))
+  :txt(new fragment_cache(style_fragment(text_fragment(_txt), st)))
 {
-  set_bg_style(st);
 }
 
 vs_label::vs_label(const wstring &_txt)
@@ -38,6 +36,26 @@
 {
 }
 
+vs_label_ref vs_label::create(const string &txt, const style &st)
+{
+  return new vs_label(txt, st);
+}
+
+vs_label_ref vs_label::create(const string &txt)
+{
+  return new vs_label(txt);
+}
+
+vs_label_ref vs_label::create(const wstring &txt, const style &st)
+{
+  return new vs_label(txt, st);
+}
+
+vs_label_ref vs_label::create(const wstring &txt)
+{
+  return new vs_label(txt);
+}
+
 vs_label::~vs_label()
 {
   delete txt;

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_label.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_label.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_label.h	Sun Aug  7 03:20:15 2005
@@ -11,13 +11,27 @@
 class vs_label:public vscreen_widget
 {
   fragment_cache *txt;
-public:
+protected:
   vs_label(fragment *f);
   vs_label(const std::string &_txt, const style &st);
   vs_label(const std::string &_txt);
-
   vs_label(const std::wstring &_txt, const style &st);
-  vs_label(const std::wstring &_txt); 
+  vs_label(const std::wstring &_txt);
+
+public:
+  static ref_ptr<vs_label> create(fragment *f)
+  {
+    return new vs_label(f);
+  }
+
+  static ref_ptr<vs_label> create(const std::string &txt, const style &st);
+  static ref_ptr<vs_label> create(const std::string &txt);
+
+  static ref_ptr<vs_label> create(const std::wstring &txt, const style &st);
+
+  static ref_ptr<vs_label> create(const std::wstring &txt); 
+
+
  ~vs_label();
 
   bool get_cursorvisible();
@@ -43,13 +57,24 @@
 {
 protected:
   virtual bool handle_char(chtype ch);
-public:
-  vs_transientlabel(std::string msg, const style &st)
+
+  vs_transientlabel(const std::string &msg, const style &st)
     :vs_label(msg, st)
   {
   }
+public:
+  static
+  ref_ptr<vs_transientlabel> create(const std::string &msg,
+				    const style &st)
+  {
+    return new vs_transientlabel(msg, st);
+  }
 
   bool focus_me() {return true;}
 };
 
+typedef ref_ptr<vs_label> vs_label_ref;
+
+typedef ref_ptr<vs_transientlabel> vs_transientlabel_ref;
+
 #endif

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_menu.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_menu.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_menu.h	Sun Aug  7 03:20:15 2005
@@ -153,16 +153,26 @@
 
 protected:
   virtual bool handle_key(const key &k);
-public:
-  // Initialize a blank menu.
-  vs_menu();
 
-  // Deletes the items it holds!
-  ~vs_menu();
+  /** Create a blank menu. */
+  vs_menu();
 
   // Initialize a menu from a block of information.  If there is no
   // VS_MENU_END in the block, RANDOM ERRORS WILL OCCUR!!
   vs_menu(int x, int y, int w, vs_menu_info *inf);
+public:
+  static ref_ptr<vs_menu> create()
+  {
+    return new vs_menu;
+  }
+
+  static ref_ptr<vs_menu> create(int x, int y, int w, vs_menu_info *inf)
+  {
+    return new vs_menu(x, y, w, inf);
+  }
+
+  // Deletes the items it holds!
+  ~vs_menu();
 
   bool get_cursorvisible();
   point get_cursorloc();
@@ -189,4 +199,6 @@
   static void init_bindings();
 };
 
+typedef ref_ptr<vs_menu> vs_menu_ref;
+
 #endif

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_menubar.cc
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_menubar.cc	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_menubar.cc	Sun Aug  7 03:20:15 2005
@@ -2,6 +2,7 @@
 
 #include "vs_container.h"
 #include "vs_menubar.h"
+#include "vs_menu.h"
 #include "vscreen.h"
 
 #include "config/colors.h"
@@ -28,15 +29,15 @@
 
 void vs_menubar::got_focus()
 {
-  vscreen_widget *w=get_focus();
-  if(w)
+  vs_widget_ref w=get_focus();
+  if(w.valid())
     w->focussed();
 }
 
 void vs_menubar::lost_focus()
 {
-  vscreen_widget *w=get_focus();
-  if(w)
+  vs_widget_ref w=get_focus();
+  if(w.valid())
     w->unfocussed();
 }
 
@@ -44,13 +45,13 @@
 {
   if(active)
     return true;
-  else if(subwidget && subwidget->focus_me())
+  else if(subwidget.valid() && subwidget->focus_me())
     return true;
   else
     return vscreen_widget::focus_me();
 }
 
-vscreen_widget *vs_menubar::get_focus()
+vs_widget_ref vs_menubar::get_focus()
 {
   if(active)
     {
@@ -59,23 +60,26 @@
       else
 	return NULL;
     }
-  else if(subwidget)
+  else if(subwidget.valid())
     return subwidget;
   else
     return NULL;
+  // NB: could just end with 'return subwidget' but this makes the
+  // order more explicit.
 }
 
 bool vs_menubar::get_cursorvisible()
 {
-  vscreen_widget *w=get_focus();
-  return (w && w->get_cursorvisible()) || (!w && active);
+  vs_widget_ref w = get_focus();
+  return (w.valid() && w->get_cursorvisible()) ||
+    (!w.valid() && active);
 }
 
 point vs_menubar::get_cursorloc()
 {
-  vscreen_widget *w=get_focus();
+  vs_widget_ref w = get_focus();
 
-  if(w)
+  if(w.valid())
     {
       point p=w->get_cursorloc();
       p.x+=w->get_startx();
@@ -99,7 +103,8 @@
   return rval;
 }
 
-void vs_menubar::append_item(wstring title, vs_menu *menu)
+void vs_menubar::append_item(const wstring &title,
+			     const vs_menu_ref &menu)
 {
   items.push_back(item(L' '+title+L' ', menu));
 
@@ -111,28 +116,28 @@
   vscreen_update();
 }
 
-void vs_menubar::set_subwidget(vscreen_widget *w)
+void vs_menubar::set_subwidget(const vs_widget_ref &w)
 {
-  if(subwidget)
-    subwidget->set_owner(NULL);
-
-  if(subwidget)
-    subwidget->unfocussed();
+  if(subwidget.valid())
+    {
+      subwidget->set_owner(NULL);
+      subwidget->unfocussed();
+    }
 
   subwidget=w;
 
-  if(subwidget)
-    subwidget->set_owner(this);
-
-  if(subwidget)
-    subwidget->focussed();
+  if(subwidget.valid())
+    {
+      subwidget->set_owner(this);
+      subwidget->focussed();
+    }
 
   vscreen_queuelayout();
 }
 
 void vs_menubar::show_all()
 {
-  if(subwidget)
+  if(subwidget.valid())
     subwidget->show_all();
 }
 
@@ -171,7 +176,7 @@
     }
 
   // Expand the width to account for the subwidget.
-  if(subwidget)
+  if(subwidget.valid())
     w=max(w, subwidget->width_request());
 
   return w;
@@ -188,7 +193,7 @@
       i++, num++)
     h=max(h, 1+(*i)->height_request(w));
 
-  if(subwidget)
+  if(subwidget.valid())
     {
       int subwidget_h=subwidget->height_request(w);
 
@@ -243,25 +248,25 @@
 		       req_h);
     }
 
-  if(subwidget)
+  if(subwidget.valid())
     subwidget->alloc_size(0,
 			  always_visible?1:0,
 			  getmaxx(),
 			  always_visible?getmaxy()-1:getmaxy());
 }
 
-void vs_menubar::show_menu(vs_menu *w)
+void vs_menubar::show_menu(const vs_menu_ref &w)
 {
   if(active)
     {
-      vscreen_widget *old_focus=get_focus();
+      vs_widget_ref old_focus=get_focus();
 
       for(activemenulist::iterator i=active_menus.begin();
 	  i!=active_menus.end();
 	  i++)
-	assert(w!=*i);
+	assert(w != *i);
 
-      if(old_focus)
+      if(old_focus.valid())
 	old_focus->unfocussed();
 
       active_menus.push_front(w);
@@ -273,7 +278,7 @@
     }
 }
 
-void vs_menubar::hide_menu(vs_menu *w)
+void vs_menubar::hide_menu(const vs_menu_ref &w)
 {
   if(active)
     {
@@ -286,8 +291,8 @@
 	      w->unfocussed();
 	      active_menus.remove(w);
 
-	      vscreen_widget *new_focus=get_focus();
-	      if(new_focus)
+	      vs_widget_ref new_focus=get_focus();
+	      if(new_focus.valid())
 		new_focus->focussed();
 
 	      vscreen_queuelayout();
@@ -305,7 +310,7 @@
   if(!active)
     {
       active=true;
-      if(subwidget)
+      if(subwidget.valid())
 	subwidget->unfocussed();
 
       // Added to eliminate the weird "titles are selected but contents aren't"
@@ -325,7 +330,7 @@
 	active_menus.front()->hide();
 
       active=false;
-      if(subwidget)
+      if(subwidget.valid())
 	subwidget->focussed();
 
       curloc=0;
@@ -435,7 +440,7 @@
 
       return true;
     }
-  else if(subwidget && subwidget->dispatch_key(k))
+  else if(subwidget.valid() && subwidget->dispatch_key(k))
     return true;
   else
     return vscreen_widget::handle_key(k);
@@ -445,7 +450,7 @@
 
 void vs_menubar::paint(const style &st)
 {
-  if(subwidget)
+  if(subwidget.valid())
     subwidget->display(st);
 
   if(active || always_visible)
@@ -547,7 +552,7 @@
 	  }
     }
 
-  if(subwidget)
+  if(subwidget.valid())
     subwidget->dispatch_mouse(id,
 			      x-subwidget->get_startx(),
 			      y-subwidget->get_starty(), z, bmask);

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_menubar.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_menubar.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_menubar.h	Sun Aug  7 03:20:15 2005
@@ -8,27 +8,30 @@
 
 #include "vscreen_widget.h"
 #include "vs_container.h"
-#include "vs_menu.h"
 #include "config/keybindings.h"
 
 #include <string>
 #include <vector>
 
+class vs_menu;
+
+typedef ref_ptr<vs_menu> vs_menu_ref;
+
 class vs_menubar:public vs_container
 {
   struct item
   {
     std::wstring title;
-    vs_menu *menu;
+    ref_ptr<vs_menu> menu;
 
-    item(std::wstring _title, vs_menu *_menu)
+    item(std::wstring _title, ref_ptr<vs_menu> _menu)
       :title(_title), menu(_menu)
     {
     }
   };
 
   typedef std::vector<item> itemlist;
-  typedef std::list<vscreen_widget *> activemenulist;
+  typedef std::list<vs_widget_ref> activemenulist;
 
   // A list of the items in the menubar itself
   itemlist items;
@@ -44,43 +47,49 @@
   itemlist::size_type curloc;
 
   // the widget underneath this one.
-  vscreen_widget *subwidget;
+  vs_widget_ref subwidget;
 
   // Returns the starting X location of the given item in the menu
   int get_menustart(int idx);
 
   // Show/hide menus
-  void show_menu(vs_menu *w);
-  void hide_menu(vs_menu *w);
+  void show_menu(const vs_menu_ref &w);
+  void hide_menu(const vs_menu_ref &w);
 
   void appear();
   void disappear();
 
   // Similar to the passthrough widget's routine (there's not enough
   // similarity, though, to justify making this a passthrough widget)
-  vscreen_widget *get_focus();
+  vs_widget_ref get_focus();
 
   void got_focus();
   void lost_focus();
 protected:
   virtual bool handle_key(const key &k);
+
+  vs_menubar(bool _always_visible);
 public:
-  vs_menubar(bool _always_visible=true);
+  static ref_ptr<vs_menubar> create(bool always_visible = true)
+  {
+    return new vs_menubar(always_visible);
+  }
+
   ~vs_menubar();
 
   int width_request();
   int height_request(int w);
   void layout_me();
 
-  void set_subwidget(vscreen_widget *w);
+  void set_subwidget(const vs_widget_ref &w);
 
-  void append_item(std::wstring title, vs_menu *menu);
+  void append_item(const std::wstring &title, const vs_menu_ref &menu);
 
   void show_all();
 
   // These aren't, unfortunately, particularly valid in this context. !!
-  void add_widget(vscreen_widget *w) {abort();}
-  void rem_widget(vscreen_widget *w) {abort();}
+  void add_widget(const vs_widget_ref &w) {abort();}
+  void rem_widget(const vs_widget_ref &w) {abort();}
 
   virtual void paint(const style &st);
   virtual bool focus_me();
@@ -97,4 +106,6 @@
   static void init_bindings();
 };
 
+typedef ref_ptr<vs_menubar> vs_menubar_ref;
+
 #endif

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_minibuf_win.cc
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_minibuf_win.cc	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_minibuf_win.cc	Sun Aug  7 03:20:15 2005
@@ -31,11 +31,11 @@
 {
   do_layout.connect(sigc::mem_fun(*this, &vs_minibuf_win::layout_me));
 
-  status=new vs_multiplex;
-  status_lbl=new vs_label("");
+  status=vs_multiplex::create();
+  status_lbl=vs_label::create("");
   status_lbl->set_bg_style(get_style("Status"));
   status->add_widget(status_lbl);
-  header=new vs_label("");
+  header=vs_label::create("");
   header->set_bg_style(get_style("Header"));
 
   status->set_owner(this);
@@ -49,15 +49,15 @@
 {
   set_main_widget(NULL);
 
-  delete header;
-  delete status;
+  header->set_owner(NULL);
+  status->set_owner(NULL);
 }
 
-void vs_minibuf_win::set_main_widget(vscreen_widget *w)
+void vs_minibuf_win::set_main_widget(const vs_widget_ref &w)
 {
   defocus();
 
-  if(main_widget)
+  if(main_widget.valid())
     {
       main_destroy_conn.disconnect();
       main_widget->set_owner(NULL);
@@ -65,7 +65,7 @@
 
   main_widget=w;
 
-  if(main_widget)
+  if(main_widget.valid())
     {
       main_widget->set_owner(this);
       main_destroy_conn=main_widget->destroyed.connect(sigc::bind(sigc::mem_fun(*this, &vs_minibuf_win::set_main_widget), (vscreen_widget *) NULL));
@@ -84,7 +84,7 @@
 
   w=max(w, header->width_request());
 
-  if(main_widget)
+  if(main_widget.valid())
     w=max(w, main_widget->width_request());
 
   return w;
@@ -94,7 +94,7 @@
 {
   int h=2;
 
-  if(main_widget)
+  if(main_widget.valid())
     h=max(h, main_widget->height_request(w));
   return h;
 }
@@ -105,7 +105,7 @@
 
   if(getmaxy()>1)
     {
-      if(getmaxy()>2 && main_widget)
+      if(getmaxy()>2 && main_widget.valid())
 	main_widget->alloc_size(0, 1, getmaxx(), getmaxy()-2);
 
       status->alloc_size(0, getmaxy()-1, getmaxx(), 1);
@@ -114,7 +114,7 @@
 
 void vs_minibuf_win::paint(const style &st)
 {
-  if(main_widget && main_widget->get_visible())
+  if(main_widget.valid() && main_widget->get_visible())
     main_widget->display(st);
 
   status->display(st);
@@ -131,14 +131,14 @@
   status_lbl->set_text(new_status);
 }
 
-void vs_minibuf_win::add_widget(vscreen_widget *widget)
+void vs_minibuf_win::add_widget(const vs_widget_ref &widget)
 {
   defocus();
   status->add_widget(widget);
   refocus();
 }
 
-void vs_minibuf_win::rem_widget(vscreen_widget *widget)
+void vs_minibuf_win::rem_widget(const vs_widget_ref &widget)
 {
   defocus();
   status->rem_widget(widget);
@@ -147,17 +147,17 @@
 
 void vs_minibuf_win::show_all()
 {
-  if(main_widget)
+  if(main_widget.valid())
     main_widget->show_all();
   status->show();
   header->show();
 }
 
-vscreen_widget *vs_minibuf_win::get_focus()
+vs_widget_ref vs_minibuf_win::get_focus()
 {
   if(status->focus_me())
     return status;
-  else if(main_widget && main_widget->get_visible() && main_widget->focus_me())
+  else if(main_widget.valid() && main_widget->get_visible() && main_widget->focus_me())
     return main_widget;
   else
     return NULL;
@@ -165,5 +165,5 @@
 
 void vs_minibuf_win::display_error(string err)
 {
-  add_widget(new vs_transientlabel(err, get_style("Error")));
+  add_widget(vs_transientlabel::create(err, get_style("Error")));
 }

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_minibuf_win.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_minibuf_win.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_minibuf_win.h	Sun Aug  7 03:20:15 2005
@@ -42,19 +42,27 @@
 
 class vs_minibuf_win:public vs_passthrough
 {
-  vs_label *status_lbl, *header;
+  ref_ptr<vs_label> status_lbl, header;
 
-  vscreen_widget *main_widget;
+  vs_widget_ref main_widget;
   // This is displayed in the center of the screen.
 
-  vs_multiplex *status;
+  ref_ptr<vs_multiplex> status;
 
   sigc::connection main_destroy_conn;
-public:
+
+protected:
   vs_minibuf_win();
+public:
+  static
+  ref_ptr<vs_minibuf_win> create()
+  {
+    return new vs_minibuf_win;
+  }
+
   ~vs_minibuf_win();
 
-  void set_main_widget(vscreen_widget *w);
+  void set_main_widget(const vs_widget_ref &w);
 
   int width_request();
   int height_request(int w);
@@ -72,19 +80,21 @@
   // Set the status and header lines of the window, respectively.
   // These routines do NOT call refresh()!
 
-  vscreen_widget *get_focus();
+  vs_widget_ref get_focus();
 
   static const style &retr_header_style() {return get_style("Header");}
   static const style &retr_status_style() {return get_style("Status");}
   void display_error(std::string err);
 
-  void add_widget(vscreen_widget *widget);
+  void add_widget(const vs_widget_ref &widget);
   // Adds a widget.  Widgets are automatically shown if they're the first
   // one to be added, otherwise show() should be called.
-  void rem_widget(vscreen_widget *widget);
+  void rem_widget(const vs_widget_ref &widget);
   // Removes a widget
 
   void show_all();
 };
 
+typedef ref_ptr<vs_minibuf_win> vs_minibuf_win_ref;
+
 #endif

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_multiplex.cc
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_multiplex.cc	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_multiplex.cc	Sun Aug  7 03:20:15 2005
@@ -240,7 +240,7 @@
     visible_child->w->show_all();
 }
 
-void vs_multiplex::show_widget(vscreen_widget *w)
+void vs_multiplex::show_widget(const vs_widget_ref &w)
 {
   assert(!children.empty());
 
@@ -273,7 +273,7 @@
   vscreen_update();
 }
 
-void vs_multiplex::hide_widget(vscreen_widget *w)
+void vs_multiplex::hide_widget(const vs_widget_ref &w)
 {
   assert(!children.empty());
 
@@ -318,12 +318,12 @@
   vscreen_update();
 }
 
-vscreen_widget *vs_multiplex::get_focus()
+vs_widget_ref vs_multiplex::get_focus()
 {
   return visible_child==children.end()?NULL:visible_child->w;
 }
 
-void vs_multiplex::rem_widget(vscreen_widget *w)
+void vs_multiplex::rem_widget(const vs_widget_ref &w)
 {
   hide_widget(w);
 
@@ -355,7 +355,7 @@
   vscreen_update();
 }
 
-void vs_multiplex::add_widget(vscreen_widget *w,
+void vs_multiplex::add_widget(const vs_widget_ref &w,
 			      const wstring &title)
 {
   w->shown_sig.connect(sigc::bind(sigc::mem_fun(*this, &vs_multiplex::show_widget), w));
@@ -368,12 +368,14 @@
     show_widget(w);
 }
 
-void vs_multiplex::add_widget(vscreen_widget *w)
+void vs_multiplex::add_widget(const vs_widget_ref &w)
 {
   add_widget(w, L"Untitled");
 }
 
-void vs_multiplex::add_widget_after(vscreen_widget *w, vscreen_widget *after, const wstring &title)
+void vs_multiplex::add_widget_after(const vs_widget_ref &w,
+				    const vs_widget_ref &after,
+				    const wstring &title)
 {
   for(list<child_info>::iterator i=children.begin();
       i!=children.end();
@@ -400,7 +402,8 @@
   add_widget(w);
 }
 
-void vs_multiplex::add_widget_after(vscreen_widget *w, vscreen_widget *after)
+void vs_multiplex::add_widget_after(const vs_widget_ref &w,
+				    const vs_widget_ref &after)
 {
   add_widget_after(w, after, L"Untitled");
 }
@@ -485,7 +488,7 @@
     }
 }
 
-vscreen_widget *vs_multiplex::visible_widget()
+vs_widget_ref vs_multiplex::visible_widget()
 {
   if(visible_child!=children.end())
     return visible_child->w;

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_multiplex.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_multiplex.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_multiplex.h	Sun Aug  7 03:20:15 2005
@@ -43,10 +43,10 @@
 {
   struct child_info
   {
-    vscreen_widget *w;
+    vs_widget_ref w;
     std::wstring title;
 
-    child_info(vscreen_widget *_w, const std::wstring &_title)
+    child_info(const vs_widget_ref &_w, const std::wstring &_title)
       :w(_w), title(_title)
     {
     }
@@ -67,17 +67,23 @@
    */
   bool tabs_visible() const;
 
-  void show_widget(vscreen_widget *widget);
+  void show_widget(const vs_widget_ref &widget);
   // Used to bring a widget to the front
-  void hide_widget(vscreen_widget *widget);
+  void hide_widget(const vs_widget_ref &widget);
   // Used to hide a widget
 
   void got_focus();
   void lost_focus();
 protected:
   bool winavail() {return get_win();}
+
+  vs_multiplex(bool _show_tabs);
 public:
-  vs_multiplex(bool _show_tabs=false);
+  static ref_ptr<vs_multiplex> create(bool show_tabs = false)
+  {
+    return new vs_multiplex(show_tabs);
+  }
+
   virtual ~vs_multiplex();
 
   /** Returns the maximum width requested by any child. */
@@ -88,8 +94,8 @@
 
   void layout_me();
 
-  virtual vscreen_widget *get_focus();
-  vscreen_widget *visible_widget();
+  virtual vs_widget_ref get_focus();
+  vs_widget_ref visible_widget();
   unsigned int num_children();
   // Returns the number of widgets in the multiplexer.
   unsigned int num_visible();
@@ -103,15 +109,20 @@
    *  function and for backwards compatibility; use of this routine is
    *  deprecated.
    */
-  void add_widget(vscreen_widget *widget);
-  void add_widget(vscreen_widget *widget, const std::wstring &title);
-  void add_widget_after(vscreen_widget *widget, vscreen_widget *after);
-  void add_widget_after(vscreen_widget *widget, vscreen_widget *after, const std::wstring &title);
-  void rem_widget(vscreen_widget *widget);
+  void add_widget(const vs_widget_ref &widget);
+  void add_widget(const vs_widget_ref &widget, const std::wstring &title);
+  void add_widget_after(const vs_widget_ref &widget,
+			const vs_widget_ref &after);
+  void add_widget_after(const vs_widget_ref &widget,
+			const vs_widget_ref &after,
+			const std::wstring &title);
+  void rem_widget(const vs_widget_ref &widget);
 
   // These cycle forward and backwards through the list of visible items.
   void cycle_forward();
   void cycle_backward();
 };
 
+typedef ref_ptr<vs_multiplex> vs_multiplex_ref;
+
 #endif

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_pager.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_pager.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_pager.h	Sun Aug  7 03:20:15 2005
@@ -39,6 +39,12 @@
 
   /** Handles resizing the widget. */
   void layout_me();
+
+protected:
+  vs_pager(const char *text, int len, const char *encoding = NULL);
+  vs_pager(const std::string &s, const char *encoding = NULL);
+  vs_pager(const std::wstring &s);
+
 public:
   /** Create a vs_pager from the given memory region.
    *
@@ -46,20 +52,32 @@
    *  \param len the length of the buffer
    *  \param encoding the encoding of text, or \b NULL to use LC_CTYPE
    */
-  vs_pager(const char *text, int len, const char *encoding=NULL);
+  static ref_ptr<vs_pager>
+  create(const char *text, int len, const char *encoding = NULL)
+  {
+    return new vs_pager(text, len, encoding);
+  }
 
   /** Create a vs_pager from a string.
    *
    *  \param s the text to display
    *  \param encoding the encoding of s, or \b NULL to use LC_CTYPE
    */
-  vs_pager(const std::string &s, const char *encoding=NULL);
+  static ref_ptr<vs_pager>
+  create(const std::string &s, const char *encoding = NULL)
+  {
+    return new vs_pager(s, encoding);
+  }
 
   /** Create a vs_pager from a wide character string.
    *
    *  \param s the text to display
    */
-  vs_pager(const std::wstring &s);
+  static ref_ptr<vs_pager>
+  create (const std::wstring &s)
+  {
+    return new vs_pager(s);
+  }
 
   /** Destroy this vs_pager. */
   virtual ~vs_pager();
@@ -160,17 +178,37 @@
 /** Load a file from disk; it's assumed to be ASCII for now. */
 class vs_file_pager:public vs_pager
 {
-public:
   vs_file_pager();
-  vs_file_pager(const std::string &filename, const char *encoding=NULL);
+  vs_file_pager(const std::string &filename, const char *encoding);
+  vs_file_pager(const std::wstring &filename, const char *encoding);
+
+  vs_file_pager(const char *text, int len, const char *encoding);
+public:
+  static ref_ptr<vs_file_pager> create()
+  {
+    return new vs_file_pager;
+  }
+
+  static ref_ptr<vs_file_pager> create(const std::string &filename, const char *encoding=NULL)
+  {
+    return new vs_file_pager(filename, encoding);
+  }
 
   /** Attempts to convert the string to a multibyte representation and
    *  then load it; a nonconvertible string is treated as any other
    *  load failure would be.
    */
-  vs_file_pager(const std::wstring &filename, const char *encoding=NULL);
-
-  vs_file_pager(const char *text, int len, const char *encoding=NULL);
+  static ref_ptr<vs_file_pager>
+  create(const std::wstring &filename, const char *encoding=NULL)
+  {
+    return new vs_file_pager(filename, encoding);
+  }
+
+  static ref_ptr<vs_file_pager>
+  create(const char *text, int len, const char *encoding=NULL)
+  {
+    return new vs_file_pager(text, len, encoding);
+  }
 
   /** Loads the given file into the pager.
    *
@@ -199,4 +237,7 @@
   void load_file(const std::wstring &filename);
 };
 
+typedef ref_ptr<vs_pager> vs_pager_ref;
+typedef ref_ptr<vs_file_pager> vs_file_pager_ref;
+
 #endif

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_passthrough.cc
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_passthrough.cc	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_passthrough.cc	Sun Aug  7 03:20:15 2005
@@ -22,25 +22,25 @@
 
 void vs_passthrough::gained_focus()
 {
-  vscreen_widget *w=get_focus();
+  vs_widget_ref w = get_focus();
 
-  if(w)
+  if(w.valid())
     w->focussed();
 }
 
 void vs_passthrough::lost_focus()
 {
-  vscreen_widget *w=get_focus();
+  vs_widget_ref w = get_focus();
 
-  if(w)
+  if(w.valid())
     w->unfocussed();
 }
 
 bool vs_passthrough::focus_me()
 {
-  vscreen_widget *w=get_focus();
+  vs_widget_ref w = get_focus();
 
-  if(w && w->focus_me())
+  if(w.valid() && w->focus_me())
     return true;
   else
     return vs_container::focus_me();
@@ -48,16 +48,16 @@
 
 bool vs_passthrough::get_cursorvisible()
 {
-  vscreen_widget *w=get_focus();
+  vs_widget_ref w = get_focus();
 
-  return w && w->get_cursorvisible();
+  return w.valid() && w->get_cursorvisible();
 }
 
 point vs_passthrough::get_cursorloc()
 {
-  vscreen_widget *w=get_focus();
+  vs_widget_ref w = get_focus();
 
-  if(w)
+  if(w.valid())
     {
       point p=w->get_cursorloc();
       p.x+=w->get_startx();
@@ -71,9 +71,9 @@
 
 bool vs_passthrough::handle_key(const key &k)
 {
-  vscreen_widget *w=get_focus();
+  vs_widget_ref w = get_focus();
 
-  if(w && w->get_visible() && w->focus_me())
+  if(w.valid() && w->get_visible() && w->focus_me())
     return w->dispatch_key(k) || vs_container::handle_key(k);
   else
     return vs_container::handle_key(k);
@@ -82,8 +82,8 @@
 void vs_passthrough::dispatch_mouse(short id, int x, int y, int z,
 				    mmask_t bstate)
 {
-  vscreen_widget *w=get_focus();
+  vs_widget_ref w = get_focus();
 
-  if(w && w->get_visible())
+  if(w.valid() && w->get_visible())
     w->dispatch_mouse(id, x-w->get_startx(), y-w->get_starty(), z, bstate);
 }

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_passthrough.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_passthrough.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_passthrough.h	Sun Aug  7 03:20:15 2005
@@ -22,11 +22,13 @@
   // Provided to make it easier to manage focus simply.
   void defocus();
   void refocus();
-public:
+
+protected:
   vs_passthrough();
 
+public:
   // Returns the currently focussed widget, if any.
-  virtual vscreen_widget *get_focus()=0;
+  virtual vs_widget_ref get_focus()=0;
   virtual void dispatch_mouse(short id, int x, int y, int z, mmask_t bstate);
 
   virtual bool focus_me();
@@ -34,4 +36,6 @@
   virtual point get_cursorloc();
 };
 
+typedef ref_ptr<vs_passthrough> vs_passthrough_ref;
+
 #endif

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_radiogroup.cc
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_radiogroup.cc	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_radiogroup.cc	Sun Aug  7 03:20:15 2005
@@ -2,6 +2,8 @@
 
 #include "vs_radiogroup.h"
 
+#include "vs_togglebutton.h"
+
 #include <sigc++/adaptors/bind.h>
 #include <sigc++/functors/mem_fun.h>
 
@@ -39,7 +41,7 @@
     }
 }
 
-void vs_radiogroup::add_button(vs_togglebutton *b, int id)
+void vs_radiogroup::add_button(const vs_togglebutton_ref &b, int id)
 {
   assert(id>=0);
 
@@ -52,7 +54,7 @@
     button_pressed(items.size()-1);
 }
 
-void vs_radiogroup::rem_button(vs_togglebutton *b)
+void vs_radiogroup::rem_button(const vs_togglebutton_ref &b)
 {
   for(itemlist::size_type i=0; i<items.size(); i++)
     if(items[i].b==b)

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_radiogroup.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_radiogroup.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_radiogroup.h	Sun Aug  7 03:20:15 2005
@@ -23,24 +23,26 @@
 #ifndef VS_RADIOGROUP_H
 #define VS_RADIOGROUP_H
 
-#include "vs_togglebutton.h"
+#include "ref_ptr.h"
 
 #include <vector>
 
 #include <sigc++/connection.h>
 #include <sigc++/trackable.h>
 
+class vs_togglebutton;
+
 class vs_radiogroup:public sigc::trackable
 {
   struct item
   {
-    vs_togglebutton *b;
+    ref_ptr<vs_togglebutton> b;
     int id;
 
     // Needed, unfortunately.
     sigc::connection destroyed_conn, pressed_conn;
 
-    item(vs_togglebutton *_b, int _id,
+    item(const ref_ptr<vs_togglebutton> &_b, int _id,
 	 const sigc::connection &_dconn, const sigc::connection &_pconn)
       :b(_b), id(_id), destroyed_conn(_dconn), pressed_conn(_pconn) {}
   };
@@ -59,8 +61,8 @@
   vs_radiogroup();
   ~vs_radiogroup();
 
-  void add_button(vs_togglebutton *b, int id);
-  void rem_button(vs_togglebutton *b);
+  void add_button(const ref_ptr<vs_togglebutton> &b, int id);
+  void rem_button(const ref_ptr<vs_togglebutton> &b);
 
   /** \return \b true if a button is selected. */
   bool selection_valid();

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_scrollbar.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_scrollbar.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_scrollbar.h	Sun Aug  7 03:20:15 2005
@@ -26,12 +26,24 @@
    *  \return the slider location, or -1 if it is not visible.
    */
   int get_slider();
-public:
+protected:
   vs_scrollbar(direction _dir, int _val, int _max)
     :dir(_dir), max(_max), val(_val) {}
 
   vs_scrollbar(direction _dir)
     :dir(_dir), max(0), val(0) {}
+public:
+  static
+  ref_ptr<vs_scrollbar> create(direction dir, int val, int max)
+  {
+    return new vs_scrollbar(dir, val, max);
+  }
+
+  static
+  ref_ptr<vs_scrollbar> create(direction dir)
+  {
+    return new vs_scrollbar(dir);
+  }
 
   void paint(const style &st);
 
@@ -51,4 +63,6 @@
   sigc::signal1<void, bool> scrollbar_interaction;
 };
 
+typedef ref_ptr<vs_scrollbar> vs_scrollbar_ref;
+
 #endif

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_size_box.cc
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_size_box.cc	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_size_box.cc	Sun Aug  7 03:20:15 2005
@@ -10,7 +10,7 @@
 
 using namespace std;
 
-vs_size_box::vs_size_box(size s, vscreen_widget *w):min_size(s)
+vs_size_box::vs_size_box(size s, const vs_widget_ref &w):min_size(s)
 {
   set_subwidget(w);
   set_opaque(false);
@@ -20,9 +20,9 @@
 
 int vs_size_box::width_request()
 {
-  vscreen_widget *child=get_subwidget();
+  vs_widget_ref child = get_subwidget();
 
-  if(child)
+  if(child.valid())
     return max(child->width_request(), min_size.w);
   else
     return min_size.w;
@@ -30,9 +30,9 @@
 
 int vs_size_box::height_request(int w)
 {
-  vscreen_widget *child=get_subwidget();
+  vs_widget_ref child = get_subwidget();
 
-  if(child)
+  if(child.valid())
     return max(child->height_request(w), min_size.h);
   else
     return min_size.h;
@@ -40,11 +40,13 @@
 
 void vs_size_box::layout_me()
 {
-  if(get_subwidget())
+  vs_widget_ref child = get_subwidget();
+
+  if(child.valid())
     {
-      if(get_subwidget()->get_visible())
-	get_subwidget()->alloc_size(0, 0, getmaxx(), getmaxy());
+      if(child->get_visible())
+	child->alloc_size(0, 0, getmaxx(), getmaxy());
       else
-	get_subwidget()->alloc_size(0, 0, 0, 0);
+	child->alloc_size(0, 0, 0, 0);
     }
 }

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_size_box.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_size_box.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_size_box.h	Sun Aug  7 03:20:15 2005
@@ -19,6 +19,9 @@
 
   /** Internal: actually allocates the child's size. */
   void layout_me();
+protected:
+  vs_size_box(size s, const vs_widget_ref &w);
+
 public:
   /** Create a vs_size_box.
    *
@@ -26,7 +29,10 @@
    *  \param w the widget initially contained in this box (\b NULL to
    *           create an initially empty box)
    */
-  vs_size_box(size s, vscreen_widget *w=NULL);
+  static ref_ptr<vs_size_box> create(size s, const vs_widget_ref &w=NULL)
+  {
+    return new vs_size_box(s, w);
+  }
 
   /** \return the least upper bound of the minimum size passed to the
    *  constructor and the true size request of the child.
@@ -41,4 +47,6 @@
   int height_request(int w);
 };
 
+typedef ref_ptr<vs_size_box> vs_size_box_ref;
+
 #endif

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_stacked.cc
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_stacked.cc	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_stacked.cc	Sun Aug  7 03:20:15 2005
@@ -12,7 +12,7 @@
   do_layout.connect(sigc::mem_fun(*this, &vs_stacked::layout_me));
 }
 
-void vs_stacked::add_widget(vscreen_widget *w)
+void vs_stacked::add_widget(const vs_widget_ref &w)
 {
   sigc::connection shown_conn=w->shown_sig.connect(sigc::bind(sigc::mem_fun(*this, &vs_stacked::raise_widget), w));
   sigc::connection hidden_conn=w->hidden_sig.connect(sigc::mem_fun(*this, &vs_stacked::hide_widget));
@@ -34,7 +34,7 @@
   vscreen_update();
 }
 
-void vs_stacked::rem_widget(vscreen_widget *w)
+void vs_stacked::rem_widget(const vs_widget_ref &w)
 {
   for(childlist::iterator i=children.begin();
       i!=children.end();
@@ -58,7 +58,7 @@
     }
 }
 
-void vs_stacked::raise_widget(vscreen_widget *w)
+void vs_stacked::raise_widget(const vs_widget_ref &w)
 {
   for(childlist::iterator i=children.begin();
       i!=children.end();
@@ -77,7 +77,7 @@
       }
 }
 
-void vs_stacked::lower_widget(vscreen_widget *w)
+void vs_stacked::lower_widget(const vs_widget_ref &w)
 {
   for(childlist::iterator i=children.begin();
       i!=children.end();
@@ -119,7 +119,7 @@
       }
 }
 
-vscreen_widget *vs_stacked::get_focus()
+vs_widget_ref vs_stacked::get_focus()
 {
   for(childlist::iterator i=children.begin();
       i!=children.end();

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_stacked.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_stacked.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_stacked.h	Sun Aug  7 03:20:15 2005
@@ -19,11 +19,11 @@
   // disconnect are :(
   struct child_info
   {
-    vscreen_widget *w;
+    vs_widget_ref w;
 
     sigc::connection shown_conn, hidden_conn;
 
-    child_info(vscreen_widget *_w,
+    child_info(const vs_widget_ref &_w,
 	       SigC::Connection &_shown_conn,
 	       SigC::Connection &_hidden_conn)
       :w(_w), shown_conn(_shown_conn),
@@ -43,19 +43,24 @@
   void hide_widget();
 protected:
   void paint(const style &st);
-public:
+
   // The size passed in is used as a preferred size.  (what we get might be
   // larger or smaller)
-  vs_stacked(int w=0, int h=0);
+  vs_stacked(int w, int h);
+public:
+  static ref_ptr<vs_stacked> create(int w=0, int h=0)
+  {
+    return new vs_stacked(w, h);
+  }
 
-  void add_widget(vscreen_widget *w);
-  void rem_widget(vscreen_widget *w);
-  void raise_widget(vscreen_widget *w);
-  void lower_widget(vscreen_widget *w);
+  void add_widget(const vs_widget_ref &w);
+  void rem_widget(const vs_widget_ref &w);
+  void raise_widget(const vs_widget_ref &w);
+  void lower_widget(const vs_widget_ref &w);
 
   void dispatch_mouse(short id, int x, int y, int z, mmask_t bstate);
 
-  vscreen_widget *vs_stacked::get_focus();
+  vs_widget_ref vs_stacked::get_focus();
 
   void show_all();
 
@@ -63,4 +68,6 @@
   int height_request(int w);
 };
 
+typedef ref_ptr<vs_stacked> vs_stacked_ref;
+
 #endif

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_statuschoice.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_statuschoice.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_statuschoice.h	Sun Aug  7 03:20:15 2005
@@ -44,13 +44,20 @@
 
 protected:
   bool handle_key(const key &k);
-public:
+
   vs_statuschoice(const std::wstring &_prompt, const std::wstring &_choices)
     :vscreen_widget(), prompt(_prompt), choices(_choices)
   {
     assert(choices.size()>0);
   }
 
+public:
+  static ref_ptr<vs_statuschoice> create(const std::wstring &prompt,
+					 const std::wstring &choices)
+  {
+    return new vs_statuschoice(prompt, choices);
+  }
+
   int width_request();
   int height_request(int w);
 
@@ -69,4 +76,6 @@
   static void init_bindings();
 };
 
+typedef ref_ptr<vs_statuschoice> vs_statuschoice_ref;
+
 #endif

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_table.cc
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_table.cc	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_table.cc	Sun Aug  7 03:20:15 2005
@@ -23,7 +23,7 @@
 FILE *debug=fopen("/tmp/vs.log", "w");
 #endif
 
-vs_table::child_info::child_info(vscreen_widget *_w, int _row_start, int _col_start,
+vs_table::child_info::child_info(const vs_widget_ref &_w, int _row_start, int _col_start,
 				 int _row_span, int _col_span, int xopts, int yopts,
 				 sigc::connection &_shown_conn, sigc::connection &_hidden_conn)
   :w(_w), row_start(_row_start), col_start(_col_start),
@@ -90,21 +90,21 @@
 // We need to call get_focus() here to update the "focus" pointer.
 void vs_table::got_focus()
 {
-  vscreen_widget *w=get_focus();
+  vs_widget_ref w=get_focus();
 
-  if(w)
+  if(w.valid())
     w->focussed();
 }
 
 void vs_table::lost_focus()
 {
-  vscreen_widget *w=get_focus();
+  vs_widget_ref w=get_focus();
 
-  if(w)
+  if(w.valid())
     w->unfocussed();
 }
 
-void vs_table::add_widget(vscreen_widget *w, int row_start, int col_start, int row_span, int col_span, bool expand, bool shrink)
+void vs_table::add_widget(const vs_widget_ref &w, int row_start, int col_start, int row_span, int col_span, bool expand, bool shrink)
 {
   int opts=ALIGN_CENTER;
   if(expand)
@@ -115,7 +115,7 @@
   add_widget_opts(w, row_start, col_start, row_span, col_span, opts, opts);
 }
 
-void vs_table::add_widget_opts(vscreen_widget *w, int row_start, int col_start, int row_span, int col_span, int xopts, int yopts)
+void vs_table::add_widget_opts(const vs_widget_ref &w, int row_start, int col_start, int row_span, int col_span, int xopts, int yopts)
 {
   // sanity check
   for(childlist::iterator i=children.begin(); i!=children.end(); ++i)
@@ -145,7 +145,7 @@
   vscreen_queuelayout();
 }
 
-void vs_table::hide_widget(vscreen_widget *w)
+void vs_table::hide_widget(const vs_widget_ref &w)
 {
   if(focus!=children.end() && w==focus->w)
     {
@@ -172,7 +172,7 @@
   vscreen_queuelayout();
 }
 
-void vs_table::show_widget(vscreen_widget *w)
+void vs_table::show_widget(const vs_widget_ref &w)
 {
   if(w->focus_me() && focus==children.end())
     {
@@ -189,7 +189,7 @@
   vscreen_queuelayout();
 }
 
-void vs_table::add_widget(vscreen_widget *w)
+void vs_table::add_widget(const vs_widget_ref &w)
 {
   add_widget(w, num_rows, 0, 1);
 }
@@ -209,7 +209,7 @@
   num_cols=num_cols;
 }
 
-void vs_table::rem_widget(vscreen_widget *w)
+void vs_table::rem_widget(const vs_widget_ref &w)
 {
   for(childlist::iterator i=children.begin(); i!=children.end(); ++i)
     if(i->w==w)
@@ -250,7 +250,7 @@
       }
 }
 
-void vs_table::focus_widget(vscreen_widget *w)
+void vs_table::focus_widget(const vs_widget_ref &w)
 {
   for(childlist::iterator i=children.begin(); i!=children.end(); ++i)
     if(i->w==w)
@@ -273,7 +273,7 @@
       }
 }
 
-vscreen_widget *vs_table::get_focus()
+vs_widget_ref vs_table::get_focus()
 {
   if(focus!=children.end() && focus->w->focus_me())
     return focus->w;

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_table.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_table.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_table.h	Sun Aug  7 03:20:15 2005
@@ -25,7 +25,7 @@
   struct child_info
   {
     // The widget itself
-    vscreen_widget *w;
+    vs_widget_ref w;
 
     // The upper-left corner of this widget
     int row_start, col_start;
@@ -66,7 +66,7 @@
      */
     bool ignore_size_x:1, ignore_size_y:1;
 
-    child_info(vscreen_widget *_w, int _row_start, int _col_start,
+    child_info(const vs_widget_ref &_w, int _row_start, int _col_start,
 	       int _row_span, int _col_span, int xopts, int yopts,
 	       sigc::connection &_shown_conn, sigc::connection &_hidden_conn);
   };
@@ -103,9 +103,9 @@
   void layout_me();
 
   // Focus-handling stuff
-  vscreen_widget *get_focus();
-  void hide_widget(vscreen_widget *w);
-  void show_widget(vscreen_widget *w);
+  vs_widget_ref get_focus();
+  void hide_widget(const vs_widget_ref &w);
+  void show_widget(const vs_widget_ref &w);
 
   /** Populates the given vector with lists of the widgets in each
    *  row.
@@ -143,20 +143,26 @@
 
 protected:
   bool handle_key(const key &k);
-public:
   vs_table();
+
+public:
+  static ref_ptr<vs_table> create()
+  {
+    return new vs_table;
+  }
+
   ~vs_table();
 
-  void add_widget_opts(vscreen_widget *w, int row_start, int col_start, int row_span, int col_span, int xopts, int yopts);
+  void add_widget_opts(const vs_widget_ref &w, int row_start, int col_start, int row_span, int col_span, int xopts, int yopts);
   // eww.  C++ overloading is annoying..
-  void add_widget(vscreen_widget *w, int row_start, int col_start, int row_span=1, int col_span=1, bool expand=true, bool shrink=true);
+  void add_widget(const vs_widget_ref &w, int row_start, int col_start, int row_span=1, int col_span=1, bool expand=true, bool shrink=true);
   // This form uses the same options for X and Y
 
-  void add_widget(vscreen_widget *w);
+  void add_widget(const vs_widget_ref &w);
 
-  void rem_widget(vscreen_widget *w);
+  void rem_widget(const vs_widget_ref &w);
 
-  void focus_widget(vscreen_widget *w);
+  void focus_widget(const vs_widget_ref &w);
 
   /** Set the separation between adjacent rows to the given number of
    *  characters.
@@ -192,4 +198,6 @@
   static void init_bindings();
 };
 
+typedef ref_ptr<vs_table> vs_table_ref;
+
 #endif

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_text_layout.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_text_layout.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_text_layout.h	Sun Aug  7 03:20:15 2005
@@ -27,16 +27,24 @@
  */
 class vs_text_layout:public vscreen_widget
 {
+  vs_text_layout();
+  vs_text_layout(fragment *f);
 public:
   /** Create an empty vs_text_layout. */
-  vs_text_layout();
+  static ref_ptr<vs_text_layout> create()
+  {
+    return new vs_text_layout;
+  }
 
   /** Create a vs_text_layout with the given root fragment.
    *
    *  All fragments are implicitly placed within a clipbox of width
    *  equal to the width of this widget.
    */
-  vs_text_layout(fragment *f);
+  static ref_ptr<vs_text_layout> create(fragment *f)
+  {
+    return new vs_text_layout(f);
+  }
 
   /** Handle the given keypress.  Returns \b true if the keystroke
    *  was "consumed" by this widget.
@@ -152,4 +160,6 @@
   style lastst;
 };
 
+typedef ref_ptr<vs_text_layout> vs_text_layout_ref;
+
 #endif

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_togglebutton.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_togglebutton.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_togglebutton.h	Sun Aug  7 03:20:15 2005
@@ -22,12 +22,28 @@
   // to be used mainly to avoid emitting signals (eg, if you're trying to
   // coordinate a togglebutton with an underlying option)
 
-public:
   vs_togglebutton(char _bracketl, char _mark, char _bracketr,
-		  fragment *_label, bool _checked=false);
+		  fragment *_label, bool _checked);
 
   vs_togglebutton(char _bracketl, char _mark, char _bracketr,
-		  const std::string &_label, bool _checked=false);
+		  const std::string &_label, bool _checked);
+
+public:
+  static ref_ptr<vs_togglebutton>
+  create(char bracketl, char mark, char bracketr,
+	 fragment *label, bool checked = false)
+  {
+    return new vs_togglebutton(bracketl, mark, bracketr,
+			       label, checked);
+  }
+
+  static ref_ptr<vs_togglebutton>
+  create(char bracketl, char mark, char bracketr,
+	 const std::string &label, bool checked = false)
+  {
+    return new vs_togglebutton(bracketl, mark, bracketr,
+			       label, checked);
+  }
 
   point get_cursorloc();
 
@@ -48,46 +64,92 @@
 
 class vs_checkbutton:public vs_togglebutton
 {
-public:
-  vs_checkbutton(fragment *_label, bool _checked=false)
+protected:
+  vs_checkbutton(fragment *_label, bool _checked)
     :vs_togglebutton('[', 'X', ']', _label, _checked)
   {
     pressed.connect(sigc::mem_fun(*this, &vs_togglebutton::do_toggle));
   }
 
-  vs_checkbutton(const std::string &_label, bool _checked=false)
+  vs_checkbutton(const std::string &_label, bool _checked)
     :vs_togglebutton('[', 'X', ']', _label, _checked)
   {
     pressed.connect(sigc::mem_fun(*this, &vs_togglebutton::do_toggle));
   }
 
   vs_checkbutton(char bracketr, char mark, char bracketl,
-		 fragment *_label, bool _checked=false)
+		 fragment *_label, bool _checked)
     :vs_togglebutton(bracketr, mark, bracketl, _label, _checked)
   {
     pressed.connect(sigc::mem_fun(*this, &vs_togglebutton::do_toggle));
   }
 
   vs_checkbutton(char bracketr, char mark, char bracketl,
-		 const std::string &_label, bool _checked=false)
+		 const std::string &_label, bool _checked)
     :vs_togglebutton(bracketr, mark, bracketl, _label, _checked)
   {
     pressed.connect(sigc::mem_fun(*this, &vs_togglebutton::do_toggle));
   }
+
+public:
+  static ref_ptr<vs_checkbutton>
+  create(fragment *label, bool checked = false)
+  {
+    return new vs_checkbutton(label, checked);
+  }
+
+  static ref_ptr<vs_checkbutton>
+  create(const std::string &label, bool checked = false)
+  {
+    return new vs_checkbutton(label, checked);
+  }
+
+  static ref_ptr<vs_checkbutton>
+  create(char bracketr, char mark, char bracketl,
+	 fragment *label, bool checked = false)
+  {
+    return new vs_checkbutton(bracketr, mark, bracketl,
+			      label, checked);
+  }
+
+  static ref_ptr<vs_checkbutton>
+  create(char bracketr, char mark, char bracketl,
+	 const std::string &label, bool checked = false)
+  {
+    return new vs_checkbutton(bracketr, mark, bracketl,
+			      label, checked);
+  }
 };
 
 class vs_radiobutton:public vs_togglebutton
 {
-public:
-  vs_radiobutton(fragment *_label, bool _checked=false)
+protected:
+  vs_radiobutton(fragment *_label, bool _checked)
     :vs_togglebutton('(', '*', ')', _label, _checked)
   {
   }
 
-  vs_radiobutton(const std::string &_label, bool _checked=false)
+  vs_radiobutton(const std::string &_label, bool _checked)
     :vs_togglebutton('(', '*', ')', _label, _checked)
   {
   }
+
+public:
+  static ref_ptr<vs_radiobutton>
+  create(fragment *label, bool checked = false)
+  {
+    return new vs_radiobutton(label, checked);
+  }
+
+  static ref_ptr<vs_radiobutton>
+  create(const std::string &label, bool checked = false)
+  {
+    return new vs_radiobutton(label, checked);
+  }
 };
 
+typedef ref_ptr<vs_togglebutton> vs_togglebutton_ref;
+typedef ref_ptr<vs_checkbutton> vs_checkbutton_ref;
+typedef ref_ptr<vs_radiobutton> vs_radiobutton_ref;
+
 #endif

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_transient.cc
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_transient.cc	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_transient.cc	Sun Aug  7 03:20:15 2005
@@ -6,7 +6,7 @@
 
 #include <sigc++/functors/mem_fun.h>
 
-vs_transient::vs_transient(vscreen_widget *w)
+vs_transient::vs_transient(const vs_widget_ref &w)
 {
   set_subwidget(w);
 
@@ -15,9 +15,9 @@
 
 void vs_transient::layout_me()
 {
-  vscreen_widget *w=get_subwidget();
+  vs_widget_ref w=get_subwidget();
 
-  if(w)
+  if(w.valid())
     {
       if(w->get_visible())
 	w->alloc_size(0, 0, getmaxx(), getmaxy());
@@ -28,9 +28,9 @@
 
 int vs_transient::width_request()
 {
-  vscreen_widget *w=get_subwidget();
+  vs_widget_ref w=get_subwidget();
 
-  if(w)
+  if(w.valid())
     return w->width_request();
   else
     return 0;
@@ -38,9 +38,9 @@
 
 int vs_transient::height_request(int width)
 {
-  vscreen_widget *w=get_subwidget();
+  vs_widget_ref w=get_subwidget();
 
-  if(w)
+  if(w.valid())
     return w->height_request(width);
   else
     return 0;

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_transient.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_transient.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_transient.h	Sun Aug  7 03:20:15 2005
@@ -19,12 +19,18 @@
    */
   void layout_me();
 
+protected:
+  vs_transient(const vs_widget_ref &w);
 public:
   /** Create a new vs_transient.
    *
    *  \param w the widget to place inside the transient wrapper.
    */
-  vs_transient(vscreen_widget *w=NULL);
+  static ref_ptr<vs_transient>
+  create(const vs_widget_ref &w = NULL)
+  {
+    return new vs_transient(w);
+  }
 
   /** \return the desired width of the subwidget. */
   int width_request();
@@ -46,4 +52,6 @@
   bool handle_char(chtype ch);
 };
 
+typedef ref_ptr<vs_transient> vs_transient_ref;
+
 #endif // VS_TRANSIENT_H

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_tree.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_tree.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_tree.h	Sun Aug  7 03:20:15 2005
@@ -108,9 +108,23 @@
   //  -- well, it wasn't.
 
   virtual bool handle_key(const key &k);
-public:
+
+protected:
   vs_tree();
-  vs_tree(vs_treeitem *_root, bool showroot=false);
+  vs_tree(vs_treeitem *_root, bool showroot);
+
+public:
+  static ref_ptr<vs_tree>
+  create()
+  {
+    return new vs_tree;
+  }
+
+  static ref_ptr<vs_tree>
+  create(vs_treeitem *root, bool showroot = false)
+  {
+    return new vs_tree(root, showroot);
+  }
 
   void set_root(vs_treeitem *_root, bool showroot=false);
 
@@ -160,4 +174,6 @@
   // Sets up the bindings..
 };
 
+typedef ref_ptr<vs_tree> vs_tree_ref;
+
 #endif

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_util.cc
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_util.cc	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_util.cc	Sun Aug  7 03:20:15 2005
@@ -22,97 +22,100 @@
 
 using namespace std;
 
-vscreen_widget *vs_dialog_ok(vscreen_widget *w, slot0arg okslot, wstring label,
-			     const style &st)
+vs_widget_ref vs_dialog_ok(const vs_widget_ref &w,
+			   slot0arg okslot,
+			   const wstring &label,
+			   const style &st)
 {
-  vs_center *center=new vs_center;
+  vs_center_ref center = vs_center::create();
 
-  vs_table *table=new vs_table;
+  vs_table_ref table = vs_table::create();
 
-  vs_button *okbutton=new vs_button(label);
+  vs_button_ref okbutton = vs_button::create(label);
 
-  okbutton->pressed.connect(sigc::mem_fun(*center, &vscreen_widget::destroy));
+  okbutton->pressed.connect(sigc::mem_fun(*center.unsafe_get_ref(), &vscreen_widget::destroy));
   if(okslot)
     okbutton->pressed.connect(*okslot);
 
   table->add_widget(w, 0, 0, 1, 1, true, true);
-  table->add_widget(new vs_center(okbutton), 1, 0, 1, 1, false, false);
+  table->add_widget(vs_center::create(okbutton), 1, 0, 1, 1, false, false);
   table->connect_key("Confirm", &global_bindings, okbutton->pressed.make_slot());
 
-  vs_frame *frame=new vs_frame(table);
+  vs_frame_ref frame = vs_frame::create(table);
 
   center->add_widget(frame);
   frame->set_bg_style(st);
   return center;
 }
 
-vscreen_widget *vs_dialog_ok(fragment *msg, slot0arg okslot, wstring label,
-			     const style &st, bool scrollbar)
+vs_widget_ref vs_dialog_ok(fragment *msg, slot0arg okslot,
+			   const wstring &label,
+			   const style &st, bool scrollbar)
 {
-  vscreen_widget *w;
+  vs_widget_ref w;
 
   if(scrollbar)
     {
-      vs_table *t=new vs_table;
+      vs_table_ref t = vs_table::create();
       w=t;
 
-      vs_text_layout *l=new vs_text_layout(msg);
-      vs_scrollbar *s=new vs_scrollbar(vs_scrollbar::VERTICAL);
+      vs_text_layout_ref l = vs_text_layout::create(msg);
+      vs_scrollbar_ref s = vs_scrollbar::create(vs_scrollbar::VERTICAL);
 
       t->add_widget(l, 0, 0, 1, 1, true, true);
       t->add_widget_opts(s, 0, 1, 1, 1,
 			 vs_table::ALIGN_RIGHT,
 			 vs_table::ALIGN_CENTER | vs_table::FILL);
 
-      l->location_changed.connect(sigc::mem_fun(*s, &vs_scrollbar::set_slider));
-      s->scrollbar_interaction.connect(sigc::mem_fun(*l, &vs_text_layout::scroll));
+      l->location_changed.connect(sigc::mem_fun(*s.unsafe_get_ref(), &vs_scrollbar::set_slider));
+      s->scrollbar_interaction.connect(sigc::mem_fun(*l.unsafe_get_ref(), &vs_text_layout::scroll));
     }
   else
-    w=new vs_text_layout(msg);
+    w=vs_text_layout::create(msg);
 
   return vs_dialog_ok(w, okslot, label, st);
 }
 
-vscreen_widget *vs_dialog_ok(fragment *msg, slot0arg okslot, const style &st, bool scrollbar)
+vs_widget_ref vs_dialog_ok(fragment *msg, slot0arg okslot, const style &st, bool scrollbar)
 {
   return vs_dialog_ok(msg, okslot, transcode(_("Ok")), st, scrollbar);
 }
 
-vscreen_widget *vs_dialog_ok(fragment *msg, slot0arg okslot, bool scrollbar)
+vs_widget_ref vs_dialog_ok(fragment *msg, slot0arg okslot, bool scrollbar)
 {
   return vs_dialog_ok(msg, okslot, style_attrs_flip(A_REVERSE), scrollbar);
 }
 
-vscreen_widget *vs_dialog_ok(wstring msg, slot0arg okslot,
-			     const style &st)
+vs_widget_ref vs_dialog_ok(const wstring &msg, slot0arg okslot,
+			   const style &st)
 {
-  vscreen_widget *l=new vs_label(msg);
+  vs_widget_ref l=vs_label::create (msg);
 
   return vs_dialog_ok(l, okslot, transcode(_("Ok")), st);
 }
 
-vscreen_widget *vs_dialog_ok(wstring msg, slot0arg okslot)
+vs_widget_ref vs_dialog_ok(const wstring &msg, slot0arg okslot)
 {
   return vs_dialog_ok(msg, okslot, style_attrs_flip(A_REVERSE));
 }
 
-vscreen_widget *vs_dialog_yesno(vscreen_widget *widget,
-				slot0arg yesslot,
-				wstring yeslabel,
-				slot0arg noslot,
-				wstring nolabel,
-				const style &st,
-				bool deflt)
-{
-  vs_center *center=new vs_center;
+vs_widget_ref vs_dialog_yesno(const vs_widget_ref &widget,
+			      slot0arg yesslot,
+			      wstring yeslabel,
+			      slot0arg noslot,
+			      wstring nolabel,
+			      const style &st,
+			      bool deflt)
+{
+  vs_center_ref center = vs_center::create();
 
-  vs_table *table=new vs_table;
+  vs_table_ref table = vs_table::create();
 
-  vs_button *yesbutton=new vs_button(yeslabel);
-  vs_button *nobutton=new vs_button(nolabel);
+  vs_button_ref yesbutton = vs_button::create(yeslabel);
+  vs_button_ref nobutton = vs_button::create(nolabel);
 
-  yesbutton->pressed.connect(sigc::mem_fun(*center, &vscreen_widget::destroy));
-  nobutton->pressed.connect(sigc::mem_fun(*center, &vscreen_widget::destroy));
+  yesbutton->pressed.connect(sigc::mem_fun(*center.unsafe_get_ref(), &vscreen_widget::destroy));
+  nobutton->pressed.connect(sigc::mem_fun(*center.unsafe_get_ref(), &vscreen_widget::destroy));
 
   if(yesslot)
     yesbutton->pressed.connect(*yesslot);
@@ -136,7 +139,7 @@
   else
     table->focus_widget(nobutton);
 
-  vs_frame *frame=new vs_frame(table);
+  vs_frame_ref frame = vs_frame::create(table);
   frame->set_bg_style(st);
 
   center->add_widget(frame);
@@ -144,33 +147,33 @@
   return center;
 }
 
-vscreen_widget *vs_dialog_yesno(wstring msg,
-				slot0arg yesslot,
-				wstring yeslabel,
-				slot0arg noslot,
-				wstring nolabel,
-				const style &st,
-				bool deflt)
+vs_widget_ref vs_dialog_yesno(const wstring &msg,
+			      slot0arg yesslot,
+			      const wstring &yeslabel,
+			      slot0arg noslot,
+			      const wstring &nolabel,
+			      const style &st,
+			      bool deflt)
 {
-  vscreen_widget *txt=new vs_label(msg);
+  vs_widget_ref txt=vs_label::create(msg);
 
   return vs_dialog_yesno(txt, yesslot, yeslabel, noslot, nolabel, st, deflt);
 }
 
-vscreen_widget *vs_dialog_yesno(wstring msg,
-				slot0arg yesslot,
-				slot0arg noslot,
-				const style &st,
-				bool deflt)
+vs_widget_ref vs_dialog_yesno(const wstring &msg,
+			      slot0arg yesslot,
+			      slot0arg noslot,
+			      const style &st,
+			      bool deflt)
 {
   return vs_dialog_yesno(msg, yesslot, transcode(_("Yes")),
 			 noslot, transcode(_("No")), st, deflt);
 }
 
-vscreen_widget *vs_dialog_yesno(wstring msg,
-				slot0arg yesslot,
-				slot0arg noslot,
-				bool deflt)
+vs_widget_ref vs_dialog_yesno(const wstring &msg,
+			      slot0arg yesslot,
+			      slot0arg noslot,
+			      bool deflt)
 {
   return vs_dialog_yesno(msg,
 			 yesslot,
@@ -180,11 +183,11 @@
 }
 
 
-vscreen_widget *vs_dialog_yesno(fragment *msg,
-				slot0arg yesslot,
-				slot0arg noslot,
-				bool scrollbar,
-				bool deflt)
+vs_widget_ref vs_dialog_yesno(fragment *msg,
+			      slot0arg yesslot,
+			      slot0arg noslot,
+			      bool scrollbar,
+			      bool deflt)
 {
   return vs_dialog_yesno(msg,
 			 yesslot,
@@ -194,61 +197,61 @@
 			 deflt);
 }
 
-vscreen_widget *vs_dialog_yesno(fragment *msg,
-				slot0arg yesslot,
-				slot0arg noslot,
-				const style &st,
-				bool scrollbar,
-				bool deflt)
+vs_widget_ref vs_dialog_yesno(fragment *msg,
+			      slot0arg yesslot,
+			      slot0arg noslot,
+			      const style &st,
+			      bool scrollbar,
+			      bool deflt)
 {
   return vs_dialog_yesno(msg, yesslot, transcode(_("Yes")),
 			 noslot, transcode(_("No")), st,
 			 scrollbar, deflt);
 }
 
-vscreen_widget *vs_dialog_yesno(fragment *msg,
-				slot0arg yesslot,
-				std::wstring yeslabel,
-				slot0arg noslot,
-				std::wstring nolabel,
-				const style &st,
-				bool scrollbar,
-				bool deflt)
+vs_widget_ref vs_dialog_yesno(fragment *msg,
+			      slot0arg yesslot,
+			      const std::wstring &yeslabel,
+			      slot0arg noslot,
+			      const std::wstring &nolabel,
+			      const style &st,
+			      bool scrollbar,
+			      bool deflt)
 {
-  vscreen_widget *w;
+  vs_widget_ref w;
 
   if(scrollbar)
     {
-      vs_table *t=new vs_table;
+      vs_table_ref t = vs_table::create();
       w=t;
 
-      vs_text_layout *l=new vs_text_layout(msg);
-      vs_scrollbar *s=new vs_scrollbar(vs_scrollbar::VERTICAL);
+      vs_text_layout_ref l = vs_text_layout::create(msg);
+      vs_scrollbar_ref s = vs_scrollbar::create(vs_scrollbar::VERTICAL);
 
       t->add_widget(l, 0, 0, 1, 1, true, true);
       t->add_widget_opts(s, 0, 1, 1, 1,
 			 vs_table::ALIGN_RIGHT,
 			 vs_table::ALIGN_CENTER | vs_table::FILL);
 
-      l->location_changed.connect(sigc::mem_fun(*s, &vs_scrollbar::set_slider));
-      s->scrollbar_interaction.connect(sigc::mem_fun(*l, &vs_text_layout::scroll));
+      l->location_changed.connect(sigc::mem_fun(*s.unsafe_get_ref(), &vs_scrollbar::set_slider));
+      s->scrollbar_interaction.connect(sigc::mem_fun(*l.unsafe_get_ref(), &vs_text_layout::scroll));
     }
   else
-    w=new vs_text_layout(msg);
+    w=vs_text_layout::create(msg);
 
   return vs_dialog_yesno(w, yesslot, yeslabel, noslot, nolabel, st, deflt);
 }
 
-vscreen_widget *vs_dialog_fileview(string fn,
-				   slot0arg okslot,
-				   slotarg<sigc::slot1<void, vs_pager *> > search_slot,
-				   slotarg<sigc::slot1<void, vs_pager *> > repeat_search_slot,
-				   const style &st,
-				   const char *encoding)
-{
-  vs_file_pager *p=new vs_file_pager(fn, encoding);
-  vs_scrollbar *scrollbar=new vs_scrollbar(vs_scrollbar::VERTICAL, 0, 0);
-  vs_table *t=new vs_table;
+vs_widget_ref vs_dialog_fileview(string fn,
+				 slot0arg okslot,
+				 slotarg<sigc::slot1<void, vs_pager_ref> > search_slot,
+				 slotarg<sigc::slot1<void, vs_pager_ref> > repeat_search_slot,
+				 const style &st,
+				 const char *encoding)
+{
+  vs_file_pager_ref p = vs_file_pager::create(fn, encoding);
+  vs_scrollbar_ref scrollbar = vs_scrollbar::create(vs_scrollbar::VERTICAL, 0, 0);
+  vs_table_ref t = vs_table::create();
 
   t->add_widget_opts(p, 0, 0, 1, 1,
 		     vs_table::EXPAND | vs_table::FILL | vs_table::SHRINK | vs_table::ALIGN_CENTER,
@@ -259,9 +262,9 @@
 
   //t->set_bg_style(style_attrs_off(A_REVERSE));
 
-  p->line_changed.connect(sigc::mem_fun(*scrollbar, &vs_scrollbar::set_slider));
+  p->line_changed.connect(sigc::mem_fun(*scrollbar.unsafe_get_ref(), &vs_scrollbar::set_slider));
   p->do_line_signal();
-  scrollbar->scrollbar_interaction.connect(sigc::mem_fun(*p, &vs_pager::scroll_page));
+  scrollbar->scrollbar_interaction.connect(sigc::mem_fun(*p.unsafe_get_ref(), &vs_pager::scroll_page));
 
   if(search_slot)
     p->connect_key("Search", &global_bindings, sigc::bind(*search_slot, p));
@@ -272,11 +275,11 @@
   return vs_dialog_ok(t, okslot, transcode(_("Ok")), st);
 }
 
-vscreen_widget *vs_dialog_fileview(string fn,
-				   slot0arg okslot,
-				   slotarg<sigc::slot1<void, vs_pager *> > search_slot,
-				   slotarg<sigc::slot1<void, vs_pager *> > repeat_search_slot,
-				   const char *encoding)
+vs_widget_ref vs_dialog_fileview(string fn,
+				 slot0arg okslot,
+				 slotarg<sigc::slot1<void, vs_pager_ref> > search_slot,
+				 slotarg<sigc::slot1<void, vs_pager_ref> > repeat_search_slot,
+				 const char *encoding)
 {
   return vs_dialog_fileview(fn, okslot, search_slot, repeat_search_slot,
 			    style_attrs_flip(A_REVERSE),
@@ -289,27 +292,27 @@
   realslot();
 }
 
-static void also_do_dialog_string(vs_editline *e,
+static void also_do_dialog_string(const vs_editline_ref &e,
 				  sigc::slot1<void, wstring> thestrslot)
 {
   e->add_to_history(e->get_text());
   thestrslot(e->get_text());
 }
 
-vscreen_widget *vs_dialog_string(vscreen_widget *msg,
-				 wstring deflt,
-				 slotarg<sigc::slot1<void, wstring> > slot,
-				 slotarg<sigc::slot0<void> > cancel_slot,
-				 slotarg<sigc::slot1<void, wstring> > changed_slot,
-				 vs_editline::history_list *history,
-				 const style &st)
-{
-  vs_table *t=new vs_table;
-  vs_editline *e=new vs_editline(rootwin.getmaxx()-6, L"", deflt, history);
-  vs_button *bok=new vs_button(_("Ok"));
-  vs_button *bcancel=new vs_button(_("Cancel"));
-  vs_frame *f=new vs_frame(t);
-  vs_center *c=new vs_center(f);
+vs_widget_ref vs_dialog_string(const vs_widget_ref &msg,
+			       wstring deflt,
+			       slotarg<sigc::slot1<void, wstring> > slot,
+			       slotarg<sigc::slot0<void> > cancel_slot,
+			       slotarg<sigc::slot1<void, wstring> > changed_slot,
+			       vs_editline::history_list *history,
+			       const style &st)
+{
+  vs_table_ref t = vs_table::create();
+  vs_editline_ref e = vs_editline::create(rootwin.getmaxx()-6, L"", deflt, history);
+  vs_button_ref bok = vs_button::create(_("Ok"));
+  vs_button_ref bcancel = vs_button::create(_("Cancel"));
+  vs_frame_ref f = vs_frame::create(t);
+  vs_center_ref c = vs_center::create(f);
 
   f->set_bg_style(st);
 
@@ -330,27 +333,27 @@
   t->connect_key_post("Cancel", &global_bindings,
 		      bcancel->pressed.make_slot());
 
-  bok->pressed.connect(sigc::mem_fun(*c, &vscreen_widget::destroy));
+  bok->pressed.connect(sigc::mem_fun(*c.unsafe_get_ref(), &vscreen_widget::destroy));
   if(slot)
     bok->pressed.connect(sigc::bind(sigc::ptr_fun(also_do_dialog_string),
 				    e, *slot));
 
-  bcancel->pressed.connect(sigc::mem_fun(*c, &vscreen_widget::destroy));
+  bcancel->pressed.connect(sigc::mem_fun(*c.unsafe_get_ref(), &vscreen_widget::destroy));
   if(cancel_slot)
     bcancel->pressed.connect(*cancel_slot);
 
   return c;
 }
 
-vscreen_widget *vs_dialog_string(fragment *msg,
-				 wstring deflt,
-				 slotarg<sigc::slot1<void, wstring> > slot,
-				 slotarg<sigc::slot0<void> > cancel_slot,
-				 slotarg<sigc::slot1<void, wstring> > changed_slot,
-				 vs_editline::history_list *history,
-				 const style &st)
+vs_widget_ref vs_dialog_string(fragment *msg,
+			       const wstring &deflt,
+			       slotarg<sigc::slot1<void, wstring> > slot,
+			       slotarg<sigc::slot0<void> > cancel_slot,
+			       slotarg<sigc::slot1<void, wstring> > changed_slot,
+			       vs_editline::history_list *history,
+			       const style &st)
 {
-  return vs_dialog_string(new vs_label(msg),
+  return vs_dialog_string(vs_label::create(msg),
 			  deflt,
 			  slot,
 			  cancel_slot,
@@ -359,15 +362,15 @@
 			  st);
 }
 
-vscreen_widget *vs_dialog_string(wstring msg,
-				 wstring deflt,
-				 slotarg<sigc::slot1<void, wstring> > slot,
-				 slotarg<sigc::slot0<void> > cancel_slot,
-				 slotarg<sigc::slot1<void, wstring> > changed_slot,
-				 vs_editline::history_list *history,
-				 const style &st)
+vs_widget_ref vs_dialog_string(const wstring &msg,
+			       const wstring &deflt,
+			       slotarg<sigc::slot1<void, wstring> > slot,
+			       slotarg<sigc::slot0<void> > cancel_slot,
+			       slotarg<sigc::slot1<void, wstring> > changed_slot,
+			       vs_editline::history_list *history,
+			       const style &st)
 {
-  return vs_dialog_string(new vs_label(msg),
+  return vs_dialog_string(vs_label::create(msg),
 			  deflt,
 			  slot,
 			  cancel_slot,
@@ -376,12 +379,12 @@
 			  st);
 }
 
-vscreen_widget *vs_dialog_string(wstring msg,
-				 wstring deflt,
-				 slotarg<sigc::slot1<void, wstring> > slot,
-				 slotarg<sigc::slot0<void> > cancel_slot,
-				 slotarg<sigc::slot1<void, wstring> > changed_slot,
-				 vs_editline::history_list *history)
+vs_widget_ref vs_dialog_string(const wstring &msg,
+			       const wstring &deflt,
+			       slotarg<sigc::slot1<void, wstring> > slot,
+			       slotarg<sigc::slot0<void> > cancel_slot,
+			       slotarg<sigc::slot1<void, wstring> > changed_slot,
+			       vs_editline::history_list *history)
 {
   return vs_dialog_string(msg,
 			  deflt,

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vs_util.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vs_util.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vs_util.h	Sun Aug  7 03:20:15 2005
@@ -8,6 +8,7 @@
 #ifndef VS_UTIL_H
 #define VS_UTIL_H
 
+#include "ref_ptr.h"
 #include "slotarg.h"
 #include "vs_editline.h"
 
@@ -18,6 +19,8 @@
 class vscreen_widget;
 class vs_pager;
 
+typedef ref_ptr<vscreen_widget> vs_widget_ref;
+
 // Canned dialog-boxes:
 
 /** Create a dialog box with a single button.
@@ -31,20 +34,20 @@
  *  \param attr the attributes to use for the background of the dialog
  *  box, defaults to reverse-video of DefaultWidgetBackground.
  */
-vscreen_widget *vs_dialog_ok(vscreen_widget *widget,
-			     slot0arg okslot, std::wstring label,
-			     const style &st);
-
-vscreen_widget *vs_dialog_ok(fragment *msg, slot0arg okslot=NULL, bool scrollbar=false);
-vscreen_widget *vs_dialog_ok(fragment *msg, slot0arg okslot, const style &st, bool scrollbar=false);
-vscreen_widget *vs_dialog_ok(fragment *msg, slot0arg okslot, std::wstring label,
-			     const style &st, bool scrollbar=false);
-
-vscreen_widget *vs_dialog_ok(std::wstring msg, slot0arg okslot=NULL);
-vscreen_widget *vs_dialog_ok(std::wstring msg, slot0arg okslot,
-			     const style &st);
-vscreen_widget *vs_dialog_ok(std::wstring msg, slot0arg okslot, std::wstring label,
-			     const style &st);
+vs_widget_ref vs_dialog_ok(const vs_widget_ref &widget,
+			   slot0arg okslot, const std::wstring &label,
+			   const style &st);
+
+vs_widget_ref vs_dialog_ok(fragment *msg, slot0arg okslot=NULL, bool scrollbar=false);
+vs_widget_ref vs_dialog_ok(fragment *msg, slot0arg okslot, const style &st, bool scrollbar=false);
+vs_widget_ref vs_dialog_ok(fragment *msg, slot0arg okslot, const std::wstring &label,
+			   const style &st, bool scrollbar=false);
+
+vs_widget_ref vs_dialog_ok(const std::wstring &msg, slot0arg okslot=NULL);
+vs_widget_ref vs_dialog_ok(const std::wstring &msg, slot0arg okslot,
+			   const style &st);
+vs_widget_ref vs_dialog_ok(const std::wstring &msg, slot0arg okslot, const std::wstring &label,
+			   const style &st);
 
 /** Create a dialog box with two buttons, labelled "yes" and "no".
  *
@@ -64,84 +67,84 @@
  *  \param deflt if \b true, the "yes" button will be selected by default;
  *  otherwise, the "no" button will be selected by default.
  */
-vscreen_widget *vs_dialog_yesno(vscreen_widget *widget,
-				slot0arg yesslot,
-				std::wstring yeslabel,
-				slot0arg noslot,
-				std::wstring nolabel,
-				const style &st,
-				bool deflt=true);
-
-vscreen_widget *vs_dialog_yesno(fragment *msg,
-				slot0arg yesslot,
-				slot0arg noslot,
-				bool scrollbar=false,
-				bool deflt=true);
-vscreen_widget *vs_dialog_yesno(fragment *msg,
-				slot0arg yesslot,
-				slot0arg noslot,
-				const style &st,
-				bool scrollbar=false,
-				bool deflt=true);
-vscreen_widget *vs_dialog_yesno(fragment *msg,
-				slot0arg yesslot,
-				std::wstring yeslabel,
-				slot0arg noslot,
-				std::wstring nolabel,
-				const style &st,
-				bool scrollbar=false,
-				bool deflt=true);
-
-vscreen_widget *vs_dialog_yesno(std::wstring msg,
-				slot0arg yesslot,
-				slot0arg noslot,
-				bool deflt=true);
-vscreen_widget *vs_dialog_yesno(std::wstring msg,
-				slot0arg yesslot,
-				slot0arg noslot,
-				const style &st,
-				bool deflt=true);
-vscreen_widget *vs_dialog_yesno(std::wstring msg,
-				slot0arg yesslot,
-				std::wstring yeslabel,
-				slot0arg noslot,
-				std::wstring nolabel,
-				const style &st,
-				bool deflt=true);
-
-vscreen_widget *vs_dialog_fileview(std::string fn,
-				   slot0arg okslot=NULL,
-				   slotarg<sigc::slot1<void, vs_pager *> > search_slot=NULL,
-				   slotarg<sigc::slot1<void, vs_pager *> > repeat_search_slot=NULL,
-				   const char *encoding=NULL);
-vscreen_widget *vs_dialog_fileview(std::string fn,
-				   slot0arg okslot,
-				   slotarg<sigc::slot1<void, vs_pager *> > search_slot,
-				   slotarg<sigc::slot1<void, vs_pager *> > repeat_search_slot,
-				   const style &st,
-				   const char *encoding=NULL);
-
-vscreen_widget *vs_dialog_string(fragment *msg,
-				 std::wstring deflt,
-				 slotarg<sigc::slot1<void, std::wstring> > okslot,
-				 slotarg<sigc::slot0<void> > cancel_slot,
-				 slotarg<sigc::slot1<void, std::wstring> > changed_slot,
-				 vs_editline::history_list *history,
-				 const style &st);
-
-vscreen_widget *vs_dialog_string(std::wstring msg,
-				 std::wstring deflt,
-				 slotarg<sigc::slot1<void, std::wstring> > okslot,
-				 slotarg<sigc::slot0<void> > cancel_slot,
-				 slotarg<sigc::slot1<void, std::wstring> > changed_slot,
-				 vs_editline::history_list *history,
-				 const style &st);
-
-vscreen_widget *vs_dialog_string(std::wstring msg,
-				 std::wstring deflt,
-				 slotarg<sigc::slot1<void, std::wstring> > slot,
-				 slotarg<sigc::slot0<void> > cancel_slot,
-				 slotarg<sigc::slot1<void, std::wstring> > changed_slot,
-				 vs_editline::history_list *history);
+vs_widget_ref vs_dialog_yesno(vscreen_widget *widget,
+			      slot0arg yesslot,
+			      const std::wstring &yeslabel,
+			      slot0arg noslot,
+			      const std::wstring &nolabel,
+			      const style &st,
+			      bool deflt=true);
+
+vs_widget_ref vs_dialog_yesno(fragment *msg,
+			      slot0arg yesslot,
+			      slot0arg noslot,
+			      bool scrollbar=false,
+			      bool deflt=true);
+vs_widget_ref vs_dialog_yesno(fragment *msg,
+			      slot0arg yesslot,
+			      slot0arg noslot,
+			      const style &st,
+			      bool scrollbar=false,
+			      bool deflt=true);
+vs_widget_ref vs_dialog_yesno(fragment *msg,
+			      slot0arg yesslot,
+			      const std::wstring &yeslabel,
+			      slot0arg noslot,
+			      const std::wstring &nolabel,
+			      const style &st,
+			      bool scrollbar=false,
+			      bool deflt=true);
+
+vs_widget_ref vs_dialog_yesno(const std::wstring &msg,
+			      slot0arg yesslot,
+			      slot0arg noslot,
+			      bool deflt=true);
+vs_widget_ref vs_dialog_yesno(const std::wstring &msg,
+			      slot0arg yesslot,
+			      slot0arg noslot,
+			      const style &st,
+			      bool deflt=true);
+vs_widget_ref vs_dialog_yesno(const std::wstring &msg,
+			      slot0arg yesslot,
+			      const std::wstring &yeslabel,
+			      slot0arg noslot,
+			      const std::wstring &nolabel,
+			      const style &st,
+			      bool deflt=true);
+
+vs_widget_ref vs_dialog_fileview(const std::string &fn,
+				 slot0arg okslot=NULL,
+				 slotarg<sigc::slot1<void, vs_pager *> > search_slot=NULL,
+				 slotarg<sigc::slot1<void, vs_pager *> > repeat_search_slot=NULL,
+				 const char *encoding=NULL);
+vs_widget_ref vs_dialog_fileview(const std::string &fn,
+				 slot0arg okslot,
+				 slotarg<sigc::slot1<void, vs_pager *> > search_slot,
+				 slotarg<sigc::slot1<void, vs_pager *> > repeat_search_slot,
+				 const style &st,
+				 const char *encoding=NULL);
+
+vs_widget_ref vs_dialog_string(fragment *msg,
+			       const std::wstring &deflt,
+			       slotarg<sigc::slot1<void, std::wstring> > okslot,
+			       slotarg<sigc::slot0<void> > cancel_slot,
+			       slotarg<sigc::slot1<void, std::wstring> > changed_slot,
+			       vs_editline::history_list *history,
+			       const style &st);
+
+vs_widget_ref vs_dialog_string(const std::wstring &msg,
+			       const std::wstring &deflt,
+			       slotarg<sigc::slot1<void, std::wstring> > okslot,
+			       slotarg<sigc::slot0<void> > cancel_slot,
+			       slotarg<sigc::slot1<void, std::wstring> > changed_slot,
+			       vs_editline::history_list *history,
+			       const style &st);
+
+vs_widget_ref vs_dialog_string(const std::wstring &msg,
+			       const std::wstring &deflt,
+			       slotarg<sigc::slot1<void, std::wstring> > slot,
+			       slotarg<sigc::slot0<void> > cancel_slot,
+			       slotarg<sigc::slot1<void, std::wstring> > changed_slot,
+			       vs_editline::history_list *history);
 
 #endif

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vscreen.cc
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vscreen.cc	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vscreen.cc	Sun Aug  7 03:20:15 2005
@@ -98,7 +98,7 @@
 // Cheesy way of generating mostly-unique IDs for timeouts -- just incremented 
 // once for every timeout that gets added.
 
-static vscreen_widget *toplevel=NULL;
+static vs_widget_ref toplevel = NULL;
 // The widget which is displayed as the root of everything
 
 //static bool resized=false;
@@ -170,9 +170,9 @@
 }
 ///////////////////////////////////////////////////////////////////////////////
 
-void vscreen_settoplevel(vscreen_widget *w)
+void vscreen_settoplevel(const vs_widget_ref &w)
 {
-  if(toplevel)
+  if(toplevel.valid())
     toplevel->unfocussed();
 
   toplevel=w;
@@ -329,7 +329,7 @@
 
   set_style("TreeBackground", style());
 
-  if(toplevel)
+  if(toplevel.valid())
     vscreen_settoplevel(toplevel);
 
   pthread_mutexattr_t vscreen_mutex_attr;
@@ -448,7 +448,7 @@
 
 void vscreen_updatenow()
 {
-  if(toplevel)
+  if(toplevel.valid())
     {
       toplevel->display(get_style("Default"));
       toplevel->sync();
@@ -492,7 +492,7 @@
   sigemptyset(&signals);
   sigaddset(&signals, SIGWINCH);
 
-  if(toplevel)
+  if(toplevel.valid())
     {
       wint_t wch = 0;
       int status;
@@ -517,7 +517,7 @@
 	      MEVENT ev;
 	      getmouse(&ev);
 
-	      if(toplevel)
+	      if(toplevel.valid())
 		{
 		  toplevel->dispatch_mouse(ev.id, ev.x, ev.y, ev.z, ev.bstate);
 		  main_hook();
@@ -526,7 +526,7 @@
 	    }
 	  else if(global_bindings.key_matches(k, "Refresh"))
 	    vscreen_redraw();
-	  else if(toplevel)
+	  else if(toplevel.valid())
 	    {
 	      toplevel->dispatch_key(k);
 	      main_hook();
@@ -566,14 +566,14 @@
   // flushed.
   vscreen_tryupdate();
 
-  while(!should_exit && toplevel)
+  while(!should_exit && toplevel.valid())
     {
       sigset_t prevsignals;
 
       assert(toplevel->get_win());
 
       int prevtimeout=toplevel->timeout(vscreen_mindelay());
-      vscreen_widget *curwidget=toplevel;
+      vs_widget_ref curwidget=toplevel;
       // Note that something bad might happen while we don't have the mutex..
       // OTOH, it's perfectly okay to dispatch the character to an unexpected
       // location; I just want to be sure that I reset the timeout of the
@@ -611,7 +611,7 @@
 	  MEVENT ev;
 	  getmouse(&ev);
 
-	  if(toplevel)
+	  if(toplevel.valid())
 	    {
 	      toplevel->dispatch_mouse(ev.id, ev.x, ev.y, ev.z, ev.bstate);
 	      main_hook();
@@ -620,16 +620,13 @@
 	}
       else if(global_bindings.key_matches(k, "Refresh"))
 	vscreen_redraw();
-      else if(result!=ERR && toplevel)
+      else if(result!=ERR && toplevel.valid())
 	{
 	  toplevel->dispatch_key(k);
 	  main_hook();
 	  vscreen_tryupdate();
 	}
 
-      if(main_level==1)
-	vscreen_widget::handle_pending_deletes();
-
       sigprocmask(SIG_SETMASK, &prevsignals, NULL);
     }
 
@@ -647,7 +644,7 @@
 
 void vscreen_suspend_without_signals()
 {
-  if(toplevel)
+  if(toplevel.valid())
     toplevel->set_owner_window(NULL, 0, 0, 0, 0);
   endwin();
   curses_avail=false;
@@ -680,7 +677,7 @@
     }
 
   curses_avail=true;
-  if(toplevel)
+  if(toplevel.valid())
     {
       toplevel->set_owner_window(rootwin, 0, 0, rootwin.getmaxx(), rootwin.getmaxy());
       toplevel->display(get_style("Default"));
@@ -700,7 +697,7 @@
 
 void vscreen_redraw()
 {
-  if(toplevel)
+  if(toplevel.valid())
     {
       toplevel->focussed();
       toplevel->get_win().touch();

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vscreen.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vscreen.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vscreen.h	Sun Aug  7 03:20:15 2005
@@ -29,6 +29,8 @@
 
 #include <sigc++/signal.h>
 
+#include "ref_ptr.h"
+
 class vscreen_widget;
 
 void vscreen_init();
@@ -39,7 +41,7 @@
 // cleanly shut the program down.  This can be called after the
 // program starts to re-initialize the display code.
 
-void vscreen_settoplevel(vscreen_widget *widget);
+void vscreen_settoplevel(const ref_ptr<vscreen_widget> &widget);
 // Changes the toplevel widget
 
 void vscreen_queuelayout();

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vscreen_widget.cc
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vscreen_widget.cc	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vscreen_widget.cc	Sun Aug  7 03:20:15 2005
@@ -23,7 +23,6 @@
 using namespace std;
 
 // Queues of things that Need To Be Done
-static set<vscreen_widget *> todelete;
 static list<vscreen_widget *> toresize;
 
 vscreen_widget::vscreen_widget()
@@ -31,9 +30,11 @@
    timeout_value(0),
    owner(NULL),
    geom(0,0,0,0),
+   refcount(0),
    visible(false),
    isfocussed(false),
-   pre_display_erase(true)
+   pre_display_erase(true),
+   is_destroyed(false)
 {
   focussed.connect(sigc::bind(sigc::mem_fun(*this, &vscreen_widget::set_isfocussed), true));
   unfocussed.connect(sigc::bind(sigc::mem_fun(*this, &vscreen_widget::set_isfocussed), false));
@@ -42,6 +43,7 @@
 vscreen_widget::~vscreen_widget()
 {
   assert(!owner);
+  assert(is_destroyed);
 }
 
 void vscreen_widget::set_bg_style(const style &new_style)
@@ -60,15 +62,6 @@
   isfocussed=_isfocussed;
 }
 
-void vscreen_widget::handle_pending_deletes()
-{
-  for(set<vscreen_widget *>::iterator i=todelete.begin();
-      i!=todelete.end(); i++)
-    delete *i;
-
-  todelete.erase(todelete.begin(), todelete.end());
-}
-
 void vscreen_widget::set_owner_window(cwindow _win, int x, int y, int w, int h)
 {
   if(_win)
@@ -82,6 +75,8 @@
 	win=NULL;
       else
 	{
+	  assert(!is_destroyed);
+
 	  win=_win.derwin(geom.h,
 			  geom.w,
 			  geom.y,
@@ -108,9 +103,6 @@
 {
   owner=_owner;
   alloc_size(0,0,0,0);
-
-  if(owner==NULL)
-    destroy();
 }
 
 int vscreen_widget::timeout(int msecs)
@@ -124,9 +116,11 @@
 
 void vscreen_widget::destroy()
 {
-  if(todelete.find(this) != todelete.end())
+  if(is_destroyed)
     return;
 
+  is_destroyed = true;
+
   hide();
 
   if(owner)
@@ -144,12 +138,13 @@
   do_layout.clear();
   focussed.clear();
   unfocussed.clear();
-
-  todelete.insert(this);
 }
 
 void vscreen_widget::show()
 {
+  if(is_destroyed)
+    return;
+
   visible=true;
 
   shown_sig();
@@ -157,11 +152,17 @@
 
 void vscreen_widget::show_all()
 {
+  if(is_destroyed)
+    return;
+
   show();
 }
 
 void vscreen_widget::hide()
 {
+  if(is_destroyed)
+    return;
+
   visible=false;
 
   hidden_sig();
@@ -169,6 +170,9 @@
 
 void vscreen_widget::display(const style &st)
 {
+  if(is_destroyed)
+    return;
+
   // Erase our window, using the composition of the surrounding style
   // and our background style.
   style basic_st=st+bg_style;
@@ -186,11 +190,17 @@
 
 bool vscreen_widget::focus_me()
 {
+  if(is_destroyed)
+    return false;
+
   return !auxillary_bindings.empty();
 }
 
 bool vscreen_widget::handle_key(const key &k)
 {
+  if(is_destroyed)
+    return false;
+
   bool rval=false;
 
   for(key_connection i=auxillary_post_bindings.begin();
@@ -207,6 +217,9 @@
 
 bool vscreen_widget::dispatch_key(const key &k)
 {
+  if(is_destroyed)
+    return false;
+
   bool rval=false;
 
   for(key_connection i=auxillary_bindings.begin();

Modified: branches/aptitude-0.3/aptitude/src/vscreen/vscreen_widget.h
==============================================================================
--- branches/aptitude-0.3/aptitude/src/vscreen/vscreen_widget.h	(original)
+++ branches/aptitude-0.3/aptitude/src/vscreen/vscreen_widget.h	Sun Aug  7 03:20:15 2005
@@ -1,20 +1,40 @@
 // vscreen_widget.h  -*-c++-*-
 //
-// "widgets" are sort of what they sound like -- entities that get drawn on the
-// screen in some stacked order and can grab keyboard input.  By default, the
-// widget currently on the top of the stack has keyboard "focus".  (overriding
-// this may be an option eventually but isn't right now)
-// (the widget with keyboard focus gets to determine cursor information)
+//   Copyright (C) 2000-2005 Daniel Burrows
 //
-//  A note on memory management: to avoid problems with references to widgets
-// remaining on the stack, widget destructions are queued for later handling.
-// handle_pending_deletes should be called when it's safe to do so (ie, in the
-// main loop)
+//   This program is free software; you can redistribute it and/or
+//   modify it under the terms of the GNU General Public License as
+//   published by the Free Software Foundation; either version 2 of
+//   the License, or (at your option) any later version.
 //
-//  I could maybe override the delete operator (??), but that would be
-// confusing; instead, I ask that widget deletion go through the "destroy"
-// routine.  I don't think it's possible to enforce this via the compiler, but
-// please do; Bad Things may happen if you don't..
+//   This program is distributed in the hope that it will be useful,
+//   but WITHOUT ANY WARRANTY; without even the implied warranty of
+//   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
+//   General Public License for more details.
+//
+//   You should have received a copy of the GNU General Public License
+//   along with this program; see the file COPYING.  If not, write to
+//   the Free Software Foundation, Inc., 59 Temple Place - Suite 330,
+//   Boston, MA 02111-1307, USA.
+//
+// "widgets" are sort of what they sound like -- entities that get
+// drawn on the screen in some stacked order and can grab keyboard
+// input.  By default, the widget currently on the top of the stack
+// has keyboard "focus".  (overriding this may be an option eventually
+// but isn't right now) (the widget with keyboard focus gets to
+// determine cursor information)
+//
+//
+// Lifetime of a widget: a widget is potentially active and visible
+// until it is destroyed (via the destroy() method).  Once a widget
+// has been destroyed, you cannot un-destroy it, but further calls to
+// destroy() are allowed until the widget is deleted for good.
+// Widgets should generally be referred to using ref_ptr objects; to
+// enforce this, widgets can only be allocated via W::create(...).  Of
+// course, as with any refcounting scheme, it's the user's
+// responsibility to prevent cycles by using unsafe_get_ref()
+// appropriately.  For instance, pointers to the widget's parent have
+// to be created this way.
 
 #ifndef VSCREEN_WIDGET_H
 #define VSCREEN_WIDGET_H
@@ -27,6 +47,9 @@
 
 #include "curses++.h"
 #include "config/style.h"
+#include "ref_ptr.h"
+
+#include <assert.h>
 
 class vs_container;
 class key;
@@ -53,6 +76,10 @@
 
 class keybindings;
 
+/** The basic widget interface.  Note that due to the current
+ *  reference counting implementation, this is not presently
+ *  threadsafe.
+ */
 class vscreen_widget:virtual public sigc::trackable
 {
   friend class vs_container;
@@ -61,7 +88,7 @@
   friend bool vscreen_poll();
   friend void vscreen_mainloop(int);
   friend void vscreen_redraw();
-  friend void vscreen_settoplevel(vscreen_widget *);
+  friend void vscreen_settoplevel(const ref_ptr<vscreen_widget> &);
   friend void vscreen_suspend_without_signals();
   friend void vscreen_resume();
   friend void vscreen_updatecursornow();
@@ -97,6 +124,11 @@
   /** The basic style attached to this widget. */
   style bg_style;
 
+  /** The number of live references to this object.  This is initially
+   *  0, to support the use of the generic refcounting wrapper.
+   */
+  mutable int refcount;
+
   // Whether the widget is visible (distinct from whether it has a window;
   // answers the question "should this widget have a window?")
   bool visible:1;
@@ -109,6 +141,8 @@
    */
   bool pre_display_erase:1;
 
+  bool is_destroyed:1;
+
   // Used to set the owner-window without setting the owner.  Used only
   // to handle the toplevel widget (which has a window but no owner)
   // Like alloc_size
@@ -134,7 +168,28 @@
    *  returned, further processing of the key will be performed.
    */
   virtual bool handle_key(const key &k);
+
+protected:
+  vscreen_widget();
+
 public:
+  void incref()
+  {
+    ++refcount;
+  }
+
+  void decref()
+  {
+    assert(refcount > 0);
+
+    --refcount;
+    if(refcount == 0)
+      {
+	destroy();
+	delete this;
+      }
+  }
+
   static void handle_pending_deletes();
 
   // show() and hide() do the expected.  show_all() makes a container show
@@ -161,8 +216,6 @@
       }
   }
 
-  vscreen_widget();
-
   virtual ~vscreen_widget();
 
   // This should be called when an arbitrary widget is to have a
@@ -446,5 +499,6 @@
   // Sent when we gain or lose the keyboard focus.
 };
 
-#endif
+typedef ref_ptr<vscreen_widget> vs_widget_ref;
 
+#endif



More information about the Aptitude-svn-commit mailing list