/*
 * LOGICAL-PARADOX.ORG
 * Copyright (C)2005 satoshi akabane(akabane@logical-paradox.org)
 * $Id: NetViewCanvasMouseListener.java,v 1.3 2005/03/18 13:55:26 rampil Exp $
 */
package org.logical_paradox.testsite.oln.model.handler;

import java.awt.event.MouseEvent;
import javax.swing.JPopupMenu;
import javax.swing.event.MouseInputListener;

import org.logical_paradox.testsite.oln.OverlayNetworkConstant;
import org.logical_paradox.testsite.oln.object.AppContext;
import org.logical_paradox.testsite.oln.object.Node;
import org.logical_paradox.testsite.oln.object.RequestContext;
import org.logical_paradox.testsite.oln.view.MainWndGeneralPopupMenu;
import org.logical_paradox.testsite.oln.view.NodePropertyPopupMenu;

/**
 * トポロジービュー上で発生したマウス関連イベントをハンドリングするイベントハンドラ
 * @author satoshi akabane@logical-paradox.org
 * @version $Revision: 1.3 $
 */
public class NetViewCanvasMouseListener extends AbstractOlnListenerAdapter implements MouseInputListener {
	/**
	 * マウスがプレスされた際に選択されたノード
	 */
	private Node lastSelectedNode;

	/**
	 * コンストラクタ
	 * @param context アプリケーションコンテキスト
	 * @param request リクエストコンテキスト
	 */
	public NetViewCanvasMouseListener(AppContext context, RequestContext request) {
		super(context, request);
	}
	/**
	 * マウスのボタンがクリックされた際のイベントハンドラ
	 * @param e イベントオブジェクト
	 */
	public void mouseClicked(MouseEvent e) {
		if(e.getButton() == MouseEvent.BUTTON1) {
			// 左クリックの場合
			doLeftButtonClicked(e);
		}
	}
	public void mouseEntered(MouseEvent e) {
	}
	public void mouseExited(MouseEvent e) {
	}
	/**
	 * マウスが押下された際のイベントハンドラ
	 * @param e イベントオブジェクト
	 */
	public void mousePressed(MouseEvent e) {
		if(e.getButton() == MouseEvent.BUTTON1) {
			// 右ボタンが押下された際に、マウスの下にあったノードを選択しておく
			// D&Dなどで必要
			lastSelectedNode = getAppContext().getTopology().getNode(e.getPoint());
		}
	}
	/**
	 * マウスのボタンが離された際のイベントハンドラ
	 * @param e イベントオブジェクト
	 */
	public void mouseReleased(MouseEvent e) {
		lastSelectedNode = null;
		if(e.isPopupTrigger()) {
			// 右クリックイベント
			doRightButtonClicked(e);
		}
	}
	/**
	 * ドラッグが発生した際のイベントハンドラ
	 * @param e イベントオブジェクト
	 */
	public void mouseDragged(MouseEvent e) {
		if(lastSelectedNode != null) {
			lastSelectedNode.move(e.getPoint());
			getAppContext().getFrame().repaint();
		}
	}
	/**
	 * マウスが移動した際のイベントハンドラ
	 * @param e イベントオブジェクト
	 */
	public void mouseMoved(MouseEvent e) {
		Node node = getAppContext().getTopology().getNode(e.getPoint());
		if(node != null) {
			node.mark();
		}
		getAppContext().getFrame().repaint();
	}
	/**
	 * 左クリックイベント発生
	 * クリックした位置に何らかのノードが存在する場合は、該当ノードを選択状態とする
	 * ノードがない場合、選択状態を解除する
	 * @param e イベントオブジェクト
	 */
	protected void doLeftButtonClicked(MouseEvent e) {
		Node node = getAppContext().getTopology().getNode(e.getPoint());
		if(node != null) {
			node.setSelected(true);
		} else {
			// 全てのノードの選択を解除する
			getAppContext().getTopology().deSelectAll();
		}
		// 画面再描画
		getAppContext().getFrame().repaint();
	}
	/**
	 * 右クリックイベント発生
	 * 現在のカーソル位置にノードが存在しない場合は、ポップアップダイアログを表示する
	 * 現在のカーソル位置に何らかのノードが存在する場合は、プロパティのダイアログを表示する
	 * @param e イベントオブジェクト
	 */
	protected void doRightButtonClicked(MouseEvent e) {
		Node node = getAppContext().getTopology().getNode(e.getPoint());
		JPopupMenu menu = null;
		RequestContext request = new RequestContext();
		request.setAttribute(OverlayNetworkConstant.RKEY_MOUSE_CLICKED_POS_X, new Integer(e.getX()));
		request.setAttribute(OverlayNetworkConstant.RKEY_MOUSE_CLICKED_POS_Y, new Integer(e.getY()));

		if(node != null) {
			// マウスカーソルの下にノードが存在する場合
			menu = new NodePropertyPopupMenu(getAppContext(), request, node);
		} else {
			// マウスカーソルの下にノードが存在しない場合
			menu = new MainWndGeneralPopupMenu(getAppContext(), request);
		}
		// ポップアップメニューの表示
		menu.show(e.getComponent(), e.getX(), e.getY());
	}
}
