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.

circuitikz has an op amp component type with two inputs, output, and up and down ports, usually used for power supply rails. There's also a buffer component type (which I think is provided by tikz itself, not the circuitikz library) which has one input and one output and no vertical ports.

I'm looking for a buffer/amp with one input, one output, and the vertical ports, for use as control pins. My use case is a track-and-hold (aka sample-and-hold) amplifier symbol, but a tri-state buffers are also very common and require a control input.

circuit exemplifying SHA

Ok, that figure uses a two-input SHA. But I'm sure you can imagine what the one-input version should look like (basically, I'm trying to make a single symbol that hides all that complexity, for a high-level block diagram).

tristate buffer symbols

Does tikz or one of its extension libraries provide such a beast? If not, how can I properly align a vertical wire with the edge of the buffer?

share|improve this question
    
Welcome to TeX.sx! –  lockstep Dec 12 '12 at 23:12
add comment

1 Answer

up vote 3 down vote accepted

Declaring new node shapes is a bit of a pain, but you get used to it. Here are two new circuit shapes tri state buffer active low and tri state buffer active high that behave like buffer gate and not gate, but offer a new anchor control. This allows you to draw this:

using this:

\begin{tikzpicture}[circuit logic US, on grid]
\node (i) {x};
\node (buf) [right of=i, tri state buffer active high] {};
\node (ctrl) [above=of buf] {c};
\node (o) [right of=buf] {y};

\draw (i) -- (buf.input)
    (ctrl) -- (buf.control)
    (buf.output) -- (o);
\end{tikzpicture}%

\begin{tikzpicture}[circuit logic US, on grid]
\node (i) {x};
\node (buf) [right of=i, tri state buffer active low] {};
\node (ctrl) [above=1 of buf] {c};
\node (o) [right of=buf] {y};

\draw (i) -- (buf.input)
    (ctrl) -- (buf.control)
    (buf.output) -- (o);
\end{tikzpicture}%

Full code:

\documentclass[border=5mm]{standalone}
\usepackage{tikz}
\usetikzlibrary{positioning, circuits.logic.US}

\makeatletter%
%
%
\pgfdeclareshape{tri state buffer active high}{
    \inheritsavedanchors[from=buffer gate US]
    \inheritanchorborder[from=buffer gate US]
    \inheritanchor[from=buffer gate US]{center}
    \inheritanchor[from=buffer gate US]{base}
    \inheritanchor[from=buffer gate US]{base west}
    \inheritanchor[from=buffer gate US]{base east}
    \inheritanchor[from=buffer gate US]{mid}
    \inheritanchor[from=buffer gate US]{mid west}
    \inheritanchor[from=buffer gate US]{mid east}
    \inheritanchor[from=buffer gate US]{north}
    \inheritanchor[from=buffer gate US]{north west}
    \inheritanchor[from=buffer gate US]{north east} 
    \inheritanchor[from=buffer gate US]{south}
    \inheritanchor[from=buffer gate US]{south east}
    \inheritanchor[from=buffer gate US]{south west}
    \inheritanchor[from=buffer gate US]{west}
    \inheritanchor[from=buffer gate US]{east}
    \inheritanchor[from=buffer gate US]{input}
    \inheritanchor[from=buffer gate US]{output}
    \anchor{control}{%
        \dimensions
        \pgfpointintersectionoflines{\csname pgf@anchor@buffer gate US@north west\endcsname}{\tipanchor}{\centerpoint}{\centerpoint\advance\pgf@y1pt}%
    }%
    \backgroundpath{%
        \dimensions%
        \pgf@xc\halfwidth%
        \pgf@yc\halfheight%
        \advance\pgf@xc-\outerxsep%
        \advance\pgf@yc-\outerysep%
        {%
            \pgftransformshift{\centerpoint}%
            \pgfpathmoveto{\tipanchor}%
            \pgfpathlineto{\pgfqpoint{-.833333\pgf@xc}{1.166666\pgf@yc}}%
            \pgfpathlineto{\pgfqpoint{-.833333\pgf@xc}{-1.166666\pgf@yc}}%
            \pgfpathclose%
            %
            % Draw the input.
            %
            \expandafter\ifx\expandafter\pgf@lib@sh@itext\csname input-1\endcsname%
                {%
                    \pgfpathcircle{%
                        \pgf@xa\halfside%
                        \pgf@x-.833333\pgf@xa%
                        \advance\pgf@x-.5\pgflinewidth%
                        \advance\pgf@x-\invertedradius%
                        \pgf@y0pt%
                    }{+\invertedradius}%                
                }%
            \fi%                
        }%
    }%
}

\pgfdeclareshape{tri state buffer active low}{
    \inheritsavedanchors[from=buffer gate US]
    \inheritanchorborder[from=buffer gate US]
    \inheritanchor[from=buffer gate US]{center}
    \inheritanchor[from=buffer gate US]{base}
    \inheritanchor[from=buffer gate US]{base west}
    \inheritanchor[from=buffer gate US]{base east}
    \inheritanchor[from=buffer gate US]{mid}
    \inheritanchor[from=buffer gate US]{mid west}
    \inheritanchor[from=buffer gate US]{mid east}
    \inheritanchor[from=buffer gate US]{north}
    \inheritanchor[from=buffer gate US]{north west}
    \inheritanchor[from=buffer gate US]{north east} 
    \inheritanchor[from=buffer gate US]{south}
    \inheritanchor[from=buffer gate US]{south east}
    \inheritanchor[from=buffer gate US]{south west}
    \inheritanchor[from=buffer gate US]{west}
    \inheritanchor[from=buffer gate US]{east}
    \inheritanchor[from=buffer gate US]{input}
    \inheritanchor[from=buffer gate US]{output}
    \anchor{control}{%
        \dimensions
        \tipanchor%
        \pgf@xa\pgf@x%  
        \pgf@ya\pgf@y%
        \csname pgf@anchor@buffer gate US@north west\endcsname%
        \advance\pgf@xa-\pgf@x%
        \advance\pgf@ya-\pgf@y%
        \pgfpointintersectionoflines{\csname pgf@anchor@buffer gate US@north west\endcsname}{\tipanchor}{\centerpoint}{\centerpoint\advance\pgf@y2pt}%
        \pgfmathparse{sqrt(\pgf@xa^2+\pgf@ya^2)/\pgf@xa*\invertedradius}
        \advance\pgf@y\pgfmathresult pt
        \advance\pgf@y\invertedradius
    }%
    \backgroundpath{%
        \dimensions%
        \pgf@xc\halfwidth%
        \pgf@yc\halfheight%
        \advance\pgf@xc-\outerxsep%
        \advance\pgf@yc-\outerysep%
        {%
            \pgftransformshift{\centerpoint}%
            \pgfpathmoveto{\tipanchor}%
            \pgfpathlineto{\pgfqpoint{-.833333\pgf@xc}{1.166666\pgf@yc}}%
            \pgfpathlineto{\pgfqpoint{-.833333\pgf@xc}{-1.166666\pgf@yc}}%
            \pgfpathclose%
            %
            % Draw the input.
            %
            \pgfpathcircle{%
                \tipanchor%
                \pgf@xa\pgf@x%  
                \pgf@ya\pgf@y%
                \csname pgf@anchor@buffer gate US@north west\endcsname%
                \advance\pgf@xa-\pgf@x%
                \advance\pgf@ya-\pgf@y%
                \pgfpointintersectionoflines{\csname pgf@anchor@buffer gate US@north west\endcsname}{\tipanchor}{\centerpoint}{\centerpoint\advance\pgf@y1pt}%
                \pgfmathparse{sqrt(\pgf@xa^2+\pgf@ya^2)/\pgf@xa*\invertedradius}
        \advance\pgf@y\pgfmathresult pt
                }{+\invertedradius}%
            \expandafter\ifx\expandafter\pgf@lib@sh@itext\csname input-1\endcsname%
                {%
                    \pgfpathcircle{%
                        \pgf@xa\halfside%
                        \pgf@x-.833333\pgf@xa%
                        \advance\pgf@x-.5\pgflinewidth%
                        \advance\pgf@x-\invertedradius%
                        \pgf@y0pt%
                    }{+\invertedradius}%                
                }%
            \fi%                
        }%
    }%
}

\tikzset{
    circuit declare symbol=tri state buffer active low,
    set tri state buffer active low graphic={draw, shape=tri state buffer active low, minimum size=5mm},
    circuit declare symbol=tri state buffer active high,
    set tri state buffer active high graphic={draw,shape=tri state buffer active high,minimum size=5mm}
}

\begin{document}

%
\begin{tikzpicture}[circuit logic US, on grid]
\node (i) {x};
\node (buf) [right of=i, tri state buffer active high] {};
\node (ctrl) [above=of buf] {c};
\node (o) [right of=buf] {y};

\draw (i) -- (buf.input)
    (ctrl) -- (buf.control)
    (buf.output) -- (o);
\end{tikzpicture}%

\begin{tikzpicture}[circuit logic US, on grid]
\node (i) {x};
\node (buf) [right of=i, tri state buffer active low] {};
\node (ctrl) [above=1 of buf] {c};
\node (o) [right of=buf] {y};

\draw (i) -- (buf.input)
    (ctrl) -- (buf.control)
    (buf.output) -- (o);
\end{tikzpicture}%
\end{document}
share|improve this answer
    
That's amazing. –  Ben Voigt Dec 13 '12 at 17:35
    
@BenVoigt: Does this answer your question, or are there any points left uncovered? –  Jake Dec 20 '12 at 10:53
    
I found it very useful. I wanted to wait a bit to see if someone would recommend a library that already contained it, but no one has so I'm accepting your answer. –  Ben Voigt Dec 20 '12 at 14:37
add comment

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.