summaryrefslogtreecommitdiff
path: root/Master/texmf-dist/tex/latex/webquiz/webquiz.cls
diff options
context:
space:
mode:
Diffstat (limited to 'Master/texmf-dist/tex/latex/webquiz/webquiz.cls')
-rw-r--r--Master/texmf-dist/tex/latex/webquiz/webquiz.cls391
1 files changed, 391 insertions, 0 deletions
diff --git a/Master/texmf-dist/tex/latex/webquiz/webquiz.cls b/Master/texmf-dist/tex/latex/webquiz/webquiz.cls
new file mode 100644
index 00000000000..29e6f22675e
--- /dev/null
+++ b/Master/texmf-dist/tex/latex/webquiz/webquiz.cls
@@ -0,0 +1,391 @@
+% -----------------------------------------------------------------------
+% webquiz.cls | webquiz latex class file
+% -----------------------------------------------------------------------
+%
+% Copyright (C) Andrew Mathas, University of Sydney
+%
+% Distributed under the terms of the GNU General Public License (GPL)
+% http://www.gnu.org/licenses/
+%
+% This file is part of the WebQuiz system.
+%
+% <Andrew.Mathas@sydney.edu.au>
+% ----------------------------------------------------------------------
+
+\NeedsTeXFormat{LaTeX2e}[1996/12/01]
+
+% load webquiz-ini style
+\input{webquiz-ini.code}
+
+% ----------------------------------------------------------------------
+\ProvidesClass{webquiz}[\webquiz{release date} Version \webquiz{version}]
+
+% initialise and then process document class options usng pgfopts
+\RequirePackage{etoolbox}
+\RequirePackage{pgfopts}
+\def\unknown@options{}% unknown options are passed to article.cls
+\def\WQ@HideSideMenu{DeFaUlT}% side menu visible by default
+\newif\ifWQ@Tikz\WQ@Tikzfalse% true if tikz a document class option
+
+\newif\ifWQ@Debugging % for the debugging class option
+% Process the documentclass options using pgfkeys and \ProcessPgfOptions
+\pgfkeys{/WQ@ClassOptions/.is family,
+ /WQ@ClassOptions,
+ % turn debugging on
+ debugging/.code = {\WQ@Debuggingtrue},
+ % pst2pdf
+ pst2pdf/.style = {pst2pdf value=true},
+ pst2pdf value/.initial = false,
+ % languaage
+ language/.initial = DeFaUlT,
+ % one page
+ onepage/.style = {onepage value=true},
+ separatepages/.style = {onepage value=false},
+ onepage value/.initial = DeFaUlT,
+ % side menu
+ showsidemenu/.style = {hidesidemenu value=false},
+ hidesidemenu/.style = {hidesidemenu value=true},
+ hidesidemenu value/.initial= DeFaUlT,
+ % random order of quiz questions
+ randomorder/.style = {randomorder value=true},
+ fixedorder/.style = {randomorder value=false},
+ randomorder value/.initial = DeFaUlT,
+ % theme
+ theme/.initial = DeFaUlT,
+ % tikz
+ tikz/.code = {\global\WQ@Tikztrue},
+ % unknown options => passed to article class
+ .unknown/.code={\edef\unknown@options{\unknown@options,\pgfkeyscurrentname}}
+}
+\newcommand\WQ@ClassOption[1]{\pgfkeysvalueof{/WQ@ClassOptions/#1}}
+
+% Use pgfkeys to check for valid options for the choice environment and the
+% answer comparisons. As \ERROR is not defined an error message is
+% generated by the unknown handlers below
+\pgfkeys{/webquiz checker/.is family, /webquiz checker,
+ mode/.initial = single,
+ columns value/.initial = 1,
+ columns/.style = {columns value=#1},
+ single/.style = {mode=single},
+ multiple/.style = {mode=multiple},
+ .unknown/.code = {\ERROR: invalid choice type: use single or multiple}
+ comparison/.is choice,
+ comparison/complex/.code = \relax,
+ comparison/integer/.code = \relax,
+ comparison/lowercase/.code = \relax,
+ comparison/number/.code = \relax,
+ comparison/string/.code = \relax,
+ comparison/.unknown/.code = {\ERROR: invalid input type: use integer, string or eval}
+}
+
+% now process the options
+\ProcessPgfOptions{/WQ@ClassOptions}% process options
+\LoadClass[\unknown@options]{article}% load article class with options
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+\RequirePackage{xparse}
+\RequirePackage{pgffor}
+
+% load Michal Hoftich's new tikz driver for tex4ht
+\ifWQ@Tikz
+ \ifdefined\HCode
+ \def\pgfsysdriver{pgfsys-dvisvgm4ht.def}
+ \fi
+\fi
+
+\def\WQ@Error{\PackageError{webquiz}}
+\def\WQ@Debugging#1{\ifWQ@Debugging\typeout{Debugging: #1}\fi}
+
+%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
+\RequirePackage{amsfonts,amsmath}
+\RequirePackage{bbding}
+\setlength{\parindent}{0pt}
+\setlength{\parskip}{10pt}
+
+% Macro to define a picture variant of \<command>. The latex version does
+% nothing but the cfg version converts \<command> into an image
+
+\newcommand\DisplayAsImage[2][]{\relax}
+
+% Need to declare possible graphics extensions: see https://tex.stackexchange.com/questions/213461
+% This is just placeholder - the real definition is used in the cfg file
+%\newcommand\DeclareGraphicsExtensions[1]{}
+
+% Macros for defining the university and department
+\newcommand*{\DepartmentURL}[1]{\def\WQ@departmentURL{#1}}
+\newcommand*{\Department}[1]{\def\WQ@department{#1}}
+
+% University/instution - university included for backwards compatibility
+\newcommand*{\InstitutionURL}[1]{\def\WQ@institutionURL{#1}}
+\newcommand*{\Institution}[1]{\def\WQ@institution{#1}}
+\newcommand*{\UniversityURL}[1]{\def\WQ@institutionURL{#1}}
+\newcommand*{\University}[1]{\def\WQ@institution{#1}}
+
+% Macros for defining the quiz web breadcrumbs using the unit code, name and
+% URL. The names of these macros are chosen so as to be compatible with the
+% in-house SMS package sms-uos.sty that specifies these for all units.
+\newcommand*\UnitCode[1]{\def\uos@code{#1}}
+\newcommand*\UnitName[1]{\def\uos@name{#1}}
+\newcommand*\UnitURL[1]{\def\uos@url{#1}}
+\newcommand*\QuizzesURL[1]{\def\WQ@quizzesUrl{#1}}
+\newcommand*\BreadCrumb[1]{\def\WQ@breadcrumb{#1}}
+\newcommand*\BreadCrumbs[1]{\def\WQ@breadcrumbs{#1}}
+
+% Default values - the university and department defaults can also be
+% set in the webquizrc file. The main purpose of these defaults is
+% to remind the user to set them.
+\UnitCode{Unit code?}
+\UnitName{Unit name?}
+\UnitURL{}
+\QuizzesURL{DeFaUlT}
+\BreadCrumb{}
+\BreadCrumbs{DeFaUlT}
+\Department{DeFaUlT}
+\DepartmentURL{DeFaUlT}
+\University{DeFaUlT}
+\UniversityURL{DeFaUlT}
+
+% Define page header and footer for the printable version of the quiz
+% to show the unit code information.
+\def\ps@quiz{\ps@empty
+ \def\@oddhead{\hbox to\textwidth{%
+ \uos@code\hss\textsc{\@title}\hss Page \thepage}}%
+ \let\@evenhead=\@oddhead
+}
+\def\ps@firstpage{\ps@empty}
+\pagestyle{quiz}
+
+
+\def\@title{}
+\def\maketitle{\vspace*{10mm}
+ \begin{center}
+ {\large\textsc{\@title}}%
+ \end{center}
+}
+\AtBeginDocument{
+ \maketitle%
+ \def\title{\WQ@Error{\noexpand\title can only be used in the preamble}\@ehc}
+ \thispagestyle{firstpage}%
+ \ifdefined\HCode\else
+ \textsc{WebQuiz} will process this quiz using \textbf{pst2pdf}.
+ \fi
+ \RequirePackage{tikz}
+}
+
+% -----------------------------------------------------------------------
+% WebQuiz macros
+% Define \WQ@XXXStart and \WQ@XXXEnd macros to avoid code duplication
+% in webquiz.cfg. The following switches are used for syntax checking
+% -----------------------------------------------------------------------
+
+% These are all for error checking...
+\newif\ifWQ@InFeedback
+\newif\ifWQ@InAnswer
+\newif\ifWQ@InChoice
+\newif\ifWQ@InDiscussion
+\newif\ifWQ@InItem
+\newif\ifWQ@InQuestion
+\newif\ifWQ@InQuizIndex
+\newif\ifWQ@InWhenright
+\newif\ifWQ@InWhenwrong
+
+% -----------------------------------------------------------------------
+% the quizindex environment and \quiz macro
+% -----------------------------------------------------------------------
+
+% the quiz counter keeps track of the question numbers in a quizindex environement
+\newcounter{quiz}
+\renewcommand\thequiz{\arabic{quiz}}
+\def\WQ@QuizStart{%
+ \WQ@Debugging{Starting \noexpand\quiz...}%
+ \ifWQ@InQuizIndex\else\WQ@Error{\noexpand\quiz must appear inside a quizindex environment}\fi%
+ \refstepcounter{quiz}% increment the quiz counter for the URLs
+}
+\NewDocumentCommand\quiz{som}{%
+ \WQ@QuizStart%
+ \IfBooleanTF{#1}{\def\WQ@Quiz{}}{\def\WQ@Quiz{Quiz~\thequiz.\space}}%
+ \IfNoValueTF{#2}{\def\WQ@url{quiz\thequiz.html}}{\def\WQ@url{#2}}%
+ \leavevmode\medskip\newline%
+ \WQ@Quiz #3\newline%
+ \phantom{Quiz 10}\textit{URL}:\quad \WQ@url%
+}
+
+\def\WQ@QuizIndexStart{%
+ \WQ@Debugging{Starting quizindex...}%
+ \ifWQ@InQuestion\WQ@Error{quizindex cannot appear in a question environment}\fi%
+ \ifWQ@InDiscussion\WQ@Error{quizindex environments cannot be inside a discussion environment}\fi
+ \ifWQ@InQuizIndex\WQ@Error{quizindex environments cannot be nested}\fi%
+ \global\WQ@InQuizIndextrue% here, and below, using \global is probably overkill...
+}
+\def\WQ@QuizIndexEnd{\global\WQ@InQuizIndexfalse\WQ@Debugging{Ending quizindex...}}
+\newenvironment{quizindex}{\WQ@QuizIndexStart\bigskip}{\WQ@QuizIndexEnd}
+
+% -----------------------------------------------------------------------
+% discussion environment
+% -----------------------------------------------------------------------
+
+\newcounter{discussion}
+
+% \begin{dicussion}[short title][title -default-> Discussion]
+\def\WQ@DiscussionStart{%
+ \WQ@Debugging{Starting discussion...}%
+ \ifWQ@InDiscussion\WQ@Error{discussion environments cannot be nested}\fi%
+ \ifWQ@InQuestion\WQ@Error{discussion environments cannot be inside a question environment}\fi%
+ \ifWQ@InQuizIndex\WQ@Error{discussion environments cannot be inside a quizindex environment}\fi%
+ \global\WQ@InDiscussiontrue%
+ \refstepcounter{discussion}%
+}
+\def\WQ@DiscussionEnd{\global\WQ@InDiscussionfalse\WQ@Debugging{Ending discussion...}}
+\NewDocumentEnvironment{discussion}{O{Discussion}O{#1}}
+ {\WQ@DiscussionStart\textbf{#1} (#2)}{\WQ@DiscussionEnd\par\bigskip}
+
+% ---------------------------------------------------------------------------
+% Cross referencing question and discussion environments
+% ---------------------------------------------------------------------------
+
+% \WQ@Ref{+ or -}[optional *][optional text]{mandatory label}
+\NewDocumentCommand\WQ@ref{ m s o m }{%
+\fbox{\IfBooleanTF{#2}{link}{button} to \IfNoValueTF{#3}{to #1 \ref{#4}}{ to ``#3'' (#1 \ref{#4})}}%
+}
+\newcommand\dref{\WQ@ref{discussion}}
+\newcommand\qref{\WQ@ref{question}}
+\newcommand\Qref{\WQ@ref{question number}}
+
+% -----------------------------------------------------------------------
+% question environment
+% -----------------------------------------------------------------------
+
+% the question counter keeps track of the quiz question numbers
+\newcounter{question}
+
+\def\WQ@QuestionStart{%
+ \WQ@Debugging{Starting question...}%
+ \ifWQ@InDiscussion\WQ@Error{question environments cannot be inside a discussion environment}\fi%
+ \ifWQ@InQuizIndex\WQ@Error{question environments cannot be inside a quizindex environment}\fi%
+ \ifWQ@InQuestion\WQ@Error{question environments cannot be nested!}\fi%
+ \global\WQ@InAnswerfalse%
+ \global\WQ@InChoicefalse%
+ \global\WQ@InChoicefalse%
+ \global\WQ@InItemfalse%
+ \global\WQ@InQuestiontrue%
+ \global\WQ@InFeedbackfalse%
+ \global\WQ@InWhenrightfalse%
+ \global\WQ@InWhenwrongfalse%
+ \refstepcounter{question}%
+}
+
+\def\WQ@QuestionEnd{
+ \ifWQ@InChoice\else\ifWQ@InAnswer\else%
+ \WQ@Error{Each question must contain a choice environment or an \noexpand\answer!}%
+ \fi\fi%
+ \global\WQ@InQuestionfalse%
+ \WQ@Debugging{Ending question...}%
+}
+
+\newenvironment{question}{\WQ@QuestionStart\bigskip\textbf{Question \arabic{question}.\newline}}
+ {\par\bigskip\WQ@QuestionEnd}
+
+% -----------------------------------------------------------------------
+% choice environment, \correct and \incorrect choices and \feedback
+% -----------------------------------------------------------------------
+
+% the choice counter keeps track of the choices in a choice environment
+\newcounter{choice}
+\renewcommand\thechoice{(\alph{choice})}
+
+\def\WQ@ChoiceStart#1{%
+ \WQ@Debugging{Starting choice...}%
+ \ifWQ@InQuestion\relax% Give a warning if we are not inside a question
+ \else\WQ@Error{Choice environments must be contained in a question}%
+ \fi%
+ \ifWQ@InAnswer\WQ@Error{choice environments cannot contain an \noexpand\answer!}\fi%
+ \ifWQ@InChoice\WQ@Error{choice environments cannot be nested}\fi%
+ \global\WQ@InChoicetrue%
+ \global\WQ@InItemfalse%
+ \pgfkeys{/webquiz checker, #1}%
+ \setcounter{choice}{0}% reset choice counter
+}
+
+\def\WQ@ChoiceEnd{%
+ \ifWQ@InItem\else\WQ@Error{Choice environment with no choices!}\fi%
+ \WQ@InChoicefalse%
+ \WQ@Debugging{Ending choice...}%
+}
+
+% \begin{choice}[choice type, number of columns] ... \end{choice} The
+% allowed choice types are "single" or "multiple". The type and number
+% of columns is allowed to appear in either order, so most of the fun
+% and games below is sanity checking of the argunments.
+\NewDocumentEnvironment{choice}{O{single}}{%
+ \WQ@ChoiceStart{#1}%
+ \leavevmode\newline%
+% (\textit{The choices will be printed in \pgfkeys{/webquiz checker/columns value} columns in the HTML version of the quiz})%
+ \par%
+ \setcounter{choice}{0}%
+}{\WQ@ChoiceEnd}
+
+\def\WQ@ItemStart{%
+ \WQ@Debugging{Starting item...}%
+ \ifWQ@InChoice\relax%
+ \else\WQ@Error{\noexpand\correct and \noexpand\incorrect must be inside a choice environment}%
+ \fi%
+ \global\WQ@InItemtrue\global%
+ \WQ@InFeedbackfalse%
+ \refstepcounter{choice}%
+}
+
+\def\WQ@Item#1{\WQ@ItemStart\par\bigskip #1\quad\textit{Option} \thequestion\thechoice:\qquad}
+\def\correct{\WQ@Item\CheckmarkBold}
+\def\incorrect{\WQ@Item\XSolidBrush}
+
+\def\WQ@FeedbackStart{%
+ \WQ@Debugging{Starting feedback...}%
+ \ifWQ@InItem\relax%
+ \else\WQ@Error{Missing \noexpand\correct or \noexpand\incorrect}%
+ \fi%
+ \ifWQ@InFeedback\WQ@Error{Only one feedback per option is allowed!}\fi%
+ \WQ@InFeedbacktrue%
+}
+
+\def\feedback{\WQ@FeedbackStart\leavevmode\medskip\newline\textit{Feedback:}\space}
+
+% -----------------------------------------------------------------------
+% The \answer macro and the feedback macros \whenRight, \whenWrong
+% -----------------------------------------------------------------------
+
+% supported answer comparisons
+\def\WQ@AnswerStart#1{%
+ \WQ@Debugging{Starting answer...}%
+ \ifWQ@InQuestion\relax%
+ \else\WQ@Error{\noexpand\answer\ must be contained in a question}%
+ \fi%
+ \ifWQ@InChoice\WQ@Error{You cannot have \noexpand\answer inside a choice environment}\fi%
+ \ifWQ@InAnswer\WQ@Error{Each question can contain only one \noexpand\answer command}\fi%
+ \pgfkeys{/webquiz checker/comparison/#1}%
+ \global\WQ@InAnswertrue%
+ \global\WQ@InWhenrightfalse%
+ \global\WQ@InWhenwrongfalse%
+}
+
+\NewDocumentCommand\answer{s O{string} m}{%
+ \WQ@AnswerStart{#2}%
+ \leavevmode\bigskip\newline%
+ \IfBooleanTF{#1}{\fbox{\textit{(#2 comparison):}\quad#3}}%
+ {\fbox{\textit{Answer (#2 comparison):}\quad#3}}%
+}
+
+\def\WQ@WhenStart#1{%
+ \WQ@Debugging{Starting when#1...}%
+ \ifWQ@InAnswer\relax\else\WQ@Error{missing \noexpand\answer}\fi%
+ \ifbool{WQ@InWhen#1}{%
+ \WQ@Error{Only one \noexpand\when#1 per question is allowed!}%
+ }{}%
+ \global\booltrue{WQ@InWhen#1}%
+}
+
+\def\WQ@When#1{\WQ@WhenStart{#1}\leavevmode\medskip\newline\textit{Feedback when #1:}\space}
+\def\whenRight{\WQ@When{right}}
+\def\whenWrong{\WQ@When{wrong}}
+
+\endinput
+%% End of file `webquiz.cls'.