NAME
Term::TtyRec::Plus - read a ttyrec
VERSION
Version 0.02
SYNOPSIS
Term::TtyRec::Plus
is a module that lets you read ttyrec files. The related module, Term::TtyRec is designed more for simple interactions. Term::TtyRec::Plus
gives you more information and, using a callback, lets you munge the data block and timestamp. It will do all the subtle work of making sure timing is kept consistent, and of rebuilding each frame header.
use Term::TtyRec::Plus;
my $ttyrec = Term::TtyRec::Plus->new();
while ($frame_ref = $ttyrec->next_frame())
{
# do stuff with $frame_ref, e.g.
$total_time += $frame_ref->{diff};
}
CONSTRUCTOR AND STARTUP
new()
Creates and returns a new Term::TtyRec::Plus
object.
my $ttyrec = Term::TtyRec::Plus->new();
Parameters
Here are the parameters that <Term::TtyRec::Plus-
new()>> recognizes.
- infile
-
The input filename. A value of
"-"
, which is the default, orundef
, meansSTDIN
. - filehandle
-
The input filehandle. By default this is
undef
; if you have already opened the ttyrec then you can pass its filehandle to the constructor. If both filehandle and infile are defined, filehandle is used. - time_threshold
-
The maximum difference between two frames, in seconds. If
undef
, which is the default, there is no enforced maximum. The second most common value would be10
, which some ttyrec utilities (such as timettyrec) use. - frame_filter
-
A callback, run for each frame before returning the frame to the user of
Term::TtyRec::Plus
. This callback receives three arguments: the frame text, the timestamp, and the timestamp of the previous frame. All three arguments are passed as scalar references. The previous frame's timestamp isundef
for the first frame. The return value is not currently looked at. If you modify the timestamp, the module will make sure that change is noted and respected in further frame timestamps. Modifications to the previous frame's timestamp are currently ignored.sub halve_frame_time_and_stumblify { my ($data_ref, $time_ref, $prev_ref) = @_; $$time_ref = $$prev_ref + ($$time_ref - $$prev_ref) / 2 if defined $$prev_ref; $$data_ref =~ s/Eidolos/Stumbly/g; }
State
In addition to passing arguments, you can modify Term::TtyRec::Plus
's initial state, if you want to. This could be useful if you are chaining multiple ttyrecs together; you could pass a different initial frame. Support for such chaining might be added in a future version.
- frame
-
The initial frame number. Default
0
. - prev_timestamp
-
The previous frame's timestamp. Default
undef
. - accum_diff
-
The accumulated difference of all frames seen so far; see the section on
diffed_timestamp
innext_frame()
's return value. Default0
. - relative_time
-
The time passed since the first frame. Default
0
.
METHODS
next_frame()
next_frame()
reads and processes the next frame in the ttyrec. It accepts no arguments. On EOF, it will return undef
. On malformed ttyrec input, it will die. If it cannot reconstruct the header of a frame (which might happen if the callback sets the timestamp to -1, for example), it will die. Otherwise, a hash reference is returned with the following fields set.
- data
-
The frame data, filtered through the callback. The original data block is not made available.
- orig_timestamp
-
The frame timestamp, straight out of the file.
- diffed_timestamp
-
The frame timestamp, with the accumulated difference of all of the previous frames applied to it. This is so consistent results are given. For example, if your callback adds three seconds to frame 5's timestamp, then frame 6's diffed timestamp will take into account those three seconds, so frame 6 happens three seconds later as well. So the net effect is frame 4 is extended by three seconds.
- timestamp
-
The diffed timestamp, filtered through the callback.
- prev_timestamp
-
The previous frame's timestamp (after diffing and filtering; the originals are not made available).
- diff
-
The difference between the current frame's timestamp and the previous frame's timestamp. Yes, it is equivalent to
timestamp - prev_timestamp
, but it is provided for convenience. On the first frame it will be0
(notundef
). - orig_header
-
The 12-byte frame header, straight from the file.
- header
-
The 12-byte frame header, reconstructed from
data
andtimestamp
(so, after filtering, etc.). - frame
-
The frame number, using 1-based indexing.
- relative_time
-
The time between the first frame's timestamp and the current frame's timestamp.
grep()
Returns the next frame that meets the specified criteria. grep()
accepts arguments that are subroutines, regex, or strings; anything else is a fatal error. If you pass multiple arguments to grep()
, each one must be true. The subroutines receive the frame reference that is returned by next_frame()
. You can modify the frame, but do so cautiously.
my $next_jump_frame_ref = $t->grep("Where do you want to jump?", sub { $_[0]{data} !~ /Message History/});
rewind()
Rewinds the ttyrec to the first frame and resets state variables to their initial values.
infile()
Returns the infile passed to the constructor. If a filehandle was passed, this will be undef
.
filehandle()
Returns the filehandle passed to the constructor, or if infile
was used, a handle to infile
.
time_threshold()
Returns the time threshold passed to the constructor. By default it is undef
.
frame_filter()
Returns the frame filter callback passed to the constructor. By default it is sub { @_ }
.
frame()
Returns the frame number of the most recently returned frame.
prev_timestamp()
Returns the timestamp of the most recently returned frame.
relative_time()
Returns the time so far since the first frame.
accum_diff()
Returns the total time difference between timestamps and . accum_diff
is added to the timestamp before it is passed to the frame_filter
callback.
AUTHOR
Shawn M Moore, <sartak at gmail.com>
CAVEATS
Ttyrecs are frame-based. If you are trying to modify a string that is broken across multiple frames, it will not work. Say you have a ttyrec that prints "foo" in frame one and "bar" in frame two, both with the same timestamp. In a ttyrec player, it might look like these are one frame (with data "foobar"), but it's not. There is no easy, complete way to add arbitrary substitutions; you would have to write (or reuse) a terminal emulator.
If you modify the data block, weird things could happen. This is especially true of escape-code-littered ttyrecs (such as those of NetHack). For best results, pretend the data block is an executable file; changes are OK as long as you do not change the length of the file. It really depends on the ttyrec though.
If you modify the timestamp of a frame so that it is not in sequence with other frames, the behavior is undefined (it is up to the client program).
Term::TtyRec::Plus
will not reorder the frames for you.
BUGS
Please report any bugs or feature requests to bug-term-ttyrec-supercharged at rt.cpan.org
, or through the web interface at http://rt.cpan.org/NoAuth/ReportBug.html?Queue=Term-TtyRec-Plus. I will be notified, and then you'll automatically be notified of progress on your bug as I make changes.
SUPPORT
You can find documentation for this module with the perldoc command.
perldoc Term::TtyRec::Plus
You can also look for information at:
AnnoCPAN: Annotated CPAN documentation
CPAN Ratings
RT: CPAN's request tracker
Search CPAN
ACKNOWLEDGEMENTS
Thanks to Sean Kelly for always being the catalyst. Thanks also to brian d foy for writing "How a script becomes a module".
COPYRIGHT & LICENSE
Copyright 2006 Shawn M Moore, all rights reserved.
This program is free software; you can redistribute it and/or modify it under the same terms as Perl itself.