2

I am creating a user story map with tikz but I have problems with positioning.

With

\documentclass[tikz,border=5pt]{standalone}

\usetikzlibrary{positioning}
\usetikzlibrary{arrows}

\begin{document}

\tikzset{
    box/.style  = {draw, text width=4cm, font=\sffamily, rectangle, rounded corners=2pt, thin, align=center, fill=white, fill opacity=0.8, text opacity=1},
    double/.style = {text width=8cm},
    goal/.style = {box, fill=red!20},
    activity/.style = {box, fill=blue!20},
    task/.style = {box, fill=yellow},
}

\begin{tikzpicture}[node distance=0.25cm]

\draw [->] (-1.5,0.5) -- (15,0.5) node [midway, above] {time};

\node [goal, double] (A_G1) {Goal 1};

\node [activity, below left=of A_G1] (A_A1) {Activity 1};
\node [task, below=of A_A1] (A_T11) {Task 1};
\node [task, below=of A_T11] (A_T12) {Task 2};
\node [task, below=of A_T12] (A_T13) {Task 3};
\node [task, below=of A_T13] (A_T14) {Task 4};

\node [activity, right=of A_A1] (A_A2) {Activity 2};
\node [task, below=of A_A2] (A_T21) {Task 1};
\node [task, below=of A_T21] (A_T22) {Task 2};
\node [task, below=of A_T22] (A_T23) {Task 3};
\node [task, below=of A_T23] (A_T24) {Task 4};

\node [goal, double, right=of A_G1] (B_G2) {Goal 2};

\node [activity, below=of B_G2] (A_A1) {Activity 1};
\node [task, below=of A_A1] (A_T11) {Task 1};
\node [task, below=of A_T11] (A_T12) {Task 2};
\node [task, below=of A_T12] (A_T13) {Task 3};
\node [task, below=of A_T13] (A_T14) {Task 4};

\node [activity, right=of A_A1] (A_A2) {Activity 2};
\node [task, below=of A_A2] (A_T21) {Task 1};
\node [task, below=of A_T21] (A_T22) {Task 2};
\node [task, below=of A_T22] (A_T23) {Task 3};
\node [task, below=of A_T23] (A_T24) {Task 4};
\end{tikzpicture}

\end{document}

I produce

enter image description here

In the first goal column I have tried using below left= and in the second goal column I have tried using below=. With below_left= it places the element left below of the other element and with just below= it places the element center below the other element.

I want the left borders to align each other just like

enter image description here

6

Here's an alternative solution with forest. Less is more!

Output

figure 1

Code

\documentclass[tikz,border=10pt]{standalone}
\usepackage{forest}
\usetikzlibrary{arrows.meta,shapes,positioning,trees}

\newcommand{\innerxsep}{2mm}

\tikzset{
    box/.style  = {draw, text width=4cm, inner xsep=\innerxsep, font=\sffamily, rectangle, rounded corners=2pt, thin, align=center, fill=white, fill opacity=0.8, text opacity=1},
    double/.style = {text width=8cm+\innerxsep*2+.25cm},
    goal/.style = {box, fill=red!20, double},
    activity/.style = {box, fill=blue!20},
    task/.style = {box, fill=yellow},
}

\begin{document}
\begin{forest} for tree={
    growth parent anchor=south,
    parent anchor=south,
    child anchor=north,
    edge path={none}, 
    l sep=.25cm,
}   
%
[Time, name=time
    [Goal 1, goal, name=agoal
        [Activity 1, activity
            [Task 1, task
            [Task 2, task
            [Task 2, task
            [Task 4, task] ] ] ] ]
        [Activity 1, activity
            [Task 1, task
            [Task 2, task
            [Task 2, task
            [Task 4, task] ] ] ] ] ]
    [Goal 2, goal, name=bgoal
        [Activity 1, activity
            [Task 1, task
            [Task 2, task
            [Task 2, task
            [Task 4, task] ] ] ] ]
        [Activity 1, activity
            [Task 1, task
            [Task 2, task
            [Task 2, task
            [Task 4, task] ] ] ] ] ] ]
%           
\draw [->] (agoal.north west|-time.south) -- (bgoal.north east|-time.south);
\end{forest}
\end{document}
  • Is it possible to also create a horizontal line running from far left to far right separating goals from activites and activities from tasks? – Jamgreen Jun 12 '15 at 15:42
  • @Jamgreen Yes of course. Do you want more space between those or the current space is ok? – Alenanno Jun 12 '15 at 15:45
  • The current space is fine :-D – Jamgreen Jun 12 '15 at 15:54
  • @Jamgreen Like this? – Alenanno Jun 12 '15 at 15:59
  • yes exactly. but actually I also need it between some task.. like this 3.bp.blogspot.com/-jySCPZkngcs/T2DrcIrEscI/AAAAAAAABw4/…. I really appreciate your help. It's so much better than my own try :-D – Jamgreen Jun 12 '15 at 16:11
3

Will this do? (I sort of centered things.)

Normally when you leave off the anchor point it defaults to .center but in this case is seems to grab the nearest anchor in the same direction. Note, I also increased the space between Goal 1 and Goal 2 to keep the nodes from overlapping. Finally, I used the anchors of Goal 1 and Goal 2 to define the timeline above.

tikz table

\documentclass[tikz,border=5pt]{standalone}

\usetikzlibrary{positioning,arrows,calc}


\begin{document}

\tikzset{
    box/.style  = {draw, text width=4cm, font=\sffamily, rectangle, rounded corners=2pt, thin, align=center, fill=white, fill opacity=0.8, text opacity=1},
    double/.style = {text width=8cm},
    goal/.style = {box, fill=red!20},
    activity/.style = {box, fill=blue!20},
    task/.style = {box, fill=yellow},
}

\begin{tikzpicture}[node distance=0.25cm]

\node [goal, double] (A_G1) {Goal 1};

\node [activity, below left=of A_G1.south] (A_A1) {Activity 1};
\node [task, below=of A_A1] (A_T11) {Task 1};
\node [task, below=of A_T11] (A_T12) {Task 2};
\node [task, below=of A_T12] (A_T13) {Task 3};
\node [task, below=of A_T13] (A_T14) {Task 4};

\node [activity, right=of A_A1] (A_A2) {Activity 2};
\node [task, below=of A_A2] (A_T21) {Task 1};
\node [task, below=of A_T21] (A_T22) {Task 2};
\node [task, below=of A_T22] (A_T23) {Task 3};
\node [task, below=of A_T23] (A_T24) {Task 4};

\node [goal, double, right=3em of A_G1] (B_G2) {Goal 2};

\node [activity, below left=of B_G2.south] (A_A1) {Activity 1};
\node [task, below=of A_A1] (A_T11) {Task 1};
\node [task, below=of A_T11] (A_T12) {Task 2};
\node [task, below=of A_T12] (A_T13) {Task 3};
\node [task, below=of A_T13] (A_T14) {Task 4};

\node [activity, right=of A_A1] (A_A2) {Activity 2};
\node [task, below=of A_A2] (A_T21) {Task 1};
\node [task, below=of A_T21] (A_T22) {Task 2};
\node [task, below=of A_T22] (A_T23) {Task 3};
\node [task, below=of A_T23] (A_T24) {Task 4};

\draw [->] ($(A_G1.north west) + (0,0.5)$) -- ($(B_G2.north east) + (0,0.5)$) node [midway, above] {time};
\end{tikzpicture}

\end{document}
1

Instead of a new solution I'll try to explain what's wrong with yours.

When using positioning library, any positioning option means fixing two anchor points, one at reference node and the second on new node.

\node [activity, below left=of A_G1] (A_A1) {Activity 1};

means:

  1. select lower left corner of A_G1 (A_G1.south west)
  2. select upper right corner of A_A1 (A_A1.north east)
  3. Place A_A1 selected anchor at a distance of .25cm from A_G1 selected anchor. This distance will be measured going to the left and down from A_G1 selected anchor.

A similar procedure will be done for any other option. In following figure, the distance between respective anchors (south - north, east - west, south east - north west) is always .25cm.

enter image description here

\documentclass[tikz,border=2mm]{standalone}
\usetikzlibrary{positioning}
\tikzset{
    box/.style  = {draw, text width=4cm, font=\sffamily, rectangle, 
                   rounded corners=2pt, thin, align=center, fill=white, 
                   fill opacity=0.8, text opacity=1},
    double/.style = {text width=8cm},
    goal/.style = {box, fill=red!20},
    activity/.style = {box, fill=blue!20},
    task/.style = {box, fill=yellow},
}
\begin{tikzpicture}[node distance=0.25cm]
\node [goal, double] (A_G1) {Goal 1};

\foreach \i in {left, below left, below, below right, right, above right, above, above left}
\node [activity, \i=of A_G1] (A_A1) {\i};
\end{tikzpicture}
\end{document}

With this example I hope you can understand why below left moved Activity 1 to the left of Goal 1, while below centered Activity 1 below Goal 2. And why, Activity 1 below Goal 2 is not horizontally aligned with Activity 1 below Goal 1.

But although positioning options select default anchors, you can force another selection for the new node:

\node [activity, below left=of A_G1, anchor=north west] (A_A1) {Activity 11};

will place A_A1.north west anchor at position 0.25cm below left of A_A1.south west

enter image description here

A second mistake in your code was fixing nodes measures with text width. Although double nodes have text width=8cm, they are not long enough to cover two activity columns because you didn't considered node distance between columns and inner xsep between nodes contents and nodes borders. Alenanno's solution already shows you how to solve this point with

double/.style = {text width=8cm+\innerxsep*2+.25cm},

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

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