Repository: Qiskit/qiskit

Issue:
Incorrect drawing of composite gates with qubits and classical bits when using text drawer
<!-- ⚠️ If you do not respect this template, your issue will be closed -->
<!-- ⚠️ Make sure to browse the opened and closed issues -->

### Information

- **Qiskit Terra version**: 0.18.0.dev0+2ecf45d
- **Python version**: 3.7

### What is the current behavior?

Text drawer incorrectly draws composite gates that contain both qubits and classical bits. This error seems to arise only when appending the composite gate and the qreg_list or the creg_list provided to the qc.append() is not in ascending order. 

For instance consider the following code:

```python
from qiskit import QuantumCircuit

inst = QuantumCircuit(3, 2, name='inst').to_instruction()
inst2 = QuantumCircuit(3,name='inst2').to_instruction()
qc = QuantumCircuit(4,2)
qc.append(inst,[2,1,0],[0,1])
qc.append(inst,[0,1,2],[1,0])
qc.append(inst2,[2,1,0])
qc.draw()
```

The text circuit drawn is as below:

![qiskit_text_error](https://user-images.githubusercontent.com/51048173/113936418-5b64cd00-9815-11eb-9ce2-7ac910e99d1d.png)

Also, the numbering of the active wires is incorrect.

### Suggested solutions

The error seems to be caused due to drawing the gate components in the incorrect ordering. Have a look at the following function will help.

https://github.com/Qiskit/qiskit-terra/blob/2ecf45d90d47b430493e218b218d6639cabf7ff1/qiskit/visualization/text.py#L1211




Discussion:

Resolving patch:
diff --git a/qiskit/visualization/text.py b/qiskit/visualization/text.py
--- a/qiskit/visualization/text.py
+++ b/qiskit/visualization/text.py
@@ -1276,8 +1276,6 @@ def _set_multibox(
         controlled_edge=None,
     ):
         if qubits is not None and clbits is not None:
-            qubits = list(qubits)
-            clbits = list(clbits)
             cbit_index = sorted([i for i, x in enumerate(self.clbits) if x in clbits])
             qbit_index = sorted([i for i, x in enumerate(self.qubits) if x in qubits])
 
@@ -1295,6 +1293,9 @@ def _set_multibox(
                 if cbit in clbits
             ]
 
+            qubits = sorted(qubits, key=self.qubits.index)
+            clbits = sorted(clbits, key=self.clbits.index)
+
             box_height = len(self.qubits) - min(qbit_index) + max(cbit_index) + 1
 
             self.set_qubit(qubits.pop(0), BoxOnQuWireTop(label, wire_label=qargs.pop(0)))


Test patch:
diff --git a/test/python/visualization/test_circuit_text_drawer.py b/test/python/visualization/test_circuit_text_drawer.py
--- a/test/python/visualization/test_circuit_text_drawer.py
+++ b/test/python/visualization/test_circuit_text_drawer.py
@@ -2497,6 +2497,114 @@ def test_text_2q_1c(self):
 
         self.assertEqual(str(_text_circuit_drawer(circuit)), expected)
 
+    def test_text_3q_3c_qlabels_inverted(self):
+        """Test q3-q0-q1-c0-c1-c_10 in q0-q1-q2-q3-c0-c1-c2-c_10-c_11
+        See https://github.com/Qiskit/qiskit-terra/issues/6178"""
+        expected = "\n".join(
+            [
+                "        ┌───────┐",
+                "q_0: |0>┤1      ├",
+                "        │       │",
+                "q_1: |0>┤2      ├",
+                "        │       │",
+                "q_2: |0>┤       ├",
+                "        │       │",
+                "q_3: |0>┤0      ├",
+                "        │  Name │",
+                " c_0: 0 ╡0      ╞",
+                "        │       │",
+                " c_1: 0 ╡1      ╞",
+                "        │       │",
+                " c_2: 0 ╡       ╞",
+                "        │       │",
+                "c1_0: 0 ╡2      ╞",
+                "        └───────┘",
+                "c1_1: 0 ═════════",
+                "                 ",
+            ]
+        )
+
+        qr = QuantumRegister(4, name="q")
+        cr = ClassicalRegister(3, name="c")
+        cr1 = ClassicalRegister(2, name="c1")
+        circuit = QuantumCircuit(qr, cr, cr1)
+        inst = QuantumCircuit(3, 3, name="Name").to_instruction()
+        circuit.append(inst, [qr[3], qr[0], qr[1]], [cr[0], cr[1], cr1[0]])
+
+        self.assertEqual(str(_text_circuit_drawer(circuit)), expected)
+
+    def test_text_3q_3c_clabels_inverted(self):
+        """Test q0-q1-q3-c_11-c0-c_10 in q0-q1-q2-q3-c0-c1-c2-c_10-c_11
+        See https://github.com/Qiskit/qiskit-terra/issues/6178"""
+        expected = "\n".join(
+            [
+                "        ┌───────┐",
+                "q_0: |0>┤0      ├",
+                "        │       │",
+                "q_1: |0>┤1      ├",
+                "        │       │",
+                "q_2: |0>┤       ├",
+                "        │       │",
+                "q_3: |0>┤2      ├",
+                "        │       │",
+                " c_0: 0 ╡1 Name ╞",
+                "        │       │",
+                " c_1: 0 ╡       ╞",
+                "        │       │",
+                " c_2: 0 ╡       ╞",
+                "        │       │",
+                "c1_0: 0 ╡2      ╞",
+                "        │       │",
+                "c1_1: 0 ╡0      ╞",
+                "        └───────┘",
+            ]
+        )
+
+        qr = QuantumRegister(4, name="q")
+        cr = ClassicalRegister(3, name="c")
+        cr1 = ClassicalRegister(2, name="c1")
+        circuit = QuantumCircuit(qr, cr, cr1)
+        inst = QuantumCircuit(3, 3, name="Name").to_instruction()
+        circuit.append(inst, [qr[0], qr[1], qr[3]], [cr1[1], cr[0], cr1[0]])
+
+        self.assertEqual(str(_text_circuit_drawer(circuit)), expected)
+
+    def test_text_3q_3c_qclabels_inverted(self):
+        """Test q3-q1-q2-c_11-c0-c_10 in q0-q1-q2-q3-c0-c1-c2-c_10-c_11
+        See https://github.com/Qiskit/qiskit-terra/issues/6178"""
+        expected = "\n".join(
+            [
+                "                 ",
+                "q_0: |0>─────────",
+                "        ┌───────┐",
+                "q_1: |0>┤1      ├",
+                "        │       │",
+                "q_2: |0>┤2      ├",
+                "        │       │",
+                "q_3: |0>┤0      ├",
+                "        │       │",
+                " c_0: 0 ╡1      ╞",
+                "        │  Name │",
+                " c_1: 0 ╡       ╞",
+                "        │       │",
+                " c_2: 0 ╡       ╞",
+                "        │       │",
+                "c1_0: 0 ╡2      ╞",
+                "        │       │",
+                "c1_1: 0 ╡0      ╞",
+                "        └───────┘",
+            ]
+        )
+
+        qr = QuantumRegister(4, name="q")
+        cr = ClassicalRegister(3, name="c")
+        cr1 = ClassicalRegister(2, name="c1")
+        circuit = QuantumCircuit(qr, cr, cr1)
+        inst = QuantumCircuit(3, 3, name="Name").to_instruction()
+        circuit.append(inst, [qr[3], qr[1], qr[2]], [cr1[1], cr[0], cr1[0]])
+
+        self.assertEqual(str(_text_circuit_drawer(circuit)), expected)
+
 
 class TestTextDrawerAppendedLargeInstructions(QiskitTestCase):
     """Composite instructions with more than 10 qubits