001/* 002 * Copyright 2010-2015 Institut Pasteur. 003 * 004 * This file is part of Icy. 005 * 006 * Icy is free software: you can redistribute it and/or modify 007 * it under the terms of the GNU General Public License as published by 008 * the Free Software Foundation, either version 3 of the License, or 009 * (at your option) any later version. 010 * 011 * Icy is distributed in the hope that it will be useful, 012 * but WITHOUT ANY WARRANTY; without even the implied warranty of 013 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 014 * GNU General Public License for more details. 015 * 016 * You should have received a copy of the GNU General Public License 017 * along with Icy. If not, see <http://www.gnu.org/licenses/>. 018 */ 019package icy.gui.frame.progress; 020 021import icy.gui.frame.IcyFrame; 022import icy.gui.util.GuiUtil; 023import icy.network.NetworkUtil; 024import icy.preferences.GeneralPreferences; 025import icy.system.thread.ThreadUtil; 026import icy.util.StringUtil; 027 028import java.awt.BorderLayout; 029import java.awt.Dimension; 030import java.awt.Font; 031import java.awt.event.MouseAdapter; 032import java.awt.event.MouseEvent; 033import java.util.List; 034import java.util.Timer; 035import java.util.TimerTask; 036 037import javax.swing.Box; 038import javax.swing.JCheckBox; 039import javax.swing.JEditorPane; 040import javax.swing.UIManager; 041import javax.swing.event.HyperlinkEvent; 042import javax.swing.event.HyperlinkListener; 043import javax.swing.text.html.HTMLDocument; 044 045/** 046 * @author Stephane 047 */ 048public class ToolTipFrame extends TaskFrame 049{ 050 Timer timer; 051 JEditorPane editorPane; 052 JCheckBox doNotDisplayCheckbox; 053 054 final int liveTime; 055 final String id; 056 057 /** 058 * Show an tool tip with specified parameters 059 * 060 * @param message 061 * message to display in tool tip 062 * @param liveTime 063 * life time in second (0 = infinite) 064 * @param id 065 * toolTip id, it's used to display the "Do not display in future" checkbox<br> 066 * and remember its value 067 */ 068 public ToolTipFrame(final String message, int liveTime, String id) 069 { 070 super(); 071 072 this.liveTime = liveTime; 073 this.id = id; 074 075 if (!StringUtil.isEmpty(id)) 076 { 077 // tool tip should not be displayed ? 078 if (!GeneralPreferences.getPreferencesToolTips().getBoolean(id, true) || alreadyExist(id)) 079 { 080 // close and exit 081 close(); 082 return; 083 } 084 } 085 086 if (liveTime != 0) 087 { 088 timer = new Timer("ToolTip timer"); 089 timer.schedule(new TimerTask() 090 { 091 @Override 092 public void run() 093 { 094 // EDT safe 095 doClose(); 096 } 097 }, liveTime * 1000); 098 } 099 100 ThreadUtil.invokeLater(new Runnable() 101 { 102 @Override 103 public void run() 104 { 105 editorPane = new JEditorPane("text/html", message); 106 editorPane.setMinimumSize(new Dimension(240, 60)); 107 editorPane.setEditable(false); 108 editorPane.setToolTipText("Click to close the tool tip"); 109 // set same font as JLabel for JEditorPane 110 final Font font = UIManager.getFont("Label.font"); 111 final String bodyRule = "body { font-family: " + font.getFamily() + "; " + "font-size: " 112 + font.getSize() + "pt; }"; 113 ((HTMLDocument) editorPane.getDocument()).getStyleSheet().addRule(bodyRule); 114 editorPane.addMouseListener(new MouseAdapter() 115 { 116 @Override 117 public void mouseClicked(MouseEvent e) 118 { 119 doClose(); 120 } 121 }); 122 // support link click 123 editorPane.addHyperlinkListener(new HyperlinkListener() 124 { 125 @Override 126 public void hyperlinkUpdate(HyperlinkEvent e) 127 { 128 if (e.getEventType() == HyperlinkEvent.EventType.ACTIVATED) 129 { 130 NetworkUtil.openBrowser(e.getURL()); 131 } 132 } 133 }); 134 135 doNotDisplayCheckbox = new JCheckBox("Do not display again", false); 136 doNotDisplayCheckbox.setToolTipText("Do not display this tooltip the next time"); 137 138 mainPanel.setLayout(new BorderLayout()); 139 140 mainPanel.add(editorPane, BorderLayout.CENTER); 141 if (!StringUtil.isEmpty(ToolTipFrame.this.id)) 142 mainPanel.add(GuiUtil.createLineBoxPanel(doNotDisplayCheckbox, Box.createHorizontalGlue()), 143 BorderLayout.SOUTH); 144 pack(); 145 } 146 }); 147 } 148 149 /** 150 * Show an tool tip with specified message 151 * 152 * @param message 153 * message to display in tool tip 154 * @param id 155 * toolTip id, it's used to display the "Do not display in future" checkbox<br> 156 * and remember its value 157 */ 158 public ToolTipFrame(String message, String id) 159 { 160 this(message, 0, id); 161 } 162 163 /** 164 * Show an tool tip with specified message 165 * 166 * @param message 167 * message to display in tool tip 168 * @param liveTime 169 * life time in second (0 = infinite) 170 */ 171 public ToolTipFrame(String message, int liveTime) 172 { 173 this(message, liveTime, ""); 174 } 175 176 /** 177 * Show an tool tip with specified message 178 * 179 * @param message 180 * message to display in tool tip 181 */ 182 public ToolTipFrame(String message) 183 { 184 this(message, 0, ""); 185 } 186 187 /** 188 * Return true if a tooltip with the same is is already active 189 */ 190 private boolean alreadyExist(String id) 191 { 192 final List<IcyFrame> frames = IcyFrame.getAllFrames(ToolTipFrame.class); 193 194 for (IcyFrame f : frames) 195 if ((f != this) && ((ToolTipFrame) f).id.equals(id)) 196 return true; 197 198 return false; 199 } 200 201 void doClose() 202 { 203 // save display flag only if set to false 204 if (!StringUtil.isEmpty(id) && doNotDisplayCheckbox.isSelected()) 205 GeneralPreferences.getPreferencesToolTips().putBoolean(id, false); 206 207 close(); 208 } 209 210 public void setText(final String text) 211 { 212 ThreadUtil.invokeLater(new Runnable() 213 { 214 @Override 215 public void run() 216 { 217 editorPane.setText(text); 218 pack(); 219 } 220 }); 221 } 222 223 @Override 224 public void internalClose() 225 { 226 // stop timer 227 if (timer != null) 228 timer.cancel(); 229 230 super.internalClose(); 231 } 232 233}