Shlomi Fish avatar Shlomi Fish committed fc24b3b Merge

Committed.

Comments (0)

Files changed (15)

 Module-Format/Module-Format/Makefile.PL
 Module-Format/Module-Format/_build
 Module-Format/Module-Format/blib
+Text-Format/Text-Format/Build
+Text-Format/Text-Format/META.yml
+Text-Format/Text-Format/MYMETA.yml
+Text-Format/Text-Format/_build
+Text-Format/Text-Format/blib
 a11055542b20d59bbf06869813c37cf98e552ae7 list
 0000000000000000000000000000000000000000 list
 52721ba4d6e206899358f4d3daf279aa97a87d55 Module-Format-v0.0.2
+00fdbc037a54ee15f886cf9ded720550d754c3ff Module-Format-v0.0.3
+3dc7909c6514e6f70253f5243b84493dc269b853 Text-Format-0.52
+8d8aee731ea8626ab253d4dab21eaaddf6d568d7 Text-Format-0.53

Module-Format/Module-Format/Changes

 Revision history for Module-Format
 
-0.0.3   Sat Jun 11 16:36:44 IDT 2011
+0.0.4   Sat Jun 11 16:36:44 IDT 2011
         - Small improvement to the script/perlmf POD.
 
+0.0.3   Wed Dec  1 13:03:47 IST 2010
+        - Correct a bug with the regex of guessing a 
+        MooseX/Role/BuildInstanceOf.pm -like unix path.
 0.0.2   Sun Nov 28 22:13:26 IST 2010
         - Add keywords and resources to the Build.PL/META.yml.
         - Removed the depenedency on List::MoreUtils.
Add a comment to this file

Module-Format/Module-Format/lib/Module/Format.pm

File contents unchanged.

Module-Format/Module-Format/lib/Module/Format/Module.pm

     },
     {
         name => 'unix',
-        regex => qr{\A(?:\w+/)*\.pm\z},
+        regex => qr{\A(?:\w+/)*\w+\.pm\z},
         input => sub {
             my ($class, $value) = @_;
 

Module-Format/Module-Format/t/module.t

 use strict;
 use warnings;
 
-use Test::More tests => 59;
+use Test::More tests => 63;
 
 use Module::Format::Module;
 
         "format_as works for from_guess()ed colon module",
     );
 }
+
+{
+    my $chosen_format;
+    my $module = Module::Format::Module->from_guess(
+        {
+            value => 'MooseX/Role/BuildInstanceOf.pm',
+            format_ref => \$chosen_format,
+        }
+    );
+    
+    # TEST
+    ok ($module, "from_guess initialises a module.");
+
+    # TEST
+    is_deeply(
+        $module->get_components_list(),
+        [qw(MooseX Role BuildInstanceOf)],
+        "from_guess got good components.",
+    );
+
+    # TEST
+    is ($chosen_format, 'unix', 'chosen format was initialised');
+
+    # TEST
+    is ($module->format_as('dash'), 'MooseX-Role-BuildInstanceOf',
+        "format_as works for from_guess()ed module",
+    );
+}

Text-Format/Text-Format/Build.PL

+use strict;
+use warnings;
+
+use lib "./inc";
+
+use Test::Run::Builder;
+
+my $builder = Test::Run::Builder->new(
+    module_name         => 'Text::Format',
+    license             => 'perl',
+    dist_author         => q{Shlomi Fish <shlomif@cpan.org>},
+    dist_version_from   => 'lib/Text/Format.pm',
+    requires =>
+    {
+        'Carp' => 0,
+        'vars' => 0,
+        'strict' => 0,
+        'warnings' => 0,
+    },
+    build_requires =>
+    {
+        'Test::More' => 0,
+        'vars' => 0,
+    },
+    configure_requires =>
+    {
+        'Module::Build' => 0,
+    },
+    add_to_cleanup      => [ 'Module-Format-*' ],
+    create_makefile_pl => 'traditional',
+    meta_merge =>
+    {
+        resources =>
+        {
+            repository => "http://bitbucket.org/shlomif/web-cpan",
+            homepage => "http://www.shlomifish.org/open-source/projects/Text-Format/",
+        },
+        keywords =>
+        [
+            'format',
+            'formatting',
+            'margin',
+            'margins',
+            'string',
+            'text',
+            'width',
+        ],
+    },
+);
+
+$builder->create_build_script();

Text-Format/Text-Format/Changes

+Revision history for Perl extension Text::Format.
+
+0.53 Fri Jan 28 13:02:01 IST 2011
+    - Adopted by Shlomi Fish (while disclaiming all rights).
+    - Convert the build system to Module-Build, while adding keywords
+    and resources.
+    - The archive name is now the more standard Text-Format-0.53.tar.gz.
+    - Fix some typos in the documentation.
+
+0.52 Sun Mar 29 11:32:50 1998
+    - fixed some warnings that appeared when using hanging indents
+      (tagged paragraphs).  Also added tha ability to use a list
+      as an argument to new() and config() so you can pass a hash ref or
+      a list as long as the list length is mod 2 == 0
+
+0.51 Tue Feb 24 13:32:22 1998
+    - no real bug fix, just the MANIFEST was wrong, also I got a test
+      script for testing the justify feature from the guy who originally
+      wrote the code for justify
+
+0.50 Sat Feb 21 10:19:33 1998
+    - there were no bugs but I figured that the new feature should
+      really have its own release.  I also tried to make the
+      justification a little faster, and the extra spaces are now added
+      starting on the right side of the text instead of the left
+    - fixed up the docs a little as well
+
+0.46 Wed Feb 18 17:19:43 1998
+    - fixed bug in justify when there was only one word left for the
+      last line it would consider the previous line to be the last line
+      and not justify it. :-(
+
+0.45 Wed Feb 18 00:04:01 1998
+    - changed the way hanging indents behave when there are more
+      paragraphs than indent tags, previously the first tag was reused,
+      now an empty text is used if there are no more tags available.
+    - added the justify feature, this will jsutify the text to both
+      margins, the rightAlign feture would jusstify to the rigght margin
+      and default is to justify to the left margin.  if rightAlign or
+      rightFill are set then justify is ignored.  rightFill fills the
+      right side with spaces
+
+0.44 Thu Feb 12 16:31:08 1998
+    - added quotes to hash keys as 5.003 didn't like unquoted hash keys
+      starting with an underscore
+
+0.43 Sat Feb  7 14:55:39 1998
+    - fixed some warnings that were occurring
+
+0.42 Fri Feb  6 18:37:13 1998
+    - no real changes as far as the user is concerned
+    - changed some internal subroutines from being just a reference to
+      being a real subroutine so Objects that inherit from Text::Format
+      can use them
+
+0.41  Mon Feb  2 22:57:33 1998
+    - fixed non-breaking space bug
+    - added some more error checking to new() and config()
+
+0.40  Thu Jan 29 16:47:41 1998
+    - added support for non-breaking space
+    - made some changes that make the module incompatible with the
+      previous version
+      * firstIndent and bodyIndent now take a number as an argument and
+        spaces are used for the indents at all times rather than the
+        previously specified strings
+      * expandTabs is gone - to expand tabs prior to using center()
+        just use Text::Format->expand() first
+      * subroutines wrap and fill renamed to format() and paragraphs()
+        to reflect their usage
+    - fixed the bug due to the right margin not being considered when
+      doing right alignment
+
+0.33  Wed Jan 21 17:50:39 1998
+    - added left margin and right margin spec, left out by accident
+      before
+
+0.32  Sat Jan 17 11:45:48 1998
+    - fixed another bug :-(
+
+0.31  Fri Jan 16 17:23:18 1998
+    - renamed module to Format.pm (was Manip.pm)
+      fixed a warning; was operating on an undef'ed string without
+      checking now check for defined strings
+
+0.30  Wed Jan 14 22:20:37 1998
+    - added ability to do hanging indents, fixed the interface for a
+      better object oriented design, fixed some more bugs
+
+0.23  Fri Jan 10 22:56:40 1998
+    - few bug fixes
+
+0.22  Fri Jan 10 17:39:23 1998
+    - addition of expand/unexpand routines
+
+0.21  Thu Jan  9 20:23:34 1998
+    - addition of center routine
+
+0.20  Wed Jan  8 22:20:28 1998
+    - change to object oriented module
+
+0.10  Tue Jan  6 15:28:29 1998
+    - original version
+      routines are : wrap, fill
+      basically the same as Text::Wrap at this point just without the
+      chance for dying, it's just a basic module - Andreas Koenig
+      suggested to make it object oriented

Text-Format/Text-Format/MANIFEST

+Build.PL
+Changes
+inc/Test/Run/Builder.pm
+lib/Text/Format.pm
+t/format.t
+t/justify.t
+MANIFEST
+Makefile.PL
+META.yml

Text-Format/Text-Format/Makefile.PL

+# Note: this file was auto-generated by Module::Build::Compat version 0.36_17
+use ExtUtils::MakeMaker;
+WriteMakefile
+(
+          'NAME' => 'Text::Format',
+          'VERSION_FROM' => 'lib/Text/Format.pm',
+          'PREREQ_PM' => {
+                           'Carp' => 0,
+                           'Test::More' => 0,
+                           'strict' => 0,
+                           'vars' => 0,
+                           'warnings' => 0
+                         },
+          'INSTALLDIRS' => 'site',
+          'EXE_FILES' => [],
+          'PL_FILES' => {}
+        )
+;

Text-Format/Text-Format/README

+Text::Format
+
+format()        Format text into a paragraph.  Text is first broken into
+                words and then joined back together to make up the
+                paragraph.  There are numerous attributes you can set to
+                your liking.
+
+paragraphs()    Treats each element of the array passed in as a separate
+                paragraph and passes them to format() for formatting.
+                The list returned will be then formatted into separate
+                paragraphs.
+
+center()        Centers all the lines that were passed in.
+
+expand()        Expand tabs into spaces.
+
+unexpand()      Turn spaces into tabs.  First calls expand() to expand
+                tabs into spaces and then turns tabstop number of spaces
+                into tabs, you can set tabstop size with tabstop().
+
+To install :
+
+perl Build.PL
+./Build
+./Build test
+./Build install
+
+Copyright (c) 1998 Gabor Egressy <gabor@vmunix.com>.
+All rights reserved.  All wrongs reversed.  This program is free
+software; you can redistribute and/or modify it under the same terms as
+Perl itself.

Text-Format/Text-Format/inc/Test/Run/Builder.pm

+package Test::Run::Builder;
+
+use strict;
+use warnings;
+
+use Module::Build;
+
+use vars qw(@ISA);
+
+@ISA = (qw(Module::Build));
+
+sub ACTION_runtest
+{
+    my ($self) = @_;
+    my $p = $self->{properties};
+
+    $self->depends_on('code');
+
+    local @INC = @INC;
+
+    # Make sure we test the module in blib/
+    unshift @INC, (File::Spec->catdir($p->{base_dir}, $self->blib, 'lib'),
+		 File::Spec->catdir($p->{base_dir}, $self->blib, 'arch'));
+
+    $self->do_test_run_tests;
+}
+
+sub ACTION_distruntest {
+  my ($self) = @_;
+
+  $self->depends_on('distdir');
+
+  my $start_dir = $self->cwd;
+  my $dist_dir = $self->dist_dir;
+  chdir $dist_dir or die "Cannot chdir to $dist_dir: $!";
+  # XXX could be different names for scripts
+
+  $self->run_perl_script('Build.PL') # XXX Should this be run w/ --nouse-rcfile
+      or die "Error executing 'Build.PL' in dist directory: $!";
+  $self->run_perl_script('Build')
+      or die "Error executing 'Build' in dist directory: $!";
+  $self->run_perl_script('Build', [], ['runtest'])
+      or die "Error executing 'Build test' in dist directory";
+  chdir $start_dir;
+}
+
+sub do_test_run_tests
+{
+    my $self = shift;
+
+    require Test::Run::CmdLine::Iface;
+
+    my $test_run =
+        Test::Run::CmdLine::Iface->new(
+            {
+                'test_files' => [glob("t/*.t")],
+            }   
+            # 'backend_params' => $self->_get_backend_params(),
+        );
+
+    return $test_run->run();
+}
+
+sub ACTION_tags
+{
+    return 
+        system(qw(
+            ctags -f tags --recurse --totals
+    		--exclude=blib/** --exclude=t/lib/**
+    		--exclude=.svn --exclude='*~'
+    		--languages=Perl --langmap=Perl:+.t
+    ));
+}
+
+1;
+

Text-Format/Text-Format/lib/Text/Format.pm

+package Text::Format;
+require 5.003;
+
+=head1 NAME
+
+B<Text::Format> - Various subroutines to format text.
+
+=head1 SYNOPSIS
+
+    use Text::Format;
+
+    my $text = Text::Format->new ( 
+        {
+            text           =>  [], # all
+            columns        =>  72, # format, paragraphs, center
+            leftMargin     =>   0, # format, paragraphs, center
+            rightMargin    =>   0, # format, paragraphs, center
+            firstIndent    =>   4, # format, paragraphs
+            bodyIndent     =>   0, # format, paragraphs
+            rightFill      =>   0, # format, paragraphs
+            rightAlign     =>   0, # format, paragraphs
+            justify        =>   0, # format, paragraphs
+            extraSpace     =>   0, # format, paragraphs
+            abbrevs        =>  {}, # format, paragraphs
+            hangingIndent  =>   0, # format, paragraphs
+            hangingText    =>  [], # format, paragraphs
+            noBreak        =>   0, # format, paragraphs
+            noBreakRegex   =>  {}, # format, paragraphs
+            tabstop        =>   8, # expand, unexpand,  center
+        }
+    ); # these are the default values
+
+    my %abbr = (foo => 1, bar => 1);
+    $text->abbrevs(\%abbr);
+    $text->abbrevs();
+    $text->abbrevs({foo => 1,bar => 1});
+    $text->abbrevs(qw/foo bar/);
+    $text->text(\@text);
+
+    $text->columns(132);
+    $text->tabstop(4);
+    $text->extraSpace(1);
+    $text->firstIndent(8);
+    $text->bodyIndent(4);
+    $text->config({tabstop => 4,firstIndent => 0});
+    $text->rightFill(0);
+    $text->rightAlign(0);
+
+=head1 DESCRIPTION
+
+The B<format> routine will format under all circumstances even if the
+width isn't enough to contain the longest words.  I<Text::Wrap> will die
+under these circumstances, although I am told this is fixed.  If columns
+is set to a small number and words are longer than that and the leading
+'whitespace' than there will be a single word on each line.  This will
+let you make a simple word list which could be indented or right
+aligned.  There is a chance for croaking if you try to subvert the
+module.  If you don't pass in text then the internal text is worked on,
+though not modfied.
+
+I<Text::Format> is meant for more powerful text formatting than what
+I<Text::Wrap> allows.  I also have a module called I<Text::NWrap> that
+is meant as a direct replacement for I<Text::Wrap>.  I<Text::NWrap>
+requires I<Text::Format> since it uses I<Text::Format-E<gt>format> to do the
+actual wrapping but gives you the interface of I<Text::Wrap>.
+
+General setup should be explained with the below graph.
+
+                           columns
+<------------------------------------------------------------>
+<----------><------><---------------------------><----------->
+ leftMargin  indent  text is formatted into here  rightMargin
+
+indent is firstIndent or bodyIndent depending on where we are in the
+paragraph.
+
+=over 4
+
+=item B<format> @ARRAY || \@ARRAY || [<FILEHANDLE>] || NOTHING
+
+Allows to do some advanced formatting of text into a paragraph, with
+indent for first line and body set separately.  Can specify total width
+of text, right fill with spaces or right align or justify (align to both
+margins), right margin and left margin, non-breaking space, two spaces
+at end of sentence, hanging indents (tagged paragraphs).  Strips all
+leading and trailing whitespace before proceeding.  Text is first split
+into words and then reassembled.  If no text is passed in then the
+internal text in the object is formatted.
+
+=item B<paragraphs> @ARRAY || \@ARRAY || [<FILEHANDLE>] || NOTHING
+
+Considers each element of text as a paragraph and if the indents are the
+same for first line and the body then the paragraphs are separated by a
+single empty line otherwise they follow one under the other.  If hanging
+indent is set then a single empty line will separate each paragraph as
+well.  Calls I<format> to do the actual formatting.  If no text is
+passed in then the internal text in the object is formatted, though not
+changed.
+
+=item B<center> @ARRAY || NOTHING
+
+Centers a list of strings in @ARRAY or internal text.  Empty lines
+appear as, you guessed it, empty lines.  Center strips all leading and
+trailing whitespace before proceeding.  Left margin and right margin can
+be set.  If no text is passed in then the internal text in the object is
+formatted.
+
+=item B<expand> @ARRAY || NOTHING
+
+Expand tabs in the list of text to tabstop number of spaces in @ARRAY or
+internal text.  Doesn't modify the internal text just passes back the
+modified text.  If no text is passed in then the internal text in the
+object is formatted.
+
+=item B<unexpand> @ARRAY || NOTHING
+
+Tabstop number of spaces are turned into tabs in @ARRAY or internal
+text.  Doesn't modify the internal text just passes back the modified
+text.  If no text is passed in then the internal text in the object is
+formatted.
+
+=item B<new> \%HASH || NOTHING
+
+Instantiates the object.  If you pass a reference to a hash, or an
+anonymous hash then it is used in setting attributes.
+
+=item B<config> \%HASH
+
+Allows the configuration of all object attributes at once.  Returns the
+object prior to configuration.  You can use it to make a clone of your
+object before you change attributes.
+
+=item B<columns> NUMBER || NOTHING
+
+Set width of text or retrieve width.  This is total width and includes
+indentation and the right and left margins.
+
+=item B<tabstop> NUMBER || NOTHING
+
+Set tabstop size or retrieve tabstop size, only used by expand, unexpand
+and center.
+
+=item B<firstIndent> NUMBER || NOTHING
+
+Set or get indent for the first line of paragraph.  This is the number
+of spaces to indent.
+
+=item B<bodyIndent> NUMBER || NOTHING
+
+Set or get indent for the body of paragraph.  This is the number of
+spaces to indent.
+
+=item B<leftMargin> NUMBER || NOTHING
+
+Set or get width of left margin.  This is the number of spaces used for
+the margin.
+
+=item B<rightMargin> NUMBER || NOTHING
+
+Set or get width of right margin.  This is the number of spaces used for
+the margin.
+
+=item B<rightFill> 0 || 1 || NOTHING
+
+Set right fill or retrieve its value.  The filling is done with spaces.
+Keep in mind that if I<rightAlign> is also set then both I<rightFill>
+and I<rightAlign> are ignored.
+
+=item B<rightAlign> 0 || 1 || NOTHING
+
+Set right align or retrieve its value.  Text is aligned with the right
+side of the margin.  Keep in mind that if I<rightFill> is also set then
+both I<rightFill> and I<rightAlign> are ignored.
+
+=item B<justify> 0 || 1 || NOTHING
+
+Set justify or retrieve its value.  Text is aligned with both margins,
+adding extra spaces as necessary to align text with left and right
+margins.  Keep in mind that if either of I<rightAlign> or I<rightFill>
+are set then I<justify> is ignored, even if both are set in which case
+they are all ignored.
+
+=item B<text> \@ARRAY || NOTHING
+
+Pass in a reference to your text, or an anonymous array of text that you
+want the routines to manipulate.  Returns the text held in the object.
+
+=item B<hangingIndent> 0 || 1 || NOTHING
+
+Use hanging indents in front of a paragraph, returns current value of
+attribute.  This is also called a tagged paragraph.
+
+=item B<hangingText> \@ARRAY || NOTHING
+
+The text that will be displayed in front of each paragraph, if you call
+I<format> then only the first element is used, if you call I<paragraphs>
+then I<paragraphs> cycles through all of them.  If you have more
+paragraphs than elements in your array than the remainder of the
+paragraphs will not have a hanging indented text.  Pass a reference to
+your array.  This is also called a tagged paragraph.
+
+=item B<noBreak> 0 || 1 || NOTHING
+
+Set whether you want to use the non-breaking space feature.
+
+=item B<noBreakRegex> \%HASH || NOTHING
+
+Pass in a reference to your hash that would hold the regexes on which not
+to break.  Without any arguments, it returns the hash.
+eg.
+
+    {'^Mrs?\.$' => '^\S+$','^\S+$' => '^(?:S|J)r\.$'}
+
+don't break names such as 
+Mr. Jones, Mrs. Jones, Jones Jr.
+
+The breaking algorithm is simple.  If there should not be a break at the
+current end of sentence, then a backtrack is done till there are two
+words on which breaking is allowed.  If no two such words are found then
+the end of sentence is broken anyhow.  If there is a single word on
+current line then no backtrack is done and the word is stuck on the end.
+This is so you can make a list of names for example.
+
+=item B<extraSpace> 0 || 1 || NOTHING
+
+Add extra space after end of sentence, normally I<format> would add 1
+space after end of sentence, if this is set to 1 then 2 spaces are used.
+Abbreviations are not followed by two spaces.  There are a few internal
+abbreviations and you can add your own to the object with I<abbrevs>
+
+=item B<abbrevs> \%HASH || @ARRAY || NOTHING
+
+Add to the current abbreviations, takes a reference to your hash or an
+array of abbreviations, if called a second time the original reference
+is removed and replaced by the new one.  Returns the current INTERNAL
+abbreviations.
+
+=back
+
+=head1 EXAMPLE
+
+    use Text::Format;
+
+    my $text = Text::Format->new;
+
+    $text->rightFill(1);
+    $text->columns(65);
+    $text->tabstop(4);
+
+    print $text->format("a line to format to an indented regular
+            paragraph using 65 character wide display");
+    print $text->paragraphs("paragraph one","paragraph two");
+    print $text->center("hello world","nifty line 2");
+    print $text->expand("\t\thello world\n","hmm,\twell\n");
+    print $text->unexpand("    hello world\n","    hmm");
+
+    $text->config({columns => 132, tabstop => 4});
+
+    $text = Text::Format->new();
+
+    print $text->format(@text);
+    print $text->paragraphs(@text);
+    print $text->center(@text);
+    print $text->format([<FILEHANDLE>]);
+    print $text->format([$fh->getlines()]);
+    print $text->paragraphs([<FILEHANDLE>]);
+    print $text->expand(@text);
+    print $text->unexpand(@text);
+
+    $text = Text::Format->new
+        ({tabstop => 4,bodyIndent => 4,text => \@text});
+
+    print $text->format();
+    print $text->paragraphs();
+    print $text->center();
+    print $text->expand();
+    print $text->unexpand();
+
+    print Text::Format->new({columns => 95})->format(@text);
+
+=head1 BUGS
+
+Line length can exceed the number of specified columns 
+if columns is set to a small number and long words plus leading whitespace 
+exceed the specified column length.  Actually I see this as a feature since it
+can be used to make up a nice word list.
+
+=head1 AUTHOR
+
+Gabor Egressy B<gabor@vmunix.com>
+
+Copyright (c) 1998 Gabor Egressy.  All rights reserved.  All wrongs
+reversed.  This program is free software; you can redistribute and/or
+modify it under the same terms as Perl itself.
+
+Adopted and modified by Shlomi Fish, L<http://www.shlomifish.org/> - all
+rights disclaimed.
+
+=head1 ACKNOWLEDGMENTS
+
+B<Tom Phoenix>
+
+Found a bug with code for two spaces at the end of the sentence and provided
+a code fragment for a better solution. Also some preliminary suggestions on
+the design.
+
+B<Brad Appleton>
+
+Suggestion and explanation of hanging indents, suggestion for
+non-breaking whitespace, general suggestions with regard to interface
+design.
+
+B<Byron Brummer>
+
+Suggestion for better interface design and object design, code for
+better implementation of getting abbreviations.
+
+B<H. Merijn Brand>
+
+Suggestion for a justify feature and original code for doing the
+justification.  I changed the code to take into account the extra space
+at end of sentence feature.
+
+=head1 TODO
+
+=cut
+
+use Carp;
+use strict;
+use vars qw($VERSION);
+
+$VERSION = '0.53';
+
+# local abbreviations, you can add your own with abbrevs()
+my %abbrev = (
+    Mr  => 1,
+    Mrs => 1,
+    Ms  => 1,
+    Jr  => 1,
+    Sr  => 1,
+);
+
+# formats text into a nice paragraph format.  can set a variety of
+# attributes such as first line indent, body indent, left and right
+# margin, right align, right fill with spaces, non-breaking spaces,
+# justification to both margins
+sub format($@)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+    my @wrap = @_
+        if @_ > 0;
+
+    @wrap = @{$_[0]}
+        if ref $_[0] eq 'ARRAY';
+    @wrap =  @{$this->{'_text'}}
+        if @wrap < 1;
+
+    my $findent = ' ' x $this->{'_findent'};
+    my $bindent = ' ' x $this->{'_bindent'};
+
+    my @words = split /\s+/,join ' ',@wrap;
+    shift @words
+        unless defined($words[0]) && $words[0] ne '';
+#if $words[0] eq '';
+
+    @wrap = ();
+    my ($line,$width,$abbrev);
+    $abbrev = 0;
+    $width = $this->{'_cols'} - $this->{'_findent'}
+        - $this->{'_lmargin'} - $this->{'_rmargin'};
+    $line = shift @words;
+    $abbrev = $this->__is_abbrev($line)
+        if defined $line;
+    while (defined ($_ = shift @words)) {
+        if(length($_) + length($line) < $width - 1
+                || ($line !~ /[.?!]['"]?$/ || $abbrev)
+                && length($_) + length($line) < $width) {
+            $line .= ' '
+                if $line =~ /[.?!]['"]?$/ && ! $abbrev;
+            $line .= ' ' . $_;
+        }
+        else {
+            last;
+        }
+        $abbrev = $this->__is_abbrev($_);
+    }
+    ($line,$_) = $this->__do_break($line,$_)
+        if $this->{'_nobreak'} && defined $line;
+    push @wrap,$this->__make_line($line,$findent,$width,defined $_)
+        if defined $line;
+    $line = $_;
+    $width = $this->{'_cols'} - $this->{'_bindent'}
+        - $this->{'_lmargin'} - $this->{'_rmargin'};
+    $abbrev = 0;
+    $abbrev = $this->__is_abbrev($line)
+        if defined $line;
+    while (defined ($_ = shift @words)) {
+        if(length($_) + length($line) < $width - 1
+                || ($line !~ /[.?!]['"]?$/ || $abbrev)
+                && length($_) + length($line) < $width) {
+            $line .= ' '
+                if $line =~ /[.?!]['"]?$/ && ! $abbrev;
+            $line .= ' ' . $_;
+        }
+        else {
+            ($line,$_) = $this->__do_break($line,$_)
+                if $this->{'_nobreak'};
+            push @wrap,$this->__make_line($line,$bindent,$width,defined $_)
+                if defined $line;
+            $line = $_;
+        }
+        $abbrev = $this->__is_abbrev($_)
+            if defined $_;
+    }
+    push @wrap,$this->__make_line($line,$bindent,$width,0)
+        if defined $line;
+
+    if($this->{'_hindent'} && @wrap > 0) {
+        my $caller = (caller 1)[3];
+        $caller = ''
+            unless defined $caller;
+        $this->{'_hindcurr'} = $this->{'_hindtext'}->[0]
+            if defined $this->{'_hindtext'}->[0]
+                && length($this->{'_hindcurr'}) < 1
+                && $caller ne 'Text::Format::paragraphs';
+        my ($fchar) = $wrap[0] =~ /(\S)/;
+        my $white = index $wrap[0],$fchar;
+        if($white  - $this->{'_lmargin'} - 1 > length($this->{'_hindcurr'})) {
+            $white = length($this->{'_hindcurr'}) + $this->{'_lmargin'};
+            $wrap[0] =~
+                s/^ {$white}/' ' x $this->{'_lmargin'} . $this->{'_hindcurr'}/e;
+        }
+        else {
+            unshift @wrap,' ' x $this->{'_lmargin'} . $this->{'_hindcurr'} . "\n";
+        }
+    }
+
+    wantarray ? @wrap
+              : join '', @wrap;
+}
+
+# format lines in text into paragraphs with each element of @wrap a
+# paragraph; uses Text::Format->format for the formatting
+sub paragraphs($@)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+    my @wrap = @_
+        if @_ > 0;
+
+    @wrap = @{$_[0]}
+        if ref $_[0] eq 'ARRAY';
+    @wrap =  @{$this->{'_text'}}
+        if @wrap < 1;
+
+    my (@ret,$end,$cnt,$line);
+
+    # if indents are same, use newline between paragraphs
+    if($this->{'_findent'} == $this->{'_bindent'} ||
+            $this->{'_hindent'}) {
+        $end = "\n";
+    }
+    else {
+        $end = '';
+    }
+
+    $cnt = 0;
+    for (@wrap) {
+        $this->{'_hindcurr'} = $this->{'_hindtext'}->[$cnt]
+            if $this->{'_hindent'};
+        $this->{'_hindcurr'} = ''
+            unless defined $this->{'_hindcurr'};
+        $line = $this->format($_);
+        push @ret,$line . $end
+            if defined $line && length $line > 0;
+        ++$cnt;
+    }
+    chop $ret[$#ret]
+        if defined($ret[$#ret]) && $ret[$#ret] =~ /\n\n$/;
+#if $ret[$#ret] =~ /\n\n$/;
+
+    wantarray ? @ret
+              : join '',@ret;
+}
+
+# center text using spaces on left side to pad it out
+# empty lines are preserved
+sub center($@)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+    my @center = @_
+        if @_ > 0;
+    @center =  @{$this->{'_text'}}
+        if @center < 1;
+    my ($tabs);
+    my $width = $this->{'_cols'} - $this->{'_lmargin'} - $this->{'_rmargin'};
+
+    for (@center) {
+        s/(?:^\s+|\s+$)|\n//g;
+        $tabs = tr/\t//; # count tabs
+        substr($_,0,0) = ' ' x int(($width - length($_)
+                - $tabs * $this->{'_tabs'} + $tabs) / 2)
+            if length > 0;
+        substr($_,0,0) = ' ' x $this->{'_lmargin'}
+            if length > 0;
+        substr($_,length) = "\n";
+    }
+
+    wantarray ? @center
+              : join '',@center;
+}
+
+# expand tabs to spaces
+# should be similar to Text::Tabs::expand
+sub expand($@)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+    my @lines = @_
+        if @_ > 0;
+    @lines =  @{$this->{'_text'}}
+        if @lines < 1;
+
+    for (@lines) {
+        s/\t/' ' x $this->{'_tabs'}/eg;
+    }
+
+    wantarray ? @lines
+              : $lines[0];
+}
+
+# turn tabstop number of spaces into tabs
+# should be similar to Text::Tabs::unexpand
+sub unexpand($@)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+    my @lines = $this->expand(@_);
+
+    for (@lines) {
+        s/ {$this->{'_tabs'}}/\t/g;
+    }
+
+    wantarray ? @lines
+              : $lines[0];
+}
+
+# return a reference to the object, call as $text = Text::Format->new()
+# can be used to clone the current reference $ntext = $text->new()
+sub new($@)
+{
+    my $this = shift;
+    my $ref;
+    if(ref $_[0] eq 'HASH') {
+        $ref = shift;
+    }
+    elsif(scalar(@_) % 2 == 0) {
+        my %ref = @_;
+        $ref = \%ref;
+    }
+    else {
+        $ref = '';
+    }
+    my %clone = %{$this}
+        if ref $this;
+
+    my $conf = {
+        _cols          =>  72,
+        _tabs          =>   8,
+        _findent       =>   4,
+        _bindent       =>   0,
+        _fill          =>   0,
+        _align         =>   0,
+        _justify       =>   0,
+        _lmargin       =>   0,
+        _rmargin       =>   0,
+        _space         =>   0,
+        _abbrs         =>  {},
+        _text          =>  [],
+        _hindent       =>   0,
+        _hindtext      =>  [],
+        _hindcurr      =>  '',
+        _nobreak       =>   0,
+        _nobreakregex  =>  {},
+    };
+
+    if(ref $ref eq 'HASH') {
+        $conf->{'_cols'} = abs int $ref->{'columns'}
+            if defined $ref->{'columns'};
+        $conf->{'_tabs'} = abs int $ref->{'tabstop'}
+            if defined $ref->{'tabstop'};
+        $conf->{'_findent'} = abs int $ref->{'firstIndent'}
+            if defined $ref->{'firstIndent'};
+        $conf->{'_bindent'} = abs int $ref->{'bodyIndent'}
+            if defined $ref->{'bodyIndent'};
+        $conf->{'_fill'} = abs int $ref->{'rightFill'}
+            if defined $ref->{'rightFill'};
+        $conf->{'_align'} = abs int $ref->{'rightAlign'}
+            if defined $ref->{'rightAlign'};
+        $conf->{'_justify'} = abs int $ref->{'justify'}
+            if defined $ref->{'justify'};
+        $conf->{'_lmargin'} = abs int $ref->{'leftMargin'}
+            if defined $ref->{'leftMargin'};
+        $conf->{'_rmargin'} = abs int $ref->{'rightMargin'}
+            if defined $ref->{'rightMargin'};
+        $conf->{'_space'} = abs int $ref->{'extraSpace'}
+            if defined $ref->{'extraSpace'};
+        $conf->{'_abbrs'} = $ref->{'abbrevs'}
+            if defined $ref->{'abbrevs'}
+                && ref $ref->{'abbrevs'} eq 'HASH';
+        $conf->{'_text'} = $ref->{'text'}
+            if defined $ref->{'text'}
+                && ref $ref->{'text'} eq 'ARRAY';
+        $conf->{'_hindent'} = abs int $ref->{'hangingIndent'}
+            if defined $ref->{'hangingIndent'};
+        $conf->{'_hindtext'} = $ref->{'hangingText'}
+            if defined $ref->{'hangingText'}
+                && ref $ref->{'hangingText'} eq 'ARRAY';
+        $conf->{'_nobreak'} = abs int$ref->{'noBreak'}
+            if defined $ref->{'noBreak'};
+        $conf->{'_nobreakregex'} = $ref->{'noBreakRegex'}
+            if defined $ref->{'noBreakRegex'}
+                && ref $ref->{'noBreakRegex'} eq 'HASH';
+    }
+
+    ref $this ? bless \%clone, ref $this
+              : bless $conf, $this;
+}
+
+# configure all the attributes of the object
+# returns the old object prior to configuration
+sub config($@)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+    my $conf;
+    if(ref $_[0] eq 'HASH') {
+        $conf = shift;
+    }
+    elsif(scalar(@_) % 2 == 0) {
+        my %conf = @_;
+        $conf = \%conf;
+    }
+    else {
+        croak "Bad hash ref";
+    }
+    my %clone = %{$this};
+
+    $this->{'_cols'} = abs int $conf->{'columns'}
+        if defined $conf->{'columns'};
+    $this->{'_tabs'} = abs int $conf->{'tabstop'}
+        if defined $conf->{'tabstop'};
+    $this->{'_findent'} = abs int $conf->{'firstIndent'}
+        if defined $conf->{'firstIndent'};
+    $this->{'_bindent'} = abs int $conf->{'bodyIndent'}
+        if defined $conf->{'bodyIndent'};
+    $this->{'_fill'} = abs int $conf->{'rightFill'}
+        if defined $conf->{'rightFill'};
+    $this->{'_align'} = abs int $conf->{'rightAlign'}
+        if defined $conf->{'rightAlign'};
+    $this->{'_justify'} = abs int $conf->{'justify'}
+        if defined $conf->{'justify'};
+    $this->{'_lmargin'} = abs int $conf->{'leftMargin'}
+        if defined $conf->{'leftMargin'};
+    $this->{'_rmargin'} = abs int $conf->{'rightMargin'}
+        if defined $conf->{'rightMargin'};
+    $this->{'_space'} = abs int $conf->{'extraSpace'}
+        if defined $conf->{'extraSpace'};
+    $this->{'_abbrs'} = $conf->{'abbrevs'}
+        if defined $conf->{'abbrevs'}
+            && ref $conf->{'abbrevs'} eq 'HASH';
+    $this->{'_text'} = $conf->{'text'}
+        if defined $conf->{'text'}
+            && ref $conf->{'text'} eq 'ARRAY';
+    $this->{'_hindent'} = abs int $conf->{'hangingIndent'}
+        if defined $conf->{'hangingIndent'};
+    $this->{'_hindtext'} = $conf->{'hangingText'}
+        if defined $conf->{'hangingText'}
+            && ref $conf->{'hangingText'} eq 'ARRAY';
+    $this->{'_nobreak'} = abs int $conf->{'noBreak'}
+        if defined $conf->{'noBreak'};
+    $this->{'_nobreakregex'} = $conf->{'noBreakRegex'}
+        if defined $conf->{'noBreakRegex'}
+            && ref $conf->{'noBreakRegex'} eq 'HASH';
+
+    bless \%clone, ref $this;
+}
+
+sub columns($;$)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+
+    @_ ? $this->{'_cols'} = abs int shift
+       : $this->{'_cols'};
+}
+
+sub tabstop($;$)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+
+    @_ ? $this->{'_tabs'} = abs int shift
+       : $this->{'_tabs'};
+}
+
+sub firstIndent($;$)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+
+    @_ ? $this->{'_findent'} = abs int shift
+       : $this->{'_findent'};
+}
+
+sub bodyIndent($;$)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+
+    @_ ? $this->{'_bindent'} = abs int shift
+       : $this->{'_bindent'};
+}
+
+sub rightFill($;$)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+
+    @_ ? $this->{'_fill'} = abs int shift
+       : $this->{'_fill'};
+}
+
+sub rightAlign($;$)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+
+    @_ ? $this->{'_align'} = abs int shift
+       : $this->{'_align'};
+}
+
+sub justify($;$)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+
+    @_ ? $this->{'_justify'} = abs int shift
+       : $this->{'_justify'};
+}
+
+sub leftMargin($;$)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+
+    @_ ? $this->{'_lmargin'} = abs int shift
+       : $this->{'_lmargin'};
+}
+
+sub rightMargin($;$)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+
+    @_ ? $this->{'_rmargin'} = abs int shift
+       : $this->{'_rmargin'};
+}
+
+sub extraSpace($;$)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+
+    @_ ? $this->{'_space'} = abs int shift
+       : $this->{'_space'};
+}
+
+# takes a reference to your hash or takes a list of abbreviations,
+# returns the INTERNAL abbreviations
+sub abbrevs($@)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+
+    if(ref $_[0] eq 'HASH') {
+        $this->{'_abbrs'} = shift;
+    }
+    elsif(@_ > 0) {
+        my %tmp;
+        @tmp{@_} = @_;
+        $this->{'_abbrs'} = \%tmp;
+    }
+
+    wantarray ? sort keys %abbrev
+              : join ' ',sort keys %abbrev;
+}
+
+sub text($;$)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+    my $text = shift;
+
+    $this->{'_text'} = $text
+        if ref $text eq 'ARRAY';
+
+    wantarray ? @{$this->{'_text'}}
+              : join ' ', @{$this->{'_text'}};
+}
+
+sub hangingIndent($;$)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+
+    @_ ? $this->{'_hindent'} = abs int shift
+       : $this->{'_hindent'};
+}
+
+sub hangingText($;$)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+    my $text = shift;
+
+    $this->{'_hindtext'} = $text
+        if ref $text eq 'ARRAY';
+
+    wantarray ?  @{$this->{'_hindtext'}}
+              : join ' ', @{$this->{'_hindtext'}};
+}
+
+sub noBreak($;$)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+
+    @_ ? $this->{'_nobreak'} = abs int shift
+       : $this->{'_nobreak'};
+}
+
+sub noBreakRegex($;$)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+    my $nobreak = shift;
+    
+    $this->{'_nobreakregex'} = $nobreak
+        if ref $nobreak eq 'HASH';
+
+    %{$this->{'_nobreakregex'}};
+}
+
+# internal routine, should not be called by an external routine
+sub __make_line($$$$$)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+    my ($line,$lead_white,$width,$not_last) = @_;
+    my $fill = '';
+    my $lmargin = ' ' x $this->{'_lmargin'};
+
+    $fill = ' ' x ($width - length($line))
+        if $this->{'_fill'} && ! $this->{'_align'};
+    if($this->{'_justify'} && ! ($this->{'_fill'} || $this->{'_align'})
+            && defined $line && $line =~ /\S+\s+\S+/ && $not_last) {
+        my $spaces = $width - length($line);
+        my @words = split /(\s+)/,$line;
+        my $ws = int ($spaces / int (@words / 2)); # for filling all gaps
+        $spaces %= int (@words / 2)
+            if $ws > 0; # if we must fill between every single word
+        for (reverse @words) {
+            next
+                if /^\S/;
+            substr($_,0,0) = ' ' x $ws;
+            $spaces || next;
+            substr($_,0,0) = ' ';
+            --$spaces;
+        }
+        $line = join '',@words;
+    }
+    $line = $lmargin . $lead_white . $line . $fill . "\n"
+        if defined $line;
+    substr($line,0,0) = ' ' x ($this->{'_cols'}
+            - $this->{'_rmargin'} - (length($line) - 1))
+        if $this->{'_align'} && ! $this->{'_fill'} && defined $line;
+
+    $line;
+}
+
+# internal routine, should not be called by an external routine
+sub __is_abbrev($$)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+    my $word = shift;
+
+    $word =~ s/\.$//
+        if defined $word; # remove period if there is one
+    # if we have an abbreviation OR no extra space is wanted after
+    # sentence endings
+    return 1
+        if ! $this->{'_space'}
+            || exists($abbrev{$word}) || exists(${$this->{'_abbrs'}}{$word});
+
+    0;
+}
+
+# internal routine, should not be called by an external routine
+sub __do_break($$$)
+{
+    my $this = shift;
+    croak "Bad method call"
+        unless ref $this;
+    my ($line,$next_line) = @_;
+    my $no_break = 0;
+    my @words = split /\s+/,$line
+        if defined $line;
+    my $last_word = $words[$#words];
+
+    for (keys %{$this->{'_nobreakregex'}}) {
+        $no_break = 1
+            if $last_word =~ m
+                && $next_line =~ m
+    }
+
+    if($no_break && @words > 1) {
+        my $i;
+        for($i = $#words;$i > 0;--$i) {
+            $no_break = 0;
+            for (keys %{$this->{'_nobreakregex'}}) {
+                $no_break = 1
+                    if $words[$i - 1] =~ m
+                        && $words[$i] =~
+                            m
+            }
+            last
+                if ! $no_break;
+        }
+        if($i > 0) { # found break point
+            $line =~ s/((?:\S+\s+){$i})(.+)/$1/;
+            $next_line = $2 . ' ' . $next_line;
+            $line =~ s/\s+$//;
+        }
+        # else, no breakpoint found and must break here anyways :<
+    }
+    ($line,$next_line);
+}
+
+1;

Text-Format/Text-Format/t/format.t

+# Before `make install' is performed this script should be runnable with
+# `make test'. After `make install' it should work as `perl test.pl'
+
+######################### We start with some black magic to print on failure.
+
+use strict;
+use warnings;
+
+# Should be 5.
+use Test::More tests => 5;
+
+use Text::Format;
+
+# TEST
+ok(1, "Text::Format loaded.");
+
+######################### End of black magic.
+
+# Insert your test code below (better if it prints "ok 13"
+# (correspondingly "not ok 13") depending on the success of chunk 13
+# of the test code):
+
+{
+    my $text = Text::Format->new;
+
+    my @results = $text->paragraphs("hello world","cool");
+    # TEST
+    is (scalar(@results), 2, "2 results.");
+
+    @results = $text->format("hello world","cool");
+    # TEST
+    is (scalar(@results), 1, "formatting as one line.");
+
+    @results = $text->center("hello world","cool");
+    # TEST
+    is (scalar(@results), 2, "center()");
+
+    $text->columns(10);
+    $text->bodyIndent(8);
+
+    @results = $text->format("hello world","cool");
+
+    # TEST
+    is (scalar(@results), 3, "columns and bodyIndent");
+}

Text-Format/Text-Format/t/justify.t

+#!/usr/bin/perl
+
+# H.Merijn Brand, 23 Feb 1998 for PROCURA B.V., Heerhugowaard, The Netherlands
+# Testing Text::Format for justification only.
+
+# Running this script should yield the data after __END__
+# This test does not use tabstops, hanging indents or extra indents
+
+use strict;
+use warnings;
+
+# Should be 8.
+use Test::More tests => 8;
+
+use Text::Format;
+
+# TEST
+ok(1, "Loaded");
+
+# make test uses .../bin/perl
+# perl t/justify.t generates the <DATA> part
+
+my $text = 
+        "gjyfg uergf au eg uyefg uayg uyger uge uvyger uvga erugf uevg ueyrgv ".
+        "uaygerv uygaer uvygaervuy. aureyg aeurgv uayergv uegrv uyagr fuyg uyg".
+        " ruvyg aeruvg uevrg auygvre ayergv uyaergv uyagre vuyagervuygervuyg a".
+        "reuvg aervg eryvg revg yregv aregv ergv ugre vgerg aerug areuvg auerg".
+        " uyrgve uegr vuaguyf gaerfu ageruwf. augawfuygaweufyg rygg auydfg auy".
+        "efga uywef. auyefg uayergf uyagr yerg uger uweg g uyg uaygref uerg ae".
+        "gr uagr reg yeg ueg";
+
+my $t = Text::Format->new ({
+    columns	=> 40,
+    firstIndent	=> 0
+    });
+
+my $test = 2;
+
+# TEST
+ok (!chk_data (fmt_text (2, $t, 1, 0, 1, $text)), "2,1,0,1");
+# TEST
+ok (!chk_data (fmt_text (3, $t, 1, 0, 0, $text)), "3,1,0,0");
+# TEST
+ok (!chk_data (fmt_text (4, $t, 0, 1, 1, $text)), "4,0,1,1");
+# TEST
+ok (!chk_data (fmt_text (5, $t, 0, 1, 0, $text)), "5,0,1,0");
+
+my @nat = ("Nederlandse", "Duitse", "Tibetaanse", "Kiribatische", "Kongoleesche",
+        "Burger van Nieuw West-Vlaanderland", "Verweggistaneesche");
+
+# TEST
+ok (!chk_data (fmt_natio (6, $t, 47, 0, 1, @nat)), "fmt_natio 6");
+# TEST
+ok (!chk_data (fmt_natio (7, $t, 25, 0, 1, @nat)), "fmt_natio 7");
+# TEST
+ok (!chk_data (fmt_natio (8, $t, 25, 1, 0, @nat)), "fmt_natio 8");
+
+### ###########################################################################
+
+{
+    my @DATA;
+sub get_data
+{
+    # get what should be the result of the next test
+    my @data = ();
+    unless (@DATA) {
+        while (<DATA>) {
+            chomp;
+           s/^\s*=\s// && s/\s=$//;
+            push (@DATA, $_);
+            }
+        }
+
+    while ($DATA[0] =~ m/^#/) {
+        shift (@DATA);
+        }
+    until ($DATA[0] =~ m/^# Test/) {
+        push (@data, shift (@DATA));
+        }
+    @data;
+    } # get_data
+}
+
+sub chk_data
+{
+    my @gen = @_;
+    my @dat = get_data ();
+
+    scalar      @gen  == scalar      @dat  || return (1);
+    join ("\n", @gen) eq join ("\n", @dat) || return (1);
+    return (0);
+}
+
+sub fmt_text
+{
+    my ($tst, $t, $j, $f, $e, $text) = @_;
+
+    # $verbose &&
+    # print STDERR "# Test $tst: ",
+    #     $j ? "JUSTIFY"    : "justify",	", ",
+    #     $f ? "FILL"       : "fill",		", ",
+    #     $e ? "EXTRASPACE" : "extraspace",	"\n";
+
+    $t->config ({ justify => $j, extraSpace => $e, rightFill => $f });
+    my @lines = split ("\n", $t->format ($text));
+
+    # $verbose &&
+    # print STDERR "= ", join (" =\n= ", @lines), " =\n";
+
+    @lines;
+    } # fmt_text
+
+sub fmt_natio
+{
+    my ($tst, $t, $c, $j, $f, @nat) = @_;
+
+    # $verbose &&
+    # print STDERR "# Test $tst: ",
+    # $j ? "JUSTIFY" : "justify",	", ",
+    # $f ? "FILL"    : "fill",	"\n";
+    $t->config ({ columns => $c, justify => $j, rightFill => $f });
+    my @lines = split ("\n", $t->format (join (", ", @nat)));
+    # $verbose &&
+    # print STDERR "= ", join (" =\n= ", @lines), " =\n";
+    @lines;
+    } # fmt_natio
+
+__END__
+# Test 1: Loading Text::Format [Version]
+# Test 2: JUSTIFY, fill, EXTRASPACE
+= gjyfg uergf au eg uyefg uayg  uyger  uge =
+= uvyger uvga erugf  uevg  ueyrgv  uaygerv =
+= uygaer   uvygaervuy.    aureyg    aeurgv =
+= uayergv  uegrv  uyagr  fuyg  uyg   ruvyg =
+= aeruvg  uevrg  auygvre  ayergv   uyaergv =
+= uyagre  vuyagervuygervuyg  areuvg  aervg =
+= eryvg revg yregv aregv ergv  ugre  vgerg =
+= aerug areuvg auerg uyrgve  uegr  vuaguyf =
+= gaerfu ageruwf.   augawfuygaweufyg  rygg =
+= auydfg auyefga  uywef.   auyefg  uayergf =
+= uyagr yerg uger uweg g uyg uaygref  uerg =
+= aegr uagr reg yeg ueg =
+# Test 3: JUSTIFY, fill, extraspace
+= gjyfg uergf au eg uyefg uayg  uyger  uge =
+= uvyger uvga erugf  uevg  ueyrgv  uaygerv =
+= uygaer uvygaervuy. aureyg aeurgv uayergv =
+= uegrv uyagr fuyg uyg ruvyg aeruvg  uevrg =
+= auygvre    ayergv     uyaergv     uyagre =
+= vuyagervuygervuyg  areuvg  aervg   eryvg =
+= revg yregv aregv ergv ugre  vgerg  aerug =
+= areuvg auerg uyrgve uegr vuaguyf  gaerfu =
+= ageruwf.  augawfuygaweufyg  rygg  auydfg =
+= auyefga uywef. auyefg uayergf uyagr yerg =
+= uger uweg g uyg uaygref uerg  aegr  uagr =
+= reg yeg ueg =
+# Test 4: justify, FILL, EXTRASPACE
+= gjyfg uergf au eg uyefg uayg uyger uge   =
+= uvyger uvga erugf uevg ueyrgv uaygerv    =
+= uygaer uvygaervuy.  aureyg aeurgv        =
+= uayergv uegrv uyagr fuyg uyg ruvyg       =
+= aeruvg uevrg auygvre ayergv uyaergv      =
+= uyagre vuyagervuygervuyg areuvg aervg    =
+= eryvg revg yregv aregv ergv ugre vgerg   =
+= aerug areuvg auerg uyrgve uegr vuaguyf   =
+= gaerfu ageruwf.  augawfuygaweufyg rygg   =
+= auydfg auyefga uywef.  auyefg uayergf    =
+= uyagr yerg uger uweg g uyg uaygref uerg  =
+= aegr uagr reg yeg ueg                    =
+# Test 5: justify, FILL, extraspace
+= gjyfg uergf au eg uyefg uayg uyger uge   =
+= uvyger uvga erugf uevg ueyrgv uaygerv    =
+= uygaer uvygaervuy. aureyg aeurgv uayergv =
+= uegrv uyagr fuyg uyg ruvyg aeruvg uevrg  =
+= auygvre ayergv uyaergv uyagre            =
+= vuyagervuygervuyg areuvg aervg eryvg     =
+= revg yregv aregv ergv ugre vgerg aerug   =
+= areuvg auerg uyrgve uegr vuaguyf gaerfu  =
+= ageruwf. augawfuygaweufyg rygg auydfg    =
+= auyefga uywef. auyefg uayergf uyagr yerg =
+= uger uweg g uyg uaygref uerg aegr uagr   =
+= reg yeg ueg                              =
+# Test 6:
+= Nederlandse, Duitse, Tibetaanse, Kiribatische,  =
+= Kongoleesche, Burger van Nieuw                  =
+= West-Vlaanderland, Verweggistaneesche           =
+# Test 7:
+= Nederlandse, Duitse,      =
+= Tibetaanse, Kiribatische, =
+= Kongoleesche, Burger van  =
+= Nieuw West-Vlaanderland,  =
+= Verweggistaneesche        =
+# Test 8:
+= Nederlandse,      Duitse, =
+= Tibetaanse, Kiribatische, =
+= Kongoleesche, Burger  van =
+= Nieuw  West-Vlaanderland, =
+= Verweggistaneesche =
+# Test End
Tip: Filter by directory path e.g. /media app.js to search for public/media/app.js.
Tip: Use camelCasing e.g. ProjME to search for ProjectModifiedEvent.java.
Tip: Filter by extension type e.g. /repo .js to search for all .js files in the /repo directory.
Tip: Separate your search with spaces e.g. /ssh pom.xml to search for src/ssh/pom.xml.
Tip: Use ↑ and ↓ arrow keys to navigate and return to view the file.
Tip: You can also navigate files with Ctrl+j (next) and Ctrl+k (previous) and view the file with Ctrl+o.
Tip: You can also navigate files with Alt+j (next) and Alt+k (previous) and view the file with Alt+o.