Java 将可滚动画布添加到JFrame

Java 将可滚动画布添加到JFrame,java,java-canvas,Java,Java Canvas,我想将一个可滚动画布添加到JFrame,一些网络研究让我找到了一个将可滚动画布作为Java小程序的解决方案。我试图将此应用于JFrame,结果是: import java.awt.BorderLayout; import java.awt.EventQueue; import java.awt.FlowLayout; import javax.swing.JFrame; import javax.swing.JPanel; import javax.swing.border.EmptyBord

我想将一个可滚动画布添加到
JFrame
,一些网络研究让我找到了一个将可滚动画布作为Java小程序的解决方案。我试图将此应用于
JFrame
,结果是:

import java.awt.BorderLayout;
import java.awt.EventQueue;
import java.awt.FlowLayout;

import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.border.EmptyBorder;
import java.awt.Canvas;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.Image;
import java.awt.Panel;
import java.awt.Scrollbar;
import javax.swing.JButton;
import java.awt.event.ActionListener;
import java.awt.event.ActionEvent;

public class Frame extends JFrame {
private JPanel contentPane;

class ScrollCanvas extends Panel {
     int vw,vh;
     int rw,rh;
     Color b,f;
     myCanvas c;
     Scrollbar sv, sh;

     // constructor
     //   visible h w
     //   real    h w
     //   background foreground
     ScrollCanvas
        (int vw1, int vh1,  int rw1, int rh1, Color b1, Color f1) {
      super();
      vw = vw1; vh = vh1;
      rh = rh1; rw = rw1;
      b  = b1;  f  = f1;
      int ScrollIncrement = 10;
      setLayout(new BorderLayout());
      c = new myCanvas(vw, vh, rw, rh, b ,f);
      add("West", c);
      sv = new Scrollbar
        (Scrollbar.VERTICAL,0, ScrollIncrement, 0, rh);
      add("East", sv);
      sh = new Scrollbar
        (Scrollbar.HORIZONTAL, 0, ScrollIncrement, 0, rw);
      add("South", sh);
      }

     public void redraw() {
      int y = sv.getValue();
      int x = sh.getValue();
      c.draw(x,y);
      }

     public Dimension minimumSize() {
      return new Dimension(vw,vh);
      }

     public Dimension preferredSize() {
      return new Dimension(vw,vh);
      }
    }

   class myCanvas extends Canvas {
     int vw, vh;
     int rw, rh;
     Color b, f;
     int x, y;
     Image buffImage;
     Graphics offscreen;
     boolean initDone;

     myCanvas
        (int vw1, int vh1, int rw1, int rh1, Color b1, Color f1) {
      super();
      vw = vw1; vh = vh1;
      rh = rh1; rw = rw1;
      b  = b1;  f  = f1;
      initDone = false;
      repaint();
      }

     public void paint(Graphics g) {
      if (!initDone)
       initpaint(g);
      else
       g.drawImage(buffImage, x, y,  this);
      }

     public void update(Graphics g) {
      g.drawImage(buffImage, x, y,  this);
      }

     public void initpaint(Graphics g) {
      try {
       buffImage = this.createImage(rw, rh);
       offscreen = buffImage.getGraphics();
       offscreen.setColor(b);
       offscreen.fillRect(0, 0, rw, rh);
       offscreen.setColor(f);
       offscreen.setFont(new Font("Courier", Font.ITALIC, 42));
       offscreen.drawString("Hello World!", 0, 50);
       initDone = true;
       g.drawImage(buffImage,0,0, this);
       }
      catch (Exception e) {
       System.out.println("oups...");
       }
      }

     public void draw (int x1, int y1)  {
      x = -x1;
      y = -y1;
      update(getGraphics());
      }

     public Dimension minimumSize() {
      return new Dimension(vw,vh);
      }

     public Dimension preferredSize() {
      return new Dimension(vw,vh);
      }
   }
   /**
 * Launch the application.
 */
public static void main(String[] args) {
    EventQueue.invokeLater(new Runnable() {
        public void run() {
            try {
                Frame frame = new Frame();
                frame.setVisible(true);
            } catch (Exception e) {
                e.printStackTrace();
            }
        }
    });
}

/**
 * Create the frame.
 */
public Frame() {

    setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
    setBounds(267, 267, 1000, 900);
    contentPane = new JPanel();
    contentPane.setBorder(new EmptyBorder(5, 5, 5, 5));
    contentPane.setLayout(new BorderLayout(0, 0));
    setContentPane(contentPane);

    ScrollCanvas myCV = new ScrollCanvas(500, 500, 1000, 1000, Color.BLACK, Color.RED);
    contentPane.add(myCV);
    }
}
工作正常,画布在框架上显示得非常好,但它不可滚动,我无法重新绘制(例如,在
JFrame
的GUI上按
按钮更改背景色)。这不是向
JFrame
添加可滚动画布的合适方法,或者我遗漏了一些您可能更了解的内容,请与我分享


谢天谢地

注意:画布本身应该是可滚动的,不要混合AWT和Swing组件。除非有奇怪的限制,否则只能使用Swing组件。
一些网络研究让我找到了一个带有可滚动画布的解决方案
——这是旧代码,应该避免使用。这不是向容器添加组件的方式。这不是使用Swing时进行自定义绘制的方式。重写JPanel的paintComponent()方法。从上的Swing教程中的一个简单示例开始。本教程还有一个关于
自定义绘制的部分,其中包含工作示例。