1# Convert POD data to formatted text.
2#
3# This module converts POD to formatted text.  It replaces the old Pod::Text
4# module that came with versions of Perl prior to 5.6.0 and attempts to match
5# its output except for some specific circumstances where other decisions
6# seemed to produce better output.  It uses Pod::Parser and is designed to be
7# very easy to subclass.
8#
9# SPDX-License-Identifier: GPL-1.0-or-later OR Artistic-1.0-Perl
10
11##############################################################################
12# Modules and declarations
13##############################################################################
14
15package Pod::Text;
16
17use 5.006;
18use strict;
19use warnings;
20
21use vars qw(@ISA @EXPORT %ESCAPES $VERSION);
22
23use Carp qw(carp croak);
24use Encode qw(encode);
25use Exporter ();
26use Pod::Simple ();
27
28@ISA = qw(Pod::Simple Exporter);
29
30# We have to export pod2text for backward compatibility.
31@EXPORT = qw(pod2text);
32
33$VERSION = '4.11';
34
35# Ensure that $Pod::Simple::nbsp and $Pod::Simple::shy are available.  Code
36# taken from Pod::Simple 3.32, but was only added in 3.30.
37my ($NBSP, $SHY);
38if ($Pod::Simple::VERSION ge 3.30) {
39    $NBSP = $Pod::Simple::nbsp;
40    $SHY  = $Pod::Simple::shy;
41} else {
42    if ($] ge 5.007_003) {
43        $NBSP = chr utf8::unicode_to_native(0xA0);
44        $SHY  = chr utf8::unicode_to_native(0xAD);
45    } elsif (Pod::Simple::ASCII) {
46        $NBSP = "\xA0";
47        $SHY  = "\xAD";
48    } else {
49        $NBSP = "\x41";
50        $SHY  = "\xCA";
51    }
52}
53
54##############################################################################
55# Initialization
56##############################################################################
57
58# This function handles code blocks.  It's registered as a callback to
59# Pod::Simple and therefore doesn't work as a regular method call, but all it
60# does is call output_code with the line.
61sub handle_code {
62    my ($line, $number, $parser) = @_;
63    $parser->output_code ($line . "\n");
64}
65
66# Initialize the object and set various Pod::Simple options that we need.
67# Here, we also process any additional options passed to the constructor or
68# set up defaults if none were given.  Note that all internal object keys are
69# in all-caps, reserving all lower-case object keys for Pod::Simple and user
70# arguments.
71sub new {
72    my $class = shift;
73    my $self = $class->SUPER::new;
74
75    # Tell Pod::Simple to handle S<> by automatically inserting &nbsp;.
76    $self->nbsp_for_S (1);
77
78    # Tell Pod::Simple to keep whitespace whenever possible.
79    if ($self->can ('preserve_whitespace')) {
80        $self->preserve_whitespace (1);
81    } else {
82        $self->fullstop_space_harden (1);
83    }
84
85    # The =for and =begin targets that we accept.
86    $self->accept_targets (qw/text TEXT/);
87
88    # Ensure that contiguous blocks of code are merged together.  Otherwise,
89    # some of the guesswork heuristics don't work right.
90    $self->merge_text (1);
91
92    # Pod::Simple doesn't do anything useful with our arguments, but we want
93    # to put them in our object as hash keys and values.  This could cause
94    # problems if we ever clash with Pod::Simple's own internal class
95    # variables.
96    my %opts = @_;
97    my @opts = map { ("opt_$_", $opts{$_}) } keys %opts;
98    %$self = (%$self, @opts);
99
100    # Send errors to stderr if requested.
101    if ($$self{opt_stderr} and not $$self{opt_errors}) {
102        $$self{opt_errors} = 'stderr';
103    }
104    delete $$self{opt_stderr};
105
106    # Validate the errors parameter and act on it.
107    if (not defined $$self{opt_errors}) {
108        $$self{opt_errors} = 'pod';
109    }
110    if ($$self{opt_errors} eq 'stderr' || $$self{opt_errors} eq 'die') {
111        $self->no_errata_section (1);
112        $self->complain_stderr (1);
113        if ($$self{opt_errors} eq 'die') {
114            $$self{complain_die} = 1;
115        }
116    } elsif ($$self{opt_errors} eq 'pod') {
117        $self->no_errata_section (0);
118        $self->complain_stderr (0);
119    } elsif ($$self{opt_errors} eq 'none') {
120        $self->no_errata_section (1);
121        $self->no_whining (1);
122    } else {
123        croak (qq(Invalid errors setting: "$$self{errors}"));
124    }
125    delete $$self{errors};
126
127    # Initialize various things from our parameters.
128    $$self{opt_alt}      = 0  unless defined $$self{opt_alt};
129    $$self{opt_indent}   = 4  unless defined $$self{opt_indent};
130    $$self{opt_margin}   = 0  unless defined $$self{opt_margin};
131    $$self{opt_loose}    = 0  unless defined $$self{opt_loose};
132    $$self{opt_sentence} = 0  unless defined $$self{opt_sentence};
133    $$self{opt_width}    = 76 unless defined $$self{opt_width};
134
135    # Figure out what quotes we'll be using for C<> text.
136    $$self{opt_quotes} ||= '"';
137    if ($$self{opt_quotes} eq 'none') {
138        $$self{LQUOTE} = $$self{RQUOTE} = '';
139    } elsif (length ($$self{opt_quotes}) == 1) {
140        $$self{LQUOTE} = $$self{RQUOTE} = $$self{opt_quotes};
141    } elsif (length ($$self{opt_quotes}) % 2 == 0) {
142        my $length = length ($$self{opt_quotes}) / 2;
143        $$self{LQUOTE} = substr ($$self{opt_quotes}, 0, $length);
144        $$self{RQUOTE} = substr ($$self{opt_quotes}, $length);
145    } else {
146        croak qq(Invalid quote specification "$$self{opt_quotes}");
147    }
148
149    # If requested, do something with the non-POD text.
150    $self->code_handler (\&handle_code) if $$self{opt_code};
151
152    # Return the created object.
153    return $self;
154}
155
156##############################################################################
157# Core parsing
158##############################################################################
159
160# This is the glue that connects the code below with Pod::Simple itself.  The
161# goal is to convert the event stream coming from the POD parser into method
162# calls to handlers once the complete content of a tag has been seen.  Each
163# paragraph or POD command will have textual content associated with it, and
164# as soon as all of a paragraph or POD command has been seen, that content
165# will be passed in to the corresponding method for handling that type of
166# object.  The exceptions are handlers for lists, which have opening tag
167# handlers and closing tag handlers that will be called right away.
168#
169# The internal hash key PENDING is used to store the contents of a tag until
170# all of it has been seen.  It holds a stack of open tags, each one
171# represented by a tuple of the attributes hash for the tag and the contents
172# of the tag.
173
174# Add a block of text to the contents of the current node, formatting it
175# according to the current formatting instructions as we do.
176sub _handle_text {
177    my ($self, $text) = @_;
178    my $tag = $$self{PENDING}[-1];
179    $$tag[1] .= $text;
180}
181
182# Given an element name, get the corresponding method name.
183sub method_for_element {
184    my ($self, $element) = @_;
185    $element =~ tr/-/_/;
186    $element =~ tr/A-Z/a-z/;
187    $element =~ tr/_a-z0-9//cd;
188    return $element;
189}
190
191# Handle the start of a new element.  If cmd_element is defined, assume that
192# we need to collect the entire tree for this element before passing it to the
193# element method, and create a new tree into which we'll collect blocks of
194# text and nested elements.  Otherwise, if start_element is defined, call it.
195sub _handle_element_start {
196    my ($self, $element, $attrs) = @_;
197    my $method = $self->method_for_element ($element);
198
199    # If we have a command handler, we need to accumulate the contents of the
200    # tag before calling it.
201    if ($self->can ("cmd_$method")) {
202        push (@{ $$self{PENDING} }, [ $attrs, '' ]);
203    } elsif ($self->can ("start_$method")) {
204        my $method = 'start_' . $method;
205        $self->$method ($attrs, '');
206    }
207}
208
209# Handle the end of an element.  If we had a cmd_ method for this element,
210# this is where we pass along the text that we've accumulated.  Otherwise, if
211# we have an end_ method for the element, call that.
212sub _handle_element_end {
213    my ($self, $element) = @_;
214    my $method = $self->method_for_element ($element);
215
216    # If we have a command handler, pull off the pending text and pass it to
217    # the handler along with the saved attribute hash.
218    if ($self->can ("cmd_$method")) {
219        my $tag = pop @{ $$self{PENDING} };
220        my $method = 'cmd_' . $method;
221        my $text = $self->$method (@$tag);
222        if (defined $text) {
223            if (@{ $$self{PENDING} } > 1) {
224                $$self{PENDING}[-1][1] .= $text;
225            } else {
226                $self->output ($text);
227            }
228        }
229    } elsif ($self->can ("end_$method")) {
230        my $method = 'end_' . $method;
231        $self->$method ();
232    }
233}
234
235##############################################################################
236# Output formatting
237##############################################################################
238
239# Wrap a line, indenting by the current left margin.  We can't use Text::Wrap
240# because it plays games with tabs.  We can't use formline, even though we'd
241# really like to, because it screws up non-printing characters.  So we have to
242# do the wrapping ourselves.
243sub wrap {
244    my $self = shift;
245    local $_ = shift;
246    my $output = '';
247    my $spaces = ' ' x $$self{MARGIN};
248    my $width = $$self{opt_width} - $$self{MARGIN};
249    while (length > $width) {
250        if (s/^([^\n]{0,$width})\s+// || s/^([^\n]{$width})//) {
251            $output .= $spaces . $1 . "\n";
252        } else {
253            last;
254        }
255    }
256    $output .= $spaces . $_;
257    $output =~ s/\s+$/\n\n/;
258    return $output;
259}
260
261# Reformat a paragraph of text for the current margin.  Takes the text to
262# reformat and returns the formatted text.
263sub reformat {
264    my $self = shift;
265    local $_ = shift;
266
267    # If we're trying to preserve two spaces after sentences, do some munging
268    # to support that.  Otherwise, smash all repeated whitespace.
269    if ($$self{opt_sentence}) {
270        s/ +$//mg;
271        s/\.\n/. \n/g;
272        s/\n/ /g;
273        s/   +/  /g;
274    } else {
275        s/\s+/ /g;
276    }
277    return $self->wrap ($_);
278}
279
280# Output text to the output device.  Replace non-breaking spaces with spaces
281# and soft hyphens with nothing, and then try to fix the output encoding if
282# necessary to match the input encoding unless UTF-8 output is forced.  This
283# preserves the traditional pass-through behavior of Pod::Text.
284sub output {
285    my ($self, @text) = @_;
286    my $text = join ('', @text);
287    if ($NBSP) {
288        $text =~ s/$NBSP/ /g;
289    }
290    if ($SHY) {
291        $text =~ s/$SHY//g;
292    }
293    unless ($$self{opt_utf8}) {
294        my $encoding = $$self{encoding} || '';
295        if ($encoding && $encoding ne $$self{ENCODING}) {
296            $$self{ENCODING} = $encoding;
297            eval { binmode ($$self{output_fh}, ":encoding($encoding)") };
298        }
299    }
300    if ($$self{ENCODE}) {
301        print { $$self{output_fh} } encode ('UTF-8', $text);
302    } else {
303        print { $$self{output_fh} } $text;
304    }
305}
306
307# Output a block of code (something that isn't part of the POD text).  Called
308# by preprocess_paragraph only if we were given the code option.  Exists here
309# only so that it can be overridden by subclasses.
310sub output_code { $_[0]->output ($_[1]) }
311
312##############################################################################
313# Document initialization
314##############################################################################
315
316# Set up various things that have to be initialized on a per-document basis.
317sub start_document {
318    my ($self, $attrs) = @_;
319    if ($$attrs{contentless} && !$$self{ALWAYS_EMIT_SOMETHING}) {
320        $$self{CONTENTLESS} = 1;
321    } else {
322        delete $$self{CONTENTLESS};
323    }
324    my $margin = $$self{opt_indent} + $$self{opt_margin};
325
326    # Initialize a few per-document variables.
327    $$self{INDENTS} = [];       # Stack of indentations.
328    $$self{MARGIN}  = $margin;  # Default left margin.
329    $$self{PENDING} = [[]];     # Pending output.
330
331    # We have to redo encoding handling for each document.
332    $$self{ENCODING} = '';
333
334    # When UTF-8 output is set, check whether our output file handle already
335    # has a PerlIO encoding layer set.  If it does not, we'll need to encode
336    # our output before printing it (handled in the output() sub).  Wrap the
337    # check in an eval to handle versions of Perl without PerlIO.
338    $$self{ENCODE} = 0;
339    if ($$self{opt_utf8}) {
340        $$self{ENCODE} = 1;
341        eval {
342            my @options = (output => 1, details => 1);
343            my $flag = (PerlIO::get_layers ($$self{output_fh}, @options))[-1];
344            if ($flag & PerlIO::F_UTF8 ()) {
345                $$self{ENCODE} = 0;
346                $$self{ENCODING} = 'UTF-8';
347            }
348        };
349    }
350
351    return '';
352}
353
354# Handle the end of the document.  The only thing we do is handle dying on POD
355# errors, since Pod::Parser currently doesn't.
356sub end_document {
357    my ($self) = @_;
358    if ($$self{complain_die} && $self->errors_seen) {
359        croak ("POD document had syntax errors");
360    }
361}
362
363##############################################################################
364# Text blocks
365##############################################################################
366
367# Intended for subclasses to override, this method returns text with any
368# non-printing formatting codes stripped out so that length() correctly
369# returns the length of the text.  For basic Pod::Text, it does nothing.
370sub strip_format {
371    my ($self, $string) = @_;
372    return $string;
373}
374
375# This method is called whenever an =item command is complete (in other words,
376# we've seen its associated paragraph or know for certain that it doesn't have
377# one).  It gets the paragraph associated with the item as an argument.  If
378# that argument is empty, just output the item tag; if it contains a newline,
379# output the item tag followed by the newline.  Otherwise, see if there's
380# enough room for us to output the item tag in the margin of the text or if we
381# have to put it on a separate line.
382sub item {
383    my ($self, $text) = @_;
384    my $tag = $$self{ITEM};
385    unless (defined $tag) {
386        carp "Item called without tag";
387        return;
388    }
389    undef $$self{ITEM};
390
391    # Calculate the indentation and margin.  $fits is set to true if the tag
392    # will fit into the margin of the paragraph given our indentation level.
393    my $indent = $$self{INDENTS}[-1];
394    $indent = $$self{opt_indent} unless defined $indent;
395    my $margin = ' ' x $$self{opt_margin};
396    my $tag_length = length ($self->strip_format ($tag));
397    my $fits = ($$self{MARGIN} - $indent >= $tag_length + 1);
398
399    # If the tag doesn't fit, or if we have no associated text, print out the
400    # tag separately.  Otherwise, put the tag in the margin of the paragraph.
401    if (!$text || $text =~ /^\s+$/ || !$fits) {
402        my $realindent = $$self{MARGIN};
403        $$self{MARGIN} = $indent;
404        my $output = $self->reformat ($tag);
405        $output =~ s/^$margin /$margin:/ if ($$self{opt_alt} && $indent > 0);
406        $output =~ s/\n*$/\n/;
407
408        # If the text is just whitespace, we have an empty item paragraph;
409        # this can result from =over/=item/=back without any intermixed
410        # paragraphs.  Insert some whitespace to keep the =item from merging
411        # into the next paragraph.
412        $output .= "\n" if $text && $text =~ /^\s*$/;
413
414        $self->output ($output);
415        $$self{MARGIN} = $realindent;
416        $self->output ($self->reformat ($text)) if ($text && $text =~ /\S/);
417    } else {
418        my $space = ' ' x $indent;
419        $space =~ s/^$margin /$margin:/ if $$self{opt_alt};
420        $text = $self->reformat ($text);
421        $text =~ s/^$margin /$margin:/ if ($$self{opt_alt} && $indent > 0);
422        my $tagspace = ' ' x $tag_length;
423        $text =~ s/^($space)$tagspace/$1$tag/ or warn "Bizarre space in item";
424        $self->output ($text);
425    }
426}
427
428# Handle a basic block of text.  The only tricky thing here is that if there
429# is a pending item tag, we need to format this as an item paragraph.
430sub cmd_para {
431    my ($self, $attrs, $text) = @_;
432    $text =~ s/\s+$/\n/;
433    if (defined $$self{ITEM}) {
434        $self->item ($text . "\n");
435    } else {
436        $self->output ($self->reformat ($text . "\n"));
437    }
438    return '';
439}
440
441# Handle a verbatim paragraph.  Just print it out, but indent it according to
442# our margin.
443sub cmd_verbatim {
444    my ($self, $attrs, $text) = @_;
445    $self->item if defined $$self{ITEM};
446    return if $text =~ /^\s*$/;
447    $text =~ s/^(\n*)([ \t]*\S+)/$1 . (' ' x $$self{MARGIN}) . $2/gme;
448    $text =~ s/\s*$/\n\n/;
449    $self->output ($text);
450    return '';
451}
452
453# Handle literal text (produced by =for and similar constructs).  Just output
454# it with the minimum of changes.
455sub cmd_data {
456    my ($self, $attrs, $text) = @_;
457    $text =~ s/^\n+//;
458    $text =~ s/\n{0,2}$/\n/;
459    $self->output ($text);
460    return '';
461}
462
463##############################################################################
464# Headings
465##############################################################################
466
467# The common code for handling all headers.  Takes the header text, the
468# indentation, and the surrounding marker for the alt formatting method.
469sub heading {
470    my ($self, $text, $indent, $marker) = @_;
471    $self->item ("\n\n") if defined $$self{ITEM};
472    $text =~ s/\s+$//;
473    if ($$self{opt_alt}) {
474        my $closemark = reverse (split (//, $marker));
475        my $margin = ' ' x $$self{opt_margin};
476        $self->output ("\n" . "$margin$marker $text $closemark" . "\n\n");
477    } else {
478        $text .= "\n" if $$self{opt_loose};
479        my $margin = ' ' x ($$self{opt_margin} + $indent);
480        $self->output ($margin . $text . "\n");
481    }
482    return '';
483}
484
485# First level heading.
486sub cmd_head1 {
487    my ($self, $attrs, $text) = @_;
488    $self->heading ($text, 0, '====');
489}
490
491# Second level heading.
492sub cmd_head2 {
493    my ($self, $attrs, $text) = @_;
494    $self->heading ($text, $$self{opt_indent} / 2, '==  ');
495}
496
497# Third level heading.
498sub cmd_head3 {
499    my ($self, $attrs, $text) = @_;
500    $self->heading ($text, $$self{opt_indent} * 2 / 3 + 0.5, '=   ');
501}
502
503# Fourth level heading.
504sub cmd_head4 {
505    my ($self, $attrs, $text) = @_;
506    $self->heading ($text, $$self{opt_indent} * 3 / 4 + 0.5, '-   ');
507}
508
509##############################################################################
510# List handling
511##############################################################################
512
513# Handle the beginning of an =over block.  Takes the type of the block as the
514# first argument, and then the attr hash.  This is called by the handlers for
515# the four different types of lists (bullet, number, text, and block).
516sub over_common_start {
517    my ($self, $attrs) = @_;
518    $self->item ("\n\n") if defined $$self{ITEM};
519
520    # Find the indentation level.
521    my $indent = $$attrs{indent};
522    unless (defined ($indent) && $indent =~ /^\s*[-+]?\d{1,4}\s*$/) {
523        $indent = $$self{opt_indent};
524    }
525
526    # Add this to our stack of indents and increase our current margin.
527    push (@{ $$self{INDENTS} }, $$self{MARGIN});
528    $$self{MARGIN} += ($indent + 0);
529    return '';
530}
531
532# End an =over block.  Takes no options other than the class pointer.  Output
533# any pending items and then pop one level of indentation.
534sub over_common_end {
535    my ($self) = @_;
536    $self->item ("\n\n") if defined $$self{ITEM};
537    $$self{MARGIN} = pop @{ $$self{INDENTS} };
538    return '';
539}
540
541# Dispatch the start and end calls as appropriate.
542sub start_over_bullet { $_[0]->over_common_start ($_[1]) }
543sub start_over_number { $_[0]->over_common_start ($_[1]) }
544sub start_over_text   { $_[0]->over_common_start ($_[1]) }
545sub start_over_block  { $_[0]->over_common_start ($_[1]) }
546sub end_over_bullet { $_[0]->over_common_end }
547sub end_over_number { $_[0]->over_common_end }
548sub end_over_text   { $_[0]->over_common_end }
549sub end_over_block  { $_[0]->over_common_end }
550
551# The common handler for all item commands.  Takes the type of the item, the
552# attributes, and then the text of the item.
553sub item_common {
554    my ($self, $type, $attrs, $text) = @_;
555    $self->item if defined $$self{ITEM};
556
557    # Clean up the text.  We want to end up with two variables, one ($text)
558    # which contains any body text after taking out the item portion, and
559    # another ($item) which contains the actual item text.  Note the use of
560    # the internal Pod::Simple attribute here; that's a potential land mine.
561    $text =~ s/\s+$//;
562    my ($item, $index);
563    if ($type eq 'bullet') {
564        $item = '*';
565    } elsif ($type eq 'number') {
566        $item = $$attrs{'~orig_content'};
567    } else {
568        $item = $text;
569        $item =~ s/\s*\n\s*/ /g;
570        $text = '';
571    }
572    $$self{ITEM} = $item;
573
574    # If body text for this item was included, go ahead and output that now.
575    if ($text) {
576        $text =~ s/\s*$/\n/;
577        $self->item ($text);
578    }
579    return '';
580}
581
582# Dispatch the item commands to the appropriate place.
583sub cmd_item_bullet { my $self = shift; $self->item_common ('bullet', @_) }
584sub cmd_item_number { my $self = shift; $self->item_common ('number', @_) }
585sub cmd_item_text   { my $self = shift; $self->item_common ('text',   @_) }
586sub cmd_item_block  { my $self = shift; $self->item_common ('block',  @_) }
587
588##############################################################################
589# Formatting codes
590##############################################################################
591
592# The simple ones.
593sub cmd_b { return $_[0]{alt} ? "``$_[2]''" : $_[2] }
594sub cmd_f { return $_[0]{alt} ? "\"$_[2]\"" : $_[2] }
595sub cmd_i { return '*' . $_[2] . '*' }
596sub cmd_x { return '' }
597
598# Apply a whole bunch of messy heuristics to not quote things that don't
599# benefit from being quoted.  These originally come from Barrie Slaymaker and
600# largely duplicate code in Pod::Man.
601sub cmd_c {
602    my ($self, $attrs, $text) = @_;
603
604    # A regex that matches the portion of a variable reference that's the
605    # array or hash index, separated out just because we want to use it in
606    # several places in the following regex.
607    my $index = '(?: \[.*\] | \{.*\} )?';
608
609    # Check for things that we don't want to quote, and if we find any of
610    # them, return the string with just a font change and no quoting.
611    $text =~ m{
612      ^\s*
613      (?:
614         ( [\'\`\"] ) .* \1                             # already quoted
615       | \` .* \'                                       # `quoted'
616       | \$+ [\#^]? \S $index                           # special ($^Foo, $")
617       | [\$\@%&*]+ \#? [:\'\w]+ $index                 # plain var or func
618       | [\$\@%&*]* [:\'\w]+ (?: -> )? \(\s*[^\s,]\s*\) # 0/1-arg func call
619       | [+-]? ( \d[\d.]* | \.\d+ ) (?: [eE][+-]?\d+ )? # a number
620       | 0x [a-fA-F\d]+                                 # a hex constant
621      )
622      \s*\z
623     }xo && return $text;
624
625    # If we didn't return, go ahead and quote the text.
626    return $$self{opt_alt}
627        ? "``$text''"
628        : "$$self{LQUOTE}$text$$self{RQUOTE}";
629}
630
631# Links reduce to the text that we're given, wrapped in angle brackets if it's
632# a URL.
633sub cmd_l {
634    my ($self, $attrs, $text) = @_;
635    if ($$attrs{type} eq 'url') {
636        if (not defined($$attrs{to}) or $$attrs{to} eq $text) {
637            return "<$text>";
638        } elsif ($$self{opt_nourls}) {
639            return $text;
640        } else {
641            return "$text <$$attrs{to}>";
642        }
643    } else {
644        return $text;
645    }
646}
647
648##############################################################################
649# Backwards compatibility
650##############################################################################
651
652# The old Pod::Text module did everything in a pod2text() function.  This
653# tries to provide the same interface for legacy applications.
654sub pod2text {
655    my @args;
656
657    # This is really ugly; I hate doing option parsing in the middle of a
658    # module.  But the old Pod::Text module supported passing flags to its
659    # entry function, so handle -a and -<number>.
660    while ($_[0] =~ /^-/) {
661        my $flag = shift;
662        if    ($flag eq '-a')       { push (@args, alt => 1)    }
663        elsif ($flag =~ /^-(\d+)$/) { push (@args, width => $1) }
664        else {
665            unshift (@_, $flag);
666            last;
667        }
668    }
669
670    # Now that we know what arguments we're using, create the parser.
671    my $parser = Pod::Text->new (@args);
672
673    # If two arguments were given, the second argument is going to be a file
674    # handle.  That means we want to call parse_from_filehandle(), which means
675    # we need to turn the first argument into a file handle.  Magic open will
676    # handle the <&STDIN case automagically.
677    if (defined $_[1]) {
678        my @fhs = @_;
679        local *IN;
680        unless (open (IN, $fhs[0])) {
681            croak ("Can't open $fhs[0] for reading: $!\n");
682            return;
683        }
684        $fhs[0] = \*IN;
685        $parser->output_fh ($fhs[1]);
686        my $retval = $parser->parse_file ($fhs[0]);
687        my $fh = $parser->output_fh ();
688        close $fh;
689        return $retval;
690    } else {
691        $parser->output_fh (\*STDOUT);
692        return $parser->parse_file (@_);
693    }
694}
695
696# Reset the underlying Pod::Simple object between calls to parse_from_file so
697# that the same object can be reused to convert multiple pages.
698sub parse_from_file {
699    my $self = shift;
700    $self->reinit;
701
702    # Fake the old cutting option to Pod::Parser.  This fiddles with internal
703    # Pod::Simple state and is quite ugly; we need a better approach.
704    if (ref ($_[0]) eq 'HASH') {
705        my $opts = shift @_;
706        if (defined ($$opts{-cutting}) && !$$opts{-cutting}) {
707            $$self{in_pod} = 1;
708            $$self{last_was_blank} = 1;
709        }
710    }
711
712    # Do the work.
713    my $retval = $self->Pod::Simple::parse_from_file (@_);
714
715    # Flush output, since Pod::Simple doesn't do this.  Ideally we should also
716    # close the file descriptor if we had to open one, but we can't easily
717    # figure this out.
718    my $fh = $self->output_fh ();
719    my $oldfh = select $fh;
720    my $oldflush = $|;
721    $| = 1;
722    print $fh '';
723    $| = $oldflush;
724    select $oldfh;
725    return $retval;
726}
727
728# Pod::Simple failed to provide this backward compatibility function, so
729# implement it ourselves.  File handles are one of the inputs that
730# parse_from_file supports.
731sub parse_from_filehandle {
732    my $self = shift;
733    $self->parse_from_file (@_);
734}
735
736# Pod::Simple's parse_file doesn't set output_fh.  Wrap the call and do so
737# ourself unless it was already set by the caller, since our documentation has
738# always said that this should work.
739sub parse_file {
740    my ($self, $in) = @_;
741    unless (defined $$self{output_fh}) {
742        $self->output_fh (\*STDOUT);
743    }
744    return $self->SUPER::parse_file ($in);
745}
746
747# Do the same for parse_lines, just to be polite.  Pod::Simple's man page
748# implies that the caller is responsible for setting this, but I don't see any
749# reason not to set a default.
750sub parse_lines {
751    my ($self, @lines) = @_;
752    unless (defined $$self{output_fh}) {
753        $self->output_fh (\*STDOUT);
754    }
755    return $self->SUPER::parse_lines (@lines);
756}
757
758# Likewise for parse_string_document.
759sub parse_string_document {
760    my ($self, $doc) = @_;
761    unless (defined $$self{output_fh}) {
762        $self->output_fh (\*STDOUT);
763    }
764    return $self->SUPER::parse_string_document ($doc);
765}
766
767##############################################################################
768# Module return value and documentation
769##############################################################################
770
7711;
772__END__
773
774=for stopwords
775alt stderr Allbery Sean Burke's Christiansen UTF-8 pre-Unicode utf8 nourls
776parsers
777
778=head1 NAME
779
780Pod::Text - Convert POD data to formatted text
781
782=head1 SYNOPSIS
783
784    use Pod::Text;
785    my $parser = Pod::Text->new (sentence => 1, width => 78);
786
787    # Read POD from STDIN and write to STDOUT.
788    $parser->parse_from_filehandle;
789
790    # Read POD from file.pod and write to file.txt.
791    $parser->parse_from_file ('file.pod', 'file.txt');
792
793=head1 DESCRIPTION
794
795Pod::Text is a module that can convert documentation in the POD format
796(the preferred language for documenting Perl) into formatted text.  It
797uses no special formatting controls or codes whatsoever, and its output is
798therefore suitable for nearly any device.
799
800As a derived class from Pod::Simple, Pod::Text supports the same methods and
801interfaces.  See L<Pod::Simple> for all the details; briefly, one creates a
802new parser with C<< Pod::Text->new() >> and then normally calls parse_file().
803
804new() can take options, in the form of key/value pairs, that control the
805behavior of the parser.  The currently recognized options are:
806
807=over 4
808
809=item alt
810
811If set to a true value, selects an alternate output format that, among other
812things, uses a different heading style and marks C<=item> entries with a
813colon in the left margin.  Defaults to false.
814
815=item code
816
817If set to a true value, the non-POD parts of the input file will be included
818in the output.  Useful for viewing code documented with POD blocks with the
819POD rendered and the code left intact.
820
821=item errors
822
823How to report errors.  C<die> says to throw an exception on any POD
824formatting error.  C<stderr> says to report errors on standard error, but
825not to throw an exception.  C<pod> says to include a POD ERRORS section
826in the resulting documentation summarizing the errors.  C<none> ignores
827POD errors entirely, as much as possible.
828
829The default is C<pod>.
830
831=item indent
832
833The number of spaces to indent regular text, and the default indentation for
834C<=over> blocks.  Defaults to 4.
835
836=item loose
837
838If set to a true value, a blank line is printed after a C<=head1> heading.
839If set to false (the default), no blank line is printed after C<=head1>,
840although one is still printed after C<=head2>.  This is the default because
841it's the expected formatting for manual pages; if you're formatting
842arbitrary text documents, setting this to true may result in more pleasing
843output.
844
845=item margin
846
847The width of the left margin in spaces.  Defaults to 0.  This is the margin
848for all text, including headings, not the amount by which regular text is
849indented; for the latter, see the I<indent> option.  To set the right
850margin, see the I<width> option.
851
852=item nourls
853
854Normally, LZ<><> formatting codes with a URL but anchor text are formatted
855to show both the anchor text and the URL.  In other words:
856
857    L<foo|http://example.com/>
858
859is formatted as:
860
861    foo <http://example.com/>
862
863This option, if set to a true value, suppresses the URL when anchor text
864is given, so this example would be formatted as just C<foo>.  This can
865produce less cluttered output in cases where the URLs are not particularly
866important.
867
868=item quotes
869
870Sets the quote marks used to surround CE<lt>> text.  If the value is a
871single character, it is used as both the left and right quote.  Otherwise,
872it is split in half, and the first half of the string is used as the left
873quote and the second is used as the right quote.
874
875This may also be set to the special value C<none>, in which case no quote
876marks are added around CE<lt>> text.
877
878=item sentence
879
880If set to a true value, Pod::Text will assume that each sentence ends in two
881spaces, and will try to preserve that spacing.  If set to false, all
882consecutive whitespace in non-verbatim paragraphs is compressed into a
883single space.  Defaults to false.
884
885=item stderr
886
887Send error messages about invalid POD to standard error instead of
888appending a POD ERRORS section to the generated output.  This is
889equivalent to setting C<errors> to C<stderr> if C<errors> is not already
890set.  It is supported for backward compatibility.
891
892=item utf8
893
894By default, Pod::Text uses the same output encoding as the input encoding
895of the POD source (provided that Perl was built with PerlIO; otherwise, it
896doesn't encode its output).  If this option is given, the output encoding
897is forced to UTF-8.
898
899Be aware that, when using this option, the input encoding of your POD
900source should be properly declared unless it's US-ASCII.  Pod::Simple will
901attempt to guess the encoding and may be successful if it's Latin-1 or
902UTF-8, but it will produce warnings.  Use the C<=encoding> command to
903declare the encoding.  See L<perlpod(1)> for more information.
904
905=item width
906
907The column at which to wrap text on the right-hand side.  Defaults to 76.
908
909=back
910
911The standard Pod::Simple method parse_file() takes one argument naming the
912POD file to read from.  By default, the output is sent to C<STDOUT>, but
913this can be changed with the output_fh() method.
914
915The standard Pod::Simple method parse_from_file() takes up to two
916arguments, the first being the input file to read POD from and the second
917being the file to write the formatted output to.
918
919You can also call parse_lines() to parse an array of lines or
920parse_string_document() to parse a document already in memory.  As with
921parse_file(), parse_lines() and parse_string_document() default to sending
922their output to C<STDOUT> unless changed with the output_fh() method.
923
924To put the output from any parse method into a string instead of a file
925handle, call the output_string() method instead of output_fh().
926
927See L<Pod::Simple> for more specific details on the methods available to
928all derived parsers.
929
930=head1 DIAGNOSTICS
931
932=over 4
933
934=item Bizarre space in item
935
936=item Item called without tag
937
938(W) Something has gone wrong in internal C<=item> processing.  These
939messages indicate a bug in Pod::Text; you should never see them.
940
941=item Can't open %s for reading: %s
942
943(F) Pod::Text was invoked via the compatibility mode pod2text() interface
944and the input file it was given could not be opened.
945
946=item Invalid errors setting "%s"
947
948(F) The C<errors> parameter to the constructor was set to an unknown value.
949
950=item Invalid quote specification "%s"
951
952(F) The quote specification given (the C<quotes> option to the
953constructor) was invalid.  A quote specification must be either one
954character long or an even number (greater than one) characters long.
955
956=item POD document had syntax errors
957
958(F) The POD document being formatted had syntax errors and the C<errors>
959option was set to C<die>.
960
961=back
962
963=head1 BUGS
964
965Encoding handling assumes that PerlIO is available and does not work
966properly if it isn't.  The C<utf8> option is therefore not supported
967unless Perl is built with PerlIO support.
968
969=head1 CAVEATS
970
971If Pod::Text is given the C<utf8> option, the encoding of its output file
972handle will be forced to UTF-8 if possible, overriding any existing
973encoding.  This will be done even if the file handle is not created by
974Pod::Text and was passed in from outside.  This maintains consistency
975regardless of PERL_UNICODE and other settings.
976
977If the C<utf8> option is not given, the encoding of its output file handle
978will be forced to the detected encoding of the input POD, which preserves
979whatever the input text is.  This ensures backward compatibility with
980earlier, pre-Unicode versions of this module, without large numbers of
981Perl warnings.
982
983This is not ideal, but it seems to be the best compromise.  If it doesn't
984work for you, please let me know the details of how it broke.
985
986=head1 NOTES
987
988This is a replacement for an earlier Pod::Text module written by Tom
989Christiansen.  It has a revamped interface, since it now uses Pod::Simple,
990but an interface roughly compatible with the old Pod::Text::pod2text()
991function is still available.  Please change to the new calling convention,
992though.
993
994The original Pod::Text contained code to do formatting via termcap
995sequences, although it wasn't turned on by default and it was problematic to
996get it to work at all.  This rewrite doesn't even try to do that, but a
997subclass of it does.  Look for L<Pod::Text::Termcap>.
998
999=head1 AUTHOR
1000
1001Russ Allbery <rra@cpan.org>, based I<very> heavily on the original
1002Pod::Text by Tom Christiansen <tchrist@mox.perl.com> and its conversion to
1003Pod::Parser by Brad Appleton <bradapp@enteract.com>.  Sean Burke's initial
1004conversion of Pod::Man to use Pod::Simple provided much-needed guidance on
1005how to use Pod::Simple.
1006
1007=head1 COPYRIGHT AND LICENSE
1008
1009Copyright 1999-2002, 2004, 2006, 2008-2009, 2012-2016, 2018 Russ Allbery
1010<rra@cpan.org>
1011
1012This program is free software; you may redistribute it and/or modify it
1013under the same terms as Perl itself.
1014
1015=head1 SEE ALSO
1016
1017L<Pod::Simple>, L<Pod::Text::Termcap>, L<perlpod(1)>, L<pod2text(1)>
1018
1019The current version of this module is always available from its web site at
1020L<https://www.eyrie.org/~eagle/software/podlators/>.  It is also part of the
1021Perl core distribution as of 5.6.0.
1022
1023=cut
1024
1025# Local Variables:
1026# copyright-at-end-flag: t
1027# End:
1028