2016-04-04 8 views
3

私は現在、小さな「ペイント」プログラムでコーディングしています。今のところ、ペンで描画し、100倍に拡大して、色を選択することができます。次に追加したいのは、編集するように選択されたイメージが描かれているJPanelサブクラスをドラッグする可能性でした。基本的には、マウスの右ボタンを押したままにすると、JInternalFrameにあるJPanelサブクラスの場所が変更されます。私はそれ自身でうまく動作するはずのコードサンプルを持っています。少なくともそれは私のためです。問題を再現するには、DragPanelTestクラスを起動し、赤色の境界線を持つコンポーネント上にマウスをドラッグするだけです。パネルはスムーズにドラッグされず、常に前後にジャンプします。JPanelのサブクラスは、ドラッグすると「ジャンプ」します

コード:私は、コードを少し短くするためにいくつかのSystem.out.println()または@Overrideコマンドを残し

import java.awt.Color; 
import java.awt.Dimension; 
import java.awt.Point; 
import java.awt.Toolkit; 
import java.awt.event.MouseEvent; 
import java.awt.event.MouseListener; 
import java.awt.event.MouseMotionListener; 

import javax.swing.BorderFactory; 
import javax.swing.JDesktopPane; 
import javax.swing.JFrame; 
import javax.swing.JInternalFrame; 
import javax.swing.JPanel; 

@SuppressWarnings("serial") 
public class DragPanelTest extends JPanel implements MouseMotionListener, MouseListener { 
    Point oldDragPt; 
    boolean dragEnabled; 
    int newX; 
    int newY; 

    public static void main(String[] args) { 
     System.out.println("Launching Test.java ..."); 

     JFrame frame = new JFrame("Title"); 
     JInternalFrame intFrame = new JInternalFrame("title", true, true, true, true); 
     JDesktopPane deskPane = new JDesktopPane(); 
     DragPanelTest dragPanel = new DragPanelTest(); 

     frame.setSize(300, 300);; 
     frame.setLayout(null); 
     frame.setVisible(true); 
     Dimension d = Toolkit.getDefaultToolkit().getScreenSize(); 
     int x = (d.width - frame.getWidth())/2; 
     int y = (d.height - frame.getHeight())/2; 
     frame.setLocation(x, y); 

     deskPane.setBounds(50, 50, 200, 200); 
     deskPane.setBorder(BorderFactory.createLineBorder(Color.BLACK)); 
     frame.add(deskPane); 


     deskPane.add(intFrame); 
     intFrame.setSize(150, 150); 
     intFrame.add(dragPanel); 
     intFrame.setVisible(true); 
    } 

    public DragPanelTest() { 
     this.setSize(100,100); 
     this.setBorder(BorderFactory.createLineBorder(Color.RED)); 
     this.addMouseListener(this); 
     this.addMouseMotionListener(this); 
    } 

    public void mousePressed(MouseEvent e) { 
     if (e.isMetaDown()) { 
      dragEnabled = true; 
      oldDragPt = new Point((int) this.getMousePosition().getX(), (int) this.getMousePosition().getY()); 
     } 
     repaint(); 
    } 

    public void mouseReleased(MouseEvent e) { 
     dragEnabled = false; 
     oldDragPt = null; 
    } 

    public void mouseDragged(MouseEvent e) { 
     if (e.isMetaDown() && this.getMousePosition() != null) { 
      if (oldDragPt != null) { 
       if (dragEnabled) { 
        int mouseX = (int) this.getMousePosition().getX(); 
        int mouseY = (int) this.getMousePosition().getY(); 
        int x = this.getX(); 
        int y = this.getY(); 
        int diffX = (mouseX - (int) oldDragPt.getX()); 
        int diffY = (mouseY - (int) oldDragPt.getY()); 
        newX = getX() + diffX; 
        newY = getY() + diffY; 
        this.setLocation(newX, newY); 
        this.repaint(); 
        oldDragPt = new Point(mouseX, mouseY); 
       } 
      } else { 
       oldDragPt = new Point((int) this.getMousePosition().getX(), (int) this.getMousePosition().getY()); 
      } 
     } 
    } 

    public void mouseClicked(MouseEvent e) {} 
    public void mouseEntered(MouseEvent e) {} 
    public void mouseExited(MouseEvent e) {} 
    public void mouseMoved(MouseEvent e) {} 
} 

注意。

私が間違ってやっていることを誰かが知っていれば、何を改善すればいいでしょうか、とても感謝しています。

+1

それは周りのジャンプだ理由があるため、 'getMousePosition'です。これは現在のコンポーネントに関連していますが、そのコンポーネントは動いているため、コードがマウスの最後の位置に影響しています。 – resueman

答えて

6

パネルはスムーズにドラッグされず、代わりに常に前後にジャンプします。

マウスとコンポーネントと親パネルの間の相対的な動きがオフであるため、ジャンプしたときにジャンプしたとき。あなたのコードは複雑すぎて問題を引き起こす正確な行を指摘することはできません。

パネルコンポーネントのドラッグするための基本的なコードは次のとおりです。より多くの機能を備えた、より高度なコードの場合

public class DragListener extends MouseInputAdapter 
{ 
    Point location; 
    MouseEvent pressed; 

    public void mousePressed(MouseEvent me) 
    { 
     pressed = me; 
    } 

    public void mouseDragged(MouseEvent me) 
    { 
     Component component = me.getComponent(); 
     location = component.getLocation(location); 
     int x = location.x - pressed.getX() + me.getX(); 
     int y = location.y - pressed.getY() + me.getY(); 
     component.setLocation(x, y); 
    } 
} 

あなたもMoving Windowsで見つかったComponent Moverクラスをチェックアウトすることができます。

0

スクロールペインのビューポートを移動するのと同様の問題がありました。私は、コンポーネントが再配置されたときに、保存されたポイントの値が元の位置からの相対値であり、新しい位置からの相対位置が間違っていると思います。非公式な私のソリューションは、ドラッグ操作がスムーズに行われるようにしました。私がしたことは、ポイントデルタを保存された場所に戻すことです。

これは、ビューポートをドラッグするための基本的なコードです:

Point priorPanPoint; 

public void mouseDragged(MouseEvent e) { 
    Point newPt = subtractPoints(priorPanPoint, e.getPoint()); 
    priorPanPoint = addPoints(e.getPoint(), newPt); 
    newPt = addPoints(getVisibleRect().getLocation(), newPt); 
    viewport.setViewPosition(newPt); 
} 

public void mousePressed(MouseEvent e) { 
    priorPanPoint = e.getPoint(); 
} 

private Point addPoints(Point p1, Point p2) { 
    return new Point(p1.x + p2.x, p1.y + p2.y); } 

private Point subtractPoints(Point p1, Point p2) { 
    return new Point(p1.x - p2.x, p1.y - p2.y); 
} 
関連する問題