1

For the following, I would like to get an exact measurement of 10mm for both the right and left margins of the graph paper instead of 20 mm.

enter image description here

% https://tex.stackexchange.com/a/356984/2288
\documentclass{article}

\usepackage{pgfplots}
\usepackage{siunitx}

\usepackage[
a4paper , right = 10mm , left = 10mm , includeheadfoot, 
]{geometry}

\begin{document}
\pagestyle{empty}
\centering

% http://tex.stackexchange.com/a/15002/100384
\newcommand*{\getlength}[2]{%
   % Convert to `cm` and round to two fractional digits:
   \pgfmathsetmacro#1{round(0.0351459804*#2)}%
}

\vspace*{\fill}

\rotatebox{0}{
    \begin{tikzpicture}
        % a factor for measures, since pfplots produces slightly bigger images than defined
        %   in width/height. This can be used to adjust that problem manually
        \pgfmathsetmacro{\factor}{0.9}% 0.9

        % we will need some length in `cm`, without units, and rounded
        \getlength{\yMax}{\factor*\textheight}
        \getlength{\xMax}{\factor*\textwidth}

        \begin{axis}[
            set layers,
            width=\factor\textwidth, height=\factor\textheight,
            x = 1cm, y = 1cm,
            xtick={0,1,...,\xMax},
            ytick={0,1,...,\yMax},
            minor xtick={0,0.1,0.2,...,\xMax},
            minor ytick={0,0.1,0.2,...,\yMax},
            tick style = {line width = 0.6pt, black!40!white},
            minor tick style = {draw = none},
            major tick style = {draw = none},
            ticklabel style = {draw = none},
            xticklabels=\empty, %xlabel = \empty,
            yticklabels=\empty, %ylabel = \empty,
            axis line style = {-latex},
            grid = both,
            minor grid style={line width=0.2pt, black!20!white},
            major grid style={line width=0.6pt, black!60!white},
            ymin=0, ymax=\yMax,
            xmin=0, xmax=\xMax,
            ]
            \begin{pgfonlayer}{axis grid}
            \draw[line width=0.40pt, step=0.5cm, black!40!white] (axis cs: 0, 0) grid (axis cs: \xMax, \yMax);
            \end{pgfonlayer}
        \end{axis}
    \end{tikzpicture}
}

\vspace*{\fill}

\end{document}

Update

When editing @JohnKormylo's answer to have

\usepackage[
a4paper , right = 10mm , left = 10mm , 
top = 5 mm, headheight = 0 mm, headsep = 0 mm, 
foot = 0 mm, bottom = 5 mm, showframe
]{geometry}

the output has two issues:

1- the drawing is on the second page, while the first page is empty

2- the bottom margin is less than the specified value of 5 mm.

Diaa
  • 9,599

1 Answers1

2

Since your page already has 1cm margins, I assume you want the graph paper to fill the text area (rounded to the nearest cm).

There is an automatic \vskip\topskip at the start of every page to set the first baseline.

The showframe option is for debugging/alignment only.

\documentclass{article}

\usepackage{pgfplots}
\usepackage{siunitx}

\usepackage[
a4paper , right = 10mm , left = 10mm , includeheadfoot, showframe
]{geometry}


% http://tex.stackexchange.com/a/15002/100384
\newcommand*{\getlength}[2]{%
   % Convert to `cm` and round to two fractional digits:
   \pgfmathsetmacro#1{round(0.0351459804*#2)}%
}
\pagestyle{empty}

\begin{document}
\vspace*{\fill}\vskip-\topskip
\centering
\begin{tikzpicture}
        % a factor for measures, since pfplots produces slightly bigger images than defined
        %   in width/height. This can be used to adjust that problem manually
        \pgfmathsetmacro{\factor}{1.0}% 0.9

        % we will need some length in `cm`, without units, and rounded
        \getlength{\yMax}{\factor*\textheight}
        \getlength{\xMax}{\factor*\textwidth}

        \begin{axis}[
            set layers,
            width=\factor\textwidth, height=\factor\textheight,
            scale only axis, name=border,
            x = 1cm, y = 1cm,
            xtick={0,1,...,\xMax},
            ytick={0,1,...,\yMax},
            minor xtick={0,0.1,0.2,...,\xMax},
            minor ytick={0,0.1,0.2,...,\yMax},
            tick style = {line width = 0.6pt, black!40!white},
            minor tick style = {draw = none},
            major tick style = {draw = none},
            ticklabel style = {draw = none},
            xticklabels=\empty, %xlabel = \empty,
            yticklabels=\empty, %ylabel = \empty,
            axis line style = {-latex},
            grid = both,
            minor grid style={line width=0.2pt, black!20!white},
            major grid style={line width=0.6pt, black!60!white},
            ymin=0, ymax=\yMax,
            xmin=0, xmax=\xMax,
            ]
        %\begin{pgfonlayer}{axis grid}% redundant
        %\draw[line width=0.40pt, step=0.5cm, black!40!white] (axis cs: 0, 0) grid (axis cs: \xMax, \yMax);
        %\end{pgfonlayer}
        \end{axis}
    \pgfresetboundingbox
    \path (border.south west) (border.north east);
    \draw[red] (current bounding box.south west) rectangle (current bounding box.north east);
\end{tikzpicture}\vspace*{\fill}
\end{document}

This version puts the grid into a savebox, then places it at (current page.center) using [remember picture, overlay]. Be sure to run it twice.

\documentclass[a4paper]{article}
\usepackage{pgfplots}
\usepackage{siunitx}

% http://tex.stackexchange.com/a/15002/100384
\newcommand*{\getlength}[2]{%
   % Convert to `cm` and round to two fractional digits:
   \pgfmathsetmacro#1{round(0.0351459804*#2)}%
}
\newsavebox{\gridbox}
\savebox\gridbox{\begin{tikzpicture}
    \pgfmathsetmacro{\width}{\paperwidth-2cm}
    \pgfmathsetmacro{\height}{\paperheight-2cm}
        % we will need some length in `cm`, without units, and rounded
        \getlength{\yMax}{\height}
        \getlength{\xMax}{\width}

        \begin{axis}[
            set layers,
            width=\width, height=\height,
            scale only axis, name=border,
            x = 1cm, y = 1cm,
            xtick={0,1,...,\xMax},
            ytick={0,1,...,\yMax},
            minor xtick={0,0.1,0.2,...,\xMax},
            minor ytick={0,0.1,0.2,...,\yMax},
            tick style = {line width = 0.6pt, black!40!white},
            minor tick style = {draw = none},
            major tick style = {draw = none},
            ticklabel style = {draw = none},
            xticklabels=\empty, %xlabel = \empty,
            yticklabels=\empty, %ylabel = \empty,
            axis line style = {-latex},
            grid = both,
            minor grid style={line width=0.2pt, black!20!white},
            major grid style={line width=0.6pt, black!60!white},
            ymin=0, ymax=\yMax,
            xmin=0, xmax=\xMax,
            ]
        %\begin{pgfonlayer}{axis grid}% redundant
        %\draw[line width=0.40pt, step=0.5cm, black!40!white] (axis cs: 0, 0) grid (axis cs: \xMax, \yMax);
        %\end{pgfonlayer}
        \end{axis}
    \pgfresetboundingbox
    \path (border.south west) (border.north east);
\end{tikzpicture}}

\pagestyle{empty}
\begin{document}
\begin{tikzpicture}[remember picture, overlay]
  \node at (current page.center) {\usebox\gridbox};
\end{tikzpicture}
\end{document}
John Kormylo
  • 79,712
  • 3
  • 50
  • 120
  • If you take a look at this document, you will notice that the output is slightly shifted upward and left from the page center. May I know why? And how to fix it? – Diaa Feb 26 '20 at 13:14
  • Unfortunately, I don't quite understand if you are talking about fixes or general recommendations. In case of the former, I would be grateful if you could show me how to apply your fixes. – Diaa Feb 26 '20 at 14:21
  • You will note that the bounding box no longer matches the graph paper, since you removed the \pgfresetcounding box code. Second, the tikzpicture is centered relative to the text area, not the page. One can ignore the page geometry by using [remember picture,overlay] and (current page.center). – John Kormylo Feb 26 '20 at 14:41
  • I am so sorry if I am bothering you, but I would be highly grateful if you could edit my document and paste the enhanced one on pastebin.com to show me what you mean. My ultimate aim is to perfectly center the graph paper both vertically and horizontally according to the actual A4 page. – Diaa Feb 26 '20 at 17:02
  • Thanks for your consideration; I am curious to understand: (1) did you intentionally remove the package geometry since I need to make sure the output is a4paper? (2) what does \pgfresetboundingbox \path (border.south west) (border.north east); do? (3) also, what does \begin{tikzpicture}[remember picture, overlay] \node at (current page.center) {\usebox\gridbox}; \end{tikzpicture} do? I hope your patience hasn't run out :). – Diaa Feb 26 '20 at 21:53
  • I did remove geometry just to show you didn't need to mess with it. I forgot about a4paper. – John Kormylo Feb 26 '20 at 22:13
  • 1
    \pgfresetboundingbox resets the bounding box (to empty). The \path sets it to be the same as the axis border. [remember picture] is needed to define (current page.center). Basically tikz stores the origin location (in the aux file) in the first run, then computes the offset needed in the second run. Overlay produces no bounding box, so that it can overlap anything else on the page. – John Kormylo Feb 26 '20 at 22:32
  • Many thanks for the explanation. Before \pgfresetboundingbox, what was the original bounding box? – Diaa Feb 27 '20 at 18:31
  • 1
    You can draw it using the \draw command at the end of the first solution.. Pgfplots reserves extra space for the tick marks, labels, titles etc. even when it doesn't have any. – John Kormylo Feb 28 '20 at 02:17
  • If you don't mind. would you please tell me why this document doesn't get the correct expected output? and how to fix it? – Diaa Mar 01 '20 at 18:30
  • I ran it more than twice. This is why I needed to make sure it is written correctly. – Diaa Mar 02 '20 at 05:07
  • 1
    Don't use [overlay] inside a savebox. In this case, there is not point in using a savebox at all. Just put the tikzpicture into the document. – John Kormylo Mar 02 '20 at 15:30