# tikz-timing with non-linear rise time?

Is there a good way to draw signals in tikz-timing with a non-linear rise time? I didn't see any direct means. I have a very manual solution (drawing bezier curves between tikz-timing anchors), but it is tedious and I'm hoping that someone more familiar with tikz / tikz-timing can point me to a more general / automated way of doing this:

\documentclass{article}

\usepackage{color}
\usepackage{
tikz,
tikz-timing,
}
\usetikzlibrary{positioning}
\pagenumbering{gobble}

\begin{document}
\centering
\begin{tikztimingtable}[timing/wscale=3.0,timing/slope=.3]
SCL & HHHHH
L N(cl1){.5S} {.5S} [white]{0H}[black] N(ch1){.5H}{.5H}
L N(cl2){.5S} {.5S} [white]{0H}[black] N(ch2){.5H}{.5H}
L N(cl3){.5S} {.5S} [white]{0H}[black] N(ch3){.5H}{.5H}
\\
SDA & HHHHL
{.1L} N(dl1){.5S} {.5S} [white]{0H}[black] N(dh1){.5H}{.5H} {.9H}
{.1H} L {.9L}
{.1L} N(dl2){.5S} {.5S} [white]{0H}[black] N(dh2){.5H}{.5H} {.9H}
\\
& \\
\extracode
% Draw rising curves
\begin{scope}
[color=red]
\draw (cl1.south) ..
controls
([xshift=.2em,yshift=.9em] cl1) and
([xshift=-.2em,yshift=-.1em] ch1) ..
(ch1.north);
\draw (cl2.south) ..
controls
([xshift=.2em,yshift=.9em] cl2) and
([xshift=-.2em,yshift=-.1em] ch2) ..
(ch2.north);
\draw (cl3.south) ..
controls
([xshift=.2em,yshift=.9em] cl3) and
([xshift=-.2em,yshift=-.1em] ch3) ..
(ch3.north);
\draw (dl1.south) ..
controls
([xshift=.2em,yshift=.9em] dl1) and
([xshift=-.2em,yshift=-.1em] dh1) ..
(dh1.north);
\draw (dl2.south) ..
controls
([xshift=.2em,yshift=.9em] dl2) and
([xshift=-.2em,yshift=-.1em] dh2) ..
(dh2.north);
\end{scope}

\begin{pgfonlayer}{background}
\begin{scope}[semithick,dashed]
\vertlines[color=red]{12}
\vertlines[color=gray]{15,21,...,\twidth}
\end{scope}
\end{pgfonlayer}

\begin{scope}
[font=\bf\sffamily,shift={(-3.0em,0)},anchor=east,color=blue]
\node at (  0,  -0.5) {Traditional};
\end{scope}

\begin{scope}
[font=\bf\sffamily,shift={(-1,3.5)},anchor=north,align=center]
\node at (13, 0) {Start};
\node at (19, 0) {1};
\node at (25, 0) {0};
\node at (31, 0) {ACK};
\end{scope}
\end{tikztimingtable}

\end{document}


Here is one possibility. I didn't define all possible transitions, only the ones used in your example here. If more transitions are needed, you should be able to use the code and explanation here to create them on your own.

After looking through the package code to see how things were done, I decided to add a new timing character, Y, to serve as this non-linear rise active state:

\tikztimingchar{Y}{++(0,\height)}{-- ++(#1,0)}


This defines the character Y to be identical to H, a high or active state: beginning at the current baseline, go up \height and draw 1 unit to the right from there. So, what makes it different from using the H character then? That comes in the definition of the transitions.

We need a definition of the transition for each combination of timing characters used in the diagram. For this use case, we need only LY (low non-linear rise to high), YL (high to low), and YH (stay high).

The LY transition is the most important here, since it's where the non-linear rise is set up:

\tikztimingdef{LY}{
to[out=85,in=180]  ++(0.5*#1, \height)
-- ++(0.5*#1, 0)
}


This draws the curve with specified in and out angles from the base line to a point one half of a unit width to the right and up \height. The second line of the definition finishes the last half of the unit width with a straight line.

After this, we just need to cover the falling (YL) and held (YH) transitions, which are very similar to the standard variants (HL and HH, respectively):

\tikztimingdef{YL}{
-- ++(\slope,-\height)
\tikztiminguse{YH}{#1-\slope}
}
\tikztimingdef{YH}{
-- ++(#1,0)
}


With these definitions made, we can use the Y character any time we want the non-linear slow rise for the signal. A warning message will be issued if a transition that hasn't been defined is used in the code. So the first line of your table becomes

SCL & HHHHHLYLYLY \\


Here's the complete code and output. I've added some formatting just to show that most things will work as expected:

\documentclass{standalone}

\usepackage{tikz-timing}
\usetikzlibrary{positioning}
\pagenumbering{gobble}

\tikztimingchar{Y}{++(0,\height)}{-- ++(#1,0)}
\tikztimingdef{LY}{
to[out=85,in=180]  ++(0.5*#1, \height)
-- ++(0.5*#1, 0)
}
\tikztimingdef{YL}{
-- ++(\slope,-\height)
\tikztiminguse{YH}{#1-\slope}
}
\tikztimingdef{YH}{
-- ++(#1,0)
}

\begin{document}
\centering
\begin{tikztimingtable}[timing/wscale=3.0,timing/slope=.3]
SCL & HHHHHLYLYLY \\
SDA & HHHHLYHLLYH \\
SCL formatted & HHHHHL;Y[blue];L;Y[green];L;Y[cyan] \\
SDA formatted & HHHHL;Y[red];HLL;Y[red];H \\
& \\
\extracode
\begin{pgfonlayer}{background}
\begin{scope}[semithick,dashed]
\vertlines[color=red]{12}
\vertlines[color=gray]{15,21,...,\twidth}
\end{scope}
\end{pgfonlayer}

\begin{scope}
[font=\bf\sffamily,shift={(-3.0em,0)},anchor=east,color=blue]
\node at (  0,  -0.5) {Traditional};
\end{scope}

\begin{scope}
[font=\bf\sffamily,shift={(-1,3.5)},anchor=north,align=center]
\node at (13, 0) {Start};
\node at (19, 0) {1};
\node at (25, 0) {0};
\node at (31, 0) {ACK};
\end{scope}
\end{tikztimingtable}

\end{document}


• That was surprisingly simple. I surrendered to brute force a while ago, but hopefully this helps someone else in the future. Thanks for answering this one from the archives :). – Pat Jan 16 '15 at 10:03
• @Pat you're welcome! Most of the built-in formatting should work just fine (see the edit), but if you end up using this and run into problems, feel free to leave a comment here. I can take a look at it. – Paul Gessler Jan 16 '15 at 12:50