0

在过去的一天半里,我一直在搜索谷歌,试图弄清楚这一点。如您所见,我试图让 mouseClicked 更新变量 clickcolumnindex 和 clickrowindex 以使 mouseClicked 方法中的 replaint() 方法更新,从而在另一列/行中显示由绘制显示创建的计数器。

在尝试了很多事情之后,我觉得这可能是一个非常简单的解决方法,我有点迷失了思路。

帮助将不胜感激。

import java.awt.*;
import java.awt.geom.*;
import javax.swing.*;
import java.awt.event.MouseListener;
import java.awt.event.MouseEvent;

            class GridPanel extends JPanel implements MouseListener
            {
                int numCols;
                int numRows;
                int w;
                int h;
                int x;
                int y;
                int clickcolumnindex;
                int clickrowindex;


                public void mouseReleased(MouseEvent event)
                {
                    System.out.println("Mouse released.");
                }
                public void mousePressed(MouseEvent event)
                {
                    System.out.println("Mouse Pressed");
                }
                public void mouseClicked(MouseEvent event)
                {
                    int clickcolumnindex = 7 * x / getWidth();
                    int clickrowindex = 5 * y / getHeight();
                    int x = event.getX();
                    int y = event.getY();
                    System.out.println("x position of click is: " +x);
                    System.out.println("y position of click is: " +y);
                    System.out.println("Click is in column " +clickcolumnindex);
                    System.out.println("Click is in row " +clickrowindex);
                    repaint();

                }


   public void mouseReleased(MouseEvent event) {
      System.out.println("Mouse released.");
   }

   public void mousePressed(MouseEvent event) {
      System.out.println("Mouse Pressed");
   }

   public void mouseClicked(MouseEvent event) {
      int x = event.getX();
      int y = event.getY();
      System.out.println("x position of click is: " + x);
      System.out.println("y position of click is: " + y);
      System.out.println("Click is in column " + clickcolumnindex);
      System.out.println("Click is in row " + clickrowindex);
      repaint();
   }

   public void mouseEntered(MouseEvent event) {
      System.out.println("Mouse entered.");
   }

   public void mouseExited(MouseEvent event) {
      System.out.println("Mouse exited.");
   }

   public GridPanel(int nc, int nr) {
      numCols = nc;
      numRows = nr;
      addMouseListener(this);
   }

   Rectangle getRect(int thisCol, int thisRow) {
      // if input is out of range, return "null"
      if (thisCol < 0 || thisRow < 0)
         return null;
      if (thisCol >= numCols || thisRow >= numRows)
         return null;
      // otherwise, make and return the Rectangle
      int w = getWidth() / numCols;
      int h = getHeight() / numRows;
      int x = thisCol * w;
      int y = thisRow * h;
      Rectangle myRect = new Rectangle(x, y, w, h);
      return myRect;
   }

   public void paint(Graphics g) {
      g.setColor(Color.gray);
      g.fillRect(0, 0, getWidth(), getHeight());
      g.setColor(Color.black);
      Graphics2D g2 = (Graphics2D) g;
      // we'll use Graphics2D for it's "draw" method -
      // neater than the Graphics "drawRect" suppled
      // (which you could also use)
      for (int i = 0; i < numCols; i++) {
         for (int j = 0; j < numRows; j++) {
            Rectangle r = getRect(i, j);
            g2.draw(r);
         }
      }
      g2.setColor(Color.blue);
      Rectangle r1 = getRect(clickcolumnindex, clickrowindex);
      g2.fillOval(r1.x, r1.y, r1.width, r1.height);
      System.out.println("variable updates " + clickcolumnindex + clickrowindex);
   }

   // copied from the W2MouseEvents for convenience
   // (so we can run the program from GridPanel class too!)
   public static void main(String[] args) {
      W2MouseEvents w = new W2MouseEvents();
      w.setVisible(true);
   }
}

W2MouseEvents.java:

import javax.swing.JFrame;

public class W2MouseEvents extends JFrame {
   GridPanel myGridPanel;

   public static void main(String[] args) {
      W2MouseEvents w = new W2MouseEvents();
      w.setVisible(true);
   }

   public W2MouseEvents() {
      setTitle("Workshop 2 (Mouse Events): starting code");
      setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
      setSize(500, 400);
      setLocation(300, 300);
      myGridPanel = new GridPanel(7, 5);
      add(myGridPanel);
   }

}
4

3 回答 3

3

至少有两个问题: 变量不会神奇地自动更新自己。如果更改,则不会更新位于其右侧的x变量(假设它们在同一范围内)。x澄清:

int x = 4;
int var = x + 1; // var == 5
x = 5 // var still is 5, not 6

假设您想要更改x并且y“全局”(如“类实例的属性”),您必须解决的第二个问题是

public void mouseClicked(MouseEvent event)
{
    int x = event.getX();
    int y = event.getY();
    // ...
}

这里发生的情况是您声明了两个新的局部变量xy但是无论您分配给它们什么值,您的“全局”变量xy不会改变,除非您省略声明性的int. 如果您重新计算mouseClicked/mousePressed/... 方法之一的值clickColumnIndex和内部的值,这不是问题。clickRowIndex

编辑 我看到你已经将计算clickColumnIndex及其兄弟移到了mouseClicked方法中。但如上所述,您正在创建两个隐藏“全局”变量的变量。只需删除.int

于 2012-08-04T15:56:14.363 回答
1

您在声明它时设置 clickcolumnindex,在鼠标事件发生之前。您需要在鼠标侦听器中设置它。

换句话说,这是没有意义的:

        class GridPanel extends JPanel implements MouseListener
        {
            int numCols;
            int numRows;
            int w;
            int h;
            int x;
            int y;
            int clickcolumnindex = 7 * x / getWidth();
            int clickrowindex = 5 * y / getHeight();

因为此时 x 为 0,getWidth() 也为 0(很惊讶您在这里没有得到除以零的错误)。

您想改为在 MouseListener 的mousePressed(...)方法中设置 clickXXXindex。我更喜欢使用mousePressed(...)而不是mouseClicked(...)因为前者对按下鼠标后移动鼠标并不挑剔。

此外,您需要使用 JPanel 的paintComponent(...)方法而不是它的paint(...)方法进行绘图。

于 2012-08-04T15:44:29.520 回答
1

声明:

   int clickcolumnindex = 7 * x / getWidth();
   int clickrowindex = 5 * y / getHeight();

不允许在构造函数、方法或静态初始化块之外。

正如 HoverMeister 所指出的,这些只分配一次。为什么没有单独的方法来更新这些变量和随后的 repaint()?

于 2012-08-04T15:57:01.067 回答