change listview/grid so that members of a grid can have actions by default, it will...
groditi [Sat, 11 Oct 2008 21:00:05 +0000 (21:00 +0000)]
lib/Reaction/UI/ViewPort/Collection.pm
lib/Reaction/UI/ViewPort/Collection/Grid.pm
lib/Reaction/UI/ViewPort/ListView.pm
lib/Reaction/UI/Widget/Collection/Grid.pm
lib/Reaction/UI/Widget/ListView.pm
share/skin/base/layout/collection/grid.tt
share/skin/base/layout/list_view.tt
share/skin/default/layout/collection/grid.tt
share/skin/default/layout/list_view.tt

index d9692ef..fef825a 100644 (file)
@@ -8,8 +8,6 @@ use aliased 'Reaction::UI::ViewPort::Object';
 use namespace::clean -except => [ qw(meta) ];
 extends 'Reaction::UI::ViewPort';
 
-
-
 has members => (is => 'rw', isa => 'ArrayRef', lazy_build => 1);
 
 has collection         => (is => 'ro', isa => IM_Collection, required   => 1);
@@ -17,29 +15,35 @@ has current_collection => (is => 'rw', isa => IM_Collection, lazy_build => 1);
 
 has member_args  => ( is => 'rw', isa => 'HashRef', lazy_build => 1);
 has member_class => ( is => 'ro', isa => 'Str',     lazy_build => 1);
+
 sub BUILD {
   my ($self, $args) = @_;
   if( my $member_args = delete $args->{Member} ){
     $self->member_args( $member_args );
   }
-};
-sub _build_member_args { {} };
+}
+
+sub _build_member_args { {} }
+
 sub _build_member_class { Object };
 
 after clear_current_collection => sub{
   shift->clear_members; #clear the members the current collection changes, duh
 };
+
 sub _build_current_collection {
   return $_[0]->collection;
-};
+}
 
 #I'm not really sure why this is here all of a sudden.
-sub model { shift->current_collection };
+sub model { shift->current_collection }
+
 sub _build_members {
   my ($self) = @_;
   my (@members, $i);
   my $args = $self->member_args;
   my $builders = {};
+  my $field_orders = {};
   my $ctx = $self->ctx;
   my $loc = join('-', $self->location, 'member');
   my $class = $self->member_class;
@@ -50,13 +54,24 @@ sub _build_members {
   for my $obj ( $self->current_collection->members ) {
     my $type = blessed $obj;
     my $builder_cache = $builders->{$type} ||= {};
+    my @order;
+    if( exists $args->{computed_field_order} ){
+      @order = (computed_field_order => $args->{computed_field_order});
+    } elsif( exists $field_orders->{$type} ) {
+      @order = (computed_field_order => $field_orders->{$type});
+    }
+
     my $member = $class->new(
-                          ctx           => $ctx,
-                          model         => $obj,
-                          location      => join('-', $loc, $i++),
-                          builder_cache => $builder_cache,
-                          %$args
-                         );
+      ctx => $ctx,
+      model => $obj,
+      location => join('-', $loc, $i++),
+      builder_cache => $builder_cache,
+      @order, %$args,
+    );
+
+    #cache to prevent the sort function from having to be run potentially
+    #hundreds of times
+    $field_orders->{$type} ||= $member->computed_field_order unless @order;
     push(@members, $member);
   }
   return \@members;
index 329dc18..95e341e 100644 (file)
@@ -3,29 +3,48 @@ package Reaction::UI::ViewPort::Collection::Grid;
 use Reaction::Class;
 
 use aliased 'Reaction::InterfaceModel::Collection' => 'IM_Collection';
-use aliased 'Reaction::UI::ViewPort::Collection::Grid::Member';
+use aliased 'Reaction::UI::ViewPort::Collection::Grid::Member::WithActions';
 
 use namespace::clean -except => [ qw(meta) ];
 extends 'Reaction::UI::ViewPort::Collection';
 
-
-
-has field_order     => ( is => 'ro', isa => 'ArrayRef', lazy_build => 1);
+has field_order => ( is => 'ro', isa => 'ArrayRef', lazy_build => 1);
 has excluded_fields => ( is => 'ro', isa => 'ArrayRef', lazy_build => 1);
+has computed_field_order => (is => 'ro', isa => 'ArrayRef', lazy_build => 1);
+
 has _raw_field_labels => (
-  is       => 'rw', isa => 'HashRef',
+  is => 'rw',
+  isa => 'HashRef',
   init_arg => 'field_labels',
-  default  => sub { {} },
+  default => sub { {} },
 );
+
 has field_labels => (
-  is         => 'ro', isa => 'HashRef',
-  lazy_build => 1, init_arg => undef,
+  is => 'ro',
+  isa => 'HashRef',
+  lazy_build => 1,
+  init_arg => undef,
 );
 
-has computed_field_order => (is => 'ro', isa => 'ArrayRef', lazy_build => 1);
+has member_action_count => (
+  is => 'rw',
+  isa => 'Int',
+  required => 1,
+  lazy => 1,
+  default => sub {
+    my $self = shift;
+    for (@{ $self->members }) {
+      my $protos = $_->action_prototypes;
+      return scalar(@$protos);
+      #return scalar(keys(%$protos));
+    }
+    return 1;
+  },
+);
 
 ####################################
-sub _build_member_class { Member };
+sub _build_member_class { WithActions };
+
 sub _build_field_labels {
   my $self = shift;
   my %labels = %{$self->_raw_field_labels};
@@ -34,9 +53,14 @@ sub _build_field_labels {
     $labels{$field} = join(' ', map{ ucfirst } split('_', $field));
   }
   return \%labels;
-};
-sub _build_field_order { []; };
-sub _build_excluded_fields { []; };
+}
+
+sub _build_field_order { []; }
+
+sub _build_excluded_fields { []; }
+
+#this is a total clusterfuck and it sucks we should just eliminate it and have
+# the grid members not render ArrayRef or Collection fields
 sub _build_computed_field_order {
   my ($self) = @_;
   my %excluded = map { $_ => undef } @{ $self->excluded_fields };
@@ -53,11 +77,24 @@ sub _build_computed_field_order {
         $self->current_collection->member_type->parameter_attributes;
 
   return $self->sort_by_spec($self->field_order, \@names);
-};
+}
 
-before _build_members => sub {
-  my ($self) = @_;
+around _build_members => sub {
+  my $orig = shift;
+  my $self = shift;
   $self->member_args->{computed_field_order} ||= $self->computed_field_order;
+#  $self->member_args->{computed_action_order} ||= [];
+  my $members = $self->$orig(@_);
+
+  # cache everything yo
+#  for my $member (@$members){
+#    $member->clear_computed_action_order;
+#    my $order = $member->computed_action_order;
+#    @{ $self->member_args->{computed_action_order} } = @$order;
+#    last;
+#  }
+
+  return $members;
 };
 
 __PACKAGE__->meta->make_immutable;
index 356fc18..d1778bd 100644 (file)
@@ -1,8 +1,6 @@
 package Reaction::UI::ViewPort::ListView;
 
 use Reaction::Class;
-use aliased 'Reaction::UI::ViewPort::Collection::Grid::Member::WithActions';
-
 use namespace::clean -except => [ qw(meta) ];
 extends 'Reaction::UI::ViewPort::Collection::Grid';
 
@@ -10,21 +8,6 @@ with 'Reaction::UI::ViewPort::Collection::Role::Order';
 with 'Reaction::UI::ViewPort::Collection::Role::Pager';
 with 'Reaction::UI::ViewPort::Role::Actions';
 
-#If I decide that object actions and collection actions should be
-#lumped together i oculd move these into the collection action role
-#ooor we could create a third role that does this, but gah, no?
-sub _build_member_class { WithActions };
-
-#You'se has to goes aways. sorry.
-#if i saved the args as an attribute i could probably get around this....
-sub object_action_count {
-  my $self = shift;
-  for ( @{ $self->members } ) {
-    #pickup here, and of to the widget for listview
-    return scalar @{ $_->action_prototypes };
-  }
-};
-
 __PACKAGE__->meta->make_immutable;
 
 
index 41ae736..823afc6 100644 (file)
@@ -5,19 +5,23 @@ use Reaction::UI::WidgetClass;
 use namespace::clean -except => [ qw(meta) ];
 extends 'Reaction::UI::Widget::Collection';
 
-
-
 implements fragment header_cells {
   arg 'labels' => $_{viewport}->field_labels;
   render header_cell => over $_{viewport}->computed_field_order;
+  if ($_{viewport}->member_action_count) {
+    render 'header_action_cell';
+  }
 };
 
 implements fragment header_cell {
   arg label => localized $_{labels}->{$_};
 };
 
-__PACKAGE__->meta->make_immutable;
+implements fragment header_action_cell {
+  arg col_count => $_{viewport}->member_action_count;
+};
 
+__PACKAGE__->meta->make_immutable;
 
 1;
 
index 58d26ce..966493a 100644 (file)
@@ -5,8 +5,6 @@ use Reaction::UI::WidgetClass;
 use namespace::clean -except => [ qw(meta) ];
 extends 'Reaction::UI::Widget::Collection::Grid';
 
-
-
 after fragment widget {
   arg pager_obj => $_{viewport}->pager;
 };
@@ -26,12 +24,6 @@ implements fragment action {
   render 'viewport';
 };
 
-after fragment header_cells {
-  if ($_{viewport}->object_action_count) {
-    render 'header_action_cell';
-  }
-};
-
 around fragment header_cell {
   arg order_uri => event_uri {
     order_by => $_,
@@ -41,10 +33,6 @@ around fragment header_cell {
   call_next;
 };
 
-implements fragment header_action_cell {
-  arg col_count => $_{viewport}->object_action_count;
-};
-
 implements fragment page_list {
   render numbered_page_fragment
     => over [ $_{pager_obj}->first_page .. $_{pager_obj}->last_page ];
index 4042652..43cb204 100644 (file)
 
 [% label %]
 
+=for layout header_action_cell
+
+Actions
+
 =for layout body
 
 [% members %]
index 8a0197d..40be738 100644 (file)
 
 [% actions %]
 
-=for layout header_action_cell
-
-Actions
-
 =for layout header_cell_contents
 
 <a href="[% order_uri %]">[% call_next %]</a>
index 9b7eb49..cf1d882 100644 (file)
 
 <th> [% call_next %] </th>
 
+=for layout header_action_cell
+
+<th colspan="[% col_count %]"> [% call_next %] </th>
+
 =for layout body
 
 <tbody>
-
   [% call_next %]
-
 </tbody>
 
 =cut
index f1a72b1..ead72b9 100644 (file)
 
 [% actions %]
 
-=for layout header_action_cell
-
-<th colspan="[% col_count %]"> Actions </th>
-
 =for layout header_cell_contents
 
 <a href="[% order_uri %]">[% call_next %]</a>