まず第一に、スタイルと個人的な好みの問題だと思います。また、アプリケーションが何をどのように実行するかによっても異なります。
あなたのJPanelがすべて特定の点で非常に類似している場合、JPanelから拡張することはおそらく理にかなっています。たとえば、すべてのパネルに10個のボタンがあり、ボタン1が対応するモデルオブジェクトに対して常にアクションxyz()を実行し(特に、このオブジェクトが1つのJPanelのすべてのボタンで同じである場合)、ボタン2がabc()を実行する場合...
JPanelsがこのように強く相関していない場合は、コードをJFrameまたはGUI全体を外部から設定する3番目のオブジェクトに配置します。
それはactionlistenersと似ています。アクションが非常に少ない場合は、使いやすさのために1つのコントローラーオブジェクトのみを使用します(ファイルは多くありません)。さまざまなアクションがたくさんある場合は、同様のアクションをアクションのグループごとに1つのコントローラーオブジェクトにグループ化します。
とはいえ、JFrame / 3番目のオブジェクトからすべてを実行し、アクションリスナーを1つ持つ単純なアプローチ(YAGNI)から始めて、分割することでよりクリーンで柔軟なデザインが得られると感じたときにリファクタリングするのがおそらく最善です。