[1022] in BarnOwl Developers
[D-O-H] r1006 - branches/barnowl_sqlite/owl
daemon@ATHENA.MIT.EDU (nelhage@MIT.EDU)
Thu Oct 29 18:12:13 2009
Resent-From: nelhage@mit.edu
Resent-To: barnowl-dev-mtg@charon.mit.edu
X-Original-To: nelhage@nelhage.com
To: dirty-owl-hackers@MIT.EDU
From: nelhage@MIT.EDU
Reply-to: dirty-owl-hackers@MIT.EDU
Date: Wed, 2 Apr 2008 00:42:24 -0400 (EDT)
Author: nelhage
Date: 2008-04-02 00:42:24 -0400 (Wed, 02 Apr 2008)
New Revision: 1006
Modified:
branches/barnowl_sqlite/owl/perlwrap.pm
Log:
First pass at lazily populating views.
This is minimally tested, doesn't work for many cases, and can
crash. But that's why this is an experimental branch, and it does
sorta work.
Modified: branches/barnowl_sqlite/owl/perlwrap.pm
===================================================================
--- branches/barnowl_sqlite/owl/perlwrap.pm 2008-04-02 04:42:21 UTC (rev 1005)
+++ branches/barnowl_sqlite/owl/perlwrap.pm 2008-04-02 04:42:24 UTC (rev 1006)
@@ -412,10 +412,14 @@
package BarnOwl::View;
-sub get_name {return shift->{name}};
-sub messages {return shift->{messages}};
-sub get_filter {return shift->{filter}};
+sub get_name {shift->{name}};
+sub messages {shift->{messages}};
+sub get_filter {shift->{filter}};
+sub at_start {shift->{at_start}};
+sub at_end {shift->{at_end}};
+sub offset {shift->{offset}};
+
sub new {
my $class = shift;
my $name = shift;
@@ -431,6 +435,7 @@
sub consider_message {
my $self = shift;
my $msg = shift;
+ return unless $self->at_end;
if(BarnOwl::filter_message_match($self->get_filter, $msg)) {
push @{$self->messages}, $msg;
}
@@ -438,14 +443,71 @@
sub recalculate {
my $self = shift;
- my $ml = BarnOwl::message_list();
- $ml->iterate_begin(0, 0);
$self->{messages} = [];
- while(my $msg = $ml->iterate_next) {
- $self->consider_message($msg);
+ $self->{at_start} = $self->{at_end} = 0;
+ $self->{offset} = 0;
+}
+
+sub recalculate_around {
+ my $self = shift;
+ my $where = shift;
+ if($where == 0) {
+ $self->{at_start} = 1;
+ $self->fill_forward(0);
+ } elsif($where < 0) {
+ $self->{at_end} = 1;
+ $self->fill_back(-1);
+ } else {
+ $self->fill_back($where);
+ $self->fill_forward;
}
}
+my $FILL_STEP = 100;
+
+sub fill_back {
+ my $self = shift;
+ my $pos = shift || $self->messages->[0] - 1;
+ my $ml = BarnOwl::message_list();
+ return if $self->at_start;
+ $ml->iterate_begin($pos, 1);
+ my $count = 0;
+ while($count < $FILL_STEP) {
+ my $m = $ml->iterate_next;
+ unless(defined $m) {
+ $self->{at_start} = 1;
+ last;
+ }
+ if(BarnOwl::filter_message_match($self->get_filter, $m)) {
+ $self->{offset}++;
+ $count++;
+ unshift @{$self->messages}, $m
+ }
+ }
+ $ml->iterate_done;
+}
+
+sub fill_forward {
+ my $self = shift;
+ my $pos = shift || $self->messages->[-1] + 1;
+ my $ml = BarnOwl::message_list();
+ return if $self->at_end;
+ $ml->iterate_begin($pos, 0);
+ my $count = 0;
+ while($count < $FILL_STEP) {
+ my $m = $ml->iterate_next;
+ unless(defined $m) {
+ $self->{at_end} = 1;
+ last;
+ }
+ if(BarnOwl::filter_message_match($self->get_filter, $m)) {
+ $count++;
+ push @{$self->messages}, $m
+ }
+ }
+ $ml->iterate_done;
+}
+
sub new_filter {
my $self = shift;
my $filter = shift;
@@ -470,6 +532,10 @@
sub view {return shift->{view}}
sub index {return shift->{index}}
+sub eff_index {
+ my $self = shift;
+ return $self->index + $self->view->offset;
+}
sub new {
my $class = shift;
@@ -491,13 +557,15 @@
my $view = shift;
$self->{view} = $view;
$self->{index} = 0;
+ $view->recalculate_around(0);
}
sub initialize_at_end {
my $self = shift;
my $view = shift;
$self->{view} = $view;
- $self->{index} = $self->view->_size - 1;
+ $self->{index} = 0;
+ $view->recalculate_around(-1);
}
sub initialize_at_id {
@@ -505,8 +573,8 @@
my $view = shift;
my $id = shift;
$self->{view} = $view;
- my $list = $self->view->messages;
- $self->{index} = BarnOwl::MessageList::binsearch($list, $id, sub{shift->id});
+ $self->{index} = 0;
+ $view->recalculate_around($id);
}
sub clone {
@@ -518,21 +586,25 @@
sub has_prev {
my $self = shift;
+ $self->fill_back;
return $self->index > 0;
}
sub has_next {
my $self = shift;
+ $self->fill_forward;
return $self->index < $self->view->_size - 1;
}
sub at_start {
my $self = shift;
+ $self->fill_back;
return $self->index < 0;
}
sub at_end {
my $self = shift;
+ $self->fill_forward;
return $self->index >= $self->view->_size;
}
@@ -556,9 +628,23 @@
sub get_message {
my $self = shift;
- return $self->view->messages->[$self->index];
+ return $self->view->messages->[$self->eff_index];
}
+sub fill_back {
+ my $self = shift;
+ if($self->eff_index == 0) {
+ $self->view->fill_back;
+ }
+}
+
+sub fill_forward {
+ my $self = shift;
+ if($self->eff_index == (scalar @{$self->view->messages}) - 1) {
+ $self->view->fill_forward;
+ }
+}
+
sub cmp {
my $self = shift;
my $other = shift;