-%
-%
-% # options example...
-% #
-% # 'name' =>
-% # 'table' =>
-% # #? 'primary_key' => #required when the dbdef doesn't know...???
-% # 'labels' => {
-% # 'column' => 'Label',
-% # }
-% #
-% # listref - each item is a literal column name (or method) or hashref
-% # or (notyet) coderef
-% # if not specified all columns (except for the primary key) will be editable
-% # 'fields' => [
-% # 'columname',
-% # { 'field' => 'another_columname',
-% # 'type' => 'text', #text, fixed, hidden, checkbox
-% # #eventually more for <SELECT>, etc.
-% # 'value' => 'Y', #only for checkbox
-% # },
-% # ]
-% #
-% # 'menubar' => '', #menubar arrayref
-% #
-% # #run when re-displaying with an error
-% # 'error_callback' => sub { my( $cgi, $object ) = @_; },
-% #
-% # #run when editing
-% # 'edit_callback' => sub { my( $cgi, $object ) = @_; },
-% #
-% # # returns a hashref for the new object
-% # 'new_hashref_callback'
-% #
-% # #run when adding
-% # 'new_callback' => sub { my( $cgi, $object ) = @_; },
-% #
-% # #XXX describe
-% # 'field_callback' => sub { },
-% #
-% # #string or coderef of additional HTML to add before </TABLE>
-% # 'html_table_bottom' => '',
-% #
-% # 'viewall_dir' => '', #'search' or 'browse', defaults to 'search'
-% #
-% # 'html_bottom' => '', #string
-% # 'html_bottom' => sub {
-% # my $object = shift;
-% # # ...
-% # "html_string";
-% # },
-%
-% my(%opt) = @_;
-%
-% #false laziness w/process.html
-% my $table = $opt{'table'};
-% my $class = "FS::$table";
-% my $pkey = dbdef->table($table)->primary_key; #? $opt{'primary_key'} ||
-% my $fields = $opt{'fields'}
-% #|| [ grep { $_ ne $pkey } dbdef->table($table)->columns ];
-% || [ grep { $_ ne $pkey } fields($table) ];
-% #my @actualfields = map { ref($_) ? $_->{'field'} : $_ } @$fields;
-%
-% my $object;
-% if ( $cgi->param('error') ) {
-%
-% $object = $class->new( {
-% map { $_ => scalar($cgi->param($_)) } fields($table)
-% });
-%
-% &{$opt{'error_callback'}}($cgi, $object)
-% if $opt{'error_callback'};
-%
-% } elsif ( $cgi->keywords || $cgi->param($pkey) ) { #editing
-%
-% my( $query ) = $cgi->keywords;
-% $query = $cgi->param($pkey) unless $query;
-% $query =~ /^(\d+)$/;
-% $object = qsearchs( $table, { $pkey => $1 } );
-% warn "$table $pkey => $1"
-% if $opt{'debug'};
-%
-% &{$opt{'edit_callback'}}($cgi, $object)
-% if $opt{'edit_callback'};
-%
-% } else { #adding
-%
-% my $hashref = $opt{'new_hashref_callback'}
-% ? &{$opt{'new_hashref_callback'}}
-% : {};
-%
-% $object = $class->new( $hashref );
-%
-% &{$opt{'new_callback'}}($cgi, $object)
-% if $opt{'new_callback'};
-%
-% }
-%
-% my $action = $object->$pkey() ? 'Edit' : 'Add';
-%
-% my $title = "$action $opt{'name'}";
-%
-% my $viewall_url = $p . ( $opt{'viewall_dir'} || 'search' ) . "/$table.html";
-% $viewall_url = $opt{'viewall_url'} if $opt{'viewall_url'};
-%
-% my @menubar = ();
-% if ( $opt{'menubar'} ) {
-% @menubar = @{ $opt{'menubar'} };
-% } else {
-% @menubar = (
-% 'Main menu' => $p, #eventually get rid of this when the ACL/UI update is done
-% #eventually use Lingua::bs to pluralize
-% "View all $opt{'name'}s" => $viewall_url,
-% );
-% }
-%
-%
-<% include("/elements/header.html", $title,
+<%doc>
+
+Example:
+
+ include( 'elements/edit.html',
+ 'name' =>
+ 'table' =>
+ #? 'primary_key' => #required when the dbdef doesn't know...???
+ 'labels' => {
+ 'column' => 'Label',
+ }
+
+ #listref - each item is a literal column name (or method) or hashref
+ # or (notyet) coderef
+ #if not specified all columns (except for the primary key) will be editable
+ 'fields' => [
+ 'columname',
+ { 'field' => 'another_columname',
+ 'type' => 'text', #text
+ #password
+ #money
+ #percentage
+ #checkbox
+ #select
+ #selectlayers (can't use after a tablebreak-tr-title yet... grep "OneTrueTable")
+ #title
+ #tablebreak-tr-title
+ #hidden - hidden value from object
+ #fixed - display fixed value from object or here
+ #fixed-country
+ #fixed-state
+ 'value' => 'Y', #for checkbox, title, fixed, fixedhidden
+ 'disabled' => 0,
+ 'onchange' => 'javascript_function',
+ 'm2name_table' => 'table_name', #only tested w/
+ # selectlayers so far
+ # might work w/select
+ # dunno others
+ 'm2name_namecol' => 'name_column', #
+ 'm2name_label' => 'Label', #
+ 'm2name_new_default' => \@table_name_objects, #default
+ #m2name
+ #objects for
+ #new records
+ 'm2name_error_callback' => sub { my($cgi, $object) = @_; },
+ 'm2name_remove_warnings' => \%warnings, #hashref of warning
+ #messages for
+ #m2name removal
+ 'm2name_new_js' => 'function_name', #javascript function
+ #called on spawned rows
+ #(one arg: new_element)
+ 'm2name_remove_js' => 'function_name', #js function called
+ #when a row is
+ #deleted
+ #(three args:
+ # value, text,
+ # 'no_match')
+ #layer_fields & layer_values_callback only for selectlayer
+ 'layer_fields' => [
+ 'fieldname' => 'Label',
+ 'another_field' => {
+ label=>'Label',
+ type =>'text', #text, money
+ },
+ ],
+ 'layer_values_callback' =>
+ sub {
+ my( $cgi, $object ) = @_;
+ { 'layer' => { 'fieldname' => 'current_value',
+ 'fieldname2' => 'field2value',
+ ...
+ },
+ 'layer2' => { 'l2fieldname' => 'l2value',
+ ...
+ },
+ ...
+ };
+ },
+ },
+ ]
+
+ 'menubar' => '', #menubar arrayref
+
+ #agent virtualization
+ 'agent_virt' => 1,
+ 'agent_null_right' => 'Access Right Name',
+
+ #run when re-displaying with an error
+ 'error_callback' => sub { my( $cgi, $object, $fields_listref ) = @_; },
+
+ #run when editing
+ 'edit_callback' => sub { my( $cgi, $object, $fields_listref ) = @_; },
+
+ # returns a hashref for the new object
+ 'new_hashref_callback'
+
+ #run when adding
+ 'new_callback' => sub { my( $cgi, $object, $fields_listref ) = @_; },
+
+ #run before display to return a different value
+ 'value_callback' => sub { my( $columname, $value } ) = @_; },
+
+ #XXX describe
+ 'field_callback' => sub { },
+
+ #string or coderef of additional HTML to add before </TABLE>
+ 'html_table_bottom' => '',
+
+ 'viewall_dir' => '', #'search' or 'browse', defaults to 'search'
+
+ 'html_bottom' => '', #string
+ 'html_bottom' => sub {
+ my $object = shift;
+ # ...
+ "html_string";
+ },
+
+ # overrides default popurl(1)."process/$table.html"
+ 'post_url' => popurl(1).'process/something',
+
+ #we're in a popup (no title/menu/searchboxes)
+ 'popup' => 1,
+
+ );
+
+</%doc>
+
+<% include('/elements/header'. ( $opt{popup} ? '-popup' : '' ). '.html',
+ $title,