From 20bff15f6c497b9632641f97a96b966d909cdadb Mon Sep 17 00:00:00 2001 From: Yana Stamcheva Date: Fri, 19 Jun 2009 12:20:24 +0000 Subject: [PATCH] - Double click on file image in outgoing file transfer would open the file. - Popup and sound notification for incoming file transfer - in the future the popup notification could be extended to allow to show a custom icon in order to show a file preview. - Set the default (arrow) cursor when over a file transfer component (instead of the edit cursor, which is default for the chat conversation area). --- resources/sounds/sounds.properties | 1 + .../main/chat/ChatConversationComponent.java | 82 ++++++++++++++++++- .../ReceiveFileConversationComponent.java | 67 +-------------- .../SendFileConversationComponent.java | 48 +++++++++-- .../gui/main/contactlist/ContactListPane.java | 12 +++ .../impl/gui/utils/NotificationManager.java | 15 ++++ .../impl/gui/utils/SoundProperties.java | 3 + 7 files changed, 156 insertions(+), 72 deletions(-) diff --git a/resources/sounds/sounds.properties b/resources/sounds/sounds.properties index e644ec0cf..2d0ed7525 100644 --- a/resources/sounds/sounds.properties +++ b/resources/sounds/sounds.properties @@ -1,4 +1,5 @@ INCOMING_MESSAGE=resources/sounds/incomingMessage.wav +INCOMING_FILE=resources/sounds/incomingMessage.wav INCOMING_CALL=resources/sounds/incomingCall.wav OUTGOING_CALL=resources/sounds/ring.wav diff --git a/src/net/java/sip/communicator/impl/gui/main/chat/ChatConversationComponent.java b/src/net/java/sip/communicator/impl/gui/main/chat/ChatConversationComponent.java index f08dd235a..eecc203d1 100644 --- a/src/net/java/sip/communicator/impl/gui/main/chat/ChatConversationComponent.java +++ b/src/net/java/sip/communicator/impl/gui/main/chat/ChatConversationComponent.java @@ -8,10 +8,13 @@ import java.awt.*; import java.awt.event.*; +import java.io.*; import javax.swing.*; import net.java.sip.communicator.impl.gui.*; +import net.java.sip.communicator.service.resources.*; +import net.java.sip.communicator.util.*; import net.java.sip.communicator.util.swing.*; /** @@ -21,9 +24,12 @@ * * @author Yana Stamcheva */ -public class ChatConversationComponent +public abstract class ChatConversationComponent extends JPanel { + private static final Logger logger + = Logger.getLogger(ChatConversationComponent.class); + protected final GridBagConstraints constraints = new GridBagConstraints(); private static final Color defaultColor @@ -36,6 +42,9 @@ public class ChatConversationComponent private Color backgroundColor = defaultColor; + protected static final ResourceManagementService resources + = GuiActivator.getResources(); + /** * Creates a ChatConversationComponent. */ @@ -43,6 +52,7 @@ public ChatConversationComponent() { this.setLayout(new GridBagLayout()); this.setOpaque(false); + this.setCursor(Cursor.getDefaultCursor()); } /** @@ -147,4 +157,74 @@ private void internalPaintComponent(Graphics g) g2.fillRoundRect( 1, 1, this.getWidth() - 1, this.getHeight() -1, 15, 15); } + + /** + * Opens the given file through the DesktopService. + * + * @param downloadFile the file to open + */ + protected void openFile(File downloadFile) + { + try + { + GuiActivator.getDesktopService().open(downloadFile); + } + catch (IllegalArgumentException e) + { + logger.debug("Unable to open file.", e); + + this.showErrorMessage( + resources.getI18NString( + "service.gui.FILE_DOES_NOT_EXIST")); + } + catch (NullPointerException e) + { + logger.debug("Unable to open file.", e); + + this.showErrorMessage( + resources.getI18NString( + "service.gui.FILE_DOES_NOT_EXIST")); + } + catch (UnsupportedOperationException e) + { + logger.debug("Unable to open file.", e); + + this.showErrorMessage( + resources.getI18NString( + "service.gui.FILE_OPEN_NOT_SUPPORTED")); + } + catch (SecurityException e) + { + logger.debug("Unable to open file.", e); + + this.showErrorMessage( + resources.getI18NString( + "service.gui.FILE_OPEN_NO_PERMISSION")); + } + catch (IOException e) + { + logger.debug("Unable to open file.", e); + + this.showErrorMessage( + resources.getI18NString( + "service.gui.FILE_OPEN_NO_APPLICATION")); + } + catch (Exception e) + { + logger.debug("Unable to open file.", e); + + this.showErrorMessage( + resources.getI18NString( + "service.gui.FILE_OPEN_FAILED")); + } + } + + /** + * Shows the given error message to the user. This method is made abstract + * in order to allow extension classes to provide custom implementations + * of how errors are shown to the users. + * + * @param errorMessage the error message to show + */ + protected abstract void showErrorMessage(String errorMessage); } diff --git a/src/net/java/sip/communicator/impl/gui/main/chat/filetransfer/ReceiveFileConversationComponent.java b/src/net/java/sip/communicator/impl/gui/main/chat/filetransfer/ReceiveFileConversationComponent.java index 3fbe6daa4..10d5c14a7 100644 --- a/src/net/java/sip/communicator/impl/gui/main/chat/filetransfer/ReceiveFileConversationComponent.java +++ b/src/net/java/sip/communicator/impl/gui/main/chat/filetransfer/ReceiveFileConversationComponent.java @@ -18,7 +18,6 @@ import net.java.sip.communicator.impl.gui.utils.*; import net.java.sip.communicator.service.protocol.*; import net.java.sip.communicator.service.protocol.event.*; -import net.java.sip.communicator.service.resources.*; import net.java.sip.communicator.util.*; import net.java.sip.communicator.util.swing.*; // Disambiguates SwingWorker on Java 6 in the presence of javax.swing.* @@ -57,9 +56,6 @@ public class ReceiveFileConversationComponent private JProgressBar progressBar = new JProgressBar(); - private static final ResourceManagementService resources - = GuiActivator.getResources(); - private IncomingFileTransferRequest fileTransferRequest; private FileTransfer fileTransfer; @@ -535,7 +531,7 @@ public void finished() * * @param message the message to show */ - private void showErrorMessage(String message) + protected void showErrorMessage(String message) { errorArea.setText(message); errorIconLabel.setVisible(true); @@ -553,65 +549,4 @@ private void setTextAreaStyle(JTextArea textArea) textArea.setLineWrap(true); textArea.setWrapStyleWord(true); } - - /** - * Opens the given file through the DesktopService. - * - * @param downloadFile the file to open - */ - private void openFile(File downloadFile) - { - try - { - GuiActivator.getDesktopService().open(downloadFile); - } - catch (IllegalArgumentException e) - { - logger.debug("Unable to open file.", e); - - this.showErrorMessage( - resources.getI18NString( - "service.gui.FILE_DOES_NOT_EXIST")); - } - catch (NullPointerException e) - { - logger.debug("Unable to open file.", e); - - this.showErrorMessage( - resources.getI18NString( - "service.gui.FILE_DOES_NOT_EXIST")); - } - catch (UnsupportedOperationException e) - { - logger.debug("Unable to open file.", e); - - this.showErrorMessage( - resources.getI18NString( - "service.gui.FILE_OPEN_NOT_SUPPORTED")); - } - catch (SecurityException e) - { - logger.debug("Unable to open file.", e); - - this.showErrorMessage( - resources.getI18NString( - "service.gui.FILE_OPEN_NO_PERMISSION")); - } - catch (IOException e) - { - logger.debug("Unable to open file.", e); - - this.showErrorMessage( - resources.getI18NString( - "service.gui.FILE_OPEN_NO_APPLICATION")); - } - catch (Exception e) - { - logger.debug("Unable to open file.", e); - - this.showErrorMessage( - resources.getI18NString( - "service.gui.FILE_OPEN_FAILED")); - } - } } diff --git a/src/net/java/sip/communicator/impl/gui/main/chat/filetransfer/SendFileConversationComponent.java b/src/net/java/sip/communicator/impl/gui/main/chat/filetransfer/SendFileConversationComponent.java index 2b94a077e..087a95826 100644 --- a/src/net/java/sip/communicator/impl/gui/main/chat/filetransfer/SendFileConversationComponent.java +++ b/src/net/java/sip/communicator/impl/gui/main/chat/filetransfer/SendFileConversationComponent.java @@ -18,7 +18,6 @@ import net.java.sip.communicator.impl.gui.utils.*; import net.java.sip.communicator.service.protocol.*; import net.java.sip.communicator.service.protocol.event.*; -import net.java.sip.communicator.service.resources.*; import net.java.sip.communicator.util.*; /** @@ -39,15 +38,15 @@ public class SendFileConversationComponent private final JLabel imageLabel = new JLabel(); private final JLabel titleLabel = new JLabel(); private final JLabel fileLabel = new JLabel(); + private final JTextArea errorArea = new JTextArea(); + private final JLabel errorIconLabel = new JLabel( + new ImageIcon(ImageLoader.getImage(ImageLoader.EXCLAMATION_MARK))); private ChatConversationButton cancelButton = new ChatConversationButton(); private ChatConversationButton retryButton = new ChatConversationButton(); private JProgressBar progressBar = new JProgressBar(); - private static final ResourceManagementService resources - = GuiActivator.getResources(); - private final String toContactName; private FileTransfer fileTransfer; @@ -67,7 +66,7 @@ public class SendFileConversationComponent */ public SendFileConversationComponent( ChatPanel chatPanel, String toContactName, - File file) + final File file) { this.parentChatPanel = chatPanel; this.toContactName = toContactName; @@ -82,6 +81,18 @@ public SendFileConversationComponent( ChatPanel chatPanel, add(imageLabel, constraints); this.setFileIcon(file); + imageLabel.setToolTipText( + resources.getI18NString("service.gui.OPEN_FILE_FROM_IMAGE")); + imageLabel.addMouseListener(new MouseAdapter() + { + public void mouseClicked(MouseEvent e) + { + if (e.getClickCount() > 1) + { + openFile(file); + } + } + }); constraints.gridx = 1; constraints.gridy = 0; @@ -105,6 +116,21 @@ public SendFileConversationComponent( ChatPanel chatPanel, add(fileLabel, constraints); fileLabel.setText(getFileName(file)); + constraints.gridx = 1; + constraints.gridy = 2; + constraints.anchor = GridBagConstraints.WEST; + constraints.insets = new Insets(0, 5, 0, 5); + constraints.fill = GridBagConstraints.NONE; + + add(errorIconLabel, constraints); + errorIconLabel.setVisible(false); + + constraints.gridx = 2; + constraints.gridy = 2; + constraints.anchor = GridBagConstraints.WEST; + constraints.insets = new Insets(0, 5, 0, 5); + constraints.fill = GridBagConstraints.HORIZONTAL; + constraints.gridx = 1; constraints.gridy = 3; constraints.gridwidth = 1; @@ -314,4 +340,16 @@ else if (sourceButton.equals(retryButton)) parentChatPanel.sendFile(file, this); } } + + /** + * Shows the given error message in the error area of this component. + * + * @param message the message to show + */ + protected void showErrorMessage(String message) + { + errorArea.setText(message); + errorIconLabel.setVisible(true); + errorArea.setVisible(true); + } } diff --git a/src/net/java/sip/communicator/impl/gui/main/contactlist/ContactListPane.java b/src/net/java/sip/communicator/impl/gui/main/contactlist/ContactListPane.java index 79d8943a3..1ad148fb9 100755 --- a/src/net/java/sip/communicator/impl/gui/main/contactlist/ContactListPane.java +++ b/src/net/java/sip/communicator/impl/gui/main/contactlist/ContactListPane.java @@ -602,6 +602,18 @@ public void run() chatWindowManager.openChat(chatPanel, false); } }); + + // Fire notification + String title = GuiActivator.getResources().getI18NString( + "service.gui.FILE_RECEIVING_FROM", + new String[]{sourceContact.getDisplayName()}); + + NotificationManager.fireChatNotification( + sourceContact, + NotificationManager.INCOMING_FILE, + title, + request.getFileName()); + } /** diff --git a/src/net/java/sip/communicator/impl/gui/utils/NotificationManager.java b/src/net/java/sip/communicator/impl/gui/utils/NotificationManager.java index 70bf0259c..e061a659b 100644 --- a/src/net/java/sip/communicator/impl/gui/utils/NotificationManager.java +++ b/src/net/java/sip/communicator/impl/gui/utils/NotificationManager.java @@ -28,6 +28,8 @@ public class NotificationManager public static final String CALL_SECURITY_ON = "CallSecurityOn"; public static final String CALL_SECURITY_ERROR = "CallSecurityError"; + + public static final String INCOMING_FILE = "IncomingFile"; public static void registerGuiNotifications() { @@ -116,6 +118,19 @@ public static void registerGuiNotifications() SoundProperties.CALL_SECURITY_ERROR, null); + // Register sound notification for incoming files. + notificationService.registerDefaultNotificationForEvent( + INCOMING_FILE, + NotificationService.ACTION_POPUP_MESSAGE, + null, + null); + + notificationService.registerDefaultNotificationForEvent( + INCOMING_FILE, + NotificationService.ACTION_SOUND, + SoundProperties.INCOMING_FILE, + null); + } /** diff --git a/src/net/java/sip/communicator/impl/gui/utils/SoundProperties.java b/src/net/java/sip/communicator/impl/gui/utils/SoundProperties.java index ebbfb947a..a969b5b8a 100644 --- a/src/net/java/sip/communicator/impl/gui/utils/SoundProperties.java +++ b/src/net/java/sip/communicator/impl/gui/utils/SoundProperties.java @@ -18,6 +18,8 @@ public final class SoundProperties { public static final String INCOMING_MESSAGE; + public static final String INCOMING_FILE; + public static final String OUTGOING_CALL; public static final String INCOMING_CALL; @@ -66,6 +68,7 @@ public final class SoundProperties ResourceManagementService resources = GuiActivator.getResources(); INCOMING_MESSAGE = resources.getSoundPath("INCOMING_MESSAGE"); + INCOMING_FILE = resources.getSoundPath("INCOMING_FILE"); OUTGOING_CALL = resources.getSoundPath("OUTGOING_CALL"); INCOMING_CALL = resources.getSoundPath("INCOMING_CALL"); DIAL_ZERO = resources.getSoundPath("DIAL_ZERO");