[system] / trunk / pg / macros / contextTypeset.pl Repository:
ViewVC logotype

View of /trunk/pg/macros/contextTypeset.pl

Parent Directory Parent Directory | Revision Log Revision Log


Revision 6773 - (download) (as text) (annotate)
Fri Apr 1 21:01:31 2011 UTC (8 years, 9 months ago) by gage
File size: 40297 byte(s)
fix one  "non numeric permision level" error  by adding default

add three new specialized macro packages  contextTypeset.pl and its supporting file parserQuotedString.pl
are used for PGML  -- the answerDiscusson.pl is a proof of concept for allowing student written feedback.


    1 loadMacros("Parser.pl");
    2 
    3 package Typeset;
    4 
    5 sub addVariables {
    6   my $context = shift; my @vars;
    7   foreach my $v ('a'..'z','A'..'Z') {push(@vars,$v=>'Real')}
    8   $context->variables->are(@vars);
    9   $context->variables->remove('U'); # used as operator below
   10 }
   11 
   12 ######################################################################
   13 
   14 package Typeset::Function;
   15 @ISA = qw(Parser::Function);
   16 
   17 sub _check {
   18   my $self = shift;
   19   $self->{type} = $Value::Type{number};
   20 }
   21 
   22 sub eval {
   23   my $self = shift;
   24   $self->Error("Can't evaluate '%s'",$self->{name});
   25 }
   26 
   27 sub perl {
   28   my $self = shift;
   29   $self->Error("No perl form for '%s'",$slef->{name});
   30 }
   31 
   32 ######################################################################
   33 
   34 package Typeset::Function::named;
   35 @ISA = qw(Typeset::Function);
   36 
   37 # just override the _check method
   38 
   39 ######################################################################
   40 
   41 package Typeset::Function::text;
   42 @ISA = qw(Typeset::Function);
   43 
   44 sub TeX {
   45   my $self = shift; my @params;
   46   foreach my $p (@{$self->{params}}) {push(@params,$p->{isQuoted}? $p->{value}: $p->string)};
   47   return '\hbox{'.join('',@params).'}';
   48 }
   49 
   50 ######################################################################
   51 
   52 package Typeset::Function::TeX;
   53 @ISA = qw(Typeset::Function);
   54 
   55 sub TeX {
   56   my $self = shift; my @params;
   57   foreach my $p (@{$self->{params}}) {push(@params,$p->{isQuoted}? $p->{value}: $p->string)};
   58   return join('',@params);
   59 }
   60 
   61 ######################################################################
   62 
   63 package Typeset::Function::bf;
   64 @ISA = qw(Typeset::Function);
   65 
   66 sub TeX {
   67   my $self = shift; my @params;
   68   foreach my $p (@{$self->{params}}) {push(@params,$p->TeX)};
   69   return '{\bf '.join('',@params).'}';
   70 }
   71 
   72 ######################################################################
   73 
   74 package Typeset::Function::cal;
   75 @ISA = qw(Typeset::Function);
   76 
   77 sub TeX {
   78   my $self = shift; my @params;
   79   foreach my $p (@{$self->{params}}) {push(@params,$p->TeX)};
   80   return '{\cal '.join('',@params).'}';
   81 }
   82 
   83 ######################################################################
   84 
   85 package Typeset::Function::det;
   86 @ISA = qw(Typeset::Function);
   87 
   88 sub TeX {
   89   my $self = shift;
   90   return $self->SUPER::TeX(@_) unless $self->{params}[0]->type eq 'Matrix';
   91   my $M = bless {%{$self->{params}[0]}, open => '|', close => '|'}, ref($self->{params}[0]);
   92   return '\det'.$M->TeX;
   93 }
   94 
   95 ######################################################################
   96 
   97 package Typeset::Function::accent;
   98 @ISA = qw(Typeset::Function);
   99 
  100 sub _check {
  101   my $self = shift;
  102   return if $self->checkArgCount(1);
  103   $self->{type} = $self->{params}[0]->typeRef;
  104 }
  105 
  106 sub TeX {
  107   my $self = shift;
  108   return '{'.$self->{def}{TeX}.'{'.$self->{params}[0]->TeX.'}}';
  109 }
  110 
  111 ######################################################################
  112 
  113 package Typeset::Function::overunder;
  114 @ISA = qw(Typeset::Function);
  115 
  116 sub _check {
  117   my $self = shift;
  118   return if $self->checkArgCount(1);
  119   $self->{type} = $self->{params}[0]->typeRef;
  120 }
  121 
  122 sub TeX {
  123   my $self = shift;
  124   return $self->{def}{TeX}.'{'.$self->{params}[0]->TeX.'}';
  125 }
  126 
  127 ######################################################################
  128 
  129 package Typeset::Function::Fence;
  130 @ISA = qw(Typeset::Function);
  131 
  132 sub _check {
  133   my $self = shift; my $n = scalar(@{$self->{params}});
  134   $self->Error("Fence requires an open parenthesis, a formula, and a close parenthesis") if $n < 3;
  135   if ($n > 3) {$self->{type} = Value::Type("List",$n,$Value::Type{unknown})}
  136     else {$self->{type} = $self->{params}[1]->typeRef}
  137 }
  138 
  139 sub TeX {
  140   my $self = shift; my @params = @{$self->{params}};
  141   my $open = shift(@params); my $close = pop(@params);
  142   $open = $open->{isQuoted}? $open->{value}: $open->string;
  143   $close = $close->{isQuoted}? $close->{value}: $close->string;
  144   $open = "." unless $open; $close = "." unless $close;
  145   $open = '\{' if $open eq '{'; $close = '\}' if $close eq '}';
  146   foreach my $p (@params) {$p = $p->TeX}
  147   return '\left'.$open." ".join(',',@params).'\right'.$close." ";
  148 }
  149 
  150 ######################################################################
  151 
  152 package Typeset::Function::Cases;
  153 @ISA = qw(Typeset::Function);
  154 
  155 sub _check {
  156   my $self = shift;
  157   $self->{formulas} = []; $self->{conditions} = [];
  158   $self->Error("There must be at least one argument for '%s'",$self->{name})
  159     unless scalar(@{$self->{params}}) > 0;
  160   foreach my $p (@{$self->{params}}) {
  161     if ($p->type eq 'List' && $p->length == 2) {
  162       push(@{$self->{formulas}},$p->{coords}[0]);
  163       push(@{$self->{conditions}},$p->{coords}[1]);
  164     } elsif ($p->class eq 'BOP' && $p->{bop} eq '->') {
  165       push(@{$self->{formulas}},$p->{rop});
  166       push(@{$self->{conditions}},$p->{lop});
  167     } elsif ($p->class eq 'BOP' && $p->{bop} eq 'if ') {
  168       push(@{$self->{formulas}},$p->{lop});
  169       my $if = $self->{equation}{context}{parser}{UOP}->new($self->{equation},'_if_',$p->{rop});
  170       push(@{$self->{conditions}},$if);
  171     } elsif ($p->class eq 'UOP' && $p->{uop} eq 'otherwise') {
  172       push(@{$self->{formulas}},$p->{op});
  173       my $otherwise = $self->{equation}{context}{parser}{String}->new($self->{equation},'"otherwise"');
  174       push(@{$self->{conditions}},$otherwise);
  175     } else {
  176       $self->Error("The arguments for '%s' must be function-condition pairs",$self->{name});
  177     }
  178   }
  179   my $type = $self->{formulas}[0]->typeRef;
  180   foreach my $f (@{$self->{formulas}}) {
  181     $self->Error("The formulas for '%s' must all be of the same type",$self->{name})
  182       unless Parser::Item::typeMatch($type,$f->typeRef);
  183   }
  184   $self->{type} = $type;
  185 }
  186 
  187 sub TeX {
  188   my $self = shift; my @rows = ();
  189   my @f = @{$self->{formulas}}; my @c = @{$self->{conditions}};
  190   foreach my $i (0..$#f) {push(@rows,$f[$i]->TeX.'&'.$c[$i]->TeX."\\\\ ")}
  191   return '\begin{cases}'.join('',@rows).'\end{cases}';
  192 }
  193 
  194 ######################################################################
  195 
  196 package Typeset::Function::Array;
  197 @ISA = qw(Typeset::Function);
  198 
  199 sub _check {
  200   my $self = shift;
  201   my $equation = $self->{equation}; my $context = $equation->{context};
  202   my $template; my $param = $self->{params}[0];
  203   $self->Error("Array requires a list of entries") unless defined $param;
  204   if ($param && $param->class eq 'QuotedString') {
  205     $template = shift(@{$self->{params}})->{value};
  206   }
  207   if (scalar(@{$self->{params}}) == 1 && $self->{params}[0]->type eq 'Matrix') {
  208     $self->{M} = $self->{params}[0];
  209   } else {
  210     my $null = $context->{parser}{Constant}->new($equation,"Null");
  211     my @rows = @{$self->{params}};
  212     @rows = @{$rows[0]->{coords}} if scalar(@rows) == 1 && $rows[0]->class eq 'List';
  213     my $c = 0; foreach my $r (@rows) {$c = $r->length if $r->length > $c}
  214     if ($c == 1 && scalar(@rows) > 1) {
  215       $c = scalar(@rows);
  216       @rows = ($context->{parser}{List}->new($equation,[@rows],0,$context->{parens}{start}));
  217     }
  218     foreach my $r (@rows) {
  219       $r = ($r->class eq 'List'? $r->{coords} : [$r]);
  220       while (scalar(@{$r}) < $c) {push(@{$r},$null)};
  221       $r = bless
  222         $context->{parser}{List}->new($equation,$r,0,$context->{parens}{start},$Value::Type{number},'[',']'),
  223         $context->{lists}{Matrix}{class};
  224     }
  225     $self->{M} = bless
  226         $context->{parser}{List}->new($equation,\@rows,0,$context->{parens}{start},$rows[0]->typeRef),
  227         $context->{lists}{Matrix}{class};
  228   }
  229   $self->{M}{open} = $self->{M}{close} = '';
  230   $self->{M}{array_template} = $template;
  231   $self->{type} = $self->{M}->typeRef;
  232 }
  233 
  234 sub TeX {my $self = shift; $self->{M}->TeX}
  235 
  236 ######################################################################
  237 
  238 package Typeset::Function::bigOp;
  239 @ISA = qw(Typeset::Function);
  240 
  241 sub _check {
  242   my $self = shift; my $name = $self->{name};
  243   my @params = @{$self->{params}}; my $allowMax = !$self->{def}{noMax};
  244   ## check for (x;fn),  (m,M; fn),  (x:m,M; fn),  (x,m,M; fn),  (x->m; fn)
  245   if (scalar(@params) == 2) {
  246     $self->{op} = $params[1]; my $lop = $params[0];
  247     if ($lop->type eq 'List') {
  248       if ($lop->length == 2 && $allowMax) {
  249   $self->{min} = $lop->{coords}[0];
  250   $self->{max} = $lop->{coords}[1];
  251       } elsif ($lop->length == 3 && $lop->{coords}[0]->class eq 'Variable' && $allowMax) {
  252   $self->{var} = $lop->{coords}[0];
  253   $self->{min} = $lop->{coords}[1];
  254   $self->{max} = $lop->{coords}[2];
  255       } else {
  256   $self->{min} = $lop;
  257       }
  258     } elsif ($lop->class eq 'Variable') {
  259       $self->{var} = $lop;
  260     } elsif ($lop->class eq 'BOP' && $lop->{bop} eq ':') {
  261       if ($lop->{lop}->class eq 'Variable') {
  262   $self->{var} = $lop->{lop};
  263   if ($lop->{rop}->class eq 'List' && $lop->{rop}->length == 2 && $allowMax) {
  264     $self->{min} = $lop->{rop}{coords}[0];
  265     $self->{max} = $lop->{rop}{coords}[1];
  266   } else {$self->{min} = $lop->{rop}}
  267       } else {$self->{min} = $lop}
  268     } elsif ($lop->class eq 'BOP' && $lop->{bop} eq '->') {
  269       if ($lop->{lop}->class eq 'Variable' && $self->{def}{allowArrow}) {
  270   $self->{var} = $lop->{lop};
  271   $self->{min} = $lop->{rop};
  272       } else {$self->{min} = $lop}
  273     } else {$self->{min} = $lop}
  274   } elsif (scalar(@params) == 1) {
  275     $self->{op} = $params[0];
  276   } else {
  277     $self->Error("Function '%s' has too many inputs",$name) if scalar(@params) > 2;
  278     $self->Error("Function '%s' requires a formula as input",$name) unless scalar(@params) < 1;
  279   }
  280   if (!$self->{var}) {
  281     my $variable = $self->{equation}{context}{parser}{Variable};
  282     my @vars = keys %{$self->{op}->getVariables};
  283     if (scalar(@vars) == 1) {
  284       $self->{var} = $variable->new($self->{equation},$vars[0]);
  285       $self->{implicitVar} = 1;
  286     }
  287   }
  288   $self->{type} = $self->{op}->typeRef;
  289 }
  290 
  291 sub TeX {
  292   my ($self,$precedence,$showparens,$position) = @_;
  293   my $fn = $self->{def}; my $x = $self->{var};
  294   my $min = $self->{min}; my $max = $self->{max};
  295   $min = $min->TeX if defined $min;
  296   $max = $max->TeX if defined $max;
  297   $min = (defined($min)? $x->TeX.($fn->{allowArrow} ? '\to ' : '=').$min : $x->TeX)
  298     if defined $x && !$fn->{dx};
  299   my $TeX = $fn->{TeX}.(defined($min)? "_{$min}": "").
  300                        (defined($max)? "^{$max}": "")." ".$self->{op}->TeX;
  301   $TeX .= '\,d'.$x->TeX if defined $x && $fn->{dx};
  302   if (defined($precedence) and $precedence > $fn->{precedence})
  303     {$TeX = '\left('.$TeX.'\right)'} else {$TeX = "{$TeX}"}
  304   return $TeX;
  305 }
  306 
  307 sub string {
  308   my ($self,$precedence,$showparens,$position,$outerRight,$power) = @_;
  309   my $fn = $self->{equation}{context}{operators}{'fn'};
  310   my $fn_precedence = $fn->{precedence};
  311   $fn_precedence = $fn->{parenPrecedence}
  312     if ($position && $position eq 'right' && $fn->{parenPrecedence});
  313   $fn = $self->{def}; my $x = $self->{var};
  314   my $min = $self->{min}; my $max = $self->{max};
  315   $min = $min->string if defined $min;
  316   $max = $max->string if defined $max;
  317   $min = (defined($min)? $x->string.($fn->{allowArrow}? "->": ":").$min : $x->string)
  318     if defined $x && !$self->{implicitVar};
  319   my $string = (defined($min)? $min: "").(defined($max)? ",$max": "");
  320   $string .= ";" if $string ne "";
  321   $string = $self->{name}.'('.$string.$self->{op}->string.')';
  322   $string = $self->addParens($string) if (defined($precedence) and $precedence > $fn_precedence);
  323   return $string;
  324 }
  325 
  326 ######################################################################
  327 
  328 package Typeset::BOP;
  329 @ISA = qw(Parser::BOP);
  330 
  331 ######################################################################
  332 
  333 package Typeset::BOP::TeX;
  334 @ISA = qw(Typeset::BOP);
  335 
  336 sub _check {
  337   my $self = shift;
  338   $self->{isConstant} = 0;
  339   $self->{type} = $Value::Type{number};
  340 }
  341 
  342 sub _eval {
  343   my $self = shift;
  344   my $name = $self->{def}{string} || $self->{bop};
  345   $self->Error("Can't evaluate '%s'",$name);
  346 }
  347 
  348 sub perl {
  349   my $self = shift;
  350   my $name = $self->{def}{string} || $self->{bop};
  351   $self->Error("No perl form for '%s'",$name);
  352 }
  353 
  354 ######################################################################
  355 
  356 package Typeset::BOP::subtract;
  357 @ISA = qw(Parser::BOP::subtract);
  358 
  359 sub matchError {
  360   my $self = shift; my ($ltype,$rtype) = @_;
  361   return $self->SUPER::matchError(@_)
  362     unless $ltype->{name} =~ m/Number|Set/ && $rtype->{name} =~ m/Number|Set/;
  363   $self->{type} = Value::Type('Set',1);
  364 }
  365 
  366 ######################################################################
  367 
  368 package Typeset::BOP::union;
  369 @ISA = qw(Parser::BOP::union);
  370 
  371 # handle _check to set type for numbers and sets
  372 
  373 ######################################################################
  374 
  375 package Typeset::BOP::divide;
  376 @ISA = qw(Parser::BOP::divide);
  377 
  378 sub TeX {
  379   my $self = shift;
  380   my ($precedence,$showparens,$position,$outerRight) = @_;
  381   my $TeX; my $bop = $self->{def};
  382   return $self->SUPER::TeX(@_) if $self->{def}{noFrac};
  383   $showparens = '' unless defined($showparens);
  384   my $addparens =
  385       defined($precedence) &&
  386       ($showparens eq 'all' || ($precedence > $bop->{precedence} && $showparens ne 'nofractions') ||
  387       ($precedence == $bop->{precedence} &&
  388         ($bop->{associativity} eq 'right' || $showparens eq 'same')));
  389 
  390   $self->{lop}{showParens} = $self->{rop}{showParens} = 0;
  391   $TeX = '\frac{'.($self->{lop}->TeX).'}{'.($self->{rop}->TeX).'}';
  392   $self->{lop}{showParens} = $self->{rop}{showParens} = 1;
  393 
  394   $TeX = '\left('.$TeX.'\right)' if $addparens;
  395   return $TeX;
  396 }
  397 
  398 
  399 ######################################################################
  400 
  401 package Typeset::BOP::power;
  402 @ISA = qw(Parser::BOP::power);
  403 
  404 sub TeX {
  405   my $self = shift; my $rop = $self->{rop};
  406   my ($open,$close,$parens) = ($rop->{open},$rop->{close});
  407   $rop->{open} = $rop->{close} = "" if $rop->{isSetType} || $rop->{isListType};
  408   my $tex = Parser::BOP::underscore::TeX($self,@_);
  409   $rop->{open} = $open; $rop->{close} = $close;
  410   return $tex;
  411 }
  412 
  413 ######################################################################
  414 
  415 package Typeset::BOP::underscore;
  416 @ISA = qw(Typeset::BOP::TeX);
  417 
  418 sub TeX {
  419   my $self = shift; my $rop = $self->{rop};
  420   my ($open,$close,$parens) = ($rop->{open},$op->{close});
  421   $rop->{open} = $rop->{close} = "" if $rop->{isSetType} || $rop->{isListType};
  422   my $tex = Parser::BOP::underscore::TeX($self,@_);
  423   $rop->{open} = $open; $rop->{close} = $close;
  424   return $tex;
  425 }
  426 
  427 ######################################################################
  428 
  429 package Typeset::BOP::colon;
  430 @ISA = qw(Typeset::BOP::TeX);
  431 
  432 sub string {
  433   my $self = shift;
  434   my ($lop,$rop) = ($self->{lop},$self->{rop});
  435   return $self->SUPER::string(@_) unless $lop->class eq 'Variable' &&
  436     $rop->class eq 'BOP' && $rop->{def}{isFnArrow};
  437   return $lop->string.': '.$rop->string;
  438 }
  439 
  440 sub TeX {
  441   my $self = shift;
  442   my ($lop,$rop) = ($self->{lop},$self->{rop});
  443   return $self->SUPER::TeX(@_) unless $lop->class eq 'Variable' &&
  444     $rop->class eq 'BOP' && $rop->{def}{isFnArrow};
  445   return $lop->TeX.'\colon '.$rop->TeX;
  446 }
  447 
  448 ######################################################################
  449 
  450 package Typeset::BOP::semicolon;
  451 @ISA = qw(Typeset::BOP);
  452 
  453 sub _check {
  454   my $self = shift;
  455   my ($ltype,$rtype) = ($self->{lop}->typeRef,$self->{rop}->typeRef);
  456   my $type = Value::Type('Comma',2,$Value::Type{unknown});
  457   if ($ltype->{name} eq 'Comma' && $self->{lop}{isSemicolon}) {
  458     $type->{length} += $self->{lop}->length - 1;
  459     $ltype = $self->{lop}->entryType;
  460   }
  461   $type->{entryType} = $ltype if (Parser::Item::typeMatch($ltype,$rtype));
  462   $self->{type} = $type;
  463   $self->{isSemicolon} = 1;
  464 }
  465 
  466 sub _eval {($_[1],$_[2])}
  467 
  468 sub makeList {
  469   my $self = shift;
  470   return $self unless $self->{isSemicolon};
  471   my ($lop,$rop) = ($self->{lop},$self->{rop});
  472   my $equation = $self->{equation}; my $context = $equation->{context};
  473   $lop = $context->{parser}{List}->
  474     new($equation,[$lop->makeList],$lop->{isConstant},$context->{parens}{start},$lop->entryType,'(',')')
  475       if $lop->{def}{isComma} && !$lop->{isSemicolon};
  476   $rop = $context->{parser}{List}->
  477     new($equation,[$rop->makeList],$dop->{isConstant},$context->{parens}{start},$rop->entryType,'(',')')
  478       if $rop->{def}{isComma};
  479   return (($self->{lop}{isSemicolon} ? $lop->makeList : $lop),
  480     ($self->{rop}{isSemicolon} ? $rop->makeList : $rop));
  481 }
  482 
  483 ######################################################################
  484 
  485 package Typeset::UOP;
  486 @ISA = qw(Parser::UOP);
  487 
  488 sub TeX {
  489   my ($self,$precedence,$showparens,$position,$outerRight) = @_;
  490   my $TeX; my $uop = $self->{def}; $position = '' unless defined($position);
  491   my $fracparens = ($uop->{nofractionparens}) ? "nofractions" : "";
  492   my $addparens = $outerRight;
  493   $TeX = (defined($uop->{TeX}) ? $uop->{TeX} : $uop->{string});
  494   if ($uop->{associativity} eq "right") {
  495     $TeX = $self->{op}->TeX($uop->{precedence},$fracparens) . $TeX;
  496   } else {
  497     $TeX = $TeX . $self->{op}->TeX($uop->{precedence},$fracparens);
  498   }
  499   $TeX = '\left('.$TeX.'\right)' if $addparens;
  500   return $TeX;
  501 }
  502 
  503 ######################################################################
  504 
  505 package Typeset::UOP::TeX;
  506 @ISA = qw(Typeset::UOP);
  507 
  508 sub _check {
  509   my $self = shift;
  510   $self->{isConstant} = 0;
  511   $self->{type} = $Value::Type{number};
  512 }
  513 
  514 sub _eval {
  515   my $self = shift;
  516   my $name = $self->{def}{string} || $self->{bop};
  517   $self->Error("Can't evaluate '%s'",$name);
  518 }
  519 
  520 sub TeX {
  521   my ($self,$precedence) = @_;
  522   my $TeX; my $uop = $self->{def};
  523   $TeX = (defined($uop->{TeX}) ? $uop->{TeX} : $uop->{string});
  524   if ($uop->{associativity} eq "right")
  525      {$TeX = $self->{op}->TeX($uop->{precedence}) . $TeX} else
  526      {$TeX = $TeX . $self->{op}->TeX($uop->{precedence})}
  527   return $TeX;
  528 }
  529 
  530 sub perl {
  531   my $self = shift;
  532   my $name = $self->{def}{string} || $self->{bop};
  533   $self->Error("No perl form for '%s'",$name);
  534 }
  535 
  536 ######################################################################
  537 
  538 package Typeset::UOP::_if_;
  539 @ISA = qw(Typeset::UOP::TeX);
  540 
  541 sub string {
  542   my $self = shift;
  543   return ' if '.$self->{op}->string;
  544 }
  545 
  546 sub TeX {
  547   my $self = shift;
  548   return '\hbox{if }'.$self->{op}->TeX;
  549 }
  550 
  551 ######################################################################
  552 
  553 package Typeset::UOP::prime;
  554 @ISA = qw(Typeset::UOP::TeX);
  555 
  556 sub string {
  557   my ($self,$precedence,$showparens,$position,$outerRight) = @_;
  558   my $uop = $self->{def}; $position = '' unless defined($position);
  559   my $addparens = defined($precedence) &&
  560     ($precedence > $uop->{precedence} || $position eq 'right' || $outerRight);
  561   my $string = $self->{op}->string($uop->{precedence},$fracparens) . "'";
  562   $string = '\left('.$string.'\right)' if $addparens;
  563   return $string;
  564 }
  565 
  566 sub TeX {
  567   my ($self,$precedence,$showparens,$position,$outerRight) = @_;
  568   my $uop = $self->{def}; $position = '' unless defined($position);
  569   my $addparens = defined($precedence) &&
  570     ($precedence > $uop->{precedence} || $position eq 'right' || $outerRight);
  571   my $TeX = $self->{op}->TeX($uop->{precedence},$fracparens) . "'";
  572   $TeX = '\left('.$TeX.'\right)' if $addparens;
  573   return $TeX;
  574 }
  575 
  576 ######################################################################
  577 
  578 package Typeset::UOP::root;
  579 @ISA = qw(Typeset::UOP::TeX);
  580 
  581 sub TeX {
  582   my $self = shift;
  583   return "\\root ".$self->{op}->TeX if $self->{op}->class eq 'BOP' && $self->{op}{bop} eq 'of ';
  584   return "\\root ".$self->{op}{coords}[0]->TeX." \\of {".$self->{op}{coords}[1]->TeX."}"
  585     if $self->{op}->class eq 'List' && scalar(@{$self->{op}{coords}}) == 2;
  586   return "\\sqrt{".$self->{op}->TeX."}";
  587 }
  588 
  589 package Typeset::BOP::of;
  590 @ISA = qw(Typeset::BOP::TeX);
  591 
  592 sub TeX {
  593   my $self = shift;
  594   return $self->{lop}->TeX . " \\of {" . $self->{rop}->TeX . "}";
  595 }
  596 
  597 ######################################################################
  598 
  599 package Typeset::List;
  600 @ISA = qw(Parser::List);
  601 
  602 sub _eval {
  603   my $self = shift;
  604   return $self->SUPER::_eval(@_) unless $self->type eq 'Number';
  605   $self->{coords}[0]->eval(@_);
  606 }
  607 
  608 sub new {
  609   my $self = shift;
  610   my $equation = shift; my $coords = shift;
  611   my $constant = shift; my $paren = shift;
  612   my $entryType = shift || $Value::Type{unknown};
  613   my $open = shift || ''; my $close = shift || '';
  614   my $context = $equation->{context};
  615   my $parens = $context->{parens};
  616 
  617   if ($paren && $close && $paren->{formInterval}) {
  618     $paren = $parens->{interval}
  619       if ($paren->{close} ne $close || (scalar(@{$coords}) == 2 &&
  620            ($coords->[0]->{isInfinite} || $coords->[1]->{isInfinite})));
  621   }
  622   my $type = Value::Type($paren->{type},scalar(@{$coords}),$entryType,
  623                                 list => 1, formMatrix => $paren->{formMatrix});
  624   if ($type->{name} ne 'Interval' && ($type->{name} ne 'Set' || $type->{length} != 0)) {
  625     if ($paren->{formMatrix} && $entryType->{formMatrix}) {$type->{name} = 'Matrix'}
  626     elsif ($entryType->{name} eq 'unknown') {
  627       if ($paren->{formList}) {$type->{name} = 'List'}
  628       elsif ($type->{name} eq 'Point') {
  629         $equation->Error("Entries in a Matrix must be of the same type and length")}
  630       elsif ($type->{name} ne 'Set') {
  631   $type->{name} = "Matrix" if $paren->{formMatrix};
  632   $equation->Error(["Entries in a %s must be of the same type",$type->{name}]);
  633       }
  634     }
  635   }
  636   $open = '' if $open eq 'start'; $close = '' if $close eq 'start';
  637   my $list = bless {
  638     coords => $coords, type => $type, open => $open, close => $close,
  639     paren => $paren, equation => $equation, isConstant => $constant
  640   }, $context->{lists}{$type->{name}}{class};
  641 
  642   my $zero = 1;
  643   foreach my $x (@{$coords}) {$zero = 0, last unless $x->{isZero}}
  644   $list->{isZero} = 1 if $zero && scalar(@{$coords}) > 0;
  645 
  646   $list->_check;
  647 
  648   warn ">> $list->{type}{name} of $list->{type}{entryType}{name} of length $list->{type}{length}\n";
  649 
  650   if ($list->{isConstant} && $context->flag('reduceConstants')) {
  651     $type = $list->{type};
  652     $list = $lis->Item("Value")->new($equation,[$list->eval]);
  653     $list->{type} = $type; $list->{open} = $open; $list->{close} = $close;
  654     $list->{value}->{open} = $open, $list->{value}->{close} = $close
  655       if ref($list->{value});
  656   }
  657   return $list;
  658 }
  659 
  660 ######################################################################
  661 
  662 package Typeset::List::List;
  663 @ISA = qw(Typeset::List Parser::List::List);
  664 
  665 sub _check {
  666   my $self = shift;
  667   $self->{isListType} = 1; $self->{showParens} = 1;
  668   return unless $self->length == 1;
  669   $self->{type} = {%{$self->{coords}[0]->typeRef}};
  670   $self->{type}{formMatrix} = 1 if $self->context->{parens}{$self->{open}}{formMatrix};
  671   $self->{isSingle} = 1;
  672 }
  673 
  674 sub TeX {
  675   my $self = shift;
  676   return $self->SUPER::TeX(@_) if $self->{showParens} || $self->length != 1;
  677   return $self->{coords}[0]->TeX(@_);
  678 }
  679 
  680 ######################################################################
  681 
  682 package Typeset::List::Vector;
  683 @ISA = qw(Parser::List::List);
  684 
  685 sub TeX {
  686   my $self = shift; my $precedence = shift; my @coords = ();
  687   my $def = $self->context->{lists}{Vector};
  688   my ($open,$close) = ($def->{TeX_open},$def->{TeX_close});
  689   $open = '\{' if $open eq '{'; $close = '\}' if $close eq '}';
  690   $open  = '\left' .$open  if $open  ne '';
  691   $close = '\right'.$close if $close ne '';
  692   foreach my $x (@{$self->{coords}}) {push(@coords,$x->TeX)}
  693   return $open.join(',',@coords).$close unless $self->{ColumnVector};
  694   '\left[\begin{array}{c}'.join('\cr'."\n",@coords).'\cr\end{array}\right]';
  695 }
  696 
  697 ######################################################################
  698 
  699 package Typeset::List::Set;
  700 @ISA = qw(Typeset::List);
  701 
  702 sub _check {
  703   my $self = shift;
  704   $self->{isSetType} = 1; $self->{showParens} = 1;
  705   return unless $self->length == 1;
  706   my $x = $self->{coords}[0];
  707   if ($x->{isSetType}) {
  708     $x->{showParens} = 1;
  709     $self->{showParens} = 0;
  710   } else {
  711     if ($x->class =~ m/BOP|UOP/) {
  712       $self->{type} = $self->{coords}[0]->typeRef;
  713       $self->{showParens} = 0;
  714     }
  715   }
  716 }
  717 
  718 sub canBeInUnion {1};
  719 
  720 sub TeX {
  721   my $self = shift; my $precedence = shift;
  722   return $self->SUPER::string(@_) if $self->{showParens} || $self->length > 1;
  723   my $set = $self->{coords}[0];
  724   return '{ '.$set->string.' }' if $set->class eq 'BOP' && $set->{def}{formSet};
  725   return $self->{coords}[0]->string;
  726 }
  727 
  728 sub TeX {
  729   my $self = shift; my $precedence = shift;
  730   return $self->SUPER::TeX(@_) if $self->{showParens} || $self->length > 1;
  731   my $set = $self->{coords}[0];
  732   return '\left\{\,'.$set->TeX.'\,\right\}' if $set->class eq 'BOP' && $set->{def}{formSet};
  733   return $self->{coords}[0]->TeX;
  734 }
  735 
  736 ######################################################################
  737 
  738 package Typeset::List::AbsoluteValue;
  739 @ISA = qw(Parser::List::AbsoluteValue);
  740 
  741 sub TeX {
  742   my $self = shift;
  743   return $self->SUPER::TeX(@_) unless $self->{coords}[0]->type eq 'Matrix';
  744   my $M = bless {%{$self->{coords}[0]}, open => '|', close => '|'}, ref($self->{coords}[0]);
  745   $M->TeX;
  746 }
  747 
  748 ######################################################################
  749 
  750 package main;
  751 
  752 $context{Typeset} = $Parser::Context::Default::fullContext->copy;
  753 $context{Typeset}->flags->set(
  754   reduceConstants => 0,
  755   reduceConstantFunctions => 0,
  756   allowMissingOperands => 1,          # turn off most error checking
  757   allowMissingFunctionInputs => 1,    #  by setting these four
  758   allowBadOperands => 1,              #  flags to 1
  759   allowBadFunctionInputs => 1,        #
  760   showExtraParens => 0,               # Try to keep the author's parens
  761 );
  762 $context{Typeset}->{_initialized} = 0;  # prevent updating of patterns until we're done
  763 
  764 sub TeXOp {
  765   my $type = shift; my $prec = shift; my $assoc = shift;
  766   my $op = shift; my $string = shift; my $tex = shift;
  767   my $class = 'Typeset::'.($type eq 'bin'? "BOP" : "UOP").'::TeX';
  768   return $op => {precedence => $prec, associativity => $assoc, type => $type,
  769     string => $string, TeX=>$tex." ", class=>$class, @_};
  770 }
  771 sub TeXUnary {my $op = shift; TeXOp("unary",1,"left",$op," $op ",@_)}
  772 sub TeXBin {my $op = shift; TeXOp("bin",.8,"left",$op," $op ",@_)}
  773 sub TeXRel {my $op = shift; TeXOp("bin",.7,"left",$op," $op ",@_)}
  774 sub TeXArrow {my $op = shift; TeXOp("bin",.7,"left",$op," $op ",@_)}
  775 
  776 $context{Typeset}->operators->add(
  777   ';' => {
  778     precedence => 0, associativity => 'left', type => 'bin', string => ';',
  779     class => 'Typeset::BOP::semicolon', isComma => 1
  780   },
  781   '_if_' => {
  782     precedence => .61, associativity => 'left', type => 'unary', string => ' if ',
  783     class => 'Typeset::UOP::_if_', hidden => 1
  784   },
  785   "'" => {
  786     precedence => 7.5, associativity => 'right', type => 'unary', string => "'",
  787     class => 'Typeset::UOP::prime'
  788   },
  789 );
  790 
  791 $context{Typeset}->operators->set(
  792   ',' => {precedence=>.5},
  793   '_' => {class=>'Typeset::BOP::underscore',associativity=>"right"},
  794   ' ' => {string => 'space'},
  795   'space' => {precedence => 3, associativity => 'left', type => 'bin',
  796         string => '', TeX => '', class => 'Parser::BOP::multiply', hidden => 1},
  797   '/'  => {class => 'Typeset::BOP::divide'},
  798   '/ ' => {class => 'Typeset::BOP::divide'},
  799   ' /' => {class => 'Typeset::BOP::divide'},
  800   '^'  => {class => 'Typeset::BOP::power'},
  801   '**' => {class => 'Typeset::BOP::power'},
  802   '-'  => {class => 'Typeset::BOP::subtract'},
  803   'U'  => {class => 'Typeset::BOP::union'},
  804 );
  805 
  806 $context{Typeset}->operators->redefine('&', using => ",", from=>$context{Typeset});
  807 $context{Typeset}->operators->redefine("\\\\", using => ";", from => $context{Typeset});
  808 $context{Typeset}->operators->redefine("cross", using => "><", from => $context{Typeset});
  809 
  810 $context{Typeset}->operators->add(
  811   TeXArrow('->','\to',isFnArrow=>1),
  812   TeXArrow('-->','\longrightarrow'),
  813   TeXArrow('<-','\leftarrow'),
  814   TeXArrow('<--','\longleftarrow'),
  815   TeXArrow('<->','\leftrightarrow'),
  816   TeXArrow('<-->','\longleftrightarrow'),
  817   TeXArrow('|->','\mapsto'),
  818   TeXArrow('|-->','\longmapsto'),
  819   TeXArrow('*->','\hookrightarrow'),
  820   TeXArrow('<-*','\hookleftarrow'),
  821   TeXArrow('=>','\Rightarrow'),
  822   TeXArrow('==>','\Longrightarrow'),
  823   TeXArrow('<=:','\Leftarrow'),
  824   TeXArrow('<==','\Longleftarrow'),
  825   TeXArrow('<=>','\Leftrightarrow'),
  826   TeXArrow('<==>','\Longleftrightarrow'),
  827   TeXArrow("up",'\uparrow'),
  828   TeXArrow('down','\downarrow'),
  829   TeXArrow('updown','\updownarrow'),
  830   TeXArrow('Up','\Uparrow'),
  831   TeXArrow('Down','\Downarrow'),
  832   TeXArrow('Updown','\Updownarrow'),
  833   TeXArrow('NW','\nwarrow'),
  834   TeXArrow('SE','\searrow'),
  835   TeXArrow('SW','\swarrow'),
  836   TeXArrow('NE','\nearrow'),
  837   TeXArrow('iff','\Leftrightarrow'),
  838 
  839   TeXRel('<','<'),                  TeXRel('lt','<'),
  840   TeXRel('>','>'),                  TeXRel('gt','>'),
  841   TeXRel('<=','\le'),               TeXRel('le'),
  842   TeXRel('>=','\ge'),               TeXRel('ge'),
  843   TeXRel('=','='),
  844   TeXRel('!=','\ne'),               TeXRel('ne','\ne'),
  845   TeXRel('<<','\ll'),
  846   TeXRel('>>','\gg'),
  847   TeXRel('sim','\sim'),             TeXRel('~','\sim'),
  848   TeXRel('simeq','\simeq'),         TeXRel('~-','\simeq'),
  849   TeXRel('cong','\cong'),           TeXRel('~=','\cong'),
  850   TeXRel('approx','\approx'),       TeXRel('~~','\approx'),
  851   TeXRel('equiv','\equiv'),         TeXRel('-=','\equiv'),
  852   TeXRel('vdash','\vdash'),         TeXRel('|--','\vdash'),
  853   TeXRel('dashv','\dashv'),         TeXRel('--|','\dashv'),
  854   TeXRel('perp','\perp'),           TeXRel('_|_','\perp'),
  855   TeXRel('parallel','\parallel'),   TeXRel('||','\parallel'),
  856   TeXRel('doteq','\doteq'),         TeXRel('=.=','\doteq'),
  857   TeXRel('models','\models'),       TeXRel('|==','\models'),
  858   TeXRel('in','\in'),
  859   TeXRel('subset','\subset'),
  860   TeXRel('subseteq','\subseteq'),
  861   TeXRel('sqsubseteq','\sqsubseteq'),
  862   TeXRel('supset','\supset'),
  863   TeXRel('supseteq','\supseteq'),
  864   TeXRel('sqsupseteq','\sqsupseteq'),
  865   TeXRel('prec','\prec'),           TeXRel('-<','\prec'),
  866   TeXRel('preceq','\preceq'),       TeXRel('-<=','\preceq'),
  867   TeXRel('succ','\succ'),           TeXRel('>-','\succ'),
  868   TeXRel('succeq','\succeq'),       TeXRel('>-=','\succeq'),
  869   TeXRel('propto','\propto'),
  870   TeXRel('mid','\mid', precedence=>.3,formSet=>1),
  871                                     TeXRel('s.t. ','\mid',string=>" s.t. ",precedence=>.3,formSet=>1),
  872   TeXRel('ni','\ni'),               TeXRel('gets','\gets'),
  873   TeXRel('smile','\smile'),
  874   TeXRel('frown','\frown'),
  875   TeXRel('asymp','\asymp'),
  876   TeXRel('bowtie','\bowtie'),
  877 
  878   TeXRel('!<','\not<'),                TeXRel('!lt','\not<'),
  879   TeXRel('!>','\not>'),                TeXRel('!gt','\not>'),
  880   TeXRel('!<=','\not\le'),             TeXRel('!ge','\not\le'),
  881   TeXRel('!>=','\not\ge'),             TeXRel('!le','\not\ge'),
  882   TeXRel('!sim','\not\sim'),           TeXRel('!~','\not\sim'),
  883   TeXRel('!simeq','\not\simeq'),       TeXRel('!~-','\not\simeq'),
  884   TeXRel('!cong','\not\cong'),         TeXRel('!~=','\not\cong'),
  885   TeXRel('!approx','\not\approx'),     TeXRel('!~~','\not\approx'),
  886   TeXRel('!perp',',\not\perp'),        TeXRel('!_|_','\not\perp'),
  887   TeXRel('!parallel','\not\parallel'), TeXRel('!||','\not\parallel'),
  888   TeXRel('!equiv','\not\equiv'),       TeXRel('!-=','\not\equiv'),
  889   TeXRel('!in','\notin'),
  890   TeXRel('!subset','\not\subset'),
  891   TeXRel('!subseteq','\not\subseteq'),
  892   TeXRel('!sqsubseteq','\not\sqsubseteq'),
  893   TeXRel('!supset','\not\supset'),
  894   TeXRel('!supseteq','\not\supseteq'),
  895   TeXRel('!sqsupseteq','\not\sqsupseteq'),
  896   TeXRel('!prec','\not\prec'),         TeXRel('!-<','\not\prec'),
  897   TeXRel('!preceq','\not\preceq'),     TeXRel('!-<=','\not\preceq'),
  898   TeXRel('!succ','\not\succ'),         TeXRel('!>-','\not\succ'),
  899   TeXRel('!succeq','\not\succeq'),     TeXRel('!>-=','\not\succeq'),
  900   TeXRel('!asymp','\not\asymp'),
  901 
  902   TeXBin(':',' :',class=>'Typeset::BOP::colon',precedence=>.3,isColon=>1,formSet=>1),
  903   TeXBin('::',' ::'),
  904   TeXUnary('pm','\pm'),
  905   TeXUnary('mp','\mp'),
  906   TeXBin('setminus','\setminus'),
  907   TeXBin('cdot','\cdot'),
  908   TeXBin('ast','\ast'),
  909   TeXBin('star','\star'),
  910   TeXBin('diamond','\diamond'),
  911   TeXBin('circ','\circ'),    TeXBin('o ','\circ'),
  912   TeXBin('bullet','\bullet'),
  913   TeXBin('div','\div'),      TeXBin('-:','\div'),
  914   TeXBin('cap','\cap'),
  915   TeXBin('cup','\cup'),
  916   TeXBin('uplus','\uplus'),  TeXBin('u+ ','\uplus'),
  917   TeXBin('sqcap','\sqcap'),
  918   TeXBin('sqcup','\sqcup'),
  919   TeXBin('triangleleft','\triangleleft'),
  920   TeXBin('triangleright','\triangleright'),
  921   TeXBin('wr','\wr'),
  922   TeXBin('bigcirc','\bigcirc'),
  923   TeXBin('bigtriangleup','\bigtriangleup'),
  924   TeXBin('bigtriangledown','\bigtriangledown'),
  925   TeXBin('vee','\vee'),       TeXBin("\\/",'\vee'),
  926   TeXBin('wedge','\wedge'),   TeXBin("/\\",'\wedge'),
  927   TeXBin('oplus','\oplus'),   TeXBin('o+ ','\oplus'),
  928   TeXBin('ominus','\ominus'), TeXBin('o- ','\ominus'),
  929   TeXBin('otimes','\otimes'), TeXBin('ox ','\otimes'),
  930   TeXBin('oslash','\oslash'), TeXBin('o/ ','\oslash'),
  931   TeXBin('odot','\odot'),     TeXBin('o. ','\odot'),
  932   TeXBin('amalg','\amalg'),
  933   TeXBin('times','\times'),
  934 
  935   TeXOp("bin",.63,"left",'and',' and ','\hbox{ and }'),
  936   TeXOp("bin",.62,"left",'or',' or ','\hbox{ or }'),
  937   TeXOp("unary",.64,"left",'not',' not ','\hbox{not }'),
  938   TeXOp("unary",.64,"left",'neg',' neg ','\neg'),
  939 
  940   TeXOp("bin",.61,"left",'if ',' if ','\hbox{ if }'),
  941   TeXOp("unary",.61,"right",'otherwise',' otherwise','\hbox{otherwise}'),
  942 
  943   TeXUnary('root', "\\root ", class=>'Typeset::UOP::root',precedence=>.65, string=>"root "),
  944   TeXBin('of ','\of',class=>'Typeset::BOP::of',precedence=>.66),
  945 
  946   TeXBin("quad",'\quad', precedence => .2),
  947   TeXBin("qquad",'\qquad', precedence => .2),
  948 );
  949 
  950 ######################################################################
  951 
  952 sub TeXGreek {
  953   my $greek = shift; my $uc = shift;
  954   push(@_,TeX=>"{\\rm $uc}") if $uc;
  955   return ($greek => {value => Real(1), TeX=>"\\$greek ", keepName=>1, @_});
  956 }
  957 
  958 sub TeXord {
  959   my $name = shift; my $tex = shift;
  960   $tex = "\\$name " unless defined $tex; $tex .= ' ' if $tex =~ m/\\[a-zA-Z]+$/;
  961   return ($name => {value => Real(1), TeX=>$tex, keepName=>1, @_});
  962 }
  963 
  964 sub TeXconst {
  965   my $name = shift; my $tex = shift; $tex .= " " unless $tex =~ m/}$/;
  966   my $string = shift; $string = $name unless defined $string;
  967   return ($name => {value => Real(1), TeX=>$tex, string=>$string, keepName=>1, @_});
  968 }
  969 
  970 $context{Typeset}->constants->{namePattern} = '.*';
  971 $context{Typeset}->constants->are(
  972   TeXGreek('alpha'),    TeXGreek('Alpha','A'),
  973   TeXGreek('beta'),     TeXGreek('Beta','B'),
  974   TeXGreek('gamma'),    TeXGreek('Gamma'),
  975   TeXGreek('delta'),    TeXGreek('Delta'),
  976   TeXGreek('epsilon'),  TeXGreek('Epsilon','E'),   TeXGreek('varepsilon'),
  977   TeXGreek('zeta'),     TeXGreek('Zeta','Z'),
  978   TeXGreek('eta'),      TeXGreek('Eta','H'),
  979   TeXGreek('theta'),    TeXGreek('Theta',),        TeXGreek('vartheta'),
  980   TeXGreek('iota'),     TeXGreek('Iota','I'),
  981   TeXGreek('kappa'),    TeXGreek('Kappa','K'),
  982   TeXGreek('lambda'),   TeXGreek('Lambda'),
  983   TeXGreek('mu'),       TeXGreek('Mu','M'),
  984   TeXGreek('nu'),       TeXGreek('Nu','N'),
  985   TeXGreek('xi'),       TeXGreek('Xi'),
  986   TeXGreek('omicron'),  TeXGreek('Omicron','O'),
  987   TeXGreek('pi'),       TeXGreek('Pi'),            TeXGreek('varpi'),
  988   TeXGreek('rho'),      TeXGreek('Rho','P'),       TeXGreek('varrho'),
  989   TeXGreek('sigma'),    TeXGreek('Sigma'),         TeXGreek('varsigma'),
  990   TeXGreek('tau'),      TeXGreek('Tau','T'),
  991   TeXGreek('upsilon'),  TeXGreek('Upsilon'),
  992   TeXGreek('phi'),      TeXGreek('Phi'),           TeXGreek('varphi'),
  993   TeXGreek('chi'),      TeXGreek('Chi','X'),
  994   TeXGreek('psi'),      TeXGreek('Psi'),
  995   TeXGreek('omega'),    TeXGreek('Omega'),
  996 
  997   TeXconst('Null','',''),
  998   TeXconst('RR','{\bf R}','R'),
  999   TeXconst('QQ','{\bf Q}','Q'),
 1000   TeXconst('CC','{\bf C}','C'),
 1001   TeXconst('NN','{\bf N}','N'),
 1002   TeXconst('ZZ','{\bf Z}','Z'),
 1003 
 1004   TeXord('aleph'),
 1005   TeXord('hbar'),
 1006   TeXord('imath'),
 1007   TeXord('jmath'),
 1008   TeXord('ell'),
 1009   TeXord('wp'),
 1010   TeXord('emptyset'),
 1011   TeXord('nabla'),       TeXord('grad','\nabla'),
 1012   TeXord('top'),
 1013   TeXord('bot'),
 1014   TeXord('angle'),
 1015   TeXord('triangle'),
 1016   TeXord('backslash'),
 1017   TeXord('forall'),
 1018   TeXord('exists'),
 1019   TeXord('partial'),
 1020 
 1021   TeXord('ldots','\ldots'),  TeXord('..','\ldots'),
 1022   TeXord('cdots','\cdots'),  TeXord('...','\cdots'),
 1023   TeXord('vdots','\vdots'),
 1024   TeXord('ddots','\ddots'),
 1025 
 1026   TeXord('inf','\inf'),
 1027   TeXord('liminf','\liminf'),
 1028   TeXord('limsup','\limsup'),
 1029   TeXord('max','\max'),
 1030   TeXord('min','\min'),
 1031   TeXord('lim','\lim'),
 1032   TeXord('sum','\sum'),
 1033   TeXord('prod','\prod'),
 1034   TeXord('coprod','\coprod'),
 1035   TeXord('int','\int'),
 1036 # TeXord('iint','\iint'),
 1037 # TeXord('iiint','\iiint'),
 1038   TeXord('oint','\oint'),
 1039   TeXord('bigcup','\bigcup'),
 1040   TeXord('bigcap','\bigcap'),
 1041   TeXord('bigsqcup','\bigsqcup'),
 1042   TeXord('bigvee','\bigvee'),
 1043   TeXord('bigwedge','\bigwedge'),
 1044   TeXord('bigodot','\bigodot'),
 1045   TeXord('bigotimes','\bigotimes'),
 1046   TeXord('bigoplus','\bigoplus'),
 1047   TeXord('biguplus','\biguplus'),
 1048 );
 1049 $context{Typeset}->constants->add(_blank_ => {value => Real(0), hidden => 1, string => "", TeX => ""});
 1050 
 1051 ######################################################################
 1052 
 1053 sub TeXBigOp {
 1054   my $name = shift; my $tex = shift;
 1055   return ($name => {class => 'Typeset::Function::bigOp', precedence => .9, TeX => $tex, @_});
 1056 }
 1057 
 1058 sub TeXfn {
 1059   my $name = shift;
 1060   return ($name => {class => 'Typeset::Function::'.$name, @_});
 1061 }
 1062 
 1063 sub TeXnamedFn {
 1064   my $name = shift;
 1065   return ($name => {class => 'Typeset::Function::named', TeX=>"\\$name", @_});
 1066 }
 1067 
 1068 sub TeXaccent {
 1069   my $name = shift;
 1070   return ($name => {class => 'Typeset::Function::accent', TeX=>"\\$name", @_});
 1071 }
 1072 
 1073 sub TeXoverunder {
 1074   my $name = shift;
 1075   return ($name => {class => 'Typeset::Function::overunder', TeX=>"\\$name", @_});
 1076 }
 1077 
 1078 $context{Typeset}->functions->{namePattern} = qr/.*/;
 1079 $context{Typeset}->functions->add(
 1080   TeXBigOp('Lim','\lim', allowArrow => 1, noMax => 1),
 1081   TeXBigOp('Sum','\sum'),
 1082   TeXBigOp('Prod','\prod'),
 1083   TeXBigOp('Coprod','\coprod'),
 1084   TeXBigOp('Int','\int', dx => 1, precedence => 6.5),
 1085 # TeXBigOp('IInt','\iint', dx => 1, precedence => 6.5),
 1086 # TeXBigOp('IIInt','\iiint', dx => 1, precedence => 6.5),
 1087   TeXBigOp('Oint','\oint', dx => 1, precedence => 6.5),
 1088   TeXBigOp('Cup','\bigcup'),
 1089   TeXBigOp('Cap','\bigcap'),
 1090   TeXBigOp('Sqcup','\bigsqcup'),
 1091   TeXBigOp('Vee','\bigvee'),
 1092   TeXBigOp('Wedge','\bigwedge'),
 1093   TeXBigOp('Odot','\bigodot'),     TeXBigOp('O. ','\bigodot'),
 1094   TeXBigOp('Otimes','\bigotimes'), TeXBigOp('Ox ','\bigotimes'),
 1095   TeXBigOp('Oplus','\bigoplus'),   TeXBigOp('O+ ','\bigoplus'),
 1096   TeXBigOp('Uplus','\biguplus'),   TeXBigOp('U+ ','\biguplus'),
 1097 
 1098   TeXfn('text'),
 1099   TeXfn('bf'),
 1100   TeXfn('cal'),
 1101   TeXfn('Array'),
 1102   TeXfn('TeX'),
 1103   TeXfn('Fence'),
 1104   TeXfn('Cases'),
 1105 
 1106   TeXfn('det', TeX=>"\\det"),
 1107 
 1108   TeXnamedFn('deg'),
 1109   TeXnamedFn('dim'),
 1110   TeXnamedFn('gcd'),
 1111   TeXnamedFn('hom'),
 1112 #  TeXnamedFn('inf'),
 1113   TeXnamedFn('ker'),
 1114   TeXnamedFn('lg'),
 1115 #  TeXnamedFn('max'),
 1116 #  TeXnamedFn('min'),
 1117   TeXnamedFn('Pr'),
 1118 #  TeXnamedFn('sup'),
 1119 
 1120   TeXaccent('hat'),
 1121   TeXaccent('bar'),
 1122   TeXaccent('vec'),
 1123   TeXaccent('dot'),
 1124   TeXaccent('ddot'),
 1125 
 1126   TeXoverunder('underline'),
 1127   TeXoverunder('overline'),
 1128   TeXoverunder('underbrace'),
 1129   TeXoverunder('overbrace'),
 1130 );
 1131 
 1132 ######################################################################
 1133 
 1134 $context{Typeset}->parens->set(
 1135   '(' => {type => 'List', removable => 0, formMatrix => 0},
 1136   '[' => {type => 'List', removable => 0},
 1137   '{' => {type => "Set",  removable => 0, emptyOK=>1},
 1138 );
 1139 $context{Typeset}->parens->add(
 1140   '<[' => {type => "Vector", close => ']>'},
 1141 );
 1142 $context{Typeset}->parens->remove('<');
 1143 
 1144 $context{Typeset}->lists->set(
 1145   Set    => {class => 'Typeset::List::Set'},
 1146   List   => {class => 'Typeset::List::List'},
 1147   Vector => {class => 'Typeset::List::Vector', TeX_open => "<", TeX_close => ">"},
 1148   AbsoluteValue => {class => 'Typeset::List::AbsoluteValue'},
 1149 );
 1150 $context{Typeset}->{parser}{List} = 'Typeset::List';
 1151 
 1152 ######################################################################
 1153 
 1154 Typeset::addVariables($context{Typeset});
 1155 
 1156 ######################################################################
 1157 
 1158 $context{Typeset}->{_initialized} = 1; # now update the patterns
 1159 $context{Typeset}->update;
 1160 
 1161 ######################################################################
 1162 
 1163 $context{Typeset}->strings->clear();
 1164 $context{Typeset}->strings->redefine("infty", using=>"infinity");
 1165 $context{Typeset}->strings->set(infty => {string => "infty"});
 1166 $context{Typeset}->strings->redefine("infinity");
 1167 loadMacros("parserQuotedString.pl");
 1168 QuotedString::enable($context{Typeset});
 1169 
 1170 ######################################################################
 1171 
 1172 $context{"Typeset-Vector"} = $context{Typeset}->copy;
 1173 $context{"Typeset-Vector"}->operators->remove('<','>');
 1174 $context{"Typeset-Vector"}->parens->remove('<[');
 1175 $context{"Typeset-Vector"}->parens->redefine('<');
 1176 
 1177 ######################################################################
 1178 
 1179 Context("Typeset");
 1180 
 1181 ######################################################################
 1182 
 1183 1;

aubreyja at gmail dot com
ViewVC Help
Powered by ViewVC 1.0.9