質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.48%
Java

Javaは、1995年にサン・マイクロシステムズが開発したプログラミング言語です。表記法はC言語に似ていますが、既存のプログラミング言語の短所を踏まえていちから設計されており、最初からオブジェクト指向性を備えてデザインされています。セキュリティ面が強力であることや、ネットワーク環境での利用に向いていることが特徴です。Javaで作られたソフトウェアは基本的にいかなるプラットフォームでも作動します。

Swing

SwingはJavaに標準で付属するグラフィック関連のクラスライブラリを指します。

Q&A

解決済

1回答

4224閲覧

javaのSwingにて背景に画像を表示したいがされない問題

tarutarupop

総合スコア20

Java

Javaは、1995年にサン・マイクロシステムズが開発したプログラミング言語です。表記法はC言語に似ていますが、既存のプログラミング言語の短所を踏まえていちから設計されており、最初からオブジェクト指向性を備えてデザインされています。セキュリティ面が強力であることや、ネットワーク環境での利用に向いていることが特徴です。Javaで作られたソフトウェアは基本的にいかなるプラットフォームでも作動します。

Swing

SwingはJavaに標準で付属するグラフィック関連のクラスライブラリを指します。

0グッド

0クリップ

投稿2017/07/27 01:48

編集2017/07/27 20:10

###前提・実現したいこと
javaのswingでGUIについて勉強しています。今、背景に画像を使ったパネルを作り、さらにその上に一回り小さいデフォルトのパネルを作成して表示したいと考えています。
###発生している問題・エラーメッセージ
エラーメッセージはでていませんが、Mainクラスを実行すると大小二つのタブが生成されます。どちらも何も表示されていません。

###該当のソースコード

Java

1package スタート画面; 2 3import java.io.IOException; 4 5import javax.swing.JFrame; 6 7public class Main extends JFrame { 8 9 public Main(){ 10 super("test"); 11 setResizable(false); 12 setDefaultCloseOperation(EXIT_ON_CLOSE); 13 pack(); 14 setVisible(true); 15 } 16 public static void main(String[] args) throws IOException { 17 Main main = new Main(); 18 StartScreen jp = new StartScreen(); 19 main.getContentPane().add(jp); 20 21 } 22}

java

1package スタート画面; 2 3//import java.awt.CardLayout; 4import java.io.IOException; 5 6import javax.swing.ImageIcon; 7import javax.swing.JPanel; 8 9public class StartScreen extends JPanel { 10 private ImageIcon img; 11 //private CardLayout layout = new CardLayout(); 12 private JPanel mainpane; 13 14 public StartScreen() throws IOException { 15 //背景 16 BufferedImage img; 17 try { 18 img = ImageIO.read(new File("p0131_l.jpg")); 19 } catch (Exception e) { 20 e.printStackTrace(); 21 img = null; 22 } 23 //img = new ImageIcon("p0131_l.jpg"); 24 ImagePanel backpane = new ImagePanel(img); 25 backpane.setVisible(true); 26 27 //メインパネル 28 mainpane = new JPanel(); 29 mainpane.setLayout(null); 30 mainpane.setBounds(400, 400, 900, 500); 31 mainpane.setVisible(true); 32 backpane.add(mainpane); 33 } 34}

java

1package スタート画面; 2 3import java.awt.Dimension; 4import java.awt.Graphics; 5import java.awt.Image; 6 7import javax.swing.JPanel; 8 9public class ImagePanel extends JPanel{ 10 private BufferedImage image; 11 /* 12 * コンストラクタ引用(Java Swing Hacks,Joshua Marinacci著) 13 */ 14 public ImagePanel(BUfferedImage image){ 15 this.image = image; 16 Dimension size = new Dimension(image.getWidth(null),image.getHeight(null)); 17 setPreferredSize(size); 18 setMaximumSize(size); 19 setMinimumSize(size); 20 setLayout(null); 21 } 22 public void paintComponent(Graphics g){ 23 g.drawImage(image, 0, 0, null); 24 } 25} 26

StartScreenのフィールドでカードレイアウトがインスタンス化されてるのはいずれデフォルトのパネルに適応しパネルを追加して画面遷移を行いたいと考えているからです。
###補足情報(言語/FW/ツール等のバージョンなど)
作業環境はEclipseです。画像はインポートで取り込み同じプロジェクトファイル内にあります。画像の大きさは1200×1035です。

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

guest

回答1

0

ベストアンサー

なんというか、いろいろと不可解なコードです。(修正確認しました)

  • 命名がおかしい

MainとImagePanelがJFrame?SmartScreenがJPanel?

  • 画像の取り扱いがおかしい

1200x1035の画像はアイコンとは呼べないと思います。
また、どうしてJFrameにべた張りしようとしているのでしょうか。

  • コンポーネントの自己主張が激しい

特にSmartScreen。自身をaddする前にsetVisible(true)にしてしまっています。
あとMainのコンストラクタは完全に無駄だと思います。

  • setLayout(null)

せっかくlayout用意したのに使わないんですか?

もっと簡潔に書けるはずです。
重複して書いているからフレームも二つ出て、処理の順序が前後しているからまっしろです。

追記

デバッグしてみましたが、それなりの量書き換える必要がありました。
要点は次のとおりです。

  • pack()とsetVisible(true)の呼ばれるタイミングを適切にする

これらのメソッドはその性格上、コンポーネントの配置がすべて終わった時に呼ばれるべきです。

  • SmartScreenがパネルとして機能していない

フィールドのmainpaneに対して操作をしているので、SmartScreenのインスタンスjpは真っ白です。

  • パネルの親子関係に意識を向ける

下記のコードを見る限り、mainpaneはbackpaneの子なのですよね?

Java

1backpane.add(mainpane);

メインとなるフレームから子を直接呼び出すのはおかしな設計です。

  • フレームに与えるのは親のパネル

直前の項と重複しますが、子をaddしてどうするんです?

Java

1StartScreen jp = new StartScreen(); 2main.getContentPane().add(jp);
  • 必要のないsetVisibleを削る

しっかりとGUIを組めていれば、フレームを可視化すればそれで充分です。


設計的に改善するとしたら、次のどっちかですかね。

  • MainクラスからImagePanelを呼び出し、ImagePanelからStartPanelを呼び出す。
  • Mainクラスから両方を呼び出し、ImagePanelに子としてStartScreenを与える。

後者の方が柔軟な気もします。どんな機能を組み込むかにもよりますが。
ともかく、インタフェースを意識して作る必要はあるでしょう。

不明な点がありましたらコメントにてお知らせ下さい。
コードを見せちゃった方が早いんですが、質問者様のデバッグの機会を奪いたくないので。

投稿2017/07/27 02:06

編集2017/07/28 03:03
LouiS0616

総合スコア35660

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

tarutarupop

2017/07/27 20:15

処理の順序について教えてもらってもいいでしょうか?
LouiS0616

2017/07/28 03:05

追記しました。setVisibleやpackを呼び出す順序を特に気にしてください。
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.48%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問