% \iffalse meta-comment
% An Infrastructure for marking up Assignments
% Copyright (c) 2007 Michael Kohlhase, all rights reserved
%               this file is released under the
%               LaTeX Project Public License (LPPL)
% The original of this file is in the public repository at 
% http://github.com/KWARC/sTeX/
% \fi
% 
% \iffalse
%<package|cls>\NeedsTeXFormat{LaTeX2e}[1999/12/01]
%<package>\ProvidesPackage{hwexam}[2016/04/07 v1.1 homework assignments and exams]
%<cls>\ProvidesClass{hwexam}[2016/04/07 v1.1 assignment and exam documents]
%
%<*driver>
\documentclass{ltxdoc}
\usepackage{url,float}
\usepackage{hwexam}
\usepackage[show]{ed}
\usepackage[hyperref=auto,style=alphabetic]{biblatex}
\addbibresource{kwarcpubs.bib}
\addbibresource{extpubs.bib}
\addbibresource{kwarccrossrefs.bib}
\addbibresource{extcrossrefs.bib}
\usepackage{stex-logo}
\usepackage{ctangit}
\usepackage{hyperref}
\makeindex
\floatstyle{boxed}
\newfloat{exfig}{thp}{lop}
\floatname{exfig}{Example}
\def\tracissue#1{\cite{sTeX:online}, \hyperlink{http://trac.kwarc.info/sTeX/ticket/#1}{issue #1}}
\begin{document}\DocInput{hwexam.dtx}\end{document}
%</driver>
% \fi
%\CheckSum{464}
% 
% \changes{v0.9}{2006/09/18}{First Version with Documentation}
% \changes{v0.9a}{2010/06/25}{more semantic headers for exams}
% \changes{v0.9b}{2010/09/20}{adding \texttt{assignment.cls}}
% \changes{v0.9c}{2010/09/20}{renaming from \texttt{assignment} to \texttt{hwexam} to
% avoid name clashes with existing \texttt{assignment.cls} on CTAN.}
% \changes{v1.0}{2013/12/12}{adding MathHub support}
% \changes{v1.1}{2015/11/04}{moving MathHub support out to separate package}
% 
% \GetFileInfo{hwexam.sty}
% 
% \MakeShortVerb{\|}
% \def\scsys#1{{{\sc #1}}\index{#1@{\sc #1}}}
% \def\latexml{\scsys{LaTeXML}}
%
% \title{\texttt{hwexam.sty/cls}: An Infrastructure for formatting Assignments 
%        and Exams\thanks{Version {\fileversion} (last revised {\filedate})}}
%    \author{Michael Kohlhase\\
%            Jacobs University, Bremen\\
%            \url{http://kwarc.info/kohlhase}}
% \maketitle
%
% \begin{abstract}
%   The |hwexam| package and class allows individual course assignment sheets and
%   compound assignment documents using problem files marked up with the |problem| package.
% \end{abstract}
% \setcounter{tocdepth}{2}\tableofcontents\newpage
%
%\section{Introduction}\label{sec:intro}
%
% The |hwexam| package and class supplies an infrastructure that allows to format
% nice-looking assignment sheets by simply including problems from problem files marked up
% with the |problem| package~\cite{Kohlhase:problem:ctan}.  It is designed to be
% compatible with |problems.sty|, and inherits some of the functionality.
% 
% \section{The User Interface}
% 
% \subsection{Package and Class Options}\label{sec:user:options}
% 
% The |hwexam| class takes the \DescribeMacro{mh}|mh| option that turns on MathHub
% support.
%
% The |hwexam| package and class take the options |solutions|, |notes|, |hints|, |pts|,
% |min|, and |boxed| that are just passed on to the |problems| package (cf. its
% documentation for a description of the intended behavior).
% 
% If the \DescribeMacro{showmeta}|showmeta| option is set, then the metadata keys are
% shown (see~\cite{Kohlhase:metakeys:ctan} for details and customization options).
% 
% The |hwexam| class additionally accepts the options |report|, |book|, |chapter|, |part|,
% and |showignores|, of the |omdoc| package~\cite{Kohlhase:smomdl:ctan} on which it is
% based and passes them on to that. For the |extrefs| option
% see~\cite{Kohlhase:sref:ctan}.
%
% \subsection{Assignments}
%
% This package supplies the \DescribeEnv{assignment}|assignment| environment that groups
% problems into assignment sheets. It takes an optional KeyVal argument with the keys
% \DescribeMacro{number}|number| (for the assignment number; if none is given, 1 is
% assumed as the default or --- in multi-assignment documents --- the ordinal of the
% |assignment| environment), \DescribeMacro{title}|title| (for the assignment title; this
% is referenced in the title of the assignment sheet), \DescribeMacro{type}|type| (for the
% assignment type; e.g. ``quiz'', or ``homework''), \DescribeMacro{given}|given| (for the
% date the assignment was given), and \DescribeMacro{due}|due| (for the date the
% assignment is due).
% 
% \subsection{Typesetting Exams}
%
% Furthermore, the |hwexam| package takes the option
% \DescribeMacro{multiple}|multiple| that allows to combine multiple assignment sheets into
% a compound document (the assignment sheets are treated as section, there is a table of
% contents, etc.). 
% 
% Finally, there is the option \DescribeMacro{test}|test| that modifies the behavior to
% facilitate formatting tests. Only in |test| mode, the macros |\testspace|,
% |\testnewpage|, and |\testemptypage| have an effect: they generate space for the
% students to solve the given problems. Thus they can be left in the {\LaTeX} source. 
%
% \DescribeMacro{\testspace}|\testspace| takes an argument that expands to a dimension,
% and leaves vertical space accordingly. \DescribeMacro{\testnewpage}|\testnewpage| makes
% a new page in |test| mode, and \DescribeMacro{\testemptypage}|\testemptypage| generates
% an empty page with the cautionary message that this page was intentionally left empty.
%
% Finally, the \DescribeEnv{testheading}|\testheading| takes an optional keyword argument
% where the keys \DescribeMacro{duration}|duration| specifies a string that specifies the
% duration of the test, \DescribeMacro{min}|min| specifies the equivalent in number of
% minutes, and \DescribeMacro{reqpts}|reqpts| the points that are required for a perfect
% grade.
% \begin{exfig}[ht]
% \makeatletter
% \@problem{1.1}{4}{10}
% \@problem{2.1}{4}{8}
% \@problem{2.2}{6}{10}
% \@problem{2.3}{6}{10}
% \@problem{3.1}{4}{8}
% \@problem{3.2}{4}{8}
% \@problem{3.3}{2}{4}
% \makeatother
% \begin{verbatim}
% \title{320101 General Computer Science (Fall 2010)}
% \begin{testheading}[duration=one hour,min=60,reqpts=27]
%   Good luck to all students!
% \end{testheading}
% \end{verbatim}
% \vspace*{-3ex}\hrule\vspace*{.5ex}  formats to\vspace*{1ex}
% \hrule\par\noindent\vspace*{2ex}
% \title{320101 General Computer Science (Fall 2010)}
% \begin{testheading}[duration=one hour,min=60,reqpts=27]
%   good luck
% \end{testheading}
% \caption{A generated test heading.}\label{fig:testheading}
% \end{exfig}
% 
% \subsection{Including Assignments}
%
% The \DescribeMacro{\includeassignment}|\includeassignment| macro can be used to include
% an assignment from another file. It takes an optional KeyVal argument and a second
% argument which is a path to the file containing the problem (the macro assumes that
% there is only one |assignment| environment in the included file).  The keys
% \DescribeMacro{number}|number|, \DescribeMacro{title}|title|,
% \DescribeMacro{type}|type|, \DescribeMacro{given}|given|, and \DescribeMacro{due}|due|
% are just as for the |assignment| environment and (if given) overwrite the ones specified
% in the |assignment| environment in the included file.
% 
% \section{Limitations}\label{sec:limitations}
% 
% In this section we document known limitations. If you want to help alleviate them,
% please feel free to contact the package author. Some of them are currently discussed in
% the \sTeX GitHub repository~\cite{sTeX:github:on}. 
% \begin{compactenum}
% \item none reported yet. 
% \end{compactenum}
% 
% \StopEventually{\newpage\PrintIndex\newpage\PrintChanges\printbibliography}\newpage
% \newpage
%
% \section{Implementation: The hwexam Class}\label{sec:impl:cls}
%
% The functionality is spread over the |hwexam| class and package. The class provides
% the |document| environment and pre-loads some convenience packages, whereas the package
% provides the concrete functionality.
% 
% \subsection{Class Options}\label{sec:impl:cls:options}
%
% To initialize the |hwexam| class, we declare and process the necessary options by
% passing them to the respective packages and classes they come from.
% 
%    \begin{macrocode}
%<*cls>
\DeclareOption*{
  \PassOptionsToClass{\CurrentOption}{omdoc}
  \PassOptionsToPackage{\CurrentOption}{stex}
  \PassOptionsToPackage{\CurrentOption}{hwexam}
  \PassOptionsToPackage{\CurrentOption}{tikzinput}
}
\ProcessOptions
%    \end{macrocode}
%
% We load |omdoc.cls|, and the desired packages. For the {\latexml} bindings, we make
% sure the right packages are loaded.
%
%    \begin{macrocode}
\LoadClass{omdoc}
\RequirePackage{stex}
\RequirePackage{hwexam}
\RequirePackage{tikzinput}
\RequirePackage{graphicx}
\RequirePackage{a4wide}
\RequirePackage{amssymb}
\RequirePackage{amstext}
\RequirePackage{amsmath}
%    \end{macrocode}
% Finally, we register another keyword for the |document| environment. We give a default
% assignment type to prevent errors
%    \begin{macrocode}
\newcommand\assig@default@type{\hwexam@assignment@kw}
\addmetakey[\assig@default@type]{document}{hwexamtype}
\def\document@hwexamtype{\assig@default@type}
%</cls>
%    \end{macrocode}
% 
% \section{Implementation: The hwexam Package} 
%
% \subsection{Package Options}
%
% The first step is to declare (a few) package options that handle whether certain
% information is printed or not. Some come with their own conditionals that are set by the
% options, the rest is just passed on to the |problems| package.
%
%    \begin{macrocode}
%<*package>
\newif\if@hwexam@mh@\@hwexam@mh@false
\DeclareOption{mh}{\@hwexam@mh@true}
\newif\iftest\testfalse
\DeclareOption{test}{\testtrue}
\newif\ifmultiple\multiplefalse
\DeclareOption{multiple}{\multipletrue}
\DeclareOption*{\PassOptionsToPackage{\CurrentOption}{problem}}
\ProcessOptions
%    \end{macrocode}
% Then we make sure that the necessary packages are loaded (in the right versions).
%    \begin{macrocode}
\RequirePackage{keyval}[1997/11/10]
\if@hwexam@mh@\RequirePackage{hwexam-mh}\fi
\RequirePackage{problem}
%    \end{macrocode}
%
% \begin{macro}{\hwexam@*@kw}
%   For multilinguality, we define internal macros for keywords that can be specialized in
%   |*.ldf| files. 
%    \begin{macrocode}
\AfterBabelLanguage{ngerman}{\input{hwexam-ngerman.ldf}}
\newcommand\hwexam@assignment@kw{Assignment}
\newcommand\hwexam@given@kw{Given}
\newcommand\hwexam@due@kw{Due}
%    \end{macrocode}
% \end{macro}
% 
% \subsection{Assignments}
%
% Then we set up a counter for problems and make the problem counter inherited from
% |problem.sty| depend on it. Furthermore, we specialize the |\prob@label| macro to take
% the assignment counter into account.
%    \begin{macrocode}
\newcounter{assignment}
\numberproblemsin{assignment}
\renewcommand\prob@label[1]{\arabic{assignment}.#1}
%    \end{macrocode}
%
% We will prepare the keyval support for the |assignment| environment.
%
%    \begin{macrocode}
\srefaddidkey{assig}
\addmetakey{assig}{number}
\addmetakey*{assig}{title}
\addmetakey{assig}{type}
\addmetakey{assig}{given}
\addmetakey{assig}{due}
\addmetakey[false]{assig}{loadmodules}[true]
%    \end{macrocode}
%
% The next three macros are intermediate functions that handle the case gracefully, where
% the respective token registers are undefined.
% 
% The |\given@due| macro prints information about the given and due status of the
% assignment. Its arguments specify the brackets. 
% 
%    \begin{macrocode}
\newcommand\given@due[2]{%
\ifx \inclassig@given\@empty
	\ifx \assig@given\@empty
		\ifx \inclassig@due\@empty
			\ifx \assig@due\@empty% all empty do nothing
			\else #1%
			\fi
		\else #1%
		\fi
	\else #1%
	\fi
\else #1%
\fi
\ifx\inclassig@given\@empty
	\ifx\assig@given\@empty% do nothing
	\else \hwexam@given@kw\xspace \assig@given%
	\fi
\else \hwexam@given@kw\xspace \inclassig@given%
\fi
\ifx \inclassig@due\@empty
	\ifx \assig@due\@empty% do nothing
	\else
		\ifx \inclassig@given\@empty
			\ifx \assig@given\@empty% do nothing
			\else ,~%
			\fi
		\else ,~%
		\fi
	\fi
\else
	\ifx \inclassig@given\@empty
		\ifx \assig@given\@empty% do nothing
		\else ,~%
		\fi
	\else ,~%
	\fi
\fi
\ifx \inclassig@due\@empty
	\ifx \assig@due\@empty% do nothing
	\else \hwexam@due@kw\xspace \assig@due%
	\fi
\else \hwexam@due@kw\xspace \inclassig@due%
\fi
\ifx \inclassig@given\@empty
	\ifx \assig@given\@empty
		\ifx \inclassig@due\@empty
			\ifx \assig@due\@empty% all empty do nothing
			\else #2%
			\fi
		\else #2%
		\fi
	\else #2%
	\fi
\else #2%
\fi
}
%    \end{macrocode}
% 
% \begin{macro}{\assignment@title}
%   This macro prints the title of an assignment, the local title is overwritten, if there
%   is one from the |\includeassignment|. |\assignment@title| takes three arguments the
%   first is the fallback when no title is given at all, the second and third go around
%   the title, if one is given. 
%    \begin{macrocode}
\newcommand\assignment@title[3]
{\ifx\inclassig@title\@empty% if there is no outside title
\ifx\assig@title\@empty{#1}\else{#2\assig@title{#3}}\fi
\else{#2}\inclassig@title{#3}\fi}% else show the outside title
%    \end{macrocode}
% \end{macro}
% 
% \begin{macro}{\assignment@number}
%   Like |\assignment@title| only for the number, and no around part.
%    \begin{macrocode}
\newcommand\assignment@number%
{\ifx\inclassig@number\@empty% if there is no outside number
\ifx\assig@number\@empty\else\assig@number\fi
\else\inclassig@number\fi}% else show the outside number
%    \end{macrocode}
% \end{macro}
% 
% With them, we can define the central |assignment| environment. This has two forms
% (separated by |\ifmultiple|) in one we make a title block for an assignment sheet, and
% in the other we make a section heading and add it to the table of contents. We first
% define an assignment counter
% 
% \begin{environment}{assignment}
%   For the |assignment| environment we delegate the work to the |@assignment| environment
%   that depends on whether |multiple| option is given. 
%    \begin{macrocode}
\newenvironment{assignment}[1][]{\metasetkeys{assig}{#1}\sref@target%
\edef\@@num{\assignment@number}%
\ifx\@@num\@empty\stepcounter{assignment}\else\setcounter{assignment}{\@@num}\fi%
\setcounter{problem}{0}%
\def\current@section@level{\document@hwexamtype}%
\sref@label@id{\document@hwexamtype \thesection}%
\begin{@assignment}}
{\end{@assignment}}
%    \end{macrocode}
% In the multi-assignment case we just use the |omdoc| environment for suitable
% sectioning. 
%    \begin{macrocode}
\def\@@asstitle{\protect\document@hwexamtype~\arabic{assignment}%
\assignment@title{}{\;(}{)\;} -- \given@due{}{}}
\ifmultiple 
\newenvironment{@assignment}%
{\ifx\assig@loadmodules\@true
\begin{omgroup}[loadmodules]{\@@asstitle}
\else
\begin{omgroup}{\@@asstitle}
\fi}
{\end{omgroup}}
%    \end{macrocode}
% for the single-page case we make a title block from the same components. 
%    \begin{macrocode}
\else
\newenvironment{@assignment}
{\begin{center}\bf
\Large\@title\strut\\
\document@hwexamtype~\arabic{assignment}\assignment@title{\;}{:\;}{\\}%
\large\given@due{--\;}{\;--}
\end{center}}
{}
\fi% multiple
%    \end{macrocode}
% \end{environment}
% 
% \subsection{Including Assignments}
%
% \begin{macro}{\in*assignment}
%   This macro is essentially a glorified |\include| statement, it just sets some internal
%   macros first that overwrite the local points Importantly, it resets the |inclassig|
%   keys after the input.
%    \begin{macrocode}
\addmetakey{inclassig}{number}
\addmetakey*{inclassig}{title}
\addmetakey{inclassig}{type}
\addmetakey{inclassig}{given}
\addmetakey{inclassig}{due}
\addmetakey{inclassig}{mhrepos}
\clear@inclassig@keys%initially
\newcommand\includeassignment[2][]{\metasetkeys{inclassig}{#1}%
\include{#2}\clear@inclassig@keys}
\newcommand\inputassignment[2][]{\metasetkeys{inclassig}{#1}%
\input{#2}\clear@inclassig@keys}
%    \end{macrocode}
% \end{macro}
% 
% \subsection{Typesetting Exams}
%
% \begin{macro}{\quizheading}
%    \begin{macrocode}
\addmetakey{quizheading}{tas}
\newcommand\quizheading[1]{\def\@tas{#1}%
\large\noindent NAME: \hspace{8cm}  MAILBOX:\\[2ex]%
\ifx\@tas\@empty\else%
\noindent TA: \@for\@I:=\@tas\do{{\Large$\Box$}\@I\hspace*{1em}}\\[2ex]\fi}
%    \end{macrocode}
% \end{macro}
% 
% \begin{macro}{\testheading}
%    \begin{macrocode}
\addmetakey{testheading}{min}
\addmetakey{testheading}{duration}
\addmetakey{testheading}{reqpts}
\newenvironment{testheading}[1][]{\metasetkeys{testheading}{#1}
{\noindent\large{}Name: \hfill Matriculation Number:\hspace*{2cm}\strut\\[1ex]
\begin{center}\Large\textbf{\@title}\\[1ex]\large\@date\\[3ex]\end{center}  
{\textbf{You have 
\ifx\test@heading@duration\@empty\testheading@min minutes\else\testheading@duration\fi 
(sharp) for the test}};\\ Write the solutions to the sheet.}\par\noindent

\newcount\check@time\check@time=\testheading@min
\advance\check@time by -\theassignment@totalmin
The estimated time for solving this exam is {\theassignment@totalmin} minutes, 
leaving you {\the\check@time} minutes for revising your exam. 

\newcount\bonus@pts\bonus@pts=\theassignment@totalpts
\advance\bonus@pts by -\testheading@reqpts
You can reach {\theassignment@totalpts} points if you solve all problems. You will only need
{\testheading@reqpts} points for a perfect score, i.e.\ {\the\bonus@pts} points are
bonus points. \vfill
\begin{center}
  {\Large\em
%  You have ample time, so take it slow and avoid rushing to mistakes!\\[2ex]
  Different problems test different skills and knowledge, so do not get stuck on
  one problem.}\vfill\par\correction@table \\[3ex]
\end{center}}
{\newpage}
%    \end{macrocode}
% \end{macro}
% 
% \begin{macro}{\testspace}
%    \begin{macrocode}
\newcommand\testspace[1]{\iftest\vspace*{#1}\fi}
%    \end{macrocode}
% \end{macro}
% 
% \begin{macro}{\testnewpage}
%    \begin{macrocode}
\newcommand\testnewpage{\iftest\newpage\fi}
%    \end{macrocode}
% \end{macro}
% 
% \begin{macro}{\testemptypage}
%    \begin{macrocode}
\newcommand\testemptypage[1][]{\iftest\begin{center}This page was intentionally left
    blank for extra space\end{center}\vfill\eject\else\fi}
%    \end{macrocode}
% \end{macro}
% 
% \begin{macro}{\@problem}
%   This macro acts on a problem's record in the |*.aux| file. Here we redefine it to
%   generate the correction table. 
%    \begin{macrocode}
\renewcommand\@problem[3]{\stepcounter{assignment@probs}
\def\@@pts{#2}\ifx\@@pts\@empty\else\addtocounter{assignment@totalpts}{#2}\fi
\def\@@min{#3}\ifx\@@min\@empty\else\addtocounter{assignment@totalmin}{#3}\fi
\xdef\correction@probs{\correction@probs & #1}%
\xdef\correction@pts{\correction@pts & #2}
\xdef\correction@reached{\correction@reached &}}
%    \end{macrocode}
% \end{macro}
% 
% \begin{macro}{\correction@table}
%   This macro generates the correction table
%    \begin{macrocode}
\newcounter{assignment@probs}
\newcounter{assignment@totalpts}
\newcounter{assignment@totalmin}
\newcommand\correction@probs{prob.}%
\newcommand\correction@pts{total}%
\newcommand\correction@reached{reached}%
\stepcounter{assignment@probs}
\newcommand\correction@table{\begin{tabular}{|l|*{\theassignment@probs}{c|}|l|}\hline%
&\multicolumn{\theassignment@probs}{c||}%|
{\footnotesize To be used for grading, do not write here} &\\\hline
\correction@probs & Sum & grade\\\hline
\correction@pts &\theassignment@totalpts & \\\hline
\correction@reached & & \\[.7cm]\hline
\end{tabular}}
%</package>
%    \end{macrocode}
% \end{macro}
% 
% \subsection{Leftovers}
%
% at some point, we may want to reactivate the logos font, then we use
% \begin{verbatim}
% here we define the logos that characterize the assignment
% \font\bierfont=../assignments/bierglas
% \font\denkerfont=../assignments/denker
% \font\uhrfont=../assignments/uhr
% \font\warnschildfont=../assignments/achtung
%
% \newcommand\bierglas{{\bierfont\char65}}
% \newcommand\denker{{\denkerfont\char65}}
% \newcommand\uhr{{\uhrfont\char65}}
% \newcommand\warnschild{{\warnschildfont\char 65}}
% \newcommand\hardA{\warnschild}
% \newcommand\longA{\uhr}
% \newcommand\thinkA{\denker}
% \newcommand\discussA{\bierglas}
% \end{verbatim}
% \Finale
\endinput
% \iffalse
% LocalWords:  GPL structuresharing STR iffalse cls NeedsTeXFormat hwexam hwexam.dtx sc
%%% Local Variables: 
%%% mode: doctex
%%% TeX-master: t
%%% End: 
% \fi
%  LocalWords:  texttt scsys sc latexml fileversion filedate maketitle setcounter newpage
%  LocalWords:  tocdepth tableofcontents pts showmeta showmeta showignores omdoc extrefs
%  LocalWords:  testspace testnewpage testemptypage testheading testheading reqpts reqpts
%  LocalWords:  exfig makeatletter makeatother vspace hrule vspace vspace noindent textsf
%  LocalWords:  includeassignment includeassignment HorIacJuc cscpnrr11 importmodule baz
%  LocalWords:  includemhassignment includemhassignment importmhmodule foobar ldots sref
%  LocalWords:  mhcurrentrepos mh-variants mh-variant compactenum printbibliography Cwd
%  LocalWords:  langle rangle langle rangle ltxml.cls ltxml.sty respetively metakeys qw
%  LocalWords:  cwd stex graphicx amssymb amstext amsmath newif iftest testfalse testtrue
%  LocalWords:  ifsolutions solutionsfalse ifmultiple multiplefalse multipletrue keyval
%  LocalWords:  ltxml assig srefaddidkey addmetakey ifx assignment@titleblock stepcounter
%  LocalWords:  document@hwexamtype importmodules metasetkeys inclassig@title inclassig
%  LocalWords:  inclassig@title inclassig@type inclassig@type inclassig@number xspace kv
%  LocalWords:  inclassig@number inclassig@due inclassig@due inclassig@given ignorespaces
%  LocalWords:  inclassig@given newenvironment currentsectionlevel OptionalKeyVals kvi
%  LocalWords:  omgroup vals hwexamtype ednote textbackslash newcommand inputassignment
%  LocalWords:  unlist quizheading tas hspace hfill textbf newcount vfill addtocounter
%  LocalWords:  theassignment@totalmin theassignment@totalpts assignment@probs xdef hline
%  LocalWords:  assignment@totalpts assignment@totalmin correction@probs correction@probs
%  LocalWords:  newcounter theassignment@probs footnotesize mh@currentrepos endinput
%  LocalWords:  inclassig@mhrepos inclassig@mhrepos doctex inputmhassignment
