/*
* Jitsi, the OpenSource Java VoIP and Instant Messaging client.
*
* Copyright @ 2015 Atlassian Pty Ltd
*
* Licensed under the Apache License, Version 2.0 (the "License");
* you may not use this file except in compliance with the License.
* You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package net.java.sip.communicator.impl.gui.main;
import java.awt.*;
import java.awt.event.*;
import java.beans.*;
import java.util.*;
import java.util.List;
import javax.swing.*;
import net.java.sip.communicator.impl.gui.*;
import net.java.sip.communicator.impl.gui.event.*;
import net.java.sip.communicator.impl.gui.main.call.*;
import net.java.sip.communicator.impl.gui.main.chat.conference.*;
import net.java.sip.communicator.impl.gui.main.contactlist.*;
import net.java.sip.communicator.impl.gui.main.menus.*;
import net.java.sip.communicator.impl.gui.main.presence.*;
import net.java.sip.communicator.plugin.desktoputil.*;
import net.java.sip.communicator.plugin.desktoputil.event.*;
import net.java.sip.communicator.service.contacteventhandler.*;
import net.java.sip.communicator.service.contactlist.*;
import net.java.sip.communicator.service.gui.*;
import net.java.sip.communicator.service.gui.Container;
import net.java.sip.communicator.service.protocol.*;
import net.java.sip.communicator.service.protocol.OperationSetMessageWaiting.MessageType;
import net.java.sip.communicator.service.protocol.event.*;
import net.java.sip.communicator.util.*;
import net.java.sip.communicator.util.Logger;
import net.java.sip.communicator.util.skin.*;
import org.jitsi.service.configuration.*;
import org.jitsi.service.resources.*;
import org.jitsi.util.*;
import org.osgi.framework.*;
import com.explodingpixels.macwidgets.*;
/**
* The main application window. This class is the core of this UI
* implementation. It stores all available protocol providers and their
* operation sets, as well as all registered accounts, the
* MetaContactListService and all sent messages that aren't
* delivered yet.
*
* @author Yana Stamcheva
* @author Lubomir Marinov
* @author Adam Netocny
*/
public class MainFrame
extends SIPCommFrame
implements ContactListContainer,
ExportedWindow,
PluginComponentListener,
Skinnable
{
/**
* Serial version UID.
*/
private static final long serialVersionUID = 0L;
/**
* The logger.
*/
private final Logger logger = Logger.getLogger(MainFrame.class);
/**
* The main container.
*/
private final TransparentPanel mainPanel
= new TransparentPanel(new BorderLayout(0, 0));
/**
* The status bar panel.
*/
private final TransparentPanel statusBarPanel
= new TransparentPanel(new BorderLayout());
/**
* The center panel, containing the contact list.
*/
private final TransparentPanel centerPanel
= new TransparentPanel(new BorderLayout(0, 0));
/**
* The main menu.
*/
private MainMenu menu;
/**
* The search field shown above the contact list.
*/
private SearchField searchField;
/**
* A mapping of ProtocolProviderServices and their indexes.
*/
private final HashMap protocolProviders
= new LinkedHashMap();
/**
* The panel containing the accounts status menu.
*/
private AccountStatusPanel accountStatusPanel;
/**
* The panel replacing the contact list, shown when no matching is found
* for the search filter.
*/
private UnknownContactPanel unknownContactPanel;
/**
* A mapping of ProtocolProviderServices and corresponding
* ContactEventHandlers.
*/
private final Map
providerContactHandlers =
new Hashtable();
/**
* A mapping of plug-in components and their corresponding native components.
*/
private final List nativePluginsTable =
new ArrayList();
/**
* The north plug-in panel.
*/
private final JPanel pluginPanelNorth = new TransparentPanel();
/**
* The south plug-in panel.
*/
private final JPanel pluginPanelSouth = new TransparentPanel();
/**
* The west plug-in panel.
*/
private final JPanel pluginPanelWest = new TransparentPanel();
/**
* The east plug-in panel.
*/
private final JPanel pluginPanelEast = new TransparentPanel();
/**
* The container containing the contact list.
*/
private ContactListPane contactListPanel;
/**
* The user interface provider presence listener.
*/
private ProviderPresenceStatusListener uiProviderPresenceListener;
/**
* The user interface call listener.
*/
private CallListener uiCallListener;
/**
* Contact list search key dispatcher;
*/
private final ContactListSearchKeyDispatcher clKeyDispatcher;
/**
* The keyboard focus manager.
*/
final KeyboardFocusManager keyManager;
/**
* Creates an instance of MainFrame.
*/
public MainFrame()
{
if (!ConfigurationUtils.isWindowDecorated())
{
this.setUndecorated(true);
}
this.contactListPanel = new ContactListPane(this);
this.accountStatusPanel = new AccountStatusPanel();
this.searchField = new SearchField( this,
TreeContactList.searchFilter,
true,
true);
menu = new MainMenu(this);
this.initTitleFont();
ResourceManagementService resources = GuiActivator.getResources();
String applicationName
= resources.getSettingsString("service.gui.APPLICATION_NAME");
this.setTitle(applicationName);
// sets the title to application name
// fix for some windows managers(gnome3)
try
{
Toolkit xToolkit = Toolkit.getDefaultToolkit();
java.lang.reflect.Field awtAppClassNameField =
xToolkit.getClass().getDeclaredField("awtAppClassName");
awtAppClassNameField.setAccessible(true);
awtAppClassNameField.set(xToolkit, applicationName);
}
catch(Throwable t)
{
// we do nothing for it
}
this.mainPanel.setBackground(new Color(
GuiActivator.getResources()
.getColor("service.gui.MAIN_WINDOW_BACKGROUND")));
keyManager = KeyboardFocusManager.getCurrentKeyboardFocusManager();
clKeyDispatcher = new ContactListSearchKeyDispatcher( keyManager,
searchField,
this);
keyManager.addKeyEventDispatcher(clKeyDispatcher);
/*
* If the application is configured to quit when this frame is closed,
* do so.
*/
this.addWindowListener(new WindowAdapter()
{
/**
* Invoked when a window has been closed.
*/
@Override
public void windowClosed(WindowEvent event)
{
MainFrame.this.windowClosed(event);
}
/**
* Invoked when a window has been opened.
*/
@Override
public void windowOpened(WindowEvent e)
{
Window focusedWindow = keyManager.getFocusedWindow();
// If there's no other focused window we request the focus
// in the contact list.
if (focusedWindow == null)
{
requestFocusInContactList();
}
// If some other window keeps the focus we'll wait until it's
// closed.
else if (!focusedWindow.equals(MainFrame.this))
{
requestFocusLater(focusedWindow);
}
}
});
this.init();
this.initPluginComponents();
}
/**
* Adds a WindowListener to the given focusedWindow and once it's
* closed we check again if we can request the focus.
*
* @param focusedWindow the currently focused window
*/
private void requestFocusLater(Window focusedWindow)
{
focusedWindow.addWindowListener(new WindowAdapter()
{
/**
* Invoked when a window has been closed.
*/
@Override
public void windowClosed(WindowEvent event)
{
event.getWindow().removeWindowListener(this);
Window focusedWindow = keyManager.getFocusedWindow();
// If the focused window is null or it's the shared owner frame,
// which keeps focus for closed dialogs without owner, we'll
// request the focus in the contact list.
if (focusedWindow == null
|| focusedWindow.getClass().getName().equals(
"javax.swing.SwingUtilities$SharedOwnerFrame"))
{
requestFocusInContactList();
}
else if (!focusedWindow.equals(MainFrame.this))
{
requestFocusLater(focusedWindow);
}
}
});
}
/**
* Requests the focus in the center panel, which contains either the
* contact list or the unknown contact panel.
*/
public void requestFocusInContactList()
{
centerPanel.requestFocusInWindow();
GuiActivator.getContactList().requestFocus();
}
/**
* Initiates the content of this frame.
*/
private void init()
{
setDefaultCloseOperation(
GuiActivator.getUIService().getExitOnMainWindowClose()
? JFrame.DISPOSE_ON_CLOSE
: JFrame.HIDE_ON_CLOSE);
registerKeyActions();
JComponent northPanel = createTopComponent();
this.setJMenuBar(menu);
TransparentPanel searchPanel
= new TransparentPanel(new BorderLayout(5, 0));
searchPanel.add(searchField);
searchPanel.add(new DialPadButton(), BorderLayout.WEST);
if(!GuiActivator.getConfigurationService().getBoolean(
"net.java.sip.communicator.impl.gui.CALL_HISTORY_BUTTON_DISABLED",
false))
{
searchPanel.add(createButtonPanel(), BorderLayout.EAST);
}
northPanel.add(accountStatusPanel, BorderLayout.CENTER);
northPanel.add(searchPanel, BorderLayout.SOUTH);
centerPanel.add(contactListPanel, BorderLayout.CENTER);
this.mainPanel.add(northPanel, BorderLayout.NORTH);
SingleWindowContainer singleWContainer
= GuiActivator.getUIService().getSingleWindowContainer();
this.mainPanel.add(centerPanel, BorderLayout.CENTER);
if (singleWContainer != null)
{
JSplitPane topSplitPane
= new JSplitPane(JSplitPane.HORIZONTAL_SPLIT);
topSplitPane.setBorder(null); // remove default borders
topSplitPane.setOneTouchExpandable(true);
topSplitPane.setResizeWeight(0);
topSplitPane.setOpaque(false);
topSplitPane.setDividerLocation(200);
topSplitPane.add(mainPanel);
topSplitPane.add(singleWContainer);
getContentPane().add(topSplitPane, BorderLayout.CENTER);
getContentPane().add(statusBarPanel, BorderLayout.SOUTH);
}
else
{
java.awt.Container contentPane = getContentPane();
contentPane.add(mainPanel, BorderLayout.CENTER);
contentPane.add(statusBarPanel, BorderLayout.SOUTH);
}
}
private Component createButtonPanel()
{
boolean isCallButtonEnabled = false;
// Indicates if the big call button outside the search is enabled.
String callButtonEnabledString = GuiActivator.getResources()
.getSettingsString("impl.gui.CALL_BUTTON_ENABLED");
if (callButtonEnabledString != null
&& callButtonEnabledString.length() > 0)
{
isCallButtonEnabled
= new Boolean(callButtonEnabledString).booleanValue();
}
CallHistoryButton historyButton = new CallHistoryButton();
if (isCallButtonEnabled)
{
JPanel panel
= new TransparentPanel(new FlowLayout(FlowLayout.LEFT, 3, 0));
panel.add(new CallButton(this));
panel.add(historyButton);
return panel;
}
else
return historyButton;
}
/**
* Creates the toolbar panel for this chat window, depending on the current
* operating system.
*
* @return the created toolbar
*/
private JComponent createTopComponent()
{
JComponent topComponent = null;
if (OSUtils.IS_MAC)
{
UnifiedToolBar macToolbarPanel = new UnifiedToolBar();
MacUtils.makeWindowLeopardStyle(getRootPane());
macToolbarPanel.getComponent().setLayout(new BorderLayout(5, 5));
macToolbarPanel.getComponent()
.setBorder(BorderFactory.createEmptyBorder(3, 5, 3, 5));
macToolbarPanel.disableBackgroundPainter();
macToolbarPanel.installWindowDraggerOnWindow(this);
// Set the color of the center panel.
centerPanel.setOpaque(true);
centerPanel.setBackground(
new Color(GuiActivator.getResources()
.getColor("service.gui.MAC_PANEL_BACKGROUND")));
topComponent = macToolbarPanel.getComponent();
}
else
{
JPanel panel = new TransparentPanel(new BorderLayout(5, 5));
panel.setBorder(BorderFactory.createEmptyBorder(3, 5, 3, 5));
topComponent = panel;
}
return topComponent;
}
/**
* Sets frame size and position.
*/
public void initBounds()
{
int width = GuiActivator.getResources()
.getSettingsInt("impl.gui.MAIN_WINDOW_WIDTH");
int height = GuiActivator.getResources()
.getSettingsInt("impl.gui.MAIN_WINDOW_HEIGHT");
int minWidth = GuiActivator.getResources()
.getSettingsInt("impl.gui.MAIN_WINDOW_MIN_WIDTH");
int minHeight = GuiActivator.getResources()
.getSettingsInt("impl.gui.MAIN_WINDOW_MIN_HEIGHT");
this.getContentPane().setMinimumSize(new Dimension(minWidth, minHeight));
this.setSize(width, height);
this.setLocation(Toolkit.getDefaultToolkit().getScreenSize().width
- this.getWidth(), 50);
}
/**
* Initialize main window font.
*/
private void initTitleFont()
{
JComponent layeredPane = this.getLayeredPane();
ResourceManagementService resources = GuiActivator.getResources();
String fontName = resources.getSettingsString("service.gui.FONT_NAME");
int fontSize = resources.getSettingsInt("service.gui.FONT_SIZE");
Font font = new Font(fontName, Font.BOLD, fontSize);
for (int i = 0, componentCount = layeredPane.getComponentCount();
i < componentCount;
i++)
layeredPane.getComponent(i).setFont(font);
}
/**
* Enters or exits the "unknown contact" view. This view will propose to
* the user some specific operations if the current filter doesn't match
* any contacts.
* @param isEnabled true to enable the "unknown contact" view,
* false - otherwise.
*/
public void enableUnknownContactView(boolean isEnabled)
{
if (isEnabled)
{
if (unknownContactPanel == null)
unknownContactPanel = new UnknownContactPanel(this);
if (unknownContactPanel.getParent() != centerPanel)
{
contactListPanel.setVisible(false);
unknownContactPanel.setVisible(true);
centerPanel.remove(contactListPanel);
centerPanel.add(unknownContactPanel, BorderLayout.CENTER);
}
}
else
{
if (contactListPanel.getParent() != centerPanel)
{
if (unknownContactPanel != null)
{
unknownContactPanel.setVisible(false);
centerPanel.remove(unknownContactPanel);
}
contactListPanel.setVisible(true);
centerPanel.add(contactListPanel, BorderLayout.CENTER);
}
}
centerPanel.revalidate();
centerPanel.repaint();
}
/**
* Initializes the contact list panel.
*
* @param contactList The MetaContactListService containing
* the contact list data.
*/
public void setContactList(MetaContactListService contactList)
{
contactListPanel.initList(contactList);
searchField.setContactList(GuiActivator.getContactList());
clKeyDispatcher.setContactList(GuiActivator.getContactList());
}
/**
* Adds all protocol supported operation sets.
*
* @param protocolProvider The protocol provider.
*/
public void addProtocolSupportedOperationSets(
ProtocolProviderService protocolProvider)
{
Map supportedOperationSets
= protocolProvider.getSupportedOperationSets();
String ppOpSetClassName = OperationSetPersistentPresence
.class.getName();
String pOpSetClassName = OperationSetPresence.class.getName();
// Obtain the presence operation set.
if (supportedOperationSets.containsKey(ppOpSetClassName)
|| supportedOperationSets.containsKey(pOpSetClassName))
{
OperationSetPresence presence = (OperationSetPresence)
supportedOperationSets.get(ppOpSetClassName);
if(presence == null) {
presence = (OperationSetPresence)
supportedOperationSets.get(pOpSetClassName);
}
uiProviderPresenceListener
= new GUIProviderPresenceStatusListener();
presence.addProviderPresenceStatusListener(
uiProviderPresenceListener);
presence.addContactPresenceStatusListener(
GuiActivator.getContactList().getMetaContactListSource());
}
// Obtain the basic instant messaging operation set.
String imOpSetClassName = OperationSetBasicInstantMessaging
.class.getName();
if (supportedOperationSets.containsKey(imOpSetClassName))
{
OperationSetBasicInstantMessaging im
= (OperationSetBasicInstantMessaging)
supportedOperationSets.get(imOpSetClassName);
//Add to all instant messaging operation sets the Message
//listener implemented in the ContactListPanel, which handles
//all received messages.
im.addMessageListener(getContactListPanel());
}
// Obtain the sms messaging operation set.
String smsOpSetClassName = OperationSetSmsMessaging
.class.getName();
if (supportedOperationSets.containsKey(smsOpSetClassName))
{
OperationSetSmsMessaging sms
= (OperationSetSmsMessaging)
supportedOperationSets.get(smsOpSetClassName);
sms.addMessageListener(getContactListPanel());
}
// Obtain the typing notifications operation set.
String tnOpSetClassName = OperationSetTypingNotifications
.class.getName();
if (supportedOperationSets.containsKey(tnOpSetClassName))
{
OperationSetTypingNotifications tn
= (OperationSetTypingNotifications)
supportedOperationSets.get(tnOpSetClassName);
//Add to all typing notification operation sets the Message
//listener implemented in the ContactListPanel, which handles
//all received messages.
tn.addTypingNotificationsListener(this.getContactListPanel());
}
// Obtain the basic telephony operation set.
String telOpSetClassName = OperationSetBasicTelephony.class.getName();
if (supportedOperationSets.containsKey(telOpSetClassName))
{
OperationSetBasicTelephony> telephony
= (OperationSetBasicTelephony>)
supportedOperationSets.get(telOpSetClassName);
uiCallListener = new CallManager.GuiCallListener();
telephony.addCallListener(uiCallListener);
}
// Obtain the multi user chat operation set.
String multiChatClassName = OperationSetMultiUserChat.class.getName();
if (supportedOperationSets.containsKey(multiChatClassName))
{
OperationSetMultiUserChat multiUserChat
= (OperationSetMultiUserChat)
supportedOperationSets.get(multiChatClassName);
ConferenceChatManager conferenceManager
= GuiActivator.getUIService().getConferenceChatManager();
multiUserChat.addInvitationListener(conferenceManager);
multiUserChat.addInvitationRejectionListener(conferenceManager);
multiUserChat.addPresenceListener(conferenceManager);
}
// Obtain the ad-hoc multi user chat operation set.
OperationSetAdHocMultiUserChat adHocMultiChatOpSet
= protocolProvider
.getOperationSet(OperationSetAdHocMultiUserChat.class);
if (adHocMultiChatOpSet != null)
{
ConferenceChatManager conferenceManager
= GuiActivator.getUIService().getConferenceChatManager();
adHocMultiChatOpSet.addInvitationListener(conferenceManager);
adHocMultiChatOpSet.addInvitationRejectionListener(conferenceManager);
adHocMultiChatOpSet.addPresenceListener(conferenceManager);
}
// Obtain file transfer operation set.
OperationSetFileTransfer fileTransferOpSet
= protocolProvider.getOperationSet(OperationSetFileTransfer.class);
if (fileTransferOpSet != null)
{
fileTransferOpSet.addFileTransferListener(getContactListPanel());
}
OperationSetMessageWaiting messageWaiting
= protocolProvider.getOperationSet(OperationSetMessageWaiting.class);
if (messageWaiting != null)
{
messageWaiting.addMessageWaitingNotificationListener(
MessageType.VOICE,
TreeContactList.getNotificationContactSource());
}
}
/**
* Removes all protocol supported operation sets.
*
* @param protocolProvider The protocol provider.
*/
public void removeProtocolSupportedOperationSets(
ProtocolProviderService protocolProvider)
{
Map supportedOperationSets
= protocolProvider.getSupportedOperationSets();
String ppOpSetClassName = OperationSetPersistentPresence
.class.getName();
String pOpSetClassName = OperationSetPresence.class.getName();
// Obtain the presence operation set.
if (supportedOperationSets.containsKey(ppOpSetClassName)
|| supportedOperationSets.containsKey(pOpSetClassName))
{
OperationSetPresence presence = (OperationSetPresence)
supportedOperationSets.get(ppOpSetClassName);
if(presence == null)
{
presence = (OperationSetPresence)
supportedOperationSets.get(pOpSetClassName);
}
if (uiProviderPresenceListener != null)
presence.removeProviderPresenceStatusListener(
uiProviderPresenceListener);
presence.removeContactPresenceStatusListener(
GuiActivator.getContactList().getMetaContactListSource());
}
// Obtain the basic instant messaging operation set.
String imOpSetClassName = OperationSetBasicInstantMessaging
.class.getName();
if (supportedOperationSets.containsKey(imOpSetClassName))
{
OperationSetBasicInstantMessaging im
= (OperationSetBasicInstantMessaging)
supportedOperationSets.get(imOpSetClassName);
im.removeMessageListener(getContactListPanel());
}
// Obtain the sms messaging operation set.
String smsOpSetClassName = OperationSetSmsMessaging.class.getName();
if (supportedOperationSets.containsKey(smsOpSetClassName))
{
OperationSetSmsMessaging sms
= (OperationSetSmsMessaging)
supportedOperationSets.get(smsOpSetClassName);
sms.removeMessageListener(getContactListPanel());
}
// Obtain the typing notifications operation set.
String tnOpSetClassName = OperationSetTypingNotifications
.class.getName();
if (supportedOperationSets.containsKey(tnOpSetClassName))
{
OperationSetTypingNotifications tn
= (OperationSetTypingNotifications)
supportedOperationSets.get(tnOpSetClassName);
//Add to all typing notification operation sets the Message
//listener implemented in the ContactListPanel, which handles
//all received messages.
tn.removeTypingNotificationsListener(this.getContactListPanel());
}
// Obtain the basic telephony operation set.
String telOpSetClassName = OperationSetBasicTelephony.class.getName();
if (supportedOperationSets.containsKey(telOpSetClassName))
{
OperationSetBasicTelephony> telephony
= (OperationSetBasicTelephony>)
supportedOperationSets.get(telOpSetClassName);
if (uiCallListener != null)
telephony.removeCallListener(uiCallListener);
}
// Obtain the multi user chat operation set.
String multiChatClassName = OperationSetMultiUserChat.class.getName();
if (supportedOperationSets.containsKey(multiChatClassName))
{
OperationSetMultiUserChat multiUserChat
= (OperationSetMultiUserChat)
supportedOperationSets.get(multiChatClassName);
ConferenceChatManager conferenceManager
= GuiActivator.getUIService().getConferenceChatManager();
multiUserChat.removeInvitationListener(conferenceManager);
multiUserChat.removeInvitationRejectionListener(conferenceManager);
multiUserChat.removePresenceListener(conferenceManager);
}
// Obtain the ad-hoc multi user chat operation set.
OperationSetAdHocMultiUserChat adHocMultiChatOpSet
= protocolProvider
.getOperationSet(OperationSetAdHocMultiUserChat.class);
if (adHocMultiChatOpSet != null)
{
ConferenceChatManager conferenceManager
= GuiActivator.getUIService().getConferenceChatManager();
adHocMultiChatOpSet
.removeInvitationListener(conferenceManager);
adHocMultiChatOpSet
.removeInvitationRejectionListener(conferenceManager);
adHocMultiChatOpSet
.removePresenceListener(conferenceManager);
}
// Obtain file transfer operation set.
OperationSetFileTransfer fileTransferOpSet
= protocolProvider.getOperationSet(OperationSetFileTransfer.class);
if (fileTransferOpSet != null)
{
fileTransferOpSet.removeFileTransferListener(getContactListPanel());
}
OperationSetMessageWaiting messageWaiting
= protocolProvider.getOperationSet(OperationSetMessageWaiting.class);
if (messageWaiting != null)
{
messageWaiting.removeMessageWaitingNotificationListener(
MessageType.VOICE,
TreeContactList.getNotificationContactSource());
}
}
/**
* Returns a set of all protocol providers.
*
* @return a set of all protocol providers.
*/
public Iterator getProtocolProviders()
{
return new LinkedList(
protocolProviders.keySet())
.iterator();
}
/**
* Returns the protocol provider associated to the account given
* by the account user identifier.
*
* @param accountName The account user identifier.
* @return The protocol provider associated to the given account.
*/
public ProtocolProviderService getProtocolProviderForAccount(
String accountName)
{
for (ProtocolProviderService pps : protocolProviders.keySet())
{
if (pps.getAccountID().getUserID().equals(accountName))
{
return pps;
}
}
return null;
}
/**
* Adds a protocol provider.
* @param protocolProvider The protocol provider to add.
*/
public void addProtocolProvider(ProtocolProviderService protocolProvider)
{
synchronized(this.protocolProviders)
{
if(this.protocolProviders.containsKey(protocolProvider))
return;
this.protocolProviders.put(protocolProvider,
initiateProviderIndex(protocolProvider));
}
if (logger.isTraceEnabled())
logger.trace("Add the following protocol provider to the gui: "
+ protocolProvider.getAccountID().getAccountAddress());
this.addProtocolSupportedOperationSets(protocolProvider);
this.addAccount(protocolProvider);
ContactEventHandler contactHandler
= this.getContactHandlerForProvider(protocolProvider);
if (contactHandler == null)
contactHandler = new DefaultContactEventHandler(this);
this.addProviderContactHandler(protocolProvider, contactHandler);
}
/**
* Checks whether we have already loaded the protocol provider.
* @param protocolProvider the provider to check.
* @return whether we have already loaded the specified provider.
*/
public boolean hasProtocolProvider(
ProtocolProviderService protocolProvider)
{
synchronized(this.protocolProviders)
{
return this.protocolProviders.containsKey(protocolProvider);
}
}
/**
* Checks whether we have the operation set in already loaded
* protocol providers.
* @param opSet the operation set to check.
* @return whether we have provider to handle operation set.
*/
public boolean hasOperationSet(Class extends OperationSet> opSet)
{
synchronized(this.protocolProviders)
{
Iterator iter =
this.protocolProviders.keySet().iterator();
while(iter.hasNext())
{
ProtocolProviderService pp = iter.next();
if(pp.getOperationSet(opSet) != null)
{
return true;
}
}
return false;
}
}
/**
* Adds an account to the application.
*
* @param protocolProvider The protocol provider of the account.
*/
public void removeProtocolProvider(ProtocolProviderService protocolProvider)
{
if (logger.isTraceEnabled())
logger.trace("Remove the following protocol provider to the gui: "
+ protocolProvider.getAccountID().getAccountAddress());
synchronized(this.protocolProviders)
{
this.protocolProviders.remove(protocolProvider);
}
this.removeProtocolSupportedOperationSets(protocolProvider);
removeProviderContactHandler(protocolProvider);
this.updateProvidersIndexes(protocolProvider);
accountStatusPanel.removeAccount(protocolProvider);
}
/**
* Returns the index of the given protocol provider.
* @param protocolProvider the protocol provider to search for
* @return the index of the given protocol provider
*/
public int getProviderIndex(ProtocolProviderService protocolProvider)
{
Integer o = protocolProviders.get(protocolProvider);
return (o != null) ? o : 0;
}
/**
* Adds an account to the application.
*
* @param protocolProvider The protocol provider of the account.
*/
public void addAccount(ProtocolProviderService protocolProvider)
{
if (!accountStatusPanel.containsAccount(protocolProvider))
{
if (logger.isTraceEnabled())
logger.trace("Add the following account to the status bar: "
+ protocolProvider.getAccountID().getAccountAddress());
accountStatusPanel.addAccount(protocolProvider);
//request the focus in the contact list panel, which
//permits to search in the contact list
// this.contactListPanel.getContactList()
// .requestFocus();
}
}
/**
* Returns the account user id for the given protocol provider.
* @param protocolProvider the protocol provider corresponding to the
* account to add
* @return The account user id for the given protocol provider.
*/
public String getAccountAddress(ProtocolProviderService protocolProvider)
{
return protocolProvider.getAccountID().getAccountAddress();
}
/**
* Returns the account user display name for the given protocol provider.
* @param protocolProvider the protocol provider corresponding to the
* account to add
* @return The account user display name for the given protocol provider.
*/
public String getAccountDisplayName(ProtocolProviderService protocolProvider)
{
final OperationSetServerStoredAccountInfo accountInfoOpSet
= protocolProvider.getOperationSet(
OperationSetServerStoredAccountInfo.class);
try
{
if (accountInfoOpSet != null)
{
String displayName
= AccountInfoUtils.getDisplayName(accountInfoOpSet);
if(displayName != null && displayName.length() > 0)
return displayName;
}
}
catch(Throwable e)
{
logger.error("Cannot obtain display name through OPSet");
}
return protocolProvider.getAccountID().getDisplayName();
}
/**
* Returns the Web Contact Info operation set for the given
* protocol provider.
*
* @param protocolProvider The protocol provider for which the TN
* is searched.
* @return OperationSetWebContactInfo The Web Contact Info operation
* set for the given protocol provider.
*/
public OperationSetWebContactInfo getWebContactInfoOpSet(
ProtocolProviderService protocolProvider)
{
OperationSet opSet
= protocolProvider.getOperationSet(OperationSetWebContactInfo.class);
return (opSet instanceof OperationSetWebContactInfo)
? (OperationSetWebContactInfo) opSet
: null;
}
/**
* Returns the telephony operation set for the given protocol provider.
*
* @param protocolProvider The protocol provider for which the telephony
* operation set is about.
* @return OperationSetBasicTelephony The telephony operation
* set for the given protocol provider.
*/
public OperationSetBasicTelephony> getTelephonyOpSet(
ProtocolProviderService protocolProvider)
{
OperationSet opSet
= protocolProvider.getOperationSet(OperationSetBasicTelephony.class);
return (opSet instanceof OperationSetBasicTelephony>)
? (OperationSetBasicTelephony>) opSet
: null;
}
/**
* Returns the multi user chat operation set for the given protocol provider.
*
* @param protocolProvider The protocol provider for which the multi user
* chat operation set is about.
* @return OperationSetAdHocMultiUserChat The telephony operation
* set for the given protocol provider.
*/
public OperationSetAdHocMultiUserChat getAdHocMultiUserChatOpSet(
ProtocolProviderService protocolProvider)
{
OperationSet opSet
= protocolProvider.getOperationSet(
OperationSetAdHocMultiUserChat.class);
return (opSet instanceof OperationSetAdHocMultiUserChat)
? (OperationSetAdHocMultiUserChat) opSet
: null;
}
/**
* Returns true if there's any currently selected menu related to
* this ContactListContainer, false - otherwise.
*
* @return true if there's any currently selected menu related to
* this ContactListContainer, false - otherwise
*/
public boolean isMenuSelected()
{
return menu.hasSelectedMenus();
}
/**
* Listens for all providerStatusChanged and providerStatusMessageChanged
* events in order to refresh the account status panel, when a status is
* changed.
*/
private class GUIProviderPresenceStatusListener
implements ProviderPresenceStatusListener
{
public void providerStatusChanged(ProviderPresenceStatusChangeEvent evt)
{
ProtocolProviderService pps = evt.getProvider();
accountStatusPanel.updateStatus(pps, evt.getNewStatus());
}
public void providerStatusMessageChanged(PropertyChangeEvent evt) {}
}
/**
* Returns the panel containing the ContactList.
* @return ContactListPanel the panel containing the ContactList
*/
public ContactListPane getContactListPanel()
{
return this.contactListPanel;
}
/**
* Returns the text currently shown in the search field.
* @return the text currently shown in the search field
*/
public String getCurrentSearchText()
{
return searchField.getText();
}
/**
* Clears the current text in the search field.
*/
public void clearCurrentSearchText()
{
searchField.setText("");
}
/**
* Adds the given TextFieldChangeListener to listen for any changes
* that occur in the search field.
* @param l the TextFieldChangeListener to add
*/
public void addSearchFieldListener(TextFieldChangeListener l)
{
searchField.addTextChangeListener(l);
}
/**
* Removes the given TextFieldChangeListener that listens for any
* changes that occur in the search field.
* @param l the TextFieldChangeListener to remove
*/
public void removeSearchFieldListener(TextFieldChangeListener l)
{
searchField.addTextChangeListener(l);
}
/**
* Checks in the configuration xml if there is already stored index for
* this provider and if yes, returns it, otherwise creates a new account
* index and stores it.
*
* @param protocolProvider the protocol provider
* @return the protocol provider index
*/
private int initiateProviderIndex(
ProtocolProviderService protocolProvider)
{
ConfigurationService configService
= GuiActivator.getConfigurationService();
String prefix = "net.java.sip.communicator.impl.gui.accounts";
List accounts = configService
.getPropertyNamesByPrefix(prefix, true);
for (String accountRootPropName : accounts) {
String accountUID
= configService.getString(accountRootPropName);
if(accountUID.equals(protocolProvider
.getAccountID().getAccountUniqueID()))
{
String index = configService.getString(
accountRootPropName + ".accountIndex");
if(index != null) {
//if we have found the accountIndex for this protocol provider
//return this index
return Integer.parseInt(index);
}
else
{
//if there's no stored accountIndex for this protocol
//provider, calculate the index, set it in the configuration
//service and return it.
return createAccountIndex(protocolProvider,
accountRootPropName);
}
}
}
String accNodeName
= "acc" + Long.toString(System.currentTimeMillis());
String accountPackage
= "net.java.sip.communicator.impl.gui.accounts."
+ accNodeName;
configService.setProperty(accountPackage,
protocolProvider.getAccountID().getAccountUniqueID());
return createAccountIndex(protocolProvider,
accountPackage);
}
/**
* Creates and calculates the account index for the given protocol
* provider.
* @param protocolProvider the protocol provider
* @param accountRootPropName the path to where the index should be saved
* in the configuration xml
* @return the created index
*/
private int createAccountIndex(ProtocolProviderService protocolProvider,
String accountRootPropName)
{
ConfigurationService configService
= GuiActivator.getConfigurationService();
int accountIndex = -1;
for (ProtocolProviderService pps : protocolProviders.keySet())
{
if (pps.getProtocolDisplayName().equals(
protocolProvider.getProtocolDisplayName())
&& !pps.equals(protocolProvider))
{
int index = protocolProviders.get(pps);
if (accountIndex < index)
accountIndex = index;
}
}
accountIndex++;
configService.setProperty(
accountRootPropName + ".accountIndex",
accountIndex);
return accountIndex;
}
/**
* Updates the indexes in the configuration xml, when a provider has been
* removed.
* @param removedProvider the removed protocol provider
*/
private void updateProvidersIndexes(ProtocolProviderService removedProvider)
{
ConfigurationService configService
= GuiActivator.getConfigurationService();
String prefix = "net.java.sip.communicator.impl.gui.accounts";
ProtocolProviderService currentProvider = null;
int sameProtocolProvidersCount = 0;
for (ProtocolProviderService pps : protocolProviders.keySet()) {
if(pps.getProtocolDisplayName().equals(
removedProvider.getProtocolDisplayName())) {
sameProtocolProvidersCount++;
if(sameProtocolProvidersCount > 1) {
break;
}
currentProvider = pps;
}
}
if(sameProtocolProvidersCount < 2 && currentProvider != null) {
protocolProviders.put(currentProvider, 0);
List accounts = configService
.getPropertyNamesByPrefix(prefix, true);
for (String rootPropName : accounts) {
String accountUID
= configService.getString(rootPropName);
if(accountUID.equals(currentProvider
.getAccountID().getAccountUniqueID())) {
configService.setProperty(
rootPropName + ".accountIndex",
0);
}
}
}
}
/**
* Overwrites the SIPCommFrame close method. This method is
* invoked when user presses the Escape key.
* @param isEscaped indicates if this window has been closed by pressing
* the escape key
*/
@Override
protected void close(boolean isEscaped)
{
TreeContactList contactList = GuiActivator.getContactList();
Component contactListRightMenu
= contactList.getRightButtonMenu();
CommonRightButtonMenu commonPopupMenu
= getContactListPanel().getCommonRightButtonMenu();
if(contactListRightMenu != null && contactListRightMenu.isVisible())
{
contactListRightMenu.setVisible(false);
}
else if(commonPopupMenu != null && commonPopupMenu.isVisible())
{
commonPopupMenu.setVisible(false);
}
else if(accountStatusPanel.hasSelectedMenus()
|| menu.hasSelectedMenus())
{
MenuSelectionManager selectionManager
= MenuSelectionManager.defaultManager();
selectionManager.clearSelectedPath();
}
}
/**
* Returns the main menu in the application window.
* @return the main menu in the application window
*/
public MainMenu getMainMenu()
{
return menu;
}
/**
* Adds the given contactHandler to handle contact events for the
* given protocolProvider.
*
* @param protocolProvider the ProtocolProviderService, which
* contacts should be handled by the given contactHandler
* @param contactHandler the ContactEventHandler that would handle
* events coming from the UI for any contacts belonging to the given
* provider
*/
public void addProviderContactHandler(
ProtocolProviderService protocolProvider,
ContactEventHandler contactHandler)
{
providerContactHandlers.put(protocolProvider, contactHandler);
}
/**
* Removes the ContactEventHandler corresponding to the given
* protocolProvider.
*
* @param protocolProvider the protocol provider, which contact handler
* we would like to remove
*/
public void removeProviderContactHandler(
ProtocolProviderService protocolProvider)
{
providerContactHandlers.remove(protocolProvider);
}
/**
* Returns the ContactEventHandler registered for this protocol
* provider.
*
* @param protocolProvider the ProtocolProviderService for which
* we are searching a ContactEventHandler.
* @return the ContactEventHandler registered for this protocol
* provider
*/
public ContactEventHandler getContactHandler(
ProtocolProviderService protocolProvider)
{
return providerContactHandlers.get(protocolProvider);
}
/**
* Returns the ContactEventHandler for contacts given by the
* protocolProvider. The ContactEventHandler is meant to
* be used from other bundles in order to change the default behavior of
* events generated when clicking a contact.
* @param protocolProvider the protocol provider for which we want to obtain
* a contact event handler
* @return the ContactEventHandler for contacts given by the
* protocolProvider
*/
private ContactEventHandler getContactHandlerForProvider(
ProtocolProviderService protocolProvider)
{
Collection> serRefs;
String osgiFilter
= "(" + ProtocolProviderFactory.PROTOCOL + "="
+ protocolProvider.getProtocolName() + ")";
try
{
serRefs
= GuiActivator.bundleContext.getServiceReferences(
ContactEventHandler.class,
osgiFilter);
}
catch (InvalidSyntaxException ex)
{
serRefs = null;
logger.error("GuiActivator : " + ex);
}
if ((serRefs == null) || serRefs.isEmpty())
return null;
return GuiActivator.bundleContext.getService(serRefs.iterator().next());
}
/**
* Initialize plugin components already registered for this container.
*/
private void initPluginComponents()
{
pluginPanelSouth.setLayout(
new BoxLayout(pluginPanelSouth, BoxLayout.Y_AXIS));
pluginPanelNorth.setLayout(
new BoxLayout(pluginPanelNorth, BoxLayout.Y_AXIS));
pluginPanelEast.setLayout(
new BoxLayout(pluginPanelEast, BoxLayout.Y_AXIS));
pluginPanelWest.setLayout(
new BoxLayout(pluginPanelWest, BoxLayout.Y_AXIS));
java.awt.Container contentPane = getContentPane();
contentPane.add(pluginPanelNorth, BorderLayout.NORTH);
contentPane.add(pluginPanelEast, BorderLayout.EAST);
contentPane.add(pluginPanelWest, BorderLayout.WEST);
this.mainPanel.add(pluginPanelSouth, BorderLayout.SOUTH);
// Search for plugin components registered through the OSGI bundle
// context.
Collection> serRefs;
try
{
serRefs
= GuiActivator.bundleContext.getServiceReferences(
PluginComponentFactory.class,
"(|(" + Container.CONTAINER_ID + "="
+ Container.CONTAINER_MAIN_WINDOW.getID() + ")("
+ Container.CONTAINER_ID + "="
+ Container.CONTAINER_STATUS_BAR.getID() + "))");
}
catch (InvalidSyntaxException exc)
{
serRefs = null;
logger.error("Could not obtain plugin reference.", exc);
}
if ((serRefs != null) && !serRefs.isEmpty())
{
for (ServiceReference serRef : serRefs)
{
PluginComponentFactory factory
= GuiActivator.bundleContext.getService(serRef);
if (factory.isNativeComponent())
nativePluginsTable.add(factory);
else
{
String pluginConstraints = factory.getConstraints();
Object constraints;
if (pluginConstraints != null)
constraints
= UIServiceImpl
.getBorderLayoutConstraintsFromContainer(
pluginConstraints);
else
constraints = BorderLayout.SOUTH;
this.addPluginComponent(
(Component)factory.getPluginComponentInstance(this)
.getComponent(),
factory.getContainer(),
constraints);
}
}
}
GuiActivator.getUIService().addPluginComponentListener(this);
}
/**
* Adds the associated with this PluginComponentEvent component to
* the appropriate container.
* @param event the PluginComponentEvent that has notified us of
* the add of a plugin component
*/
public void pluginComponentAdded(PluginComponentEvent event)
{
PluginComponentFactory factory = event.getPluginComponentFactory();
Container pluginContainer = factory.getContainer();
if (pluginContainer.equals(Container.CONTAINER_MAIN_WINDOW)
|| pluginContainer.equals(Container.CONTAINER_STATUS_BAR))
{
String pluginConstraints = factory.getConstraints();
Object constraints;
if (pluginConstraints != null)
constraints =
UIServiceImpl
.getBorderLayoutConstraintsFromContainer(pluginConstraints);
else
constraints = BorderLayout.SOUTH;
if (factory.isNativeComponent())
{
this.nativePluginsTable.add(factory);
if (isFrameVisible())
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
addNativePlugins();
}
});
}
}
else
{
this.addPluginComponent(
(Component)factory
.getPluginComponentInstance(MainFrame.this)
.getComponent(),
pluginContainer,
constraints);
}
}
}
/**
* Removes the associated with this PluginComponentEvent component
* from this container.
* @param event the PluginComponentEvent that notified us of the
* remove of a plugin component
*/
public void pluginComponentRemoved(PluginComponentEvent event)
{
final PluginComponentFactory factory =
event.getPluginComponentFactory();
final Container containerID = factory.getContainer();
if (containerID.equals(Container.CONTAINER_MAIN_WINDOW))
{
Object constraints = UIServiceImpl
.getBorderLayoutConstraintsFromContainer(
factory.getConstraints());
if (constraints == null)
constraints = BorderLayout.SOUTH;
if (factory.isNativeComponent())
{
if (nativePluginsTable.contains(factory))
{
final Object finalConstraints = constraints;
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
removePluginComponent(
(Component)factory.getPluginComponentInstance(
MainFrame.this).getComponent(),
containerID,
finalConstraints);
getContentPane().repaint();
}
});
}
}
else
{
this.removePluginComponent(
(Component) factory
.getPluginComponentInstance(MainFrame.this)
.getComponent(),
containerID,
constraints);
}
nativePluginsTable.remove(factory);
}
}
/**
* Removes all native plugins from this container.
*/
private void removeNativePlugins()
{
for (PluginComponentFactory factory: nativePluginsTable)
{
Object constraints
= UIServiceImpl
.getBorderLayoutConstraintsFromContainer(factory
.getConstraints());
if (constraints == null)
constraints = BorderLayout.SOUTH;
this.removePluginComponent(
(Component)factory.getPluginComponentInstance(MainFrame.this)
.getComponent(),
factory.getContainer(),
constraints);
this.getContentPane().repaint();
}
}
/**
* Adds all native plugins to this container.
*/
public void addNativePlugins()
{
this.removeNativePlugins();
for (PluginComponentFactory factory: nativePluginsTable)
{
Object constraints
= UIServiceImpl
.getBorderLayoutConstraintsFromContainer(
factory.getConstraints());
Component c = (Component) factory
.getPluginComponentInstance(MainFrame.this)
.getComponent();
this.addPluginComponent(c, factory.getContainer(), constraints);
this.nativePluginsTable.add(factory);
}
}
/**
* Brings this window to front.
*/
public void bringToFront()
{
this.toFront();
}
/**
* Returns the identifier of this window.
* @return the identifier of this window
*/
public WindowID getIdentifier()
{
return ExportedWindow.MAIN_WINDOW;
}
/**
* Returns this window.
* @return this window
*/
public Object getSource()
{
return this;
}
/**
* Maximizes this window.
*/
public void maximize()
{
this.setExtendedState(JFrame.MAXIMIZED_BOTH);
}
/**
* Minimizes this window.
*/
public void minimize()
{
this.setExtendedState(JFrame.ICONIFIED);
}
/**
* Implements isVisible
in the UIService interface. Checks if
* the main application window is visible.
*
* @return true
if main application window is visible,
* false
otherwise
* @see UIService#isVisible()
*/
public boolean isFrameVisible()
{
return super.isVisible()
&& (super.getExtendedState() != JFrame.ICONIFIED);
}
/**
* Implements setVisible
in the UIService interface. Shows or
* hides the main application window depending on the parameter
* visible
.
*
* @param isVisible true if we are to show the main application frame and
* false otherwise.
*
* @see UIService#setVisible(boolean)
*/
public void setFrameVisible(final boolean isVisible)
{
ConfigurationUtils.setApplicationVisible(isVisible);
SwingUtilities.invokeLater(new Runnable(){
public void run()
{
if(isVisible)
{
MainFrame.this.addNativePlugins();
Window focusedWindow = keyManager.getFocusedWindow();
// If there's another currently focused window we prevent
// this frame from steeling the focus. This happens for
// example in the case of a Master Password window which is
// opened before the contact list window.
if (focusedWindow != null)
setFocusableWindowState(false);
MainFrame.super.setVisible(isVisible);
if (focusedWindow != null)
setFocusableWindowState(true);
MainFrame.super.setExtendedState(MainFrame.NORMAL);
MainFrame.super.toFront();
}
else
{
MainFrame.super.setVisible(isVisible);
}
}
});
}
/**
* Adds the given component with to the container corresponding to the
* given constraints.
*
* @param c the component to add
* @param container the container to which to add the given component
* @param constraints the constraints determining the container
*/
private void addPluginComponent(Component c,
Container container,
Object constraints)
{
if (container.equals(Container.CONTAINER_MAIN_WINDOW))
{
if (constraints.equals(BorderLayout.NORTH))
{
pluginPanelNorth.add(c);
pluginPanelNorth.repaint();
}
else if (constraints.equals(BorderLayout.SOUTH))
{
pluginPanelSouth.add(c);
pluginPanelSouth.repaint();
}
else if (constraints.equals(BorderLayout.WEST))
{
pluginPanelWest.add(c);
pluginPanelWest.repaint();
}
else if (constraints.equals(BorderLayout.EAST))
{
pluginPanelEast.add(c);
pluginPanelEast.repaint();
}
}
else if (container.equals(Container.CONTAINER_STATUS_BAR))
{
statusBarPanel.add(c);
}
this.getContentPane().repaint();
this.getContentPane().validate();
}
/**
* Removes the given component from the container corresponding to the given
* constraints.
*
* @param c the component to remove
* @param container the container from which to remove the given component
* @param constraints the constraints determining the container
*/
private void removePluginComponent( Component c,
Container container,
Object constraints)
{
if (container.equals(Container.CONTAINER_MAIN_WINDOW))
{
if (constraints.equals(BorderLayout.NORTH))
pluginPanelNorth.remove(c);
else if (constraints.equals(BorderLayout.SOUTH))
pluginPanelSouth.remove(c);
else if (constraints.equals(BorderLayout.WEST))
pluginPanelWest.remove(c);
else if (constraints.equals(BorderLayout.EAST))
pluginPanelEast.remove(c);
}
else if (container.equals(Container.CONTAINER_STATUS_BAR))
{
this.statusBarPanel.remove(c);
}
}
/**
* Returns the account status panel.
* @return the account status panel.
*/
public AccountStatusPanel getAccountStatusPanel()
{
return accountStatusPanel;
}
/**
* Implementation of {@link ExportedWindow#setParams(Object[])}.
*/
public void setParams(Object[] windowParams) {}
/**
* @param event Currently not used
*/
protected void windowClosed(WindowEvent event)
{
if(GuiActivator.getUIService().getExitOnMainWindowClose())
{
try
{
GuiActivator.bundleContext.getBundle(0).stop();
}
catch (BundleException ex)
{
logger.error("Failed to gently shutdown Felix", ex);
System.exit(0);
}
//stopping a bundle doesn't leave the time to the felix thread to
//properly end all bundles and call their Activator.stop() methods.
//if this causes problems don't uncomment the following line but
//try and see why felix isn't exiting (suggesting: is it running
//in embedded mode?)
//System.exit(0);
}
}
/**
* Overrides SIPCommFrame#windowClosing(WindowEvent). Reflects the closed
* state of this MainFrame in the configuration in order to make it
* accessible to interested parties, displays the warning that the
* application will not quit.
* @param event the WindowEvent that notified us
*/
@Override
protected void windowClosing(WindowEvent event)
{
super.windowClosing(event);
// On Mac systems the application is not quited on window close, so we
// don't need to warn the user.
if (!GuiActivator.getUIService().getExitOnMainWindowClose()
&& !OSUtils.IS_MAC)
{
SwingUtilities.invokeLater(new Runnable()
{
public void run()
{
if (ConfigurationUtils.isQuitWarningShown())
{
MessageDialog dialog =
new MessageDialog(null,
GuiActivator.getResources().getI18NString(
"service.gui.CLOSE"),
GuiActivator.getResources().getI18NString(
"service.gui.HIDE_MAIN_WINDOW"), false);
if (dialog.showDialog() == MessageDialog.OK_DONT_ASK_CODE)
ConfigurationUtils.setQuitWarningShown(false);
}
}
});
ConfigurationUtils.setApplicationVisible(false);
}
}
/**
* Called when the ENTER key was typed when this window was the focused
* window. Performs the appropriate actions depending on the current state
* of the contact list.
*/
public void enterKeyTyped()
{
if (unknownContactPanel != null && unknownContactPanel.isVisible())
{
unknownContactPanel.addUnknownContact();
}
else if (contactListPanel.isVisible())
{
// Starts a chat with the currently selected contact.
GuiActivator.getContactList().startSelectedContactChat();
}
}
/**
* Called when the CTRL-ENTER or CMD-ENTER keys were typed when this window
* was the focused window. Performs the appropriate actions depending on the
* current state of the contact list.
*/
public void ctrlEnterKeyTyped()
{
if (unknownContactPanel != null && unknownContactPanel.isVisible())
{
unknownContactPanel.startCall();
}
else if (contactListPanel.isVisible())
{
// Starts a chat with the currently selected contact.
GuiActivator.getContactList().startSelectedContactCall();
}
}
/**
* Registers key actions for this window.
*/
private void registerKeyActions()
{
InputMap inputMap = getRootPane()
.getInputMap(JComponent.WHEN_ANCESTOR_OF_FOCUSED_COMPONENT);
// Remove the default escape key mapping as its a special
// one for the main frame and the contactlist
inputMap.remove(KeyStroke.getKeyStroke(KeyEvent.VK_ESCAPE, 0));
}
/**
* Reloads skin information
*/
public void loadSkin()
{
this.mainPanel.setBackground(new Color(
GuiActivator.getResources()
.getColor("service.gui.MAIN_WINDOW_BACKGROUND")));
}
}