
Quero criar um gráfico como o seguinte:
Abaixo está meu código:
\documentclass[11pt]{article}
\usepackage{tikz}
\usetikzlibrary{arrows}
\newcommand{\psign}{+}
\newcommand{\ppsign}{++}
\begin{document}
\noindent
\begin{tikzpicture}
\tikzstyle{my node} = [draw,rectangle,minimum width=2.2cm,minimum height=0.8cm, node distance=2cm]
%\draw[black!20] (-0.5cm,-0.5cm) grid (14cm,7cm);
\node [my node] (A) {GDI DDI};
\node [my node] (B) [above of=A] {GDI};
\begin{scope}[xshift=3cm]
\node (C) {Graphics Driver};
\node [my node] (D) [above of=C] {GDI\psign Flat API};
\node [my node] (E) [above of=D] {GDI\psign\ C\ppsign API};
\end{scope}
\begin{scope}[xshift=6cm]
\node [my node] (F) {DX DDI};
\node [my node] (G) [above of=F] {DXGI};
\node [my node] (H) [above of=G] {Direct3D};
\node [my node] (I) [above of=H,minimum width=4cm,right=0pt] {Direct2D};
\node [my node] (J) [right of=I,right=0pt,node distance=3cm] {DirectWrite};
\node [my node] (K) [right of=F, node distance=4cm] {Software Rasterizer};
\end{scope}
\begin{scope}[->,>=triangle 45,semithick]
\path (B) edge (A);
\path (E) edge (D);
\path (H) edge (G);
\path (G) edge (F);
\path (J) edge (I);
\end{scope}
\draw [dashed] (-1.25,1cm) -- (14,1cm);
\end{tikzpicture}
\end{document}
Responder1
\documentclass[11pt]{article}
\usepackage{tikz,xcolor}
\usetikzlibrary{arrows,calc,fit,backgrounds}
\definecolor{fcolor}{HTML}{F1F1F1}
\newcommand{\psign}{+}
\newcommand{\ppsign}{++}
\begin{document}
\noindent
\begin{tikzpicture}
\tikzstyle{my node} = [draw,rectangle,minimum width=2.2cm,minimum height=0.8cm, node distance=2cm]
%\draw[black!20] (-0.5cm,-0.5cm) grid (14cm,7cm);
\node [my node] (A) {GDI DDI};
\node [my node] (B) [above of=A] {GDI};
\begin{scope}[xshift=3cm]
\node (C) {Graphics Driver};
\node [my node] (D) [above of=C] {GDI\psign Flat API};
\node [my node] (E) [above of=D] {GDI\psign\ C\ppsign API};
\end{scope}
\begin{scope}[xshift=6cm]
\node [my node] (F) {DX DDI};
\node [my node] (G) [fill=white,above of=F] {DXGI};
\node [my node] (H) [fill=white,above of=G] {Direct3D};
\node [my node] (I) [fill=white,above of=H,minimum width=4.5cm,right=0pt] {Direct2D};
\node [my node] (J) [fill=white,right of=I,right=0pt,node distance=3.5cm] {DirectWrite};
\node [my node] (K) [fill=white,right of=G, node distance=4cm] {Software Rasterizer};
\end{scope}
\begin{scope}[->,>=triangle 45,semithick]
\path (B) edge (A);
\path (E) edge (D);
\path (H) edge (G);
\path (G) edge (F);
\path (J) edge (I);
\path (I.south-|K) edge (K);
\path (I.south-|{$(H.north)!.5!(H.north east)$}) edge ($(H.north)!.5!(H.north east)$);
\end{scope}
\begin{scope}[on background layer]
\node[rectangle,fill=fcolor,fit=(G.south west) (J.north east)] {};
\end{scope}
\draw [dashed] (-1.25,1cm) -- (14,1cm);
\end{tikzpicture}
\end{document}
Primeiro, corrigi o Software Rasterizer
posicionamento do nó right of=G
:
\node [my node] (K) [right of=G, node distance=4cm] {Software Rasterizer};
Então, para as duas conexões de seta restantes, adicionei ao seu edge
s estas duas linhas:
\path (I.south-|K) edge (K);
\path (I.south-|{$(H.north)!.5!(H.north east)$}) edge ($(H.north)!.5!(H.north east)$);
Aqui (I.south-|K)
está o ponto no Direct2D
nó diretamente acima do centro do Software Rasterizer
nó. A mesma ideia para (I.south-|{$(H.north)!.5!(H.north east)$})
, mas um pouco complicada. Agora é o ponto no Direct2D
nó diretamente acima do ponto médio entre o norte e o nordeste do Direct3D
nó.
Os cinco blocos destacados podem ser obtidos pela fit
biblioteca, mas desta vez dentro de um escopo ( on background layer
) para evitar desenhar os nós duas vezes. Selecionamos quaisquer dois nós mais externos, como G
e, J
e especificamos seus cantos mais externos (G.south west)
e (J.north east)
, respectivamente.
Responder2
Isso faz o que você está procurando. Observe que fit
desenha na parte superior, se precisar de uma cor completa por baixo, pode ser necessário desenhar esses nós duas vezes (uma vez para obter os nós para o fit
cálculo e uma vez para desenhá-los novamente na área de ajuste, você pode simplesmente armazenar o desenhar código em uma macro e executar essa macro duas vezes).
\documentclass[11pt]{article}
\usepackage{tikz}
\usetikzlibrary{arrows,calc}
\usetikzlibrary{positioning,fit}
\newcommand{\psign}{+}
\newcommand{\ppsign}{++}
\begin{document}
\noindent
\begin{tikzpicture}
\tikzstyle{my node} = [draw,rectangle,minimum width=2.2cm,minimum height=0.8cm, node distance=2cm]
%\draw[black!20] (-0.5cm,-0.5cm) grid (14cm,7cm);
\node [my node] (A) {GDI DDI};
\node [my node] (B) [above of=A] {GDI};
\begin{scope}[xshift=3cm]
\node (C) {Graphics Driver};
\node [my node] (D) [above of=C] {GDI\psign Flat API};
\node [my node] (E) [above of=D] {GDI\psign\ C\ppsign API};
\end{scope}
\begin{scope}[xshift=6cm]
\node [my node] (F) {DX DDI};
\node [my node] (G) [above of=F] {DXGI};
\node [my node] (H) [above of=G] {Direct3D};
\node [my node] (I) [above of=H,minimum width=4cm,right=0pt] {Direct2D};
\node [my node] (J) [right of=I,right=0pt,node distance=3cm] {DirectWrite};
\node [my node] (K) [right of=G, node distance=4cm] {Software Rasterizer};
\end{scope}
\begin{scope}[ transform canvas={xshift=1cm},
->,>=triangle 45,semithick]
\draw (I) -- (I |- K.north);
\end{scope}
\begin{scope}[ transform canvas={xshift=-4em},
->,>=triangle 45,semithick]
\draw (I) -- (I |- H.north);
\end{scope}
\begin{scope}[->,>=triangle 45,semithick]
\path (B) edge (A);
\path (E) edge (D);
\path (H) edge (G);
\path (G) edge (F);
\path (J) edge (I);
\end{scope}
\draw [dashed] (-1.25,1cm) -- (14,1cm);
\node [fill=gray,opacity=0.2,dotted,fit = (H) (I) (J) (K) ] {};
\end{tikzpicture}
\end{document}
Presumo que você consiga descobrir como adicionar a legenda acima da área cinza.
Responder3
Soluções @daleif e @ AboAmmar ligeiramente modificadas e simplificadas (me parecem quase iguais :-)):
\documentclass[11pt, border=1mm,
tikz,
preview]{standalone}
\usetikzlibrary{arrows,calc,fit,backgrounds}
\newcommand{\psign}{+}
\newcommand{\ppsign}{++}
\begin{document}
\begin{tikzpicture}[
node distance = 2cm,
every node/.style = {draw, rectangle,
fill=white, % if you liked, otherwise should be omitted
minimum width=2.2cm, minimum height=0.8cm}
]
\node (A) {GDI DDI};
\node (B) [above of=A] {GDI};
\begin{scope}[xshift=3cm]
\node (C) [draw=none] {Graphics Driver};
\node (D) [above of=C] {GDI\psign Flat API};
\node (E) [above of=D] {GDI\psign\ C\ppsign API};
\end{scope}
\begin{scope}[xshift=6cm]
\node (F) {DX DDI};
\node (G) [above of=F] {DXGI};
\node (H) [above of=G] {Direct3D};
\node (I) [above of=H,minimum width=4.5cm,right=0pt] {Direct2D};
\node (J) [right of=I,right=0pt,node distance=3.5cm] {DirectWrite};
\node (K) [right of=G, node distance=4cm] {Software Rasterizer};
\end{scope}
\coordinate (L) at ([xshift=7mm] H.north);
\path[-triangle 45,semithick]
(B) edge (A) (E) edge (D) (H) edge (G)
(G) edge (F) (J) edge (I) (I.south-|K) edge (K)
(I.south -| L) edge (L)
(I.south-|{$(H.north)!.5!(H.north east)$}) -- ($(H.north)!.5!(H.north east)$);
\scoped[on background layer]
\node (M) [rectangle,fill=gray!30,fit=(G.south west) (J.north east)] {};
\coordinate (N) at ($(A.west)!0.5!(B.west)$);
\draw [dashed] (N) -- (N -| M.east);
\end{tikzpicture}
\end{document}
Este código fornece: