]> git.donarmstrong.com Git - perltidy.git/commitdiff
add flag -lpil=s as a simpler alternative to -lpxl=s
authorSteve Hancock <perltidy@users.sourceforge.net>
Tue, 1 Feb 2022 15:14:21 +0000 (07:14 -0800)
committerSteve Hancock <perltidy@users.sourceforge.net>
Tue, 1 Feb 2022 15:14:21 +0000 (07:14 -0800)
CHANGES.md
bin/perltidy
lib/Perl/Tidy.pm
lib/Perl/Tidy/Formatter.pm
t/snippets/expect/lpxl.lpxl6 [new file with mode: 0644]
t/snippets/lpxl6.par [new file with mode: 0644]
t/snippets/packing_list.txt
t/snippets26.t

index d053725e482185e70af3682c45d7696c80b55862..b11ed0939316ad0dfabbccfbc51d332de71b4370 100644 (file)
 
       They can be changed with the flag -gaxl=s, -grep-alias-exclusion-list=s
 
+    - A new flag -lpil=s, --line-up-parentheses-inclusion-list=s, has been added
+      as an alternative to -lpxl=s, --line-up-parentheses-exclusion-list=s.
+      It supplies equivalent information but is easier to describe and use.
+
     - A new flag -xlp has been added which can be set to avoid most of the
       limitations of the -lp flag regarding side comments, blank lines, and
       code blocks.  This is off by default to avoid changing existing coding,
index 9dae624951d4eb6e572757e319b84954fca42b36..df7d6aeec85987803ee5b6ce0bbf44f092d18a3c 100755 (executable)
@@ -893,58 +893,57 @@ Some things that can be done to minimize these problems are:
 (1) Increase B<--maximum-line-length=n> above the default B<n=80> characters if
 necessary.
 
-(2) Apply this style in a limited way.  By default, it applies to all list
+(2) If you use B<-xlp> then long side comments can limit the indentation over
+multiple lines.  Consider adding the flag B<--ignore-side-comment-lengths> to
+prevent this, or minimizing the use of side comments.
+
+(3) Apply this style in a limited way.  By default, it applies to all list
 containers (not just lists in parentheses).  The next section describes how to
 limit this style to, for example, just function calls.  The default indentation
 method will be applied elsewhere.
 
-(3) If you use B<-xlp> then long side comments can limit the indentation over
-multiple lines.  Consider adding the flag B<--ignore-side-comment-lengths> to
-prevent this, or minimizing the use of side comments.
-
-=item B<-lpxl=s>,  B<--line-up-parentheses-exclusion-list>
+=item B<-lpil=s>, B<--line-up-parentheses-inclusion-list> and B<-lpxl=s>,  B<--line-up-parentheses-exclusion-list>
 
-The following discussion mentions B<-lp> but applies equally to B<-xlp>.
+These parameters can be used to restrict the application of the B<-lp> or B<-xlp> styles.
+The following discussion is written for B<-lp> but applies equally to the newer B<-xlp> version.
 
 The B<-lp> indentation style works well for some types of coding but can
 produce very long lines when variables have long names and/or containers are
-very deeply nested.  The B<-lpxl=s> flag is intended to help mitigate this problem by
-providing control over the containers to which the B<-lp> indentation style is
-applied.  The B<-lp> flag by default is "greedy" and applies to as many
-containers as possible.  This flag specifies a list of things which should
-B<not> be use B<-lp> indentation.
+very deeply nested.  One solution to this problem is to limit the application
+of this style to just certain containers.  By default, the B<-lp> flag applies
+to as many containers as possible.  The set of containers to which it applies
+can be reduced by either one of these two flags:
 
-This list is a string with space-separated items.  Each item consists of up to
-three pieces of information in this order: (1) an optional letter code (2) a
-required container type, and (3) an optional numeric code.
+The B<-lpil=s> flag to specifies the containers to which B<-lp> applies.
 
-The only required piece of information is a container type, which is one of
-'(', '[', or '{'.  For example the string
+The B<-lpxl=s> flag to specifies the containers to which B<-lp> does NOT apply.
 
-  -lpxl='[ {'
+Only one of these two flags may be used.  Both flags can achieve the same
+result, but the B<-lpil=s> flag is much easier to describe and use and is
+recommended.  The B<-lpxl=s> flag was the original implementation and is
+retained for backwards compatibility.
 
-means do B<NOT> include use -lp formatting within square-bracets or braces.  The only unspecified
-container is '(', so this string means that only the contents within parens will use -lp indentation.
+This list B<s> for these parametes is a string with space-separated items.
+Each item consists of up to three pieces of information in this order: (1) an
+optional letter code (2) a required container type, and (3) an optional numeric
+code.
 
-An optional numeric code may follow any of the container types to further refine the selection based
-on container contents.  The numeric codes are:
+The only required piece of information is a container type, which is one of
+'(', '[', or '{'.  For example the string
 
-  '0' or blank: no check on contents
-  '1' reject -lp unless the contents is a simple list without sublists
-  '2' reject -lp unless the contents is a simple list without sublists, without
-      code blocks, and without ternary operators
+  -lpil='('
 
-For example,
+means use -lp formatting only on lists within parentheses, not lists in square-bracets or braces.
+The same thing could alternatively be specified with
 
-  -lpxl = '[ { (2'
+  -lpxl = '[ {'
 
-means only apply -lp to parenthesized lists which do not contain any sublists,
-code blocks or ternary expressions.
+which says to exclude lists within square-brackets and braces.  So what remains is lists within parentheses.
 
-A third optional item of information which can be given for parens is an alphanumeric
+A second B<optional> item of information which can be given for parentheses is an alphanumeric
 letter which is used to limit the selection further depending on the type of
 token immediately before the paren.  The possible letters are currently 'k',
-'K', 'f', 'F', 'w', and 'W', with these meanings:
+'K', 'f', 'F', 'w', and 'W', with these meanings for matching whatever precedes an opening paren:
 
  'k' matches if the previous nonblank token is a perl builtin keyword (such as 'if', 'while'),
  'K' matches if 'k' does not, meaning that the previous token is not a keyword.
@@ -953,24 +952,37 @@ token immediately before the paren.  The possible letters are currently 'k',
  'w' matches if either 'k' or 'f' match.
  'W' matches if 'w' does not.
 
-The logic of writing these codes is somewhat counter-intuitive because they
-describe what is not getting the -lp indentation.  So the 'F' indicates that
-non-function calls are not getting -lp, or in other words that function calls
-are getting the -lp indentation.  In practice, one of the following examples
-is likely to be appropriate:
+For example:
+
+  -lpil = 'f('
+
+means only apply -lp to function calls, and
 
-  -lpxl = '[ { F('
+  -lpil = 'w('
 
-means only apply -lp to parenthesized lists which follow a function call.
+means only apply -lp to parenthesized lists which follow a function or a keyword.
+
+This last example could alternatively be written using the B<-lpxl=s> flag as
 
   -lpxl = '[ { W('
 
-means only apply -lp to parenthesized lists which follow a keyword or function call.
+which says exclude B<-lp> for lists within square-brackets, braces, and parens NOT preceded by
+a keyword or function.   Clearly, the B<-lpil=s> method is easier to understand.
+
+An optional numeric code may follow any of the container types to further refine the selection based
+on container contents.  The numeric codes are:
+
+  '0' or blank: no check on contents is made
+  '1' exclude B<-lp> unless the contents is a simple list without sublists
+  '2' exclude B<-lp> unless the contents is a simple list without sublists, without
+      code blocks, and without ternary operators
 
-  -lpxl = '[ { F(2'
+For example,
 
-means only apply -lp to parenthesized lists which follow a function call and
-which do not contain any sublists, code blocks or ternary expressions.
+  -lpil = 'f(2'
+
+means only apply -lp to function call lists which do not contain any sublists,
+code blocks or ternary expressions.
 
 =item B<-cti=n>, B<--closing-token-indentation>
 
@@ -4050,6 +4062,8 @@ style overrides the default style with the following parameters:
 
     -lp -bl -noll -pt=2 -bt=2 -sbt=2 -icp
 
+To use this style with B<-xlp> instead of B<-lp> use B<-gnu -xlp>.
+
 =item B<-pbp>, B<--perl-best-practices>
 
 B<-pbp> is an abbreviation for the parameters in the book B<Perl Best Practices>
@@ -4981,19 +4995,19 @@ The following list shows all short parameter names which allow a prefix
  baao   bar    bbao   bbb    bbc    bbs    bl     bli    boa    boc
  bok    bol    bom    bos    bot    cblx   ce     conv   cs     csc
  cscb   cscw   dac    dbc    dcbl   dcsc   ddf    dln    dnl    dop
- dp     dpro   dsc    dsm    dsn    dtt    dwls   dwrs   dws    f
- fll    fpva   frm    fs     fso    gcs    hbc    hbcm   hbco   hbh
- hbhh   hbi    hbj    hbk    hbm    hbn    hbp    hbpd   hbpu   hbq
- hbs    hbsc   hbv    hbw    hent   hic    hicm   hico   hih    hihh
- hii    hij    hik    him    hin    hip    hipd   hipu   hiq    his
- hisc   hiv    hiw    hsc    html   ibc    icb    icp    iob    isbc
- iscl   kgb    kgbd   kgbi   kis    lal    log    lop    lp     lsl
- mem    nib    ohbr   okw    ola    olc    oll    olq    opr    opt
- osbc   osbr   otr    ple    pod    pvl    q      sac    sbc    sbl
- scbb   schb   scp    scsb   sct    se     sfp    sfs    skp    sob
- sobb   sohb   sop    sosb   sot    ssc    st     sts    t      tac
- tbc    toc    tp     tqw    trp    ts     tsc    tso    vbc    vc
- vmll   vsc    w      wn     x      xci    xs
+ dp     dpro   dsc    dsm    dsn    dtt    dwls   dwrs   dws    eos
+ f      fll    fpva   frm    fs     fso    gcs    hbc    hbcm   hbco
+ hbh    hbhh   hbi    hbj    hbk    hbm    hbn    hbp    hbpd   hbpu
+ hbq    hbs    hbsc   hbv    hbw    hent   hic    hicm   hico   hih
+ hihh   hii    hij    hik    him    hin    hip    hipd   hipu   hiq
+ his    hisc   hiv    hiw    hsc    html   ibc    icb    icp    iob
+ isbc   iscl   kgb    kgbd   kgbi   kis    lal    log    lop    lp
+ lsl    mem    nib    ohbr   okw    ola    olc    oll    olq    opr
+ opt    osbc   osbr   otr    ple    pod    pvl    q      sac    sbc
+ sbl    scbb   schb   scp    scsb   sct    se     sfp    sfs    skp
+ sob    sobb   sohb   sop    sosb   sot    ssc    st     sts    t
+ tac    tbc    toc    tp     tqw    trp    ts     tsc    tso    vbc
+ vc     vmll   vsc    w      wn     x      xci    xlp    xs
 
 Equivalently, the prefix 'no' or 'no-' on the corresponding long names may be
 used.
index 3693b91cef77371b291a671eb7fb0baed3f1e848..33018ee9b27fa6e73f5447a06fc408a5b0923372 100644 (file)
@@ -2334,6 +2334,7 @@ sub generate_options {
     $add_option->( 'line-up-parentheses',                  'lp',    '!' );
     $add_option->( 'extended-line-up-parentheses',         'xlp',   '!' );
     $add_option->( 'line-up-parentheses-exclusion-list',   'lpxl',  '=s' );
+    $add_option->( 'line-up-parentheses-inclusion-list',   'lpil',  '=s' );
     $add_option->( 'outdent-keyword-list',                 'okwl',  '=s' );
     $add_option->( 'outdent-keywords',                     'okw',   '!' );
     $add_option->( 'outdent-labels',                       'ola',   '!' );
index 72fafad51962cfb7b0a43b2c78702225d3967616..d8abcb38feebe592999260e0d07411ab791a786b 100644 (file)
@@ -283,7 +283,8 @@ my (
     %stack_closing_token,
 
     %weld_nested_exclusion_rules,
-    %line_up_parentheses_exclusion_rules,
+    %line_up_parentheses_control_hash,
+    $line_up_parentheses_control_is_lxpl,
 
     # regex patterns for text identification.
     # Most are initialized in a sub make_**_pattern during configuration.
@@ -1945,7 +1946,27 @@ EOM
     }
 
     initialize_weld_nested_exclusion_rules($rOpts);
-    initialize_line_up_parentheses_exclusion_rules($rOpts);
+
+    %line_up_parentheses_control_hash    = ();
+    $line_up_parentheses_control_is_lxpl = 1;
+    my $lpxl = $rOpts->{'line-up-parentheses-exclusion-list'};
+    my $lpil = $rOpts->{'line-up-parentheses-inclusion-list'};
+    if ( $lpxl && $lpil ) {
+        Warn( <<EOM );
+You entered values for both -lpxl=s and -lpil=s; the -lpil list will be ignored
+EOM
+    }
+    if ($lpxl) {
+        $line_up_parentheses_control_is_lxpl = 1;
+        initialize_line_up_parentheses_control_hash(
+            $rOpts->{'line-up-parentheses-exclusion-list'}, 'lpxl' );
+    }
+    elsif ($lpil) {
+        $line_up_parentheses_control_is_lxpl = 0;
+        initialize_line_up_parentheses_control_hash(
+            $rOpts->{'line-up-parentheses-inclusion-list'}, 'lpil' );
+    }
+
     return;
 }
 
@@ -2139,11 +2160,8 @@ EOM
     return;
 }
 
-sub initialize_line_up_parentheses_exclusion_rules {
-    my ($rOpts) = @_;
-    %line_up_parentheses_exclusion_rules = ();
-    my $opt_name = 'line-up-parentheses-exclusion-list';
-    my $str      = $rOpts->{$opt_name};
+sub initialize_line_up_parentheses_control_hash {
+    my ( $str, $opt_name ) = @_;
     return unless ($str);
     $str =~ s/^\s+//;
     $str =~ s/\s+$//;
@@ -2198,13 +2216,13 @@ sub initialize_line_up_parentheses_exclusion_rules {
             next;
         }
 
-        if ( !defined( $line_up_parentheses_exclusion_rules{$key} ) ) {
-            $line_up_parentheses_exclusion_rules{$key} = [ $flag1, $flag2 ];
+        if ( !defined( $line_up_parentheses_control_hash{$key} ) ) {
+            $line_up_parentheses_control_hash{$key} = [ $flag1, $flag2 ];
             next;
         }
 
         # check for multiple conflicting specifications
-        my $rflags = $line_up_parentheses_exclusion_rules{$key};
+        my $rflags = $line_up_parentheses_control_hash{$key};
         my $err;
         if ( defined( $rflags->[0] ) && $rflags->[0] ne $flag1 ) {
             $err = 1;
@@ -2232,17 +2250,19 @@ EOM
     }
 
     # Speedup: we can turn off -lp if it is not actually used
-    my $all_off = 1;
-    foreach my $key (qw# ( { [ #) {
-        my $rflags = $line_up_parentheses_exclusion_rules{$key};
-        if ( defined($rflags) ) {
-            my ( $flag1, $flag2 ) = @{$rflags};
-            if ( $flag1 && $flag1 ne '*' ) { $all_off = 0; last }
-            if ($flag2)                    { $all_off = 0; last }
+    if ($line_up_parentheses_control_is_lxpl) {
+        my $all_off = 1;
+        foreach my $key (qw# ( { [ #) {
+            my $rflags = $line_up_parentheses_control_hash{$key};
+            if ( defined($rflags) ) {
+                my ( $flag1, $flag2 ) = @{$rflags};
+                if ( $flag1 && $flag1 ne '*' ) { $all_off = 0; last }
+                if ($flag2)                    { $all_off = 0; last }
+            }
+        }
+        if ($all_off) {
+            $rOpts->{'line-up-parentheses'} = "";
         }
-    }
-    if ($all_off) {
-        $rOpts->{'line-up-parentheses'} = "";
     }
 
     return;
@@ -11183,61 +11203,82 @@ EOM
 
 sub is_excluded_lp {
 
-    # decide if this container is excluded by user request
-    # returns true if this token is excluded (i.e., may not use -lp)
-    # returns false otherwise
+    # Decide if this container is excluded by user request:
+    #  returns true if this token is excluded (i.e., may not use -lp)
+    #  returns false otherwise
+
+    # The control hash can either describe:
+    #   what to exclude:  $line_up_parentheses_control_is_lxpl = 1, or
+    #   what to include:  $line_up_parentheses_control_is_lxpl = 0
 
-    # note similarity with sub 'is_excluded_weld'
     my ( $self, $KK ) = @_;
     my $rLL         = $self->[_rLL_];
     my $rtoken_vars = $rLL->[$KK];
     my $token       = $rtoken_vars->[_TOKEN_];
-    my $rflags      = $line_up_parentheses_exclusion_rules{$token};
-    return 0 unless ( defined($rflags) );
+    my $rflags      = $line_up_parentheses_control_hash{$token};
+
+    #-----------------------------------------------
+    # TEST #1: check match to listed container types
+    #-----------------------------------------------
+    if ( !defined($rflags) ) {
+
+        # There is no entry for this container, so we are done
+        return !$line_up_parentheses_control_is_lxpl;
+    }
+
     my ( $flag1, $flag2 ) = @{$rflags};
 
-    # There are two flags:
-    # flag1 excludes based on the preceding nonblank word
-    # flag2 excludes based on the contents of the container
-    return 0 unless ( defined($flag1) );
-    return 1 if $flag1 eq '*';
+    #-----------------------------------------------------------
+    # TEST #2: check match to flag1, the preceding nonblank word
+    #-----------------------------------------------------------
+    my $match_flag1 = !defined($flag1) || $flag1 eq '*';
+    if ( !$match_flag1 ) {
 
-    # Find the previous token
-    my ( $is_f, $is_k, $is_w );
-    my $Kp = $self->K_previous_nonblank($KK);
-    if ( defined($Kp) ) {
-        my $type_p = $rLL->[$Kp]->[_TYPE_];
-        my $seqno  = $rtoken_vars->[_TYPE_SEQUENCE_];
+        # Find the previous token
+        my ( $is_f, $is_k, $is_w );
+        my $Kp = $self->K_previous_nonblank($KK);
+        if ( defined($Kp) ) {
+            my $type_p = $rLL->[$Kp]->[_TYPE_];
+            my $seqno  = $rtoken_vars->[_TYPE_SEQUENCE_];
 
-        # keyword?
-        $is_k = $type_p eq 'k';
+            # keyword?
+            $is_k = $type_p eq 'k';
 
-        # function call?
-        $is_f = $self->[_ris_function_call_paren_]->{$seqno};
+            # function call?
+            $is_f = $self->[_ris_function_call_paren_]->{$seqno};
 
-        # either keyword or function call?
-        $is_w = $is_k || $is_f;
+            # either keyword or function call?
+            $is_w = $is_k || $is_f;
+        }
+
+        # Check for match based on flag1 and the previous token:
+        if    ( $flag1 eq 'k' ) { $match_flag1 = $is_k }
+        elsif ( $flag1 eq 'K' ) { $match_flag1 = !$is_k }
+        elsif ( $flag1 eq 'f' ) { $match_flag1 = $is_f }
+        elsif ( $flag1 eq 'F' ) { $match_flag1 = !$is_f }
+        elsif ( $flag1 eq 'w' ) { $match_flag1 = $is_w }
+        elsif ( $flag1 eq 'W' ) { $match_flag1 = !$is_w }
     }
 
-    # Check for exclusion based on flag1 and the previous token:
-    my $match;
-    if    ( $flag1 eq 'k' ) { $match = $is_k }
-    elsif ( $flag1 eq 'K' ) { $match = !$is_k }
-    elsif ( $flag1 eq 'f' ) { $match = $is_f }
-    elsif ( $flag1 eq 'F' ) { $match = !$is_f }
-    elsif ( $flag1 eq 'w' ) { $match = $is_w }
-    elsif ( $flag1 eq 'W' ) { $match = !$is_w }
-    return $match if ($match);
-
-    # Check for exclusion based on flag2 and the container contents
-    # Current options to filter on contents:
-    # 0 or blank: ignore container contents
-    # 1 exclude non-lists or lists with sublists
-    # 2 same as 1 but also exclude lists with code blocks
-
-    # Note:
-    # Containers with multiline-qw containers are automatically
-    # excluded so do not need to be checked.
+    # See if we can exclude this based on the flag1 test...
+    if ($line_up_parentheses_control_is_lxpl) {
+        return 1 if ($match_flag1);
+    }
+    else {
+        return 1 if ( !$match_flag1 );
+    }
+
+    #-------------------------------------------------------------
+    # TEST #3: exclusion based on flag2 and the container contents
+    #-------------------------------------------------------------
+
+    # Note that this is an exclusion test for both -lpxl or -lpil input methods
+    # The options are:
+    #  0 or blank: ignore container contents
+    #  1 exclude non-lists or lists with sublists
+    #  2 same as 1 but also exclude lists with code blocks
+
+    my $match_flag2;
     if ($flag2) {
 
         my $seqno = $rtoken_vars->[_TYPE_SEQUENCE_];
@@ -11246,14 +11287,15 @@ sub is_excluded_lp {
         my $has_list       = $self->[_rhas_list_]->{$seqno};
         my $has_code_block = $self->[_rhas_code_block_]->{$seqno};
         my $has_ternary    = $self->[_rhas_ternary_]->{$seqno};
+
         if (  !$is_list
             || $has_list
             || $flag2 eq '2' && ( $has_code_block || $has_ternary ) )
         {
-            $match = 1;
+            $match_flag2 = 1;
         }
     }
-    return $match;
+    return $match_flag2;
 }
 
 sub set_excluded_lp_containers {
diff --git a/t/snippets/expect/lpxl.lpxl6 b/t/snippets/expect/lpxl.lpxl6
new file mode 100644 (file)
index 0000000..de0dfa6
--- /dev/null
@@ -0,0 +1,61 @@
+# simple function call
+my $loanlength = getLoanLength(
+                                $borrower->{'categorycode'},    # sc1
+                                $iteminformation->{'itemtype'},
+                                $borrower->{'branchcode'}       # sc3
+);
+
+# function call, more than one level deep
+my $o = very::long::class::name->new(
+    {
+        propA => "a",
+        propB => "b",
+        propC => "c",
+    }
+);
+
+# function call with sublist
+debug(
+    "Connecting to DB.",
+    "Extra-Parameters: " . join( "<->", $extra_parms ),
+    "Config: " . join( "<->", %config )
+);
+
+# simple function call with code block
+$m->command(
+    -label   => 'Save',
+    -command => sub { print "DOS\n"; save_dialog($win); }
+);
+
+# function call, ternary in list
+return OptArgs2::Result->usage(
+    $style == OptArgs2::STYLE_FULL ? 'FullUsage' : 'NormalUsage',
+    'usage: ' . $usage . "\n" );
+
+# not a function call
+%blastparam = (
+    -run    => \%runparam,
+    -file   => '',
+    -parse  => 1,
+    -signif => 1e-5,
+);
+
+# 'local' is a keyword, not a user function
+local (
+    $len,    $pts,      @colspec, $char, $cols,
+    $repeat, $celldata, $at_text, $after_text
+);
+
+# square bracket with sublists
+$data = [
+    ListElem->new( id => 0, val => 100 ),
+    ListElem->new( id => 2, val => 50 ),
+    ListElem->new( id => 1, val => 10 ),
+];
+
+# curly brace with sublists
+$behaviour = {
+    cat   => { nap    => "lap",   eat  => "meat" },
+    dog   => { prowl  => "growl", pool => "drool" },
+    mouse => { nibble => "kibble" },
+};
diff --git a/t/snippets/lpxl6.par b/t/snippets/lpxl6.par
new file mode 100644 (file)
index 0000000..5f58dae
--- /dev/null
@@ -0,0 +1,2 @@
+# equivalent to -lpxl='{ [ F(2'
+-lp -lpil='f(2'
index 79792a54915ff2c711313e1ab62e2f9225cb92d0..1749d9addcb88754a4aea8e684e91ede887a4c93 100644 (file)
 ../snippets9.t rt98902.def
 ../snippets9.t rt98902.rt98902
 ../snippets9.t rt99961.def
+../snippets26.t        lpxl.lpxl6
index 7fa76d1f25b68b093bd6651e6321a4c2f5eff283..d46fcf1ffecd183b61374ebb50509e43fe8f0ce2 100644 (file)
@@ -3,6 +3,7 @@
 # Contents:
 #1 bal.bal2
 #2 bal.def
+#3 lpxl.lpxl6
 
 # To locate test #13 you can search for its name or the string '#13'
 
@@ -20,8 +21,12 @@ BEGIN {
     # BEGIN SECTION 1: Parameter combinations #
     ###########################################
     $rparams = {
-        'bal2' => "-bal=2",
-        'def'  => "",
+        'bal2'  => "-bal=2",
+        'def'   => "",
+        'lpxl6' => <<'----------',
+# equivalent to -lpxl='{ [ F(2'
+-lp -lpil='f(2'
+----------
     };
 
     ############################
@@ -35,6 +40,69 @@ BEGIN {
   L2:
   L3: return;
 };
+----------
+
+        'lpxl' => <<'----------',
+# simple function call
+my $loanlength = getLoanLength(
+                                $borrower->{'categorycode'},    # sc1
+                                $iteminformation->{'itemtype'},
+                                $borrower->{'branchcode'}       # sc3
+);
+
+# function call, more than one level deep
+my $o = very::long::class::name->new(
+    {
+        propA => "a",
+        propB => "b",
+        propC => "c",
+    }
+);
+
+# function call with sublist
+debug(
+      "Connecting to DB.",
+      "Extra-Parameters: " . join("<->", $extra_parms),
+      "Config: " . join("<->", %config)
+     );
+
+# simple function call with code block
+$m->command(-label   => 'Save',
+            -command => sub { print "DOS\n"; save_dialog($win); });
+
+# function call, ternary in list
+return
+  OptArgs2::Result->usage(
+    $style == OptArgs2::STYLE_FULL ? 'FullUsage' : 'NormalUsage',
+    'usage: ' . $usage . "\n" );
+
+# not a function call
+%blastparam = (
+    -run            => \%runparam,
+    -file           => '',
+    -parse          => 1,
+    -signif         => 1e-5,
+);
+
+# 'local' is a keyword, not a user function
+    local (
+        $len,    $pts,      @colspec, $char, $cols,
+        $repeat, $celldata, $at_text, $after_text
+    );
+
+# square bracket with sublists
+$data = [
+         ListElem->new(id => 0, val => 100),
+         ListElem->new(id => 2, val => 50),
+         ListElem->new(id => 1, val => 10),
+        ];
+
+# curly brace with sublists
+$behaviour = {
+              cat   => {nap    => "lap",   eat  => "meat"},
+              dog   => {prowl  => "growl", pool => "drool"},
+              mouse => {nibble => "kibble"},
+             };
 ----------
     };
 
@@ -64,6 +132,74 @@ BEGIN {
 };
 #2...........
         },
+
+        'lpxl.lpxl6' => {
+            source => "lpxl",
+            params => "lpxl6",
+            expect => <<'#3...........',
+# simple function call
+my $loanlength = getLoanLength(
+                                $borrower->{'categorycode'},    # sc1
+                                $iteminformation->{'itemtype'},
+                                $borrower->{'branchcode'}       # sc3
+);
+
+# function call, more than one level deep
+my $o = very::long::class::name->new(
+    {
+        propA => "a",
+        propB => "b",
+        propC => "c",
+    }
+);
+
+# function call with sublist
+debug(
+    "Connecting to DB.",
+    "Extra-Parameters: " . join( "<->", $extra_parms ),
+    "Config: " . join( "<->", %config )
+);
+
+# simple function call with code block
+$m->command(
+    -label   => 'Save',
+    -command => sub { print "DOS\n"; save_dialog($win); }
+);
+
+# function call, ternary in list
+return OptArgs2::Result->usage(
+    $style == OptArgs2::STYLE_FULL ? 'FullUsage' : 'NormalUsage',
+    'usage: ' . $usage . "\n" );
+
+# not a function call
+%blastparam = (
+    -run    => \%runparam,
+    -file   => '',
+    -parse  => 1,
+    -signif => 1e-5,
+);
+
+# 'local' is a keyword, not a user function
+local (
+    $len,    $pts,      @colspec, $char, $cols,
+    $repeat, $celldata, $at_text, $after_text
+);
+
+# square bracket with sublists
+$data = [
+    ListElem->new( id => 0, val => 100 ),
+    ListElem->new( id => 2, val => 50 ),
+    ListElem->new( id => 1, val => 10 ),
+];
+
+# curly brace with sublists
+$behaviour = {
+    cat   => { nap    => "lap",   eat  => "meat" },
+    dog   => { prowl  => "growl", pool => "drool" },
+    mouse => { nibble => "kibble" },
+};
+#3...........
+        },
     };
 
     my $ntests = 0 + keys %{$rtests};