release 1.14pre0
[descalc.git] / dct.pl
diff --git a/dct.pl b/dct.pl
deleted file mode 100755 (executable)
index d871555..0000000
--- a/dct.pl
+++ /dev/null
@@ -1,232 +0,0 @@
-#!/usr/bin/perl
-
-# DCT - desktop calculator thingy
-
-# simple modular reverse polish notition calculator
-# by Shiar <shiar.org>
-
-use strict;
-use warnings;
-use utf8;
-
-use Data::Dumper;
-
-our $VERSION = "1.12.1";
-
-use vars qw(@stack %val %set %alias %action %hook);
-
-%set = (
-       base     => 10,  # decimal; set using commands bin/oct/dec/hex/base
-#      numb     =>  0,  # fixed scientific engineering
-
-       height   =>  4,  # stack depth (lines of stack plus one)
-       width    => 42,  # limit value precision, stetch menu
-); # %set
-
-%alias = (' '=>"enter", "\004"=>"quit");  # rudimentary default key bindings
-
-%action = (
-       "enter" => [ 0, sub {
-               local $_ = defined $val{i} ? $val{i} : $stack[0];
-               undef %val;
-               return defined $_ ? $_ : ();
-       }], # duplication
-
-       "chs"   => [ 1, sub { -$_[0] }], # negative
-
-       "drop"  => [ 1, sub { defined $val{i} ? '' : () }], # drop
-       "back"  => [ 1, sub { () }], # drop essentially
-       "clear" => [ 0, sub { @stack = (); undef %val; () }], # clear all
-
-       "swap"  => [ 2, sub { reverse @_ }], # swap x<->y
-       "stack" => [-2, sub {
-               my $stackpos if 0;
-               $stackpos = 0 unless $stackpos;  # initialize
-               $stackpos %= @stack;  # cycle
-               $val{i} = $stack[$stackpos++];
-       }], # stack
-
-       "version" => [-2, sub {
-               error("Desktop Calculator Thingy $VERSION by Shiar"); ()
-       }], # version
-); # %action
-
-
-my $redraw = 2;  # set flag to refresh whole screen
-
-sub redraw($) {
-       # queue a redraw of level $_[0]
-       $redraw = $_[0] if $_[0]>$redraw;
-} # redraw
-
-sub error($) {
-       $_->($_[0]) for @{$hook{showerror}};
-       redraw(2);
-} # error
-
-sub showval;
-sub showval {
-       my ($val, $base, $baseexp) = @_;
-       return '' unless defined $val;
-       return $val if $base==10;
-
-       my $txt = '';
-
-       my $sign = $val<0 and $val = abs $val;
-       my $int = int $val;
-
-       my $exp = $val{ex} || 0;
-       while ($int>$base**10) {
-               $int /= $base;
-               $exp++;
-       } # exponent part
-
-       my $frac = $val-$int;
-       while ($int>=1) {
-               my $char = $int%$base;
-               $txt = ($char<10 ? $char : chr($char+55)) . $txt;
-               $int /= $base;
-       } # integer part
-       $txt .= '.' if $frac>0;
-       for (my $i = 0; length $txt<$set{width}-2 && $frac>0; $i++) {
-               $frac *= $base;
-               my $char = int $frac;
-               $frac -= $char;
-               $txt .= $char<10 ? $char : chr($char+55);
-       } # fraction part
-
-       $txt = "-".$txt if $sign;
-       $txt .= 'e'.showval($exp, $base) if $exp;
-
-       return $txt;
-} # showval
-
-
-sub draw {
-       if ($redraw) {
-               if ($redraw>1) {
-                       $_->() for @{$hook{refresh}};
-               }
-               $_->() for @{$hook{showstack}};
-               $redraw = 0;
-       } # do necessary redrawing
-
-       {
-               my $entry = showval($val{i}, $set{base}, $val{ex});
-               $entry .= $_->() for @{$hook{postentry}};
-               $entry .= $val{alpha} if exists $val{alpha};
-               $_->($entry) for @{$hook{showentry}};
-       } # show entry
-} # draw
-
-sub onkey($) {
-       my $key = shift;
-       $_ = exists $alias{$key} ? $alias{$key} : $key;  # command (alias maps keys to commands)
-       $_ eq "enter" and exists $val{alpha} and $_ = delete $val{alpha};  # use manual command
-
-       for my $cmd (@{$hook{precmd}}) {
-               $cmd->() and return;  # command was handled by function if returns true
-       } # precmd functions
-
-       exit if $_ eq "quit";  # break out of loop
-
-       if ($_ eq "refresh") {
-               redraw(2);
-       } # refresh
-
-       elsif (/^\033?[A-Z]$/ or exists $val{alpha}) {
-               if (defined $val{i}) {
-                       unshift @stack, $val{i};
-                       undef %val;
-                       redraw(1);
-               } # enter present value
-
-               if ($_ eq "back") {
-                       $val{alpha} = substr $val{alpha}, 0, -1 or delete $val{alpha};
-               } # backspace
-               elsif ($_ eq "drop") {
-                       delete $val{alpha};
-               } # drop
-               else {
-                       $val{alpha} .= $key =~ /^\033(.)/ ? uc $1 : lc $key;
-               } # add character
-       } # manual command entry
-
-       elsif (/^[\da-f]$/) {
-               m/^[a-z]$/ and $_ = ord($_)-87;  # digit>9
-               $val{i} = 0 unless defined $val{i};
-               $_ = -$_ if $val{i}<0;  # substract from negative value
-               $val{i} = ($val{frac} and $val{frac} *= 10)
-                       ? $val{i}+$_/$val{frac}  # add digit to fraction
-                       : defined $val{ex} ? $val{ex} = $val{ex}*$set{base}+$_  # digit to exponent
-                       : $val{i}*$set{base}+$_;  # add digit to integer part
-       } # digit
-       elsif ($_ eq '.') {
-               $val{i} = 0 unless defined $val{i};
-               $val{frac} = 1;
-       } # decimal point
-       elsif ($_ eq "eex") {
-               $val{i} = 1 unless defined $val{i};
-               $val{ex} = 0;
-       } # exponent
-       elsif ($_ eq "chs" and defined $val{i}) {
-               $val{i} = -$val{i};
-       } # change sign
-       elsif ($_ eq "back" and defined $val{i}) {
-               $val{i} = ($val{frac} and $val{frac} = int $val{frac}/10)
-                       ? int($val{i}*$val{frac})/$val{frac}  # backspace fraction digit
-                       : int $val{i}/$set{base}  # backspace digit in integer part
-       } # backspace
-
-       elsif (exists $action{$_}) {
-               my ($action, $type, $cmd) = ($_, @{$action{$_}});
-               unshift @stack, $action{enter}[1]->() if $type>0 and defined $val{i};  # auto enter
-
-               if ($type>0 and $type>@stack) {
-                       error("insufficient stack arguments for operation");
-                       next;
-               } # insufficient arguments
-
-               $_->($type, $action) for @{$hook{preaction}};
-               # put return value(s) of stack-modifying operations (type>=0) at stack
-               $type<0 ? $cmd->() : unshift @stack, $cmd->(splice @stack, 0, $type);
-               $_->($type, $action) for @{$hook{postaction}};
-
-               redraw(1) if $type>=-1;  # redraw stack
-       } # some operation
-
-       else {
-               error(
-                       "unrecognised command: "  # show string or character codes
-                       . (m/^\w*$/ ? qq{"$_"} : join ' ', map ord, split //, $_)
-               );
-       } # error
-} # onkey
-
-
-our %modules;
-{
-       my %modskip;
-       $modskip{substr $_, 1}++ for grep /^-/, @ARGV;
-       opendir my $moddir, ".";
-       for my $module (sort readdir $moddir) { # glob "*.pm"
-               $module =~ /^\d{2}_([a-z0-9-]+)(?:_(\w+))?\.pm$/ or next;
-               # files named 00_class_name.pm; ($1, $2) = (class, name)
-               next if exists $modskip{$1} or $2 && exists $modskip{$2};
-               next if defined $modules{$1};  # no such module already loaded
-               defined ($_ = do $module)  # return value means no errors
-               ? (ref $_ and $modules{$1} = $_, $modules{$1}{name} = $2 || "")
-               : print STDERR $@, "error loading $module\n\n";
-       } # load modules
-       closedir $moddir;
-} # find external modules
-
-printf STDERR "DCT %s by Shiar (%s)\n", $VERSION, join "; ",
-       map join(" ", grep $_, $_, $modules{$_}{name}, $modules{$_}{version}),
-       keys %modules;
-
-
-$_->() for @{$hook{init}};
-
-$hook{main}->();
-