本守则的一般说明

本守则的一般说明

简短的介绍

我正在尝试为带有关联图像的多项选择题创建一个模板。我希望问题看起来像这样:

我手动将这张图片 TeX 化了

在这张图片中,我展示了我希望 Tikz 图像出现的方块,并且添加了一些线条来表明方块应该与 5 个(始终是 5 个)答案选项对齐。

我想知道是否有一些类似的包文本位置它会自动接受输入,将其置于框的中心,然后调整其大小以填充整个框。

带有 MWE 的详细描述

(请耐心听我说,我发现很难描述我的问题)

我已经使用文本位置包将 tikzpicture 放置在其所需位置。这里的问题是 tikzpicture 被渲染、裁剪(适当)到 tikzpicture 的尺寸,然后被推到左上角(textpos“锚点”所在的位置)。

我希望能够绘制具有多种不同尺寸和不同坐标的 tikzpicture,但仍然让它们位于上图所示的框内。例如,通过将圆心置于 (0,0) 并使用所有 4 个象限,可以轻松绘制圆,但对于直角三角形之类的东西,将 90 度角置于 (0,0) 并仅使用第一象限更容易。

我在这方面的尝试并不成功,因为我有点手动弄乱了一切。我手动设置锚点textpos,将其向右移动纸张宽度的 0.6 倍,并从第 5 个答案选项向上移动 3.415 厘米。之后,我画了一些 tikz 图片,并确保它们的尺寸正好适合框(恰好是 3.5 厘米 x 3.5 厘米)。

下面的代码可能有助于解释我的问题。我添加了一些尺寸信息(边距、parskip 等),因为它们是我正在进行的项目的重要组成部分。我添加了一些边界线,以表明图像的高度不应大于 5 个答案选项的高度。

我认为我想要的是让 3.5cm x 3.5cm 的盒子成为我可以将某物放入其中的东西,它就会自动将其居中并调整为适当的大小。

\documentclass[11pt, twoside]{article}

\usepackage[left=1in, top=1in, right=1in, bottom=1in, head=30pt, marginparwidth=2cm, marginparsep=0.35cm]{geometry}
    \geometry{letterpaper}

\usepackage{parskip}

\usepackage{textpos}
    \setlength{\TPHorizModule}{\the\paperwidth}
    \setlength{\TPVertModule}{1cm}

\usepackage{tikz}

\newlength{\mylen}
\settoheight{\mylen}{C}



\begin{document}

\begin{enumerate}

    \item Showing the box I want the image to appear in for the examples below.
    \begin{enumerate}
        \item Choice 1 \rule[\mylen]{0.65\linewidth}{0.1pt}
        \item Choice 2
        \item Choice 3 \rule[0.5\mylen]{0.8\linewidth}{0.1pt}
        \item Choice 4
        \item Choice 5 \rule{0.65\linewidth}{0.1pt}
    \end{enumerate}


    \begin{textblock}{1}(0.6,-3.415)
        \begin{tikzpicture}[scale = 3.5/200]
            \draw[blue, fill = red!20,] (-100,-100) rectangle (100,100);
        \end{tikzpicture}
    \end{textblock}


    \item Image is cropped to just include drawings, then pushed to top left of the red box.
    \begin{enumerate}
        \item Choice 1 \rule[\mylen]{0.65\linewidth}{0.1pt}
        \item Choice 2
        \item Choice 3 \rule[0.5\mylen]{0.65\linewidth}{0.1pt}
        \item Choice 4
        \item Choice 5 \rule{0.65\linewidth}{0.1pt}
    \end{enumerate}


    \begin{textblock}{1}(0.6,-3.415)
        \framebox{%
            \begin{tikzpicture}[scale = 3.5/200]
                \draw (0,0) node {Image};           
            \end{tikzpicture}
        }
    \end{textblock}


    \item When the size or location of the image changes in ``tikz-land'', the tikzpicture is still pushed to the top left of the red box (as expected).
    \begin{enumerate}
        \item Choice 1 \rule[\mylen]{0.65\linewidth}{0.1pt}
        \item Choice 2
        \item Choice 3 \rule[0.5\mylen]{0.65\linewidth}{0.1pt}
        \item Choice 4
        \item Choice 5 \rule{0.65\linewidth}{0.1pt}
    \end{enumerate}


    \begin{textblock}{1}(0.6,-3.415)
        \framebox{
            \begin{tikzpicture}[scale = 3.5/200]
                \draw (10,10) node {\Huge{Image}};         
            \end{tikzpicture}
        }
    \end{textblock}


    \item How I want the image to look (without resizing it)
    \begin{enumerate}
        \item Choice 1 \rule[\mylen]{0.65\linewidth}{0.1pt}
        \item Choice 2
        \item Choice 3 \rule[0.5\mylen]{0.65\linewidth}{0.1pt}
        \item Choice 4
        \item Choice 5 \rule{0.65\linewidth}{0.1pt}
    \end{enumerate}


    \begin{textblock}{1}(0.6,-3.415)
        \begin{tikzpicture}[scale = 3.5/200]
            \draw[blue] (-100,-100) rectangle (100,100);
            \draw[] (0,0) node {Image};         
        \end{tikzpicture}
    \end{textblock}


    \item How I want the image to look (with resizing it)
    \begin{enumerate}
        \item Choice 1 \rule[\mylen]{0.65\linewidth}{0.1pt}
        \item Choice 2
        \item Choice 3 \rule[0.5\mylen]{0.65\linewidth}{0.1pt}
        \item Choice 4
        \item Choice 5 \rule{0.65\linewidth}{0.1pt}
    \end{enumerate}


    \begin{textblock}{1}(0.6,-3.415)
        \begin{tikzpicture}[scale = 3.5/200]
            \draw[blue] (-100,-100) rectangle (100,100);
            \draw[] (0,0) node {\Huge{Image}};         
        \end{tikzpicture}
    \end{textblock}


\end{enumerate}

\end{document}

(注:我刚刚手动创建了数字 4 和 5 的框/图像)

从这里可以看出,更改“Tikz-land”中节点的位置不会影响其位置(它仍然附着在左上角的锚点上)。如果我更改 tikzpicture 的大小,它仍然会附着在左上角,但看起来更大。我希望它附着在框的中心并调整自身大小以填充框(但不更大)。

抱歉我说得有点多,但我觉得现在就尝试充分解释清楚比回头再讨论一切要好。提前谢谢!


编辑和附加问题

在实施@frougon 提供的解决方案后,我注意到当 Tikz 坐标超过\myheight和/或\mywidth(在本例中为 3.5)时,图片会有效地“缩小”。

如果 Tikz 图片的缩放比例无关紧要,那就太好了。我认为可以通过始终缩小 Tikz 图片以使坐标不超过 3.5 来解决这个问题(参见图 4,我将图片缩放了 3.5/10,因为 10 是最大坐标值)。

也许存在一个\MaxCoordinate我不知道的所有 Tikz 图片的定义,但我不确定。

这是我的代码和输出:

\documentclass{article}
\usepackage{graphicx}
\usepackage{adjustbox}
\usepackage{xcolor}
\usepackage{tikz}

% Frame dimensions
\newlength{\mywidth}
\newlength{\myheight}
\setlength{\mywidth}{3.5cm}
\setlength{\myheight}{3.5cm}

\makeatletter

\newenvironment{choices}[1]{%
  \def\braced@stuff@to@include{{#1}}%
  \par\noindent
  \minipage{\dimexpr\linewidth-\mywidth-2\fboxrule-2\fboxsep}
  \enumerate
  \ignorespaces
}{%
  \unskip
  \endenumerate
  \endminipage
  \setlength{\fboxsep}{0pt}%
  \fcolorbox{blue!20}{green!20}{%
    \begin{minipage}[c][\myheight][c]{\mywidth}
      \centering
      \def\@tmp{%
        \adjustbox{max totalsize={\mywidth}{\myheight}}}%
      \expandafter\@tmp\braced@stuff@to@include
    \end{minipage}%
  }%
  \ignorespacesafterend
}

\makeatother




\begin{document}

\begin{enumerate}


\item Image 1
  \begin{choices}{%
      \begin{tikzpicture}
        \draw (0,0) rectangle (1,1);
        \draw (0.5,0.5) node {\textbullet};  % node placed in center of square
      \end{tikzpicture}}
  \item Choice 1
  \item Choice 2
  \item Choice 3
  \item Choice 4
  \item Choice 5
  \end{choices}

\item Image 2: same proportions as Image 1, but it's larger
  \begin{choices}{
      \begin{tikzpicture}
        \draw (0,0) rectangle (3.5,3.5);
        \draw (1.75,1.75) node {\textbullet}; % node placed in center of square
      \end{tikzpicture}
  }
  \item Choice 1
  \item Choice 2
  \item Choice 3
  \item Choice 4
  \item Choice 5
  \end{choices}

  \item Image 3: when the tikz-coordinates exceed 3.5, the image effectively ``zooms-out''
  \begin{choices}{
      \begin{tikzpicture}
        \draw (0,0) rectangle (10,10);
        \draw (5,5) node {\textbullet}; % node placed in center of square
      \end{tikzpicture}
  }
  \item Choice 1
  \item Choice 2
  \item Choice 3
  \item Choice 4
  \item Choice 5
  \end{choices}


  \item Image 4: scaling the tikzpicture down fixes the issue, but this requires knowledge that ``10'' is the largest coordinate in the tikzpicture environment
  \begin{choices}{
      \begin{tikzpicture}[scale = 3.5/10]
        \draw (0,0) rectangle (10,10);
        \draw (5,5) node {\textbullet}; % node placed in center of square
      \end{tikzpicture}
  }
  \item Choice 1
  \item Choice 2
  \item Choice 3
  \item Choice 4
  \item Choice 5
  \end{choices}


\clearpage


  \item Image 5: ideally, images 5, 6, \& 7 would look identical as they have the same coordinates, just scaled up and down.
  \begin{choices}{
      \begin{tikzpicture}
        \draw[thick] (0,0)--(1,.5);
        \draw[thick] (0,0)--(.5,-1);
        \draw[thick] (0,0)--(-1,.5);
        \draw[thick] (0,0)--(-.5,-1);
        \draw[thick] (0,0)--(1,-.5);
        \draw[thick] (0,0)--(-.5,1);
        \draw (.05,.2) node {$1$};
        \draw (-.25,.25) node {$2$};
        \draw (-.2,-.05) node {$3$};
        \draw (0,-.25) node {$4$};
        \draw (.25,-.25) node {$5$};
        \draw (.25,0) node {$6$};
      \end{tikzpicture}
  }
  \item Choice 1
  \item Choice 2
  \item Choice 3
  \item Choice 4
  \item Choice 5
  \end{choices}


  \item Image 6: all coordinates are doubled from Image 5.
  \begin{choices}{
      \begin{tikzpicture}
        \draw[thick] (0,0)--(2,1);
        \draw[thick] (0,0)--(1,-2);
        \draw[thick] (0,0)--(-2,1);
        \draw[thick] (0,0)--(-1,-2);
        \draw[thick] (0,0)--(2,-1);
        \draw[thick] (0,0)--(-1,2);
        \draw (.1,.4) node {$1$};
        \draw (-.5,.5) node {$2$};
        \draw (-.4,-.1) node {$3$};
        \draw (0,-.5) node {$4$};
        \draw (.5,-.5) node {$5$};
        \draw (.5,0) node {$6$};
      \end{tikzpicture}
  }
  \item Choice 1
  \item Choice 2
  \item Choice 3
  \item Choice 4
  \item Choice 5
  \end{choices}


  \item Image 7: all coordinates are multiplied by a factor of 5 from Image 6. (Note that the nodes are extemely tiny here).
  \begin{choices}{
      \begin{tikzpicture}
        \draw[thick] (0,0)--(10,5);
        \draw[thick] (0,0)--(5,-10);
        \draw[thick] (0,0)--(-10,5);
        \draw[thick] (0,0)--(-5,-10);
        \draw[thick] (0,0)--(10,-5);
        \draw[thick] (0,0)--(-5,10);
        \draw (.5,2) node {$1$};
        \draw (-2.5,2.5) node {$2$};
        \draw (-2,-.5) node {$3$};
        \draw (0,-2.5) node {$4$};
        \draw (2.5,-2.5) node {$5$};
        \draw (2.5,0) node {$6$};
      \end{tikzpicture}
  }
  \item Choice 1
  \item Choice 2
  \item Choice 3
  \item Choice 4
  \item Choice 5
  \end{choices}


\end{enumerate}

\end{document}

在此处输入图片描述

答案1

如果您希望图像自动调整大小以适应框架,同时保持其纵横比,则下面的代码应该可以满足您的要求。请注意,环境的主体questionpicture与 一样被装箱lrbox;它可以包含任何可以这样装箱的内容:例如,一个或多个字符标记、 中包含的图像\includegraphicstikzpicture等)。

\documentclass{article}
\usepackage{graphicx}
\usepackage{calc} % for \settototalheight (used for convenience)
\usepackage{xcolor}
\usepackage{xurl}
\usepackage{etoolbox}
\usepackage{xparse}
\usepackage{tikz}
\usetikzlibrary{calc}

% Frame dimensions
\newlength{\mywidth}
\newlength{\myheight}
\setlength{\mywidth}{3.5cm}
\setlength{\myheight}{3.5cm}

\makeatletter

% Use l3keys to support a key/value-style interface for the optional argument
% of the 'choices' environment (l3keys is great!).
\ExplSyntaxOn

\msg_new:nnn { ryanjform } { duplicate-figure-id }
  { duplicate~figure~identifier:~'\exp_not:n {#1}'. }

% Whether to perform the \scalebox-based autoscaling for a given figure
\bool_new:N \l__ryanjform_do_autoscale_pic_in_choices_bool
% Sequence recording all figure identifiers (for the 'scale to max size' TikZ
% style) found so far
\seq_new:N \g__ryanjform_scale_to_max_style_figure_ids_seq

% Define the options supported in the optional argument of the 'choices'
% environment
\keys_define:nn { ryanjform }
  {
    autoscale .bool_set:N = \l__ryanjform_do_autoscale_pic_in_choices_bool,
    % Value used when the 'autoscale' key is passed with no value
    autoscale .default:n = { true },
    autoscale .initial:n = { true }
  }

\cs_new_protected:Npn \__ryanjform_set_keys:n #1
  { \keys_set:nn { ryanjform } {#1} }

\cs_new_protected:Npn \__ryanjform_check_unique_id:n #1
  {
    \seq_if_in:NnTF \g__ryanjform_scale_to_max_style_figure_ids_seq {#1}
      { \msg_error:nnn { ryanjform } { duplicate-figure-id } {#1} }
      { \seq_gput_right:Nn \g__ryanjform_scale_to_max_style_figure_ids_seq {#1} }
  }

% Set up aliases using LaTeX2e naming style
\cs_set_eq:NN \ryanjformsetup \__ryanjform_set_keys:n
\cs_set_eq:NN \ryanjform@check@unique@id \__ryanjform_check_unique_id:n

% If-then-else command using the boolean
% \l__ryanjform_do_autoscale_pic_in_choices_bool to choose the branch
\NewDocumentCommand \ryanjform@ifautoscale@enabled { }
  {
    \bool_if:NTF \l__ryanjform_do_autoscale_pic_in_choices_bool
  }

\ExplSyntaxOff

\newsavebox{\ryanjform@box}     % will be set with \global
\newlength{\ryanjform@total@height}
\newcounter{choice}[enumi]
% In case you want to prepend the question number to the choice number in
% \thechoice, you can use \renewcommand{\thechoice}{\theenumi.\arabic{choice}}
\renewcommand{\thechoice}{\arabic{choice}} % only the choice number

\newenvironment{questionpicture}{%
  \begin{lrbox}{0}}{%
  \end{lrbox}%
  \global\setbox\ryanjform@box=\box0
}

\AfterEndEnvironment{questionpicture}{%
  \setcounter{choice}{0}%
  \par\noindent
  \setlength{\fboxsep}{0pt}%
  \begingroup
  \minipage{\dimexpr\linewidth-\mywidth-2\fboxrule-2\fboxsep}
  \begingroup
  \enumerate
  \let\ryanjform@item@cmd@orig\item
  \let\item\ryanjform@item@cmd
  \ignorespaces
}

\let\ryanjform@start@question@picture\questionpicture
\newcommand*{\ryanjform@invalid@place@for@calling@questionpicture}{%
  \errmessage{The 'questionpicture' environment must be used at the start of a
    'choices' environment}%
}
% Generate an error message unless \questionpicture is used where expected
\let\questionpicture\ryanjform@invalid@place@for@calling@questionpicture

\newenvironment{choices}[1][]{%
  \ryanjformsetup{#1}%
  \let\questionpicture\ryanjform@start@question@picture
  \ignorespaces
}{%
  % Restore \item as it was before the 'choices' environment (re)defined it
  \let\item\ryanjform@item@cmd@orig
  \unskip\ryanjform@hrule       % rule at the end of the last choice
  \endenumerate
  \endgroup
  \endminipage
  \endgroup
  %
  \settototalheight{\ryanjform@total@height}{\usebox{\ryanjform@box}}%
  \pgfmathsetmacro{\ryanjform@x@ratio}{\the\mywidth / \wd\ryanjform@box}%
  \pgfmathsetmacro{\ryanjform@y@ratio}{\the\myheight / \ryanjform@total@height}%
  \pgfmathsetmacro{\ryanjform@scale}{min(\ryanjform@x@ratio,
                                         \ryanjform@y@ratio)}%
  %
  \fcolorbox{red!20}{blue!20}{%
    \begin{minipage}[c][\myheight][c]{\mywidth}
      \centering
      \ryanjform@ifautoscale@enabled{%
        % We know that \ryanjform@scale will be (fully) expanded:
        % <https://tex.stackexchange.com/q/497769/73317>
        \scalebox{\ryanjform@scale}{\usebox{\ryanjform@box}}%
      }{%
        \usebox{\ryanjform@box}%
      }%
    \end{minipage}%
  }%
  \ignorespacesafterend
}

\newcommand*{\ryanjform@item@cmd}{%
  % Automatically insert the horizontal rule unless this is the first \item
  % in the current 'choices' environment
  \ifnum\value{choice}=0\else\unskip\ryanjform@hrule\fi
  \refstepcounter{choice}%
  \ryanjform@item@cmd@orig
}

% Autoscaling technique that doesn't affect font sizes in TikZ pictures.
% (based on code from marmot: <https://tex.stackexchange.com/a/497749/73317>)
%
% #1: unique per-picture id allowing several pictures to use this mechanism
%     in a given document (it should contain no control sequence token nor
%     active character)
% #2: width of the reference rectangle
% #3: height of the reference rectangle
\newcommand*\ryanjform@ExportBB[3]{%
 \path let
   \p1=($(current bounding box.north east)-(current bounding box.south west)$),
   \n1={#2/\x1},\n2={#3/\y1}
 in \pgfextra{\pgfmathsetmacro{\ryanjform@figscale}{min(\n1,\n2)}%
              \expandafter\xdef\csname ryanjform@auto@figscale@#1\endcsname{%
                \ryanjform@figscale}};
 \immediate\write\@mainaux{%
   \string\expandafter
   \gdef\string\csname\space ryanjform@auto@figscale@#1\string\endcsname{%
     \csname ryanjform@auto@figscale@#1\endcsname}}}

\tikzset{scale to max size/.style args={id #1 width #2height #3}{%
    execute at end picture={\ryanjform@ExportBB{#1}{#2}{#3}},
    /utils/exec={\ryanjform@check@unique@id{#1}%
                 \ifcsname ryanjform@auto@figscale@#1\endcsname
                   \wlog{Found autoscale value for picture '#1'}%
                 \else
                   \typeout{Automatically-scaled pictures: please recompile
                            for picture '#1'.}
                   \expandafter\gdef
                     \csname ryanjform@auto@figscale@#1\endcsname{1}
                 \fi},
   scale=\csname ryanjform@auto@figscale@#1\endcsname},
         form autoscale/.style={%
           scale to max size=id #1 width \mywidth height \myheight}}
% End of the code based on <https://tex.stackexchange.com/a/497749/73317>

\newcommand*{\ryanjform@hrule}{%
  \leavevmode
  \unskip\kern 0.5em
  \leaders\hrule height 3pt depth -2.6pt \hfill
  \kern 0.5em
}

\makeatother

% Sample pictures only used to show how to use the 'choices' environment
\newcommand*{\sometikzpictureBase}[1]{%
  \begin{tikzpicture}#1
    \coordinate (A) at (1,5);
    \coordinate (B) at (3,15);
    \node[below left] at (A) {$A$};
    \node[above right] at (B) {$B$};
    % Some rules may disappear if one doesn't substract some “epsilon”, see
    % <https://tex.stackexchange.com/q/13834/73317>
    \draw ($(A)-(0.001, 0.001)$) grid (B);
  \end{tikzpicture}%
}

\newcommand*{\sometikzpicture}{\sometikzpictureBase{}}
\newcommand*{\sometikzpictureWithMarmotScaling}[1]{%
  \sometikzpictureBase{[form autoscale={#1}]}%
}

\begin{document}

\begin{enumerate}
\item Showing the box I want the image to appear in for the examples below.
  \begin{choices}
    \begin{questionpicture}
      \includegraphics{example-image}
    \end{questionpicture}
     \item Choice \thechoice
     \item Choice \thechoice
     \item Choice \thechoice
     \item Choice \thechoice
     \item Choice \thechoice
  \end{choices}

\item Second question:
  \begin{choices}
    \begin{questionpicture}
      \begin{tikzpicture}
        \draw (0,0) grid (2,3);
      \end{tikzpicture}
    \end{questionpicture}
    \item Choice \thechoice
    \item Choice \thechoice
    \item Choice \thechoice
    \item Choice \thechoice
    \item Choice \thechoice
  \end{choices}

\item Third question:
  \begin{choices}
    \begin{questionpicture}
      \tikz \draw (0,0) grid (3,2);
    \end{questionpicture}
    \item Choice \thechoice
    \item Choice \thechoice
    \item Choice \thechoice
  \end{choices}

\item Fourth question using \verb|autoscale=false| in the optional argument of
      the \verb|choices| environment:
  \begin{choices}[autoscale=false]
    \begin{questionpicture}
      \tikz \draw (0,0) grid (3,2);
    \end{questionpicture}
    \item Choice \thechoice
    \item Choice \thechoice
    \item Choice \thechoice
  \end{choices}

\newpage
\item Using \verb|\scalebox|-based autoscaling (default behavior of
  the \verb|choices| environment):
  \begin{choices}
    \begin{questionpicture}
      \sometikzpicture
    \end{questionpicture}
    \item Choice \thechoice
    \item Choice \thechoice
  \end{choices}

\item Same picture using Ti\emph{k}Z scaling (scale factor found using
  marmot's technique at \url{https://tex.stackexchange.com/a/497749/73317},
  via the \verb|form autoscale| style implemented in my answer; note that
  several compilation runs may be necessary to let the computed scale factor
  converge):
  \begin{choices}[autoscale=false]
    \begin{questionpicture}
      \sometikzpictureWithMarmotScaling{grid-2}
    \end{questionpicture}
    \item Choice \thechoice
    \item Choice \thechoice
  \end{choices}

\item A triangle also scaled using the \verb|form autoscale| style:
  \begin{choices}[autoscale=false]
    \begin{questionpicture}
      \begin{tikzpicture}[form autoscale={my triangle}]
        \draw (0,0) node[below left] {$A$}-- (0.5,0.5) node[above] {$B$} --
              (1,0) node[below right] {$C$} -- cycle;
      \end{tikzpicture}
    \end{questionpicture}
    \item Choice \thechoice
    \item Choice \thechoice
  \end{choices}

\item Colored and verbatim material inside the framed box:
  \begin{choices}
    \begin{questionpicture}
      \color{green!20}\verb|@^_&~#%'${}|
    \end{questionpicture}
    \item Choice \thechoice
    \item Choice \thechoice
    \item Choice \thechoice
    \item Choice \thechoice
  \end{choices}
\end{enumerate}

\end{document}

在第 1 页:

第 1 页

在第 2 页:

第2页

本守则的一般说明

minipage正如您所见,该环境非常有用。:-) 我在这里使用了两次:

  • 具有固定的宽度和适应内容的高度:用于内部enumerate环境周围;

  • 具有固定宽度和固定高度:用于框架内部,可轻松在水平和垂直方向上居中框架材料。

\ryanjform@hrule命令允许您在中心位置调整规则参数。出于美观原因,它在两侧具有固定的字距(IMHO)。规则本身的制作方式与\leaders类似\hrulefill,但出于美观原因也被提升(请参阅heightdepth参数;由 生成的规则\hrulefill将位于基线上)。因此,在我的版本中规则长度不是硬编码的:它适应规则前同一行上的文本以及封闭的小页面。

choices关于环境进行的可选扩展

默认情况下,环境会使用choices缩放从环境内容创建的框,以便缩放后的框适合框架,并且其宽度或高度等于框架的宽度或高度。此缩放过程保留了纵横比;可以使用环境的可选参数逐张图片关闭它(见下文)。还有用于更持久更改的命令;它将在下面描述。questionpicture\scaleboxautoscale=falsechoices\ryanjformsetup

此缩放过程仅考虑框尺寸,不关心其内容。这意味着内部使用的字体tikzpicture将与图片的其余部分一起缩放。如果您希望字体不缩放,则应使用autoscale=false或编写您的tikzpictures ,以便它们不需要缩放。您可以手动或使用 TiZ 风格form autoscale(基于土拨鼠密码将图片边界框写入.aux,以便在下次运行 LaTeX 时对其进行适当缩放)。如 marmot写道,你会大概需要对使用该选项的 s禁用\scalebox基于 - 的缩放。最简单的方法是将其传递给环境,如下所示:tikzpictureremember pictureautoscale=falsechoices

\begin{choices}[autoscale=false]
  \begin{questionpicture}
    〈boxed material〉
  \end{questionpicture}

其中 〈boxedmaterial〉 代表您的图片,但可以是任何东西。

您必须为每个tikzpicture使用的对象form autoscale分配一个唯一标识符,该标识符不包含控制序列标记或活动字符。例如:

\begin{choices}[autoscale=false]
  \begin{questionpicture}
    \begin{tikzpicture}[form autoscale=my identifier]
       (...)
    \end{tikzpicture}
  \end{questionpicture}
  \item (...)
\end{choices}

如上所述,使用该form autoscale样式的图片会将其比例因子写入.aux文件,因此在第一次编译包含具有上述标识符的图片的文档后,您会在终端上看到此消息(LaTeX 输出):

Automatically-scaled pictures: please recompile for picture 'my identifier'.

下一节的示例中定义的样式form autoscale autoid允许您使用计数器自动生成此类标识符,以防您不想为它们烦恼。

可能值得期待的改变

  • 如果您想要框架内的内边框,只需在显示行中指定所需的宽度\setlength{\fboxsep}{0pt}%

  • 如果要autoscale=false使用默认设置(即\scalebox默认不执行基于 的缩放),只需将其替换autoscale .initial:n = { true }autoscale .initial:n = { false }。然后要\scalebox为给定的框架图片打开基于 的自动缩放,请在环境的可选参数中传递autoscale或:autoscale=truechoices

    \begin{choices}[autoscale] ...
    

    改变默认行为的另一种方法是,例如,在您想要影响的环境\ryanjformsetup{autoscale=false}之前的某处调用。该命令遵守 TeX 的范围规则(由组定义)。它可以在前言或文档的其他地方使用。choices\ryanjformsetup

  • 如果您更喜欢选择项和框架图片之间的这种对齐样式: 顶部对齐 请执行以下操作。

    1. 代替
      \minipage{\dimexpr\linewidth-\mywidth-2\fboxrule-2\fboxsep}
      
      和:
      \minipage[t]{\dimexpr\linewidth-\mywidth-2\fboxrule-2\fboxsep}
      
    2. 代替
      \begin{minipage}[c][\myheight][c]{\mywidth}
      
      和:
      \begin{minipage}[t][\myheight][c]{\mywidth}
      
    3. 像这样 包裹\fcolorbox内部:\raisebox{\baselineskip}{...}
      \raisebox{\baselineskip}{%
        \fcolorbox{red!20}{blue!20}{%
          \begin{minipage}[t][\myheight][c]{\mywidth}
            ...
          \end{minipage}%
      }}%
      

tikzpictures 的一般定位

关于移动 s 中使用的坐标tikzpicture不会影响它们在 LaTeX 文档中的位置这一事实,这确实是正确的。Atikzpicture表现为具有宽度、高度、深度和参考点的框,并像其他框一样由 TeX 放置。如果没有特殊选项,宽度和高度通常刚好足以容纳图片内容,参考点位于左下角;但诸如和之类的选项overlay可以baseline改变这一点。你可能想读这个答案了解更多详细信息。

回复评论时使用不同行为的代码

下面是实现不同行为的代码,如下所述此评论以及以下内容(主要是:没有水平规则,不再\choice有计数器,大写选择标签,\scalebox默认情况下基于的自动缩放关闭,并使用文件.aux对环境tikzpicture内发生的所有 s进行“marmot 自动缩放” questionpicture,使用自动生成的图片标识符):

\documentclass{article}
\usepackage{graphicx}
\usepackage{calc} % for \settototalheight (used for convenience)
\usepackage{xcolor}
\usepackage{etoolbox}
\usepackage{xparse}
\usepackage{tikz}
\usepackage{enumitem}
\usetikzlibrary{calc}

% Frame dimensions
\newlength{\mywidth}
\newlength{\myheight}
\setlength{\mywidth}{3.5cm}
\setlength{\myheight}{3.5cm}

\makeatletter

% Use l3keys to support a key/value-style interface for the optional argument
% of the 'choices' environment (l3keys is great!).
\ExplSyntaxOn

\msg_new:nnn { ryanjform } { duplicate-figure-id }
  { duplicate~figure~identifier:~'\exp_not:n {#1}'. }

% Whether to perform the \scalebox-based autoscaling for a given figure
\bool_new:N \l__ryanjform_do_autoscale_pic_in_choices_bool
% Sequence recording all figure identifiers (for the 'scale to max size' TikZ
% style) found so far
\seq_new:N \g__ryanjform_scale_to_max_style_figure_ids_seq
% Counter used when generating automatic figure identifiers for 'form autoscale'
\int_new:N \g_ryanjform_last_autogenerated_figure_nb_int

% Define the options supported in the optional argument of the 'choices'
% environment
\keys_define:nn { ryanjform }
  {
    autoscale .bool_set:N = \l__ryanjform_do_autoscale_pic_in_choices_bool,
    % Value used when the 'autoscale' key is passed with no value
    autoscale .default:n = { true },
    autoscale .initial:n = { false }
  }

\cs_new_protected:Npn \__ryanjform_set_keys:n #1
  { \keys_set:nn { ryanjform } {#1} }

\cs_new_protected:Npn \__ryanjform_check_unique_id:n #1
  {
    \seq_if_in:NnTF \g__ryanjform_scale_to_max_style_figure_ids_seq {#1}
      { \msg_error:nnn { ryanjform } { duplicate-figure-id } {#1} }
      { \seq_gput_right:Nn \g__ryanjform_scale_to_max_style_figure_ids_seq {#1} }
  }

\cs_new_protected:Npn \__ryanjform_form_autoscale:n #1
  {
    \pgfkeys { /tikz/.cd, form~autoscale={#1} }
  }

\cs_generate_variant:Nn \__ryanjform_form_autoscale:n { V }

% Automatic construction of generated ids (the pattern is defined here)
\cs_new:Npn \__ryanjform_autogenerated_id:n #1
  { ryanjform~autogenerated~id~#1 }

\cs_generate_variant:Nn \__ryanjform_autogenerated_id:n { V }

\cs_new_protected:Npn \__ryanjform_form_autoscale_autoid:
  {
    % Increment the counter
    \int_gincr:N \g_ryanjform_last_autogenerated_figure_nb_int
    \tl_set:Nx \l_tmpa_tl       % generate an id based on the counter value
      {
        \__ryanjform_autogenerated_id:V
          \g_ryanjform_last_autogenerated_figure_nb_int
      }
    % Call the 'form autoscale' style with the new id
    \__ryanjform_form_autoscale:V \l_tmpa_tl
  }

% Set up aliases using LaTeX2e naming style
\cs_set_eq:NN \ryanjformsetup \__ryanjform_set_keys:n
\cs_set_eq:NN \ryanjform@check@unique@id \__ryanjform_check_unique_id:n
\cs_set_eq:NN \ryanjform@form@autscale@autoid \__ryanjform_form_autoscale_autoid:

% If-then-else command using the boolean
% \l__ryanjform_do_autoscale_pic_in_choices_bool to choose the branch
\NewDocumentCommand \ryanjform@ifautoscale@enabled { }
  {
    \bool_if:NTF \l__ryanjform_do_autoscale_pic_in_choices_bool
  }

\ExplSyntaxOff

\newsavebox{\ryanjform@box}     % will be set with \global
\newlength{\ryanjform@total@height}

\newenvironment{questionpicture}{%
  % The OP wants 'form autoscale autoid' turned on for every picture framed by
  % the 'choices' environment
  \tikzset{every picture/.style=form autoscale autoid}%
  \begin{lrbox}{0}
}{%
  \end{lrbox}%
  \global\setbox\ryanjform@box=\box0
}

\AfterEndEnvironment{questionpicture}{%
  \par\noindent
  \setlength{\fboxsep}{0pt}%
  \begingroup
  \minipage{\dimexpr\linewidth-\mywidth-2\fboxrule-2\fboxsep}
  \begingroup
  \enumerate[label=(\Alph*)]
}

\let\ryanjform@start@question@picture\questionpicture
\newcommand*{\ryanjform@invalid@place@for@calling@questionpicture}{%
  \errmessage{The 'questionpicture' environment must be used at the start of a
    'choices' environment}%
}
% Generate an error message unless \questionpicture is used where expected
\let\questionpicture\ryanjform@invalid@place@for@calling@questionpicture

\newenvironment{choices}[1][]{%
  \ryanjformsetup{#1}%
  \let\questionpicture\ryanjform@start@question@picture
  \ignorespaces
}{%
  \endenumerate
  \endgroup
  \endminipage
  \endgroup
  %
  \settototalheight{\ryanjform@total@height}{\usebox{\ryanjform@box}}%
  \pgfmathsetmacro{\ryanjform@x@ratio}{\the\mywidth / \wd\ryanjform@box}%
  \pgfmathsetmacro{\ryanjform@y@ratio}{\the\myheight / \ryanjform@total@height}%
  \pgfmathsetmacro{\ryanjform@scale}{min(\ryanjform@x@ratio,
                                         \ryanjform@y@ratio)}%
  %
  \fcolorbox{red!20}{blue!20}{%
    \begin{minipage}[c][\myheight][c]{\mywidth}
      \centering
      \ryanjform@ifautoscale@enabled{%
        % We know that \ryanjform@scale will be (fully) expanded:
        % <https://tex.stackexchange.com/q/497769/73317>
        \scalebox{\ryanjform@scale}{\usebox{\ryanjform@box}}%
      }{%
        \usebox{\ryanjform@box}%
      }%
    \end{minipage}%
  }%
  \ignorespacesafterend
}

% Autoscaling technique that doesn't affect font sizes in TikZ pictures.
% (based on code from marmot: <https://tex.stackexchange.com/a/497749/73317>)
%
% #1: unique per-picture id allowing several pictures to use this mechanism
%     in a given document (it should contain no control sequence token nor
%     active character)
% #2: width of the reference rectangle
% #3: height of the reference rectangle
\newcommand*\ryanjform@ExportBB[3]{%
 \path let
   \p1=($(current bounding box.north east)-(current bounding box.south west)$),
   \n1={#2/\x1},\n2={#3/\y1}
 in \pgfextra{\pgfmathsetmacro{\ryanjform@figscale}{min(\n1,\n2)}%
              \expandafter\xdef\csname ryanjform@auto@figscale@#1\endcsname{%
                \ryanjform@figscale}};
 \immediate\write\@mainaux{%
   \string\expandafter
   \gdef\string\csname\space ryanjform@auto@figscale@#1\string\endcsname{%
     \csname ryanjform@auto@figscale@#1\endcsname}}}

\tikzset{scale to max size/.style args={id #1 width #2height #3}{%
    execute at end picture={\ryanjform@ExportBB{#1}{#2}{#3}},
    /utils/exec={\ryanjform@check@unique@id{#1}%
                 \ifcsname ryanjform@auto@figscale@#1\endcsname
                   \wlog{Found autoscale value for picture '#1'}%
                 \else
                   \typeout{Automatically-scaled pictures: please recompile
                            for picture '#1'.}
                   \expandafter\gdef
                     \csname ryanjform@auto@figscale@#1\endcsname{1}
                 \fi},
   scale=\csname ryanjform@auto@figscale@#1\endcsname},
         form autoscale/.style={%
           scale to max size=id #1 width \mywidth height \myheight},
         % Same style except the id is automatically generated using a counter
         form autoscale autoid/.style={%
           /utils/exec={\ryanjform@form@autscale@autoid}}}
% End of the code based on <https://tex.stackexchange.com/a/497749/73317>

\makeatother

\begin{document}

\begin{enumerate}

\item Original picture
  \begin{choices}
    \begin{questionpicture}
      \begin{tikzpicture}
        \draw[thick] (0,0)--(100,50);
        \draw[thick] (0,0)--(50,-100);
        \draw[thick] (0,0)--(-100,50);
        \draw[thick] (0,0)--(-50,-100);
        \draw[thick] (0,0)--(100,-50);
        \draw[thick] (0,0)--(-50,100);
        \draw (5,20) node {$1$};
        \draw (-25,25) node {$2$};
        \draw (-20,-5) node {$3$};
        \draw (0,-25) node {$4$};
        \draw (25,-25) node {$5$};
        \draw (25,0) node {$6$};
      \end{tikzpicture}
    \end{questionpicture}
    \item Choice
    \item Choice
    \item Choice
    \item Choice
    \item Choice
  \end{choices}

\item Original picture scaled manually by 0.1
  \begin{choices}
    \begin{questionpicture}
      \begin{tikzpicture}
        \draw[thick] (0,0)--(10,5);
        \draw[thick] (0,0)--(5,-10);
        \draw[thick] (0,0)--(-10,5);
        \draw[thick] (0,0)--(-5,-10);
        \draw[thick] (0,0)--(10,-5);
        \draw[thick] (0,0)--(-5,10);
        \draw (.5,2) node {$1$};
        \draw (-2.5,2.5) node {$2$};
        \draw (-2,-.5) node {$3$};
        \draw (0,-2.5) node {$4$};
        \draw (2.5,-2.5) node {$5$};
        \draw (2.5,0) node {$6$};
      \end{tikzpicture}
    \end{questionpicture}
    \item Choice
    \item Choice
    \item Choice
    \item Choice
    \item Choice
  \end{choices}

\item Original picture scaled manually by 0.01
  \begin{choices}
    \begin{questionpicture}
      \begin{tikzpicture}
        \draw[thick] (0,0)--(1,.5);
        \draw[thick] (0,0)--(.5,-1);
        \draw[thick] (0,0)--(-1,.5);
        \draw[thick] (0,0)--(-.5,-1);
        \draw[thick] (0,0)--(1,-.5);
        \draw[thick] (0,0)--(-.5,1);
        \draw (.05,.2) node {$1$};
        \draw (-.25,.25) node {$2$};
        \draw (-.2,-.05) node {$3$};
        \draw (0,-.25) node {$4$};
        \draw (.25,-.25) node {$5$};
        \draw (.25,0) node {$6$};
      \end{tikzpicture}
    \end{questionpicture}
    \item Choice
    \item Choice
    \item Choice
    \item Choice
    \item Choice
  \end{choices}

\clearpage

\item Original picture shifted up/right by 100.
  \begin{choices}
    \begin{questionpicture}
      \begin{tikzpicture}
        \draw[thick] (100,100)--(200,150);
        \draw[thick] (100,100)--(150,0);
        \draw[thick] (100,100)--(0,150);
        \draw[thick] (100,100)--(50,0);
        \draw[thick] (100,100)--(200,50);
        \draw[thick] (100,100)--(50,200);
        \draw (105,120) node {$1$};
        \draw (75,125) node {$2$};
        \draw (80,95) node {$3$};
        \draw (100,75) node {$4$};
        \draw (125,75) node {$5$};
        \draw (125,100) node {$6$};
      \end{tikzpicture}
    \end{questionpicture}
    \item Choice
    \item Choice
    \item Choice
    \item Choice
    \item Choice
  \end{choices}

  \item Picture from Problem 4 scaled by 0.1 (which happens to be the picture from Problem 2 shifted up/right by 10 because \emph{math})
  \begin{choices}
    \begin{questionpicture}
      \begin{tikzpicture}
        \draw[thick] (10,10)--(20,15);
        \draw[thick] (10,10)--(15,0);
        \draw[thick] (10,10)--(0,15);
        \draw[thick] (10,10)--(5,0);
        \draw[thick] (10,10)--(20,5);
        \draw[thick] (10,10)--(5,20);
        \draw (10.5,12) node {$1$};
        \draw (7.5,12.5) node {$2$};
        \draw (8,9.5) node {$3$};
        \draw (10,7.5) node {$4$};
        \draw (12.5,7.5) node {$5$};
        \draw (12.5,10) node {$6$};
      \end{tikzpicture}
    \end{questionpicture}
    \item Choice
    \item Choice
    \item Choice
    \item Choice
    \item Choice
  \end{choices}

\end{enumerate}

\end{document}

第 1 页:

第 1 页


第2页:

第2页

条件enumitem设置

正如评论中指出的那样,加载会修改环境parskip中项目之间的垂直间距。以下是处理此问题的一种方法:enumerateenumitem

\documentclass{article}

(...)

\makeatletter

\newtoggle{parskiploaded}
\@ifpackageloaded{parskip}
  {\toggletrue{parskiploaded}}
  {\togglefalse{parskiploaded}}

(...)

\AfterEndEnvironment{questionpicture}{%

  (...)

  \begingroup
  \iftoggle{parskiploaded}%
    {\enumerate[label=(\Alph*),itemsep=7pt]}%
    {\enumerate[label=(\Alph*)]}%
}

(...)

\end{document}

我们需要两个步骤,因为\@ifpackageloaded只在序言中有效。有关\iftoggle我在 中使用的替代方案etoolbox,您可能需要阅读这个答案\iftoggle不过,还是相当不错的)。

答案2

我非常谨慎地提出这种方法。坦率地说,这是一种蛮力方法。但它仍然相对简单,并且保留了 OP 的大部分原始代码。对于任何行为合理且自足的 Ti 来说,这应该是有效的Z 图形。作为示例,我使用了本文和http://www.texample.net

环境choices现在有一个可选参数,用于对图形使用的缩放比例进行校正(通常很小)(请参阅下面的第 12 和 14 项)。缩放比例用于更改 Ti 中的字体大小Z 节点仅有的。规则和界限(例如的后果\draw)未受影响。

评论中对此有很多争论,我可能忽略了一些东西。

\documentclass{article}

\usepackage{graphicx}
\usepackage{xcolor}
\usepackage{tikz}
\usepackage{anyfontsize} %% used to be able to scale CM fonts. Unnecessary with fontspec and OTF fonts.
\usepackage[margin=0.5in]{geometry}%% For the examples. Remove.
\usepackage{multicol} %% Only for compact framework for examples

\usetikzlibrary{calc,matrix} %% matrix for example 14

% Frame dimensions
\newlength{\mywidth}
\newlength{\myheight}
\setlength{\mywidth}{3.5cm}
\setlength{\myheight}{3.5cm}
\newsavebox{\testbox}
\usepackage{calc}
\newlength{\testht}

%% Alter the size of text in TikZ nodes.
\def\putit{\tikzset{every node/.append style={font=\fontsize{\testing}{\testing}\selectfont}}}

\makeatletter

\newenvironment{choices}[2][0]{% #1 Optional scaling correction; #2 the graphic
  \def\testing{10}
  \def\braced@stuff@to@include{{#2}}%
  \par\noindent
  %% Set the graphic as-is
  \sbox{\testbox}{\braced@stuff@to@include}
  %% Get the necessary scales (c)hange the 0.3cm to suit -- gives a frame to the graphic)
  \pgfmathsetmacro{\scalewd}{(\mywidth-0.3cm)/\wd\testbox}
  \pgfmathsetmacro{\scaleht}{(\myheight-0.3cm)/\ht\testbox}
  %% Choose the largest scale amount plus any correction...
  \pgfmathsetmacro{\myscale}{ifthenelse(greater(\scaleht,\scalewd),\scalewd+#1,\scaleht+#1)}
  %% ...and use it to scale type in TikZ nodes -- '8' seems best factor, but change to suit:
  \pgfmathsetmacro{\testing}{8/(\myscale)}%\typeout{!!!!!!!\theenumi: \myscale, \testing}%
  %% re-set the graphic (alas!) with altered nodes
  \sbox{\testbox}{%
    \putit %% Resize text in nodes
    \braced@stuff@to@include
}
  \minipage{\dimexpr\linewidth-\mywidth-2\fboxrule-2\fboxsep-6pt\relax}
  \enumerate
  \ignorespaces
}{%
  \unskip
  \endenumerate
  \endminipage
  \setlength{\fboxsep}{0pt}%
  \fcolorbox{blue!20}{green!20}{%
    \begin{minipage}[c][\myheight][c]{\mywidth}
      \centering
      \scalebox{\myscale}{\usebox{\testbox}}
    \end{minipage}%
  }%
  \ignorespacesafterend
}

\makeatother

\def\mychoice{Choice \arabic{enumii}}
\raggedcolumns

\begin{document}

\begin{multicols*}{2}

\begin{enumerate}

\item Image 1, scaled with a \verb+\textbullet+ in a node, but the node is at the correct size.
  \begin{choices}{%
      \begin{tikzpicture}
        \draw (0,0) rectangle (1,1);
        \draw (0.5,0.5) node {\textbullet};  % node placed in center of square
      \end{tikzpicture}}
  \item Choice 1
  \item Choice 2
  \item Choice 3
  \item Choice 4
  \item Choice 5
  \end{choices}

\item Image 2: same proportions as Image 1, but it's larger but the bullet (in a node) is the same size
  \begin{choices}{
      \begin{tikzpicture}
        \draw (0,0) rectangle (3.5,3.5);
        \draw (1.75,1.75) node {\textbullet}; % node placed in center of square
      \end{tikzpicture}
  }
  \item Choice 1
  \item Choice 2
  \item Choice 3
  \item Choice 4
  \item Choice 5
  \end{choices}

\item Showing the box I want the image to appear in for the examples below.
  \begin{choices}{\includegraphics{example-image}}
     \item \mychoice
     \item \mychoice
     \item \mychoice
     \item \mychoice
     \item \mychoice
  \end{choices}

\item Second question:
  \begin{choices}{%
      \begin{tikzpicture}
        \draw (0,0) grid (2,3);
      \end{tikzpicture}}
    \item \mychoice
    \item \mychoice
    \item \mychoice
    \item \mychoice
    \item \mychoice
  \end{choices}

\item Third question.
  \begin{choices}{\tikz \draw (0,0) grid (15,20);}
    \item \mychoice
    \item \mychoice
    \item \mychoice
  \end{choices}

\columnbreak

\item Fourth question.
  \begin{choices}{%
    \begin{tikzpicture}
    \coordinate (A) at (1,5);
    \coordinate (B) at (3,15);
    \node[below left] at (A) {$A$};
    \node[above right] at (B) {$B$};
    % Some rules may disappear if one doesn't substract some “epsilon”, see
    % <https://tex.stackexchange.com/q/13834/73317>
    \draw ($(A)-(0.001, 0.001)$) grid (B);
  \end{tikzpicture}%
}
    \item \mychoice
    \item \mychoice
  \end{choices}


\item Fifth question, a triangle.
  \begin{choices}{
    \begin{tikzpicture}
        \draw (0,0) node[below left] {$A$}-- (0.5,0.5) node[above] {$B$} --
              (1,0) node[below right] {$C$} -- cycle;
    \end{tikzpicture}}
    \item \mychoice
    \item \mychoice
  \end{choices}

  \item Image \theenumi: ideally, the next three images would look identical as they have the same coordinates, just scaled up and down. Note that the lines are scaled, but the nodes (apparently) are not.
  \begin{choices}{
      \begin{tikzpicture}
        \draw[thick] (0,0)--(1,.5);
        \draw[thick] (0,0)--(.5,-1);
        \draw[thick] (0,0)--(-1,.5);
        \draw[thick] (0,0)--(-.5,-1);
        \draw[thick] (0,0)--(1,-.5);
        \draw[thick] (0,0)--(-.5,1);
        \draw (.05,.2) node {$1$};
        \draw (-.25,.25) node {$2$};
        \draw (-.2,-.05) node {$3$};
        \draw (0,-.25) node {$4$};
        \draw (.25,-.25) node {$5$};
        \draw (.25,0) node {$6$};
      \end{tikzpicture}
  }
  \item \mychoice
  \item \mychoice
  \item \mychoice
  \item \mychoice
  \item \mychoice
  \end{choices}

  \item Image \theenumi: all coordinates are doubled from Image \number\numexpr\theenumi-1\relax.
  \begin{choices}{
      \begin{tikzpicture}
        \draw[thick] (0,0)--(2,1);
        \draw[thick] (0,0)--(1,-2);
        \draw[thick] (0,0)--(-2,1);
        \draw[thick] (0,0)--(-1,-2);
        \draw[thick] (0,0)--(2,-1);
        \draw[thick] (0,0)--(-1,2);
        \draw (.1,.4) node {$1$};
        \draw (-.5,.5) node {$2$};
        \draw (-.4,-.1) node {$3$};
        \draw (0,-.5) node {$4$};
        \draw (.5,-.5) node {$5$};
        \draw (.5,0) node {$6$};
      \end{tikzpicture}
  }
  \item \mychoice
  \item \mychoice 
  \item \mychoice
  \item \mychoice
  \item \mychoice
  \end{choices}

  \item Image \theenumi: all coordinates are multiplied by a factor of 5 from Image \number\numexpr\theenumi-1\relax. (Note that the nodes are \emph{no longer} extemely tiny here).
  \begin{choices}{
      \begin{tikzpicture}
        \draw[thick] (0,0)--(10,5);
        \draw[thick] (0,0)--(5,-10);
        \draw[thick] (0,0)--(-10,5);
        \draw[thick] (0,0)--(-5,-10);
        \draw[thick] (0,0)--(10,-5);
        \draw[thick] (0,0)--(-5,10);
        \draw (.5,2) node {$1$};
        \draw (-2.5,2.5) node {$2$};
        \draw (-2,-.5) node {$3$};
        \draw (0,-2.5) node {$4$};
        \draw (2.5,-2.5) node {$5$};
        \draw (2.5,0) node {$6$};
      \end{tikzpicture}
  }
  \item \mychoice
  \item \mychoice
  \item \mychoice
  \item \mychoice
  \item \mychoice
  \end{choices}

\columnbreak

\item A random example from TeXample.net.
\begin{choices}{
\begin{tikzpicture} 
%% http://www.texample.net/tikz/examples/parallelepiped/
% Figure parameters (tta and k needs to have the same sign)
% They can be modified at will
\def \tta{ -10.00000000000000 } % Defines the first angle of perspective
\def \k{    -3.00000000000000 } % Factor for second angle of perspective
\def \l{     6.00000000000000 } % Defines the width  of the parallelepiped
\def \d{     5.00000000000000 } % Defines the depth  of the parallelepiped
\def \h{     7.00000000000000 } % Defines the heigth of the parallelepiped

% The vertices A,B,C,D define the reference plan (vertical)
\coordinate (A) at (0,0); 
\coordinate (B) at ({-\h*sin(\tta)},{\h*cos(\tta)}); 
\coordinate (C) at ({-\h*sin(\tta)-\d*sin(\k*\tta)},
                    {\h*cos(\tta)+\d*cos(\k*\tta)}); 
\coordinate (D) at ({-\d*sin(\k*\tta)},{\d*cos(\k*\tta)}); 

% The vertices Ap,Bp,Cp,Dp define a plane translated from the 
% reference plane by the width of the parallelepiped
\coordinate (Ap) at (\l,0); 
\coordinate (Bp) at ({\l-\h*sin(\tta)},{\h*cos(\tta)}); 
\coordinate (Cp) at ({\l-\h*sin(\tta)-\d*sin(\k*\tta)},
                     {\h*cos(\tta)+\d*cos(\k*\tta)}); 
\coordinate (Dp) at ({\l-\d*sin(\k*\tta)},{\d*cos(\k*\tta)}); 

% Marking the vertices of the tetrahedron (red)
% and of the parallelepiped (black)
\fill[black]  (A) circle [radius=2pt]; 
\fill[red]    (B) circle [radius=2pt]; 
\fill[black]  (C) circle [radius=2pt]; 
\fill[red]    (D) circle [radius=2pt]; 
\fill[red]   (Ap) circle [radius=2pt]; 
\fill[black] (Bp) circle [radius=2pt]; 
\fill[red]   (Cp) circle [radius=2pt]; 
\fill[black] (Dp) circle [radius=2pt]; 

% painting first the three visible faces of the tetrahedron
\filldraw[draw=red,bottom color=red!50!black, top color=cyan!50]
  (B) -- (Cp) -- (D);
\filldraw[draw=red,bottom color=red!50!black, top color=cyan!50]
  (B) -- (D)  -- (Ap);
\filldraw[draw=red,bottom color=red!50!black, top color=cyan!50]
  (B) -- (Cp) -- (Ap);

% Draw the edges of the tetrahedron
\draw[red,-,very thick] (Ap) --  (D)
                        (Ap) --  (B)
                        (Ap) -- (Cp)
                        (B)  --  (D)
                        (Cp) --  (D)
                        (B)  -- (Cp);

% Draw the visible edges of the parallelepiped
\draw [-,thin] (B)  --  (A)
               (Ap) -- (Bp)
               (B)  --  (C)
               (D)  --  (C)
               (A)  --  (D)
               (Ap) --  (A)
               (Cp) --  (C)
               (Bp) --  (B)
               (Bp) -- (Cp);

% Draw the hidden edges of the parallelepiped
\draw [gray,-,thin] (Dp) -- (Cp);
                    (Dp) --  (D);
                    (Ap) -- (Dp);

% Name the vertices (the names are not consistent
%  with the node name, but it makes the programming easier)
\draw (Ap) node [right]           {$A$}
      (Bp) node [right, gray]     {$F$}
      (Cp) node [right]           {$D$}
      (C)  node [left,gray]       {$E$}
      (D)  node [left]            {$B$}
      (A)  node [left,gray]       {$G$}
      (B)  node [above left=+5pt] {$C$}
      (Dp) node [right,gray]      {$H$};

% Drawing again vertex $C$, node (B) because it disappeared behind the edges.
% Drawing again vertex $H$, node (Dp) because it disappeared behind the edges.
\fill[red]   (B) circle [radius=2pt]; 
\fill[gray] (Dp) circle [radius=2pt]; 

% From the reference and this example one can easily draw 
% the twin tetrahedron jointly to this one.
% Drawing the edges of the twin tetrahedron
% switching the p_s: A <-> Ap, etc...
\draw[red,-,dashed, thin] (A)  -- (Dp)
                          (A)  -- (Bp)
                          (A)  --  (C)
                          (Bp) -- (Dp)
                          (C)  -- (Dp)
                          (Bp) --  (C);
\end{tikzpicture}
}
\item \mychoice
\item \mychoice
\end{choices}

\item Another sample from TeXample.net. A small scaling correction was necessary $=-0.05$.
\begin{choices}[-.05]{% Note scaling correction
% A hexagon for memorizing trigonometric identities
% Author: Josef Nilsen
% http://www.texample.net/tikz/examples/trigonometric-hexagon/
\begin{tikzpicture}[scale=4,cap=round,>=latex]
% Radius of regular polygons
  \newdimen\R
  \R=0.8cm
  \coordinate (center) at (0,0);
 \draw (0:\R)
     \foreach \x in {60,120,...,360} {  -- (\x:\R) }
              -- cycle (300:\R) node[below] {$\csc \theta$}
              -- cycle (240:\R) node[below] {$\sec \theta$}
              -- cycle (180:\R) node[left] {$\tan \theta$}
              -- cycle (120:\R) node[above] {$\sin \theta$}
              -- cycle (60:\R) node[above] {$\cos \theta$}
              -- cycle (0:\R) node[right] {$\cot \theta$};
  \draw { (60:\R) -- (120:\R) -- (center) -- (60:\R) } [fill=gray];
  \draw { (180:\R) -- (240:\R) -- (center) -- (180:\R) } [fill=gray];
  \draw { (0:\R) -- (300:\R) -- (center) -- (0:\R) }  [fill=gray];
   \R=0.1cm
  \draw (0:\R) \foreach \x in {60,120,...,360} { -- (\x:\R) }
    [fill=white] -- cycle (center) node {1};
\end{tikzpicture}
}
\item\mychoice
\item\mychoice
\item\mychoice
\item\mychoice
\item\mychoice
\end{choices}

\item Yet another from TeXample.net
\begin{choices}{%
% CIELAB color space
% Vilson Vieira <[email protected]> - http://automata.cc - 2013 - copyleft
% http://www.texample.net/tikz/examples/cielab/
\begin{tikzpicture}[scale=1.5]
  % b* shade
  \path[draw, shade, left color=blue, right color=yellow, opacity=.6] 
    (0,0,0) node[below] {$-b*$} -- (5,2.0,0) node[below] {$+b*$}
    -- (5, 2.5, 0) -- (0, 0.5, 0) -- cycle;

  % a* shade
  \path[draw, shade, left color=green, right color=red, opacity=.6] 
  (0, 2.0, 0) node[below] {$-a*$} -- (5, 0, 0) node[below] {$+a*$} 
  -- (5, .5, 0) -- (0, 2.5, 0) -- cycle;

  % L* shade
  \path[draw, shade, top color=white, bottom color=black, opacity=.6] 
    (2.65, -1.85, 0) node[right] {$L* = 0$} -- (2.65, 4.45, 0)
    node[right] {$L*=100$} -- (2.35, 4.3, 0)  -- (2.35, -2., 0) -- cycle;

  % b*-axis
  \draw[<->] (0,0.25,0) -- (5, 2.25, 0);
  % a*-axis
  \draw[<->] (0,2.25,0) -- (5, 0.25, 0);
  % L*-axis
  \draw[<->] (2.5,-1.90,0) -- (2.5,4.35,0);
\end{tikzpicture}
}
\item\mychoice
\item\mychoice
\item\mychoice
\item\mychoice
\item\mychoice
\end{choices}

\item And yet another from TeXampe.net. This required the addition of \verb+ampersand replacement=\&+  and changing \verb+&+ to \verb+\&+ in the matrix. Note small scaling correction ($=0.1$) to enlarge the  CD slightly.
% https://tex.stackexchange.com/questions/1111/problem-with-defining-shortcuts-for-tikz-matrices
\begin{choices}[0.1]{%
\begin{tikzpicture}
% A simple commutative diagram
% Stefan Kottwitz
% http://www.texample.net/tikz/examples/commutative-diagram-tikz/
  \matrix (m) [ampersand replacement=\&,matrix of math nodes,row sep=3em,column sep=4em,minimum width=2em]
  {
     F_t(x) \& F(x) \\
     A_t \& A \\};
  \path[-stealth]
    (m-1-1) edge node [left] {$\mathcal{B}_X$} (m-2-1)
            edge [double] node [below] {$\mathcal{B}_t$} (m-1-2)
    (m-2-1.east|-m-2-2) edge node [below] {$\mathcal{B}_T$}
            node [above] {$\exists$} (m-2-2)
    (m-1-2) edge node [right] {$\mathcal{B}_T$} (m-2-2)
            edge [dashed,-] (m-2-1);
\end{tikzpicture}
}
\item\mychoice
\item\mychoice
\item\mychoice
\item\mychoice
\item\mychoice
\end{choices}

\end{enumerate}

\end{multicols*}

\end{document}

第一页

第二页

答案3

此新答案是为了回复这个请求。 它补充 我的答案并且只发布在这里,因为我的第一个答案由于 30000 个字符的限制无法再增长(!)。

problems为将每个(外部)项目包装在中的外部列表定义了一个环境minipage,因为 OP 显然想要完全防止在给定问题中分页。

\documentclass{article}
\usepackage{graphicx}
\usepackage{calc} % for \settototalheight (used for convenience)
\usepackage{xcolor}
\usepackage{etoolbox}
\usepackage{xparse}
\usepackage{tikz}
\usepackage{parskip}
\usepackage{enumitem}
\usetikzlibrary{calc}

% Frame dimensions
\newlength{\mywidth}
\newlength{\myheight}
\setlength{\mywidth}{3.5cm}
\setlength{\myheight}{3.5cm}

\makeatletter

\newtoggle{parskiploaded}
\@ifpackageloaded{parskip}
  {\toggletrue{parskiploaded}}
  {\togglefalse{parskiploaded}}

% Use l3keys to support a key/value-style interface for the optional argument
% of the 'choices' environment (l3keys is great!).
\ExplSyntaxOn

\msg_new:nnn { ryanjform } { duplicate-figure-id }
  { duplicate~figure~identifier:~'\exp_not:n {#1}'. }

% Whether to perform the \scalebox-based autoscaling for a given figure
\bool_new:N \l__ryanjform_do_autoscale_pic_in_choices_bool
% Sequence recording all figure identifiers (for the 'scale to max size' TikZ
% style) found so far
\seq_new:N \g__ryanjform_scale_to_max_style_figure_ids_seq
% Counter used when generating automatic figure identifiers for 'form autoscale'
\int_new:N \g_ryanjform_last_autogenerated_figure_nb_int

% Define the options supported in the optional argument of the 'choices'
% environment
\keys_define:nn { ryanjform }
  {
    autoscale .bool_set:N = \l__ryanjform_do_autoscale_pic_in_choices_bool,
    % Value used when the 'autoscale' key is passed with no value
    autoscale .default:n = { true },
    autoscale .initial:n = { false }
  }

\cs_new_protected:Npn \__ryanjform_set_keys:n #1
  { \keys_set:nn { ryanjform } {#1} }

\cs_new_protected:Npn \__ryanjform_check_unique_id:n #1
  {
    \seq_if_in:NnTF \g__ryanjform_scale_to_max_style_figure_ids_seq {#1}
      { \msg_error:nnn { ryanjform } { duplicate-figure-id } {#1} }
      { \seq_gput_right:Nn \g__ryanjform_scale_to_max_style_figure_ids_seq {#1} }
  }

\cs_new_protected:Npn \__ryanjform_form_autoscale:n #1
  {
    \pgfkeys { /tikz/.cd, form~autoscale={#1} }
  }

\cs_generate_variant:Nn \__ryanjform_form_autoscale:n { V }

% Automatic construction of generated ids (the pattern is defined here)
\cs_new:Npn \__ryanjform_autogenerated_id:n #1
  { ryanjform~autogenerated~id~#1 }

\cs_generate_variant:Nn \__ryanjform_autogenerated_id:n { V }

\cs_new_protected:Npn \__ryanjform_form_autoscale_autoid:
  {
    % Increment the counter
    \int_gincr:N \g_ryanjform_last_autogenerated_figure_nb_int
    \tl_set:Nx \l_tmpa_tl       % generate an id based on the counter value
      {
        \__ryanjform_autogenerated_id:V
          \g_ryanjform_last_autogenerated_figure_nb_int
      }
    % Call the 'form autoscale' style with the new id
    \__ryanjform_form_autoscale:V \l_tmpa_tl
  }

% Set up aliases using LaTeX2e naming style
\cs_set_eq:NN \ryanjformsetup \__ryanjform_set_keys:n
\cs_set_eq:NN \ryanjform@check@unique@id \__ryanjform_check_unique_id:n
\cs_set_eq:NN \ryanjform@form@autscale@autoid \__ryanjform_form_autoscale_autoid:

% If-then-else command using the boolean
% \l__ryanjform_do_autoscale_pic_in_choices_bool to choose the branch
\NewDocumentCommand \ryanjform@ifautoscale@enabled { }
  {
    \bool_if:NTF \l__ryanjform_do_autoscale_pic_in_choices_bool
  }

\bool_new:N \l__ryanjform_before_first_problem_bool

\NewDocumentCommand \ryanjform@outeritem { o }
  {
    \bool_if:NTF \l__ryanjform_before_first_problem_bool
      { \bool_set_false:N \l__ryanjform_before_first_problem_bool }
      {
        \endminipage
        \group_end:
      }

    \IfValueTF {#1}
      { \ryanjform@outeritem@ORI [#1] } % call the original
      { \ryanjform@outeritem@ORI }      % \item command

    \group_begin:
    \minipage[t]{\linewidth}
  }

\NewDocumentEnvironment { problems } { }
  {
    \group_begin:
    \enumerate
    \cs_set_eq:NN \ryanjform@outeritem@ORI \item % save the original \item
    \cs_set_eq:NN \item \ryanjform@outeritem     % locally override it
    \bool_set_true:N \l__ryanjform_before_first_problem_bool
  }
  {
    \endminipage                % for the
    \group_end:                 % last item
    \endenumerate
    \group_end:
  }

\ExplSyntaxOff

\newsavebox{\ryanjform@box}     % will be set with \global
\newlength{\ryanjform@total@height}

\newenvironment{questionpicture}{%
  % The OP wants 'form autoscale autoid' turned on for every picture framed by
  % the 'choices' environment
  \tikzset{every picture/.style=form autoscale autoid}%
  \begin{lrbox}{0}
}{%
  \end{lrbox}%
  \global\setbox\ryanjform@box=\box0
}

\AfterEndEnvironment{questionpicture}{%
  \par\noindent
  \setlength{\fboxsep}{0pt}%
  \begingroup
  \minipage{\dimexpr\linewidth-\mywidth-2\fboxrule-2\fboxsep}
  \begingroup
  \iftoggle{parskiploaded}%
    {\enumerate[label=(\Alph*),itemsep=7pt]}%
    {\enumerate[label=(\Alph*)]}%
}

\let\ryanjform@start@question@picture\questionpicture
\newcommand*{\ryanjform@invalid@place@for@calling@questionpicture}{%
  \errmessage{The 'questionpicture' environment must be used at the start of a
    'choices' environment}%
}
% Generate an error message unless \questionpicture is used where expected
\let\questionpicture\ryanjform@invalid@place@for@calling@questionpicture

\newenvironment{choices}[1][]{%
  \ryanjformsetup{#1}%
  \let\questionpicture\ryanjform@start@question@picture
  \let\item\ryanjform@outeritem@ORI
  \ignorespaces
}{%
  \endenumerate
  \endgroup
  \endminipage
  \endgroup
  %
  \settototalheight{\ryanjform@total@height}{\usebox{\ryanjform@box}}%
  \pgfmathsetmacro{\ryanjform@x@ratio}{\the\mywidth / \wd\ryanjform@box}%
  \pgfmathsetmacro{\ryanjform@y@ratio}{\the\myheight / \ryanjform@total@height}%
  \pgfmathsetmacro{\ryanjform@scale}{min(\ryanjform@x@ratio,
                                         \ryanjform@y@ratio)}%
  %
  \fcolorbox{red!20}{blue!20}{%
    \begin{minipage}[c][\myheight][c]{\mywidth}
      \centering
      \ryanjform@ifautoscale@enabled{%
        % We know that \ryanjform@scale will be (fully) expanded:
        % <https://tex.stackexchange.com/q/497769/73317>
        \scalebox{\ryanjform@scale}{\usebox{\ryanjform@box}}%
      }{%
        \usebox{\ryanjform@box}%
      }%
    \end{minipage}%
  }%
  \ignorespacesafterend
}

% Autoscaling technique that doesn't affect font sizes in TikZ pictures.
% (based on code from marmot: <https://tex.stackexchange.com/a/497749/73317>)
%
% #1: unique per-picture id allowing several pictures to use this mechanism
%     in a given document (it should contain no control sequence token nor
%     active character)
% #2: width of the reference rectangle
% #3: height of the reference rectangle
\newcommand*\ryanjform@ExportBB[3]{%
 \path let
   \p1=($(current bounding box.north east)-(current bounding box.south west)$),
   \n1={#2/\x1},\n2={#3/\y1}
 in \pgfextra{\pgfmathsetmacro{\ryanjform@figscale}{min(\n1,\n2)}%
              \expandafter\xdef\csname ryanjform@auto@figscale@#1\endcsname{%
                \ryanjform@figscale}};
 \immediate\write\@mainaux{%
   \string\expandafter
   \gdef\string\csname\space ryanjform@auto@figscale@#1\string\endcsname{%
     \csname ryanjform@auto@figscale@#1\endcsname}}}

\tikzset{scale to max size/.style args={id #1 width #2height #3}{%
    execute at end picture={\ryanjform@ExportBB{#1}{#2}{#3}},
    /utils/exec={\ryanjform@check@unique@id{#1}%
                 \ifcsname ryanjform@auto@figscale@#1\endcsname
                   \wlog{Found autoscale value for picture '#1'}%
                 \else
                   \typeout{Automatically-scaled pictures: please recompile
                            for picture '#1'.}
                   \expandafter\gdef
                     \csname ryanjform@auto@figscale@#1\endcsname{1}
                 \fi},
   scale=\csname ryanjform@auto@figscale@#1\endcsname},
         form autoscale/.style={%
           scale to max size=id #1 width \mywidth height \myheight},
         % Same style except the id is automatically generated using a counter
         form autoscale autoid/.style={%
           /utils/exec={\ryanjform@form@autscale@autoid}}}
% End of the code based on <https://tex.stackexchange.com/a/497749/73317>

\makeatother

\begin{document}

\begin{problems}

\item Original picture
  \begin{choices}
    \begin{questionpicture}
      \begin{tikzpicture}
        \draw[thick] (0,0)--(100,50);
        \draw[thick] (0,0)--(50,-100);
        \draw[thick] (0,0)--(-100,50);
        \draw[thick] (0,0)--(-50,-100);
        \draw[thick] (0,0)--(100,-50);
        \draw[thick] (0,0)--(-50,100);
        \draw (5,20) node {$1$};
        \draw (-25,25) node {$2$};
        \draw (-20,-5) node {$3$};
        \draw (0,-25) node {$4$};
        \draw (25,-25) node {$5$};
        \draw (25,0) node {$6$};
      \end{tikzpicture}
    \end{questionpicture}
    \item Choice
    \item Choice
    \item Choice
    \item Choice
    \item Choice
  \end{choices}

\item Original picture scaled manually by 0.1
  \begin{choices}
    \begin{questionpicture}
      \begin{tikzpicture}
        \draw[thick] (0,0)--(10,5);
        \draw[thick] (0,0)--(5,-10);
        \draw[thick] (0,0)--(-10,5);
        \draw[thick] (0,0)--(-5,-10);
        \draw[thick] (0,0)--(10,-5);
        \draw[thick] (0,0)--(-5,10);
        \draw (.5,2) node {$1$};
        \draw (-2.5,2.5) node {$2$};
        \draw (-2,-.5) node {$3$};
        \draw (0,-2.5) node {$4$};
        \draw (2.5,-2.5) node {$5$};
        \draw (2.5,0) node {$6$};
      \end{tikzpicture}
    \end{questionpicture}
    \item Choice
    \item Choice
    \item Choice
    \item Choice
    \item Choice
  \end{choices}

\item Original picture scaled manually by 0.01
  \begin{choices}
    \begin{questionpicture}
      \begin{tikzpicture}
        \draw[thick] (0,0)--(1,.5);
        \draw[thick] (0,0)--(.5,-1);
        \draw[thick] (0,0)--(-1,.5);
        \draw[thick] (0,0)--(-.5,-1);
        \draw[thick] (0,0)--(1,-.5);
        \draw[thick] (0,0)--(-.5,1);
        \draw (.05,.2) node {$1$};
        \draw (-.25,.25) node {$2$};
        \draw (-.2,-.05) node {$3$};
        \draw (0,-.25) node {$4$};
        \draw (.25,-.25) node {$5$};
        \draw (.25,0) node {$6$};
      \end{tikzpicture}
    \end{questionpicture}
    \item Choice
    \item Choice
    \item Choice
    \item Choice
    \item Choice
  \end{choices}

\item Original picture shifted up/right by 100.
  \begin{choices}
    \begin{questionpicture}
      \begin{tikzpicture}
        \draw[thick] (100,100)--(200,150);
        \draw[thick] (100,100)--(150,0);
        \draw[thick] (100,100)--(0,150);
        \draw[thick] (100,100)--(50,0);
        \draw[thick] (100,100)--(200,50);
        \draw[thick] (100,100)--(50,200);
        \draw (105,120) node {$1$};
        \draw (75,125) node {$2$};
        \draw (80,95) node {$3$};
        \draw (100,75) node {$4$};
        \draw (125,75) node {$5$};
        \draw (125,100) node {$6$};
      \end{tikzpicture}
    \end{questionpicture}
    \item Choice
    \item Choice
    \item Choice
    \item Choice
    \item Choice
  \end{choices}

\item Picture from Problem 4 scaled by 0.1 (which happens to be the picture from Problem 2 shifted up/right by 10 because \emph{math})
  \begin{choices}
    \begin{questionpicture}
      \begin{tikzpicture}
        \draw[thick] (10,10)--(20,15);
        \draw[thick] (10,10)--(15,0);
        \draw[thick] (10,10)--(0,15);
        \draw[thick] (10,10)--(5,0);
        \draw[thick] (10,10)--(20,5);
        \draw[thick] (10,10)--(5,20);
        \draw (10.5,12) node {$1$};
        \draw (7.5,12.5) node {$2$};
        \draw (8,9.5) node {$3$};
        \draw (10,7.5) node {$4$};
        \draw (12.5,7.5) node {$5$};
        \draw (12.5,10) node {$6$};
      \end{tikzpicture}
    \end{questionpicture}
    \item Choice
    \item Choice
    \item Choice
    \item Choice
    \item Choice
  \end{choices}

\end{problems}

\end{document}

相关内容