Take the 2-minute tour ×
TeX - LaTeX Stack Exchange is a question and answer site for users of TeX, LaTeX, ConTeXt, and related typesetting systems. It's 100% free, no registration required.

To meet the conditions of our corporate design I need other margins on the first page of each document. The normal page layout is given by

\usepackage[left=3cm,right=2cm,bottom=3cm,top=2cm]{geometry}

But on the first page I need

\usepackage[left=3cm,right=4.5cm,bottom=3cm,top=2cm]{geometry}

I am aware of commands like \newgeometry, but for such things I need to insert pagebreaks by hand.

How can I achieve different margins only on the first page without doing pagebreaks by hand? Any trick (like using wrapfig or something like this) is allowed.

Here is a MWE where I want to use it:

\documentclass[parskip=half,fontsize=11pt,ngerman]{scrlttr2}
\usepackage{babel,lipsum,txfonts}
\usepackage[left=3cm,right=2cm,bottom=3cm,top=2cm]{geometry}

\setkomavar{fromaddress}{Street}
\setkomavar{yourmail}{2013-01-10}
\setkomavar{subject}{Subject}

\begin{document}

\begin{letter}{Insert a name here}
\opening{Hi,}
\lipsum
\end{letter}

\end{document}
share|improve this question
1  
One solution could be the flowfram package. However, my preferred solution is witouth doubt insert \newgeometry after the last paragraph of the first page (this insert also the page break, \newpage or another page break is not needed) –  Fran Jul 31 '13 at 19:39
1  
@Fran flowfram doesn't work if the pagebreak is in the middle of a paragraph. –  StrongBad Aug 4 '13 at 16:53
    
While not a duplicate, this is a subset of: tex.stackexchange.com/questions/99103/… –  StrongBad Aug 4 '13 at 16:53
    
@DanielE.Shub, Pagebreak works in flowfram if text width is maintained, that is not the case in this question (and this explain why I prefer deal with geometry limitations). –  Fran Aug 4 '13 at 20:44

5 Answers 5

up vote 2 down vote accepted
+50

For the simple case of a one page letter or a page break between paragraphs all we need is

\usepackage{everyshi}
\AtNextShipout{\global\rightskip=-2.5cm\relax}

Using a modified version of David's magic can handle the case where the page breaks in the middle of a paragraph.

\makeatletter
\newlength{\textwidth@wide}
\setlength{\textwidth@wide}{\textwidth}
\addtolength{\textwidth@wide}{2.5cm}

\def\shp#1{%
\@tempcnta\z@
\loop
\advance\@tempcnta\@ne
\edef\pshape{\pshape 0pt #1 }
\ifnum\@tempcnta<\value{nlines@first}
\repeat
\advance\@tempcntb\value{nlines@first}
}

\def\reshape{%
    \@tempcntb\z@%
    \def\pshape{}
    \shp{\textwidth}\shp{\textwidth@wide}%
    \def\par{\ifhmode\\\fi\hspace*{\parindent}\ignorespaces}%
    \parshape\@tempcntb\pshape%
}
\makeatother

David was careful to put this magic into a group, however, I cannot get it to work in a group inside the scrlttr2 letter environment. This means that there might be lots of unexpected side effects. It will only be used inside the letter environment group so it might not be so bad. In order for the reshaping to work requires knowing how many lines are on the first page. We can use the lineno package to do that.

\usepackage[pagewise]{lineno}
\makeatletter
\newcounter{nlines@first}
\renewcommand{\@LN}[2]{\ifstrequal{#2}{0}{\stepcounter{nlines@first}}{}}
\def\LineNumber{}
\makeatother

We then just need to patch \opening to setup line numbering and reshaping.

\usepackage{etoolbox}
\apptocmd{\opening}{\linenumbers\reshape}{}{}

Putting it all together

\documentclass[ngerman]{scrlttr2}
\usepackage{babel}
\usepackage[left=3cm,right=4.5cm,bottom=3cm,top=2cm]{geometry}
\usepackage[nopar]{lipsum}
\setlength{\parindent}{1cm}

\usepackage{everyshi}
\AtNextShipout{\global\rightskip=-2.5cm\relax}

\usepackage[pagewise]{lineno}
\makeatletter
\newcounter{nlines@first}
\renewcommand{\@LN}[2]{\ifstrequal{#2}{0}{\stepcounter{nlines@first}}{}}
\def\LineNumber{}
\makeatother

\makeatletter
\newlength{\textwidth@wide}
\setlength{\textwidth@wide}{\textwidth}
\addtolength{\textwidth@wide}{2.5cm}

\def\shp#1{%
\@tempcnta\z@
\loop
\advance\@tempcnta\@ne
\edef\pshape{\pshape 0pt #1 }
\ifnum\@tempcnta<\value{nlines@first}
\repeat
\advance\@tempcntb\value{nlines@first}
}

\def\reshape{%
    \@tempcntb\z@%
    \def\pshape{}
    \shp{\textwidth}\shp{\textwidth@wide}%
    \def\par{\ifhmode\\\fi\hspace*{\parindent}\ignorespaces}%
    \parshape\@tempcntb\pshape%
}
\makeatother

\usepackage{etoolbox}
\apptocmd{\opening}{\linenumbers\reshape}{}{}

\setkomavar{fromaddress}{Street}
\setkomavar{yourmail}{2013-01-10}
\setkomavar{subject}{Subject}

\begin{document}
\begin{letter}{My Name}
\opening{Hi,}
\lipsum[1-2]\par\lipsum[1-3]\par\lipsum[1-3]\par\lipsum[1-3]
\end{letter}
\end{document}
share|improve this answer

If you are okay with manual fiddling you can use a combination of \rightskip and \parshape. The problem with \rightskip is that it will always act on the entire paragraph, so that the first lines on the second page would still obey the wrong margin, if they belong to a paragraph that started on the first page. \parshape can handle line by line, but you need to specify the number of lines by hand (or automatize it somehow.

\documentclass[parskip=half,fontsize=11pt,ngerman]{scrlttr2}
\usepackage{babel,lipsum}
\usepackage[left=3cm,right=2cm,bottom=3cm,top=2cm]{geometry}
\setkomavar{fromaddress}{Street}
\setkomavar{yourmail}{2013-01-10}
\setkomavar{subject}{Subject}

\setlength{\rightskip}{2.5cm}

\begin{document}

\begin{letter}{Insert a name here}
\opening{Hi,}
\lipsum[1]
\lipsum[2]
\setlength{\rightskip}{0pt}
\parshape 8
0cm \dimexpr\textwidth-2.5cm\relax
0cm \dimexpr\textwidth-2.5cm\relax
0cm \dimexpr\textwidth-2.5cm\relax
0cm \dimexpr\textwidth-2.5cm\relax
0cm \dimexpr\textwidth-2.5cm\relax
0cm \dimexpr\textwidth-2.5cm\relax
0cm \dimexpr\textwidth-2.5cm\relax
0cm \textwidth
\lipsum[3]

\lipsum[4]
\end{letter}

\end{document}

I do not claim that this is a perfect solution, but maybe it gives someone else here an idea to build on.


Edit to point out the problems with using only \rightskip

It would be much more elegant to just reset the right margin after the first page is done. However, you then run into problems, if the second page continues a paragraph that started on the first one:

\documentclass[parskip=half,fontsize=11pt,ngerman]{scrlttr2}
\usepackage{babel,lipsum}
\usepackage[left=3cm,right=2cm,bottom=3cm,top=2cm]{geometry}
\setkomavar{fromaddress}{Street}
\setkomavar{yourmail}{2013-01-10}
\setkomavar{subject}{Subject}

% reset \rightskip to zero when first page is done
\usepackage{everyshi}
\setlength{\rightskip}{2.5cm}
\AtNextShipout{\global\rightskip=0pt}

\begin{document}

\begin{letter}{Insert a name here}
\opening{Hi,}
\lipsum[1]
\lipsum[2]
\lipsum[3]
\lipsum[4]
\end{letter}

\end{document}

The above will result in a wrong indentation of the first lines on the second page.

share|improve this answer

I don't have a solution for the scrlttr2 class, although I think if you beat this answer with the letter class, you should be able to get it to work ...

Something like

\usepackage{everyshi}
\AtNextShipout{\global\rightskip=-2.5cm\relax}

can handle the simple cases of single page letters and letters where the first page break occur at a paragraph. As I see it the crux of the problem is to handle the case when the first page break occurs in the middle of a paragraph. David's answer handles simple cases by defining a parshape and keeping track of where you are. This solution works great if you start the parshape at the top of a page. The problem with letters is that there is variable amounts of "stuff" at the top of the page. This is especially true for the scrlttr2 class, which is why I cannot get it to work. Butchering David's code to handle a pages with variable numbers of lines (the first page of the letter class with your margins has 54 lines) and a variable width gives

\newlength{\textwidth@wide}
\setlength{\textwidth@wide}{\textwidth}
\addtolength{\textwidth@wide}{2.5cm}
\newcounter{nlines@first}
\setcounter{nlines@first}{54}

\def\shp#1{%
\@tempcnta\z@
\loop
\advance\@tempcnta\@ne
\edef\pshape{\pshape 0pt #1 }
\ifnum\@tempcnta<\value{nlines@first}
\repeat
\advance\@tempcntb\value{nlines@first}
}

\def\reshape{%
  \begingroup%
    \@tempcntb\z@%
    \def\pshape{}%
    \shp{\textwidth}\shp{\textwidth@wide}%
    \def\par{\ifhmode\\\fi\hspace*{\parindent}\ignorespaces}%
    \parshape\@tempcntb\pshape%
}

If you never used \opening then the solution is very easy

\usepackage{etoolbox}
\apptocmd{\letter}{\reshape}{}{}
\pretocmd{\endletter}{\endgraf\endgroup}{}{}

\opening does a whole lot more than just add the opening (e.g., it adds to and from addresses and a date). To handle this, we need to undo the change to the letter environment and modify \opening.

\pretocmd{\opening}{\endgraf\endgroup}{}{}
\apptocmd{\opening}{
  \ifx\toaddress\@empty
  \else
    \expandafter\count@lines\expandafter{\toaddress}%
    \addtocounter{nlines@first}{-2}%
  \fi
  \addtocounter{nlines@first}{-4}%
  \reshape%
}{}{}
\patchcmd{\opening}{{\raggedleft\@date\par}}{\addtocounter{nlines@first}{-2}{\raggedleft\@date\par}}{}{}
\patchcmd{\opening}{\thispagestyle{empty}}{\thispagestyle{empty}\addtocounter{nlines@first}{-4}\expandafter\count@lines\expandafter{\fromaddress}}{}{}

where we define the helper function

\newcommand{\count@lines}[1]{\@count@lines@#1\\@@@}
\long\def\@count@lines@ #1\\#2@@@{%
  \ifstrequal{#2}{}{}{%
    \addtocounter{nlines@first}{-1}%
    \@count@lines@#2@@@%
  }%
}

for counting the number of lines in the "to" and "from" addresses.

Putting it all together into a MWE

\documentclass{letter}
\usepackage[left=3cm,right=4.5cm,bottom=3cm,top=2cm]{geometry}
\usepackage[nopar]{lipsum}

\setlength{\parindent}{1cm}
\usepackage{everyshi}
\AtNextShipout{\global\rightskip=-2.5cm\relax}

\usepackage{etoolbox}
\makeatletter

\newlength{\textwidth@wide}
\setlength{\textwidth@wide}{\textwidth}
\addtolength{\textwidth@wide}{2.5cm}

\newcounter{nlines@first}
\setcounter{nlines@first}{54}

\def\shp#1{%
\@tempcnta\z@
\loop
\advance\@tempcnta\@ne
\edef\pshape{\pshape 0pt #1 }
\ifnum\@tempcnta<\value{nlines@first}
\repeat
\advance\@tempcntb\value{nlines@first}
}

\def\reshape{%
  \begingroup%
    \@tempcntb\z@%
    \def\pshape{}%
    \shp{\textwidth}\shp{\textwidth@wide}%
    \def\par{\ifhmode\\\fi\hspace*{\parindent}\ignorespaces}%
    \parshape\@tempcntb\pshape%
}

\pretocmd{\opening}{\endgraf\endgroup}{}{}
\apptocmd{\opening}{
  \ifx\toaddress\@empty
  \else
    \expandafter\count@lines\expandafter{\toaddress}%
    \addtocounter{nlines@first}{-2}%
  \fi
  \addtocounter{nlines@first}{-4}%
  \reshape%
}{}{}
\patchcmd{\opening}{{\raggedleft\@date\par}}{\addtocounter{nlines@first}{-2}{\raggedleft\@date\par}}{}{}
\patchcmd{\opening}{\thispagestyle{empty}}{\thispagestyle{empty}\addtocounter{nlines@first}{-4}\expandafter\count@lines\expandafter{\fromaddress}}{}{}

\newcommand{\count@lines}[1]{\@count@lines@#1\\@@@}
\long\def\@count@lines@ #1\\#2@@@{%
  \ifstrequal{#2}{}{}{%
    \addtocounter{nlines@first}{-1}%
    \@count@lines@#2@@@%
  }%
}
\makeatother

\apptocmd{\letter}{\reshape}{}{}
\pretocmd{\endletter}{\endgraf\endgroup}{}{}

\address{W\\X\\Y\\Z}
\begin{document}
\begin{letter}{A\\B\\C\\D\\E\\F}
\opening{Hi,}
\lipsum[1-3]\par\lipsum[1-3]\par\lipsum[1-3]\par\lipsum[1-3]
\end{letter}
\end{document}

enter image description here

The problem with the scrlttr2 class is that \opening is more complicated, but I think if you find the height of everything that is shipped out before the letter begins, you could make this approach work. If not, you should be able to create a less general company letter head class around this approach.

share|improve this answer
    
Or is it maybe possible to re-typeset the part of the paragraph that did not fit on the first page? It must be in some box that we should be able to modify? Overall I see that this is getting more complicated than expected... –  alexurba Aug 9 '13 at 19:24
    
@alexurba from my understanding keeping track of where on the page you are and typeset with the correct line width to start with is a better approach than trying and pull stuff back from TeX's stomach and redo the line breaking (although with LuaTeX you might be able to re-break lines). –  StrongBad Aug 9 '13 at 19:42

You can use the afterpage package which allows you to execute a command when a page break occurs.
For you specific problem use it as follows:

\begin{document}

\rightskip=2.5cm
\afterpage{\global\rightskip=0.0cm}

\begin{letter}{Insert a name here}
\opening{Hi,}
\lipsum
\end{letter}

\end{document}
share|improve this answer
    
Again, this one doesn't work if the page break occurs in the middle of a paragraph. –  StrongBad Aug 9 '13 at 18:42
    
@DanielE.Shub: you're right... –  Kyle_the_hacker Aug 9 '13 at 19:38

It is depreciated, but it will work for you (since you don't use memoir), the changepage package.

Simply enclose the content of the first page with \begin{adjustwidth}{<leftmargin>}{<rightmargin>} and \end{adjustwidth}, and complete with the additional margin you want on left and on right.
For your specific problem:

\begin{adjustwidth}{}{+2.5cm}
    \lipsum
\end{adjustwidth}

Update: If you don't know where the page ends (which seems to be the case), you can use \changepage{<text height>}{<text width>}{<even-side margin>}{<odd-side margin>}{<column sep.>}{<topmargin>}{<headheight>}{<headsep>}{<footskip>} and add margin or change text limits on the page the command appear; the margins and limits will be reset to document values on the next page.
For your specific problem it is simply:

\changepage{}{-2.5cm}{}{}{}{}{}{}{}
share|improve this answer
    
This requires knowing where the pagebreak will be, which isn't possible. –  Sean Allred Aug 9 '13 at 16:10
    
@SeanAllred: Ok, I didn't unterstand it like this... –  Kyle_the_hacker Aug 9 '13 at 16:54
    
@Kyle_the_hacker this doesn't work if the page break occurs in the middle of a paragraph. –  StrongBad Aug 9 '13 at 17:38
    
@DanielE.Shub: you're right... –  Kyle_the_hacker Aug 9 '13 at 17:46

Your Answer

 
discard

By posting your answer, you agree to the privacy policy and terms of service.

Not the answer you're looking for? Browse other questions tagged or ask your own question.