001/* 002 * The contents of this file are subject to the terms of the Common Development and 003 * Distribution License (the License). You may not use this file except in compliance with the 004 * License. 005 * 006 * You can obtain a copy of the License at legal/CDDLv1.0.txt. See the License for the 007 * specific language governing permission and limitations under the License. 008 * 009 * When distributing Covered Software, include this CDDL Header Notice in each file and include 010 * the License file at legal/CDDLv1.0.txt. If applicable, add the following below the CDDL 011 * Header, with the fields enclosed by brackets [] replaced by your own identifying 012 * information: "Portions Copyright [year] [name of copyright owner]". 013 * 014 * Copyright 2009 Sun Microsystems, Inc. 015 * Portions Copyright 2015-2016 ForgeRock AS. 016 */ 017 018package org.opends.guitools.controlpanel.event; 019 020import java.awt.Component; 021import java.awt.Dimension; 022import java.awt.Point; 023import java.awt.Rectangle; 024import java.awt.event.MouseAdapter; 025import java.awt.event.MouseEvent; 026 027import javax.swing.JComponent; 028import javax.swing.JTable; 029import javax.swing.JToolTip; 030import javax.swing.Popup; 031import javax.swing.PopupFactory; 032import javax.swing.table.TableCellRenderer; 033 034/** 035 * This class listens to events and displays a tooltip when the user clicks on 036 * the object that registered this listener. 037 */ 038public class ClickTooltipDisplayer extends MouseAdapter 039{ 040 private boolean isTooltipVisible; 041 private Popup tipWindow; 042 043 @Override 044 public void mouseExited(MouseEvent event) 045 { 046 hideToolTip(event); 047 } 048 049 @Override 050 public void mousePressed(MouseEvent event) 051 { 052 if (isTooltipVisible) 053 { 054 hideToolTip(event); 055 } 056 else 057 { 058 displayToolTip(event); 059 } 060 } 061 062 /** 063 * Displays a tooltip depending on the MouseEvent received. 064 * @param event the mouse event. 065 */ 066 private void displayToolTip(MouseEvent event) 067 { 068 JComponent component = (JComponent)event.getSource(); 069 String toolTipText; 070 if (component instanceof JTable) 071 { 072 JTable table = (JTable)component; 073 int row = table.rowAtPoint(event.getPoint()); 074 int column = table.columnAtPoint(event.getPoint()); 075 if (row != -1 && column != -1) 076 { 077 TableCellRenderer renderer = table.getCellRenderer(row, column); 078 Component comp = renderer.getTableCellRendererComponent(table, 079 table.getValueAt(row, column), true, true, row, column); 080 if (comp instanceof JComponent) 081 { 082 // The coordinates must be translated. 083 Rectangle rect = table.getCellRect(row, column, true); 084 int x = event.getPoint().x - rect.x; 085 int y = event.getPoint().y - rect.y; 086 MouseEvent tEv = new MouseEvent(table, event.getID(), 087 event.getWhen(), event.getModifiers(), x, y, 088 event.getClickCount(), event.isPopupTrigger(), event.getButton()); 089 toolTipText = ((JComponent)comp).getToolTipText(tEv); 090 } 091 else 092 { 093 toolTipText = null; 094 } 095 } 096 else 097 { 098 toolTipText = null; 099 } 100 } 101 else 102 { 103 toolTipText = component.getToolTipText(); 104 } 105 if (toolTipText != null) 106 { 107 Point preferredLocation = component.getToolTipLocation(event); 108 Rectangle sBounds = component.getGraphicsConfiguration(). 109 getBounds(); 110 111 JToolTip tip = component.createToolTip(); 112 tip.setTipText(toolTipText); 113 Dimension size = tip.getPreferredSize(); 114 Point location = new Point(); 115 116 Point screenLocation = component.getLocationOnScreen(); 117 if(preferredLocation != null) 118 { 119 location.x = screenLocation.x + preferredLocation.x; 120 location.y = screenLocation.y + preferredLocation.y; 121 } 122 else 123 { 124 location.x = screenLocation.x + event.getX(); 125 location.y = screenLocation.y + event.getY() + 20; 126 } 127 128 if (location.x < sBounds.x) { 129 location.x = sBounds.x; 130 } 131 else if (location.x - sBounds.x + size.width > sBounds.width) { 132 location.x = sBounds.x + Math.max(0, sBounds.width - size.width); 133 } 134 if (location.y < sBounds.y) { 135 location.y = sBounds.y; 136 } 137 else if (location.y - sBounds.y + size.height > sBounds.height) { 138 location.y = sBounds.y + Math.max(0, sBounds.height - size.height); 139 } 140 141 PopupFactory popupFactory = PopupFactory.getSharedInstance(); 142 tipWindow = popupFactory.getPopup(component, tip, location.x, location.y); 143 tipWindow.show(); 144 isTooltipVisible = true; 145 } 146 } 147 148 /** 149 * Hides the tooltip if we are displaying it. 150 * @param event the mouse event. 151 */ 152 private void hideToolTip(MouseEvent event) 153 { 154 if (tipWindow != null) 155 { 156 tipWindow.hide(); 157 tipWindow = null; 158 isTooltipVisible = false; 159 } 160 } 161}