4

I have a seemingly simple block matrix that I want to set with as few dependencies as possible. I already have amsmath and friends loaded. The only thing I'm intent on avoiding is blkarray.

Here is what I want to make:

What I want to make

Here is a failed attempt of mine, which produces the most heinous spacing imaginable with lines that don't meet to make corners.

\begin{equation}
    \begin{pmatrix}[ccc]
        J_1 & \begin{array}{|cc}0 & 0\\ 0 & 0\end{array} & \begin{array}{cc}0 & 0\\ 0 & 0\end{array}\\ \cline{1-2}
        \begin{array}{cc|}0&0\\0&0\end{array} & J_2 & \begin{array}{|cc}0&0\\0&0\end{array}\\ \cline{2-3}
        \begin{array}{cc}0 & 0\\ 0 & 0\end{array} & \begin{array}{cc|}0 & 0\\ 0 & 0\end{array} & J_3
    \end{pmatrix}
\end{equation}

Which is ugly as all get-out:

My nasty failed attempt at it

NB: I have modified pmatrix so it takes column specs as an optional argument. Just pretend it is an array.

My difficulty seems to stem from the fact that I want 2x2 blocks, while most others I've seen seem to skate by using either multirow or multicolumn, but not both.

Edit: This isn't nearly as ugly, but the vertical lines only cover half the distance of the multirow:

\begin{equation}
    \begin{array}{cccccc}
        \multicolumn{2}{c|}{\multirow{2}{*}{$J_1$}} & 0 & 0 & 0 & 0\\
                                                   & & 0 & 0 & 0 & 0\\ \cline{1-4}
        0 & 0 & \multicolumn{2}{|c|}{\multirow{2}{*}{$J_1$}} & 0 & 0\\
        0 & 0 &                                           & & 0 & 0\\ \cline{3-6}
        0 & 0 & 0 & 0 & \multicolumn{2}{|c}{\multirow{2}{*}{$J_1$}} \\
        0 & 0 & 0 & 0 & & \\
    \end{array}
\end{equation}

Better, but still not there.

2 Answers 2

4

The fundamental part of the matrix construction looks like this:

enter image description here

\documentclass{article}
\newcommand{\mc}{\multicolumn{1}{c}}
\begin{document}

\[
  \renewcommand{\arraystretch}{1.2}
  \left(
  \begin{array}{ c c | c c | c c }
    \multicolumn{1}{|c}{} & & 0 & \mc{0} & 0 & 0 \\
    \multicolumn{2}{|c|}{\raisebox{.6\normalbaselineskip}[0pt][0pt]{$J_1$}} & 0 & \mc{0} & 0 & 0 \\
    \cline{1-4}
    0 & 0 & & & 0 & 0 \\
    0 & 0 & \multicolumn{2}{c|}{\raisebox{.6\normalbaselineskip}[0pt][0pt]{$J_2$}} & 0 & 0 \\
    \cline{3-6}
    0 & \mc{0} & 0 & 0 & & \multicolumn{1}{c|}{} \\
    0 & \mc{0} & 0 & 0 & \multicolumn{2}{c|}{\raisebox{.6\normalbaselineskip}[0pt][0pt]{$J_3$}}
  \end{array}
  \right)
\]

\end{document}

Perhaps it would be best to assign variables to the other components (like A and B) in order to maintain the matrix spacing.

5
  • Thanks, this seems to get me what I want. When I added content to some of the zeros, it pushed the Js out of alignment, which I manually adjusted. Q1) How did you arrive at .6\normalbaselineskip? Q2) Can you think of a way to make the spacing automatic? Q3) Could you elaborate on your final comment about assigning labels to components?
    – Timtro
    Dec 11, 2014 at 19:52
  • @Timtro: (Q1) .6 is half of 1.2, the new \arraystretch that I set. And, since you want the Js to be raised half the row height into position, I used .6\normalbaselineskip. (Q2) What spacing? (Q3) I was thinking along these lines, since it would keep the structure of the matrix consistent, rather than spreading things out horizontally and vertically due to A, B and C's shape/size.
    – Werner
    Dec 11, 2014 at 20:09
  • (Q2) I meant the extent of the raisebox, so one needn't manually adjust. (Q3) You mean to beautify the code, rather than the typeset product, right?
    – Timtro
    Dec 11, 2014 at 21:32
  • @Timtro: (Q2) You can use \multirow (from the multirow package; (Q3) I actually means the typeset product. In many cases, the code might be very messy, but the output is beautiful. In this case, it seems like using variables keeps both neat and tidy. But I don't know the actual use-case and therefore can only suggest something.
    – Werner
    Dec 11, 2014 at 21:35
  • I see what you mean now, WRT (Q3). I agree, and perhaps will do it. This was the motivation behind defining these Js in the first place: they are large and unsightly. WRT (Q1), This basically means combining my last attempt from last night (the edit below my original post) with your fantastic \mc trick. I tried it, and works famously. Thanks.
    – Timtro
    Dec 11, 2014 at 21:56
1

With {pNiceMatrix} of nicematrix. That environment is similar to the classical environment {pmatrix} (of amsmath) but creates PGF/Tikz nodes under the rows, cells and columns. It's possible to use those nodes to draw whatever rule you want with Tikz in the \CodeAfter.

\documentclass{article}
\usepackage{nicematrix}
\usepackage{tikz}

\begin{document}

$\begin{pNiceMatrix}[margin]
\Block{2-2}{J_1} & & 0 & 0 & 0 & 0 \\
                 & & 0 & 0 & 0 & 0 \\
0 & 0 & \Block{2-2}{J_2} & & 0 & 0 \\
0 & 0 &                  & & 0 & 0 \\
0 & 0 & 0 & 0 & \Block{2-2}{J_3} \\
0 & 0 & 0 & 0 \\
\CodeAfter
  \begin{tikzpicture}
  \draw (1-|1) |- (3-|5) -- (7-|5) ;
  \draw (1-|3) |- (5-|7) -- (7-|7) ;
  \end{tikzpicture}
\end{pNiceMatrix}$

\end{document}

You need several compilations (because of the PGF/Tikz nodes).

Output of the above code

If you don't want to use Tikz explicitely, you can also specify the borders of the blocks with the key borders of the command \Block.

\documentclass{article}
\usepackage{nicematrix}
\usepackage{tikz}

\begin{document}

$\begin{pNiceMatrix}[margin]
\Block[borders={left,bottom,right}]{2-2}{J_1} & & 0 & 0 & 0 & 0 \\
                                              & & 0 & 0 & 0 & 0 \\
0 & 0 & \Block[draw]{2-2}{J_2} & & 0 & 0 \\
0 & 0 &                        & & 0 & 0 \\
0 & 0 & 0 & 0 & \Block[borders={left,top,right}]{2-2}{J_3} \\
0 & 0 & 0 & 0 \\
\end{pNiceMatrix}$

\end{document}

The output is the same.

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .