{
  "filename": "mpn_domain_comparison.png",
  "iteration": 1,
  "description": "Create comprehensive visualization comparing MPN domain architecture and JAMM motif features across active DUBs, pseudo-DUBs, and NPLOC4",
  "timestamp": "2026-06-22 01:51:37",
  "code": "\nimport matplotlib.pyplot as plt\nimport matplotlib.patches as mpatches\nimport numpy as np\n\n# Create a comprehensive comparison figure\nfig, axes = plt.subplots(2, 1, figsize=(16, 10), gridspec_kw={'height_ratios': [3, 2]})\n\n# Panel A: MPN domain architecture comparison\nax = axes[0]\n\nproteins_viz = [\n    ('PSMD14/RPN11\\n(Active MPN+)', 310, [(31, 166, 'MPN+')], True, 'Active JAMM DUB'),\n    ('BRCC3/BRCC36\\n(Active MPN+)', 316, [(12, 179, 'MPN+')], True, 'Active JAMM DUB'),\n    ('PSMD7/RPN8\\n(Inactive MPN-)', 324, [(9, 144, 'MPN-')], False, 'Pseudo-DUB'),\n    ('CSN6\\n(Inactive MPN-)', 327, [(41, 174, 'MPN-')], False, 'Pseudo-DUB'),\n    ('EIF3F\\n(Inactive MPN-)', 357, [(92, 222, 'MPN-')], False, 'Pseudo-DUB'),\n    ('NPLOC4/NPL4\\n(MPN-)', 608, [(226, 363, 'MPN-'), (580, 608, 'ZF')], False, 'Pseudo-DUB (THIS STUDY)'),\n]\n\ncolors_active = '#2ecc71'\ncolors_inactive = '#e74c3c'\ncolors_zf = '#3498db'\n\nfor i, (name, length, domains, is_active, label) in enumerate(proteins_viz):\n    y = len(proteins_viz) - 1 - i\n    \n    # Draw full-length protein bar\n    ax.barh(y, length, height=0.4, color='#ecf0f1', edgecolor='#bdc3c7', linewidth=0.5)\n    \n    for start, end, dtype in domains:\n        if dtype == 'MPN+':\n            color = colors_active\n        elif dtype == 'MPN-':\n            color = colors_inactive\n        elif dtype == 'ZF':\n            color = colors_zf\n        ax.barh(y, end - start, left=start, height=0.4, color=color, \n                edgecolor='black', linewidth=1)\n        ax.text((start + end) / 2, y, dtype, ha='center', va='center', \n                fontsize=7, fontweight='bold', color='white')\n    \n    # Add JAMM indicator\n    if is_active:\n        # Mark JAMM motif position (approximate)\n        for start, end, dtype in domains:\n            if 'MPN' in dtype:\n                jamm_pos = start + (end - start) * 0.6\n                ax.plot(jamm_pos, y + 0.25, 'v', color='gold', markersize=8, markeredgecolor='black')\n    \n    ax.text(-10, y, name, ha='right', va='center', fontsize=9, fontweight='bold')\n    ax.text(length + 5, y, f'{length} aa  [{label}]', ha='left', va='center', fontsize=8, style='italic')\n\nax.set_xlim(-120, 700)\nax.set_ylim(-0.5, len(proteins_viz) - 0.5)\nax.set_xlabel('Residue position', fontsize=10)\nax.set_yticks([])\nax.set_title('MPN Domain Architecture: Active DUBs vs Pseudo-DUBs vs NPLOC4', fontsize=13, fontweight='bold')\n\n# Legend\nlegend_elements = [\n    mpatches.Patch(facecolor=colors_active, edgecolor='black', label='MPN+ (JAMM active)'),\n    mpatches.Patch(facecolor=colors_inactive, edgecolor='black', label='MPN- (pseudo-DUB)'),\n    mpatches.Patch(facecolor=colors_zf, edgecolor='black', label='Zinc finger'),\n    plt.Line2D([0], [0], marker='v', color='w', markerfacecolor='gold', \n               markeredgecolor='black', markersize=8, label='JAMM motif (H[ST]H)'),\n]\nax.legend(handles=legend_elements, loc='lower right', fontsize=9)\n\n# Panel B: JAMM motif residue comparison table\nax2 = axes[1]\nax2.axis('off')\n\n# Create comparison table\ntable_data = [\n    ['Feature', 'PSMD14\\n(Active)', 'BRCC3\\n(Active)', 'PSMD7\\n(Inactive)', 'CSN6\\n(Inactive)', 'NPLOC4\\n(Target)'],\n    ['H[ST]H motif', '\u2713 HSH', '\u2713 HSH', '\u2717 absent', '\u2717 absent', '\u2717 ABSENT'],\n    ['HxH (any)', '\u2713 HSH', '\u2713 HIH, HSH', '\u2717 none', '\u2713 HVH', '\u2717 NONE'],\n    ['GWY conserved', '\u2713 GWY', '\u2713 GWY', '\u2713 GWY', '\u2713 GWY', '\u2717 GWI*'],\n    ['Upstream Glu (E)', '\u2713', '\u2713', 'N/A', 'N/A', 'N/A'],\n    ['Zn-coord Asp (D)', '\u2713', '\u2713', 'N/A', 'N/A', 'N/A'],\n    ['JAMM intact', '\u2713 YES', '\u2713 YES', '\u2717 NO', '\u2717 NO', '\u2717 NO'],\n    ['Classification', 'MPN+', 'MPN+', 'MPN-', 'MPN-', 'MPN-'],\n]\n\ntable = ax2.table(cellText=table_data[1:], colLabels=table_data[0],\n                  cellLoc='center', loc='center',\n                  colWidths=[0.16, 0.14, 0.14, 0.14, 0.14, 0.14])\n\ntable.auto_set_font_size(False)\ntable.set_fontsize(8)\ntable.scale(1, 1.5)\n\n# Color header\nfor j in range(6):\n    table[0, j].set_facecolor('#34495e')\n    table[0, j].set_text_props(color='white', fontweight='bold')\n\n# Color cells based on content\nfor i in range(1, 8):\n    for j in range(1, 6):\n        cell = table[i, j]\n        text = cell.get_text().get_text()\n        if '\u2713' in text:\n            cell.set_facecolor('#d5f5e3')\n        elif '\u2717' in text:\n            cell.set_facecolor('#fadbd8')\n        if j == 5:  # NPLOC4 column\n            cell.set_text_props(fontweight='bold')\n\nax2.set_title('JAMM Catalytic Motif Residue Comparison', fontsize=12, fontweight='bold', pad=20)\n\nplt.tight_layout()\nplt.savefig('mpn_domain_comparison.png', dpi=150, bbox_inches='tight')\nplt.show()\nprint(\"\\nFigure saved: mpn_domain_comparison.png\")\nprint(\"\\n* NPLOC4 has GWI instead of GWY - the conserved tryptophan is present\")\nprint(\"  but the downstream tyrosine is replaced by isoleucine, and critically,\")\nprint(\"  the H[ST]H zinc-binding motif that follows GWY in active DUBs is absent.\")\n"
}