summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAndrew John Hughes <gnu_andrew@member.fsf.org>2005-11-27 21:00:34 +0000
committerAndrew John Hughes <gnu_andrew@member.fsf.org>2005-11-27 21:00:34 +0000
commit15ee25b923180850794e71cc44c9859e65eea8a2 (patch)
tree5115c5c9f0dacfbeb537decc2bcb25ef362e039f
parent6f383d9c78e81a535c35c5e69df90cd5a4d1dbfa (diff)
downloadclasspath-15ee25b923180850794e71cc44c9859e65eea8a2.tar.gz
2005-11-27 Andrew John Hughes <gnu_andrew@member.fsf.org>
* Merge of HEAD --> generics from the release of Classpath 0.19 to 2005/11/27.
-rw-r--r--AUTHORS4
-rw-r--r--ChangeLog2954
-rw-r--r--INSTALL3
-rw-r--r--NEWS7
-rwxr-xr-xautogen.sh2
-rw-r--r--configure.ac7
-rw-r--r--doc/www.gnu.org/announce/20051102.wml247
-rwxr-xr-xdoc/www.gnu.org/cp-tools/cp-tools.wml9
-rw-r--r--doc/www.gnu.org/downloads/downloads.wml14
-rw-r--r--doc/www.gnu.org/newsitems.txt5
-rw-r--r--examples/Makefile.am7
-rw-r--r--examples/gnu/classpath/examples/CORBA/swing/README.html493
-rw-r--r--examples/gnu/classpath/examples/CORBA/swing/x5/CanvasWorld.java307
-rw-r--r--examples/gnu/classpath/examples/CORBA/swing/x5/ChatConstants.java80
-rw-r--r--examples/gnu/classpath/examples/CORBA/swing/x5/ClientFrame.java417
-rw-r--r--examples/gnu/classpath/examples/CORBA/swing/x5/Demo.java99
-rw-r--r--examples/gnu/classpath/examples/CORBA/swing/x5/GameManager.java68
-rw-r--r--examples/gnu/classpath/examples/CORBA/swing/x5/GameManagerImpl.java135
-rw-r--r--examples/gnu/classpath/examples/CORBA/swing/x5/IorReader.java124
-rw-r--r--examples/gnu/classpath/examples/CORBA/swing/x5/OrbStarter.java236
-rw-r--r--examples/gnu/classpath/examples/CORBA/swing/x5/Player.java96
-rw-r--r--examples/gnu/classpath/examples/CORBA/swing/x5/PlayerImpl.java275
-rw-r--r--examples/gnu/classpath/examples/CORBA/swing/x5/PlayingDesk.java512
-rw-r--r--examples/gnu/classpath/examples/CORBA/swing/x5/State.java82
-rw-r--r--examples/gnu/classpath/examples/CORBA/swing/x5/X5Server.java175
-rw-r--r--examples/gnu/classpath/examples/CORBA/swing/x5/_GameManagerImpl_Tie.java214
-rw-r--r--examples/gnu/classpath/examples/CORBA/swing/x5/_GameManager_Stub.java207
-rw-r--r--examples/gnu/classpath/examples/CORBA/swing/x5/_PlayerImpl_Tie.java212
-rw-r--r--examples/gnu/classpath/examples/CORBA/swing/x5/_Player_Stub.java397
-rw-r--r--examples/gnu/classpath/examples/swing/Demo.java101
-rw-r--r--examples/gnu/classpath/examples/swing/FileChooserDemo.java228
-rw-r--r--examples/gnu/classpath/examples/swing/GNULookAndFeel.java184
-rw-r--r--examples/gnu/classpath/examples/swing/ProgressBarDemo.java219
-rw-r--r--examples/gnu/classpath/examples/swing/TextFieldDemo.java488
-rw-r--r--gnu/CORBA/IOR.java49
-rw-r--r--gnu/CORBA/Interceptor/IORInterceptors.java83
-rw-r--r--gnu/CORBA/Interceptor/gnuIorInfo.java44
-rw-r--r--gnu/CORBA/Interceptor/gnuServerRequestInfo.java20
-rw-r--r--gnu/CORBA/Minor.java6
-rw-r--r--gnu/CORBA/NamingService/NameParser.java111
-rw-r--r--gnu/CORBA/OrbFunctional.java126
-rw-r--r--gnu/CORBA/OrbRestricted.java3
-rw-r--r--gnu/CORBA/Poa/AOM.java9
-rw-r--r--gnu/CORBA/Poa/ORB_1_4.java4
-rw-r--r--gnu/CORBA/Poa/gnuPOA.java381
-rw-r--r--gnu/CORBA/Poa/gnuPOAManager.java60
-rw-r--r--gnu/CORBA/SimpleDelegate.java28
-rw-r--r--gnu/CORBA/SocketRepository.java63
-rw-r--r--gnu/classpath/SystemProperties.java6
-rw-r--r--gnu/java/awt/image/ImageDecoder.java32
-rw-r--r--gnu/java/awt/peer/gtk/GdkGraphics.java5
-rw-r--r--gnu/java/awt/peer/gtk/GdkPixbufDecoder.java15
-rw-r--r--gnu/java/awt/peer/gtk/GtkComponentPeer.java7
-rw-r--r--gnu/java/awt/peer/gtk/GtkDialogPeer.java24
-rw-r--r--gnu/java/awt/peer/gtk/GtkWindowPeer.java9
-rw-r--r--gnu/java/beans/DummyAppletContext.java37
-rw-r--r--gnu/java/io/PlatformHelper.java5
-rw-r--r--gnu/java/net/protocol/file/Connection.java51
-rw-r--r--gnu/java/net/protocol/jar/Connection.java60
-rw-r--r--gnu/java/nio/SocketChannelImpl.java2
-rw-r--r--gnu/java/nio/charset/UTF_16Decoder.java19
-rw-r--r--gnu/java/nio/charset/UnicodeLittle.java2
-rw-r--r--gnu/java/nio/charset/iconv/IconvProvider.java6
-rw-r--r--gnu/javax/rmi/CORBA/UtilDelegateImpl.java10
-rw-r--r--gnu/xml/aelfred2/SAXDriver.java4
-rw-r--r--gnu/xml/stream/XMLStreamWriterImpl.java81
-rw-r--r--gnu/xml/transform/StreamSerializer.java6
-rw-r--r--gnu/xml/transform/TransformerImpl.java4
-rw-r--r--include/gnu_java_awt_peer_gtk_GtkComponentPeer.h1
-rw-r--r--java/applet/Applet.java76
-rw-r--r--java/awt/BorderLayout.java4
-rw-r--r--java/awt/Component.java67
-rw-r--r--java/awt/Container.java74
-rw-r--r--java/awt/Image.java19
-rw-r--r--java/awt/ScrollPane.java2
-rw-r--r--java/awt/Window.java79
-rw-r--r--java/awt/datatransfer/DataFlavor.java1666
-rw-r--r--java/awt/datatransfer/SystemFlavorMap.java33
-rw-r--r--java/awt/event/InvocationEvent.java25
-rw-r--r--java/awt/image/AreaAveragingScaleFilter.java2
-rw-r--r--java/awt/image/BufferedImage.java16
-rw-r--r--java/awt/image/MemoryImageSource.java2
-rw-r--r--java/beans/IndexedPropertyChangeEvent.java81
-rw-r--r--java/beans/PropertyChangeSupport.java53
-rw-r--r--java/io/File.java9
-rw-r--r--java/io/FilePermission.java8
-rw-r--r--java/io/InputStreamReader.java11
-rw-r--r--java/io/ObjectInputStream.java14
-rw-r--r--java/io/PrintWriter.java2
-rw-r--r--java/io/StreamTokenizer.java6
-rw-r--r--java/lang/Boolean.java9
-rw-r--r--java/lang/SecurityManager.java4
-rw-r--r--java/lang/StackTraceElement.java22
-rw-r--r--java/lang/String.java39
-rw-r--r--java/net/URL.java12
-rw-r--r--java/net/URLClassLoader.java98
-rw-r--r--java/security/ProtectionDomain.java4
-rw-r--r--java/util/Arrays.java72
-rw-r--r--java/util/Properties.java34
-rw-r--r--java/util/WeakHashMap.java28
-rw-r--r--javax/print/attribute/Attribute.java20
-rw-r--r--javax/print/attribute/AttributeSet.java147
-rw-r--r--javax/print/attribute/AttributeSetUtilities.java87
-rw-r--r--javax/print/attribute/DateTimeSyntax.java16
-rw-r--r--javax/print/attribute/DocAttribute.java19
-rw-r--r--javax/print/attribute/DocAttributeSet.java35
-rw-r--r--javax/print/attribute/EnumSyntax.java122
-rw-r--r--javax/print/attribute/HashAttributeSet.java190
-rw-r--r--javax/print/attribute/HashDocAttributeSet.java22
-rw-r--r--javax/print/attribute/HashPrintJobAttributeSet.java22
-rw-r--r--javax/print/attribute/HashPrintRequestAttributeSet.java22
-rw-r--r--javax/print/attribute/HashPrintServiceAttributeSet.java22
-rw-r--r--javax/print/attribute/IntegerSyntax.java25
-rw-r--r--javax/print/attribute/PrintJobAttribute.java19
-rw-r--r--javax/print/attribute/PrintJobAttributeSet.java35
-rw-r--r--javax/print/attribute/PrintRequestAttribute.java14
-rw-r--r--javax/print/attribute/PrintRequestAttributeSet.java35
-rw-r--r--javax/print/attribute/PrintServiceAttribute.java19
-rw-r--r--javax/print/attribute/PrintServiceAttributeSet.java35
-rw-r--r--javax/print/attribute/ResolutionSyntax.java105
-rw-r--r--javax/print/attribute/SetOfIntegerSyntax.java165
-rw-r--r--javax/print/attribute/Size2DSyntax.java110
-rw-r--r--javax/print/attribute/SupportedValuesAttribute.java20
-rw-r--r--javax/print/attribute/TextSyntax.java37
-rw-r--r--javax/print/attribute/URISyntax.java18
-rw-r--r--javax/print/attribute/UnmodifiableSetException.java12
-rw-r--r--javax/print/attribute/package.html9
-rw-r--r--javax/print/attribute/standard/MediaName.java86
-rw-r--r--javax/print/attribute/standard/MediaSize.java554
-rw-r--r--javax/print/attribute/standard/MediaSizeName.java16
-rw-r--r--javax/print/attribute/standard/MediaTray.java106
-rw-r--r--javax/print/event/PrintEvent.java6
-rw-r--r--javax/print/event/PrintJobAdapter.java34
-rw-r--r--javax/print/event/PrintJobAttributeEvent.java10
-rw-r--r--javax/print/event/PrintJobAttributeListener.java6
-rw-r--r--javax/print/event/PrintJobEvent.java27
-rw-r--r--javax/print/event/PrintJobListener.java15
-rw-r--r--javax/print/event/PrintServiceAttributeEvent.java10
-rw-r--r--javax/print/event/PrintServiceAttributeListener.java6
-rw-r--r--javax/print/event/package.html8
-rw-r--r--javax/sound/sampled/AudioFileFormat.java242
-rw-r--r--javax/sound/sampled/AudioFormat.java345
-rw-r--r--javax/sound/sampled/AudioInputStream.java258
-rw-r--r--javax/sound/sampled/AudioPermission.java70
-rw-r--r--javax/sound/sampled/AudioSystem.java744
-rw-r--r--javax/sound/sampled/BooleanControl.java145
-rw-r--r--javax/sound/sampled/Clip.java115
-rw-r--r--javax/sound/sampled/CompoundControl.java102
-rw-r--r--javax/sound/sampled/Control.java111
-rw-r--r--javax/sound/sampled/DataLine.java265
-rw-r--r--javax/sound/sampled/EnumControl.java126
-rw-r--r--javax/sound/sampled/FloatControl.java267
-rw-r--r--javax/sound/sampled/Line.java150
-rw-r--r--javax/sound/sampled/LineEvent.java150
-rw-r--r--javax/sound/sampled/LineListener.java55
-rw-r--r--javax/sound/sampled/LineUnavailableException.java61
-rw-r--r--javax/sound/sampled/Mixer.java206
-rw-r--r--javax/sound/sampled/Port.java135
-rw-r--r--javax/sound/sampled/ReverbType.java144
-rw-r--r--javax/sound/sampled/SourceDataLine.java77
-rw-r--r--javax/sound/sampled/TargetDataLine.java79
-rw-r--r--javax/sound/sampled/UnsupportedAudioFileException.java (renamed from native/jni/java-io/javaio.h)45
-rw-r--r--javax/sound/sampled/spi/AudioFileReader.java146
-rw-r--r--javax/sound/sampled/spi/AudioFileWriter.java131
-rw-r--r--javax/sound/sampled/spi/FormatConversionProvider.java179
-rw-r--r--javax/sound/sampled/spi/MixerProvider.java86
-rw-r--r--javax/swing/AbstractButton.java1
-rw-r--r--javax/swing/ActionMap.java8
-rw-r--r--javax/swing/ComponentInputMap.java26
-rw-r--r--javax/swing/InputMap.java12
-rw-r--r--javax/swing/JApplet.java33
-rw-r--r--javax/swing/JComponent.java338
-rw-r--r--javax/swing/JDialog.java29
-rw-r--r--javax/swing/JEditorPane.java39
-rw-r--r--javax/swing/JFileChooser.java68
-rw-r--r--javax/swing/JFrame.java29
-rw-r--r--javax/swing/JInternalFrame.java45
-rw-r--r--javax/swing/JLayeredPane.java41
-rw-r--r--javax/swing/JList.java14
-rw-r--r--javax/swing/JMenu.java3
-rw-r--r--javax/swing/JMenuBar.java61
-rw-r--r--javax/swing/JMenuItem.java2
-rw-r--r--javax/swing/JOptionPane.java24
-rw-r--r--javax/swing/JPanel.java2
-rw-r--r--javax/swing/JRootPane.java195
-rw-r--r--javax/swing/JSplitPane.java120
-rw-r--r--javax/swing/JTabbedPane.java34
-rw-r--r--javax/swing/JTable.java66
-rw-r--r--javax/swing/JTextField.java4
-rw-r--r--javax/swing/JTextPane.java36
-rw-r--r--javax/swing/JTree.java14
-rw-r--r--javax/swing/JViewport.java29
-rw-r--r--javax/swing/JWindow.java29
-rw-r--r--javax/swing/KeyboardManager.java280
-rw-r--r--javax/swing/Popup.java19
-rw-r--r--javax/swing/RepaintManager.java75
-rw-r--r--javax/swing/SizeRequirements.java27
-rw-r--r--javax/swing/SwingUtilities.java18
-rw-r--r--javax/swing/Timer.java123
-rw-r--r--javax/swing/ToolTipManager.java148
-rw-r--r--javax/swing/TransferHandler.java46
-rw-r--r--javax/swing/UIManager.java78
-rw-r--r--javax/swing/event/TreeModelEvent.java8
-rw-r--r--javax/swing/plaf/ComponentUI.java4
-rw-r--r--javax/swing/plaf/basic/BasicArrowButton.java4
-rw-r--r--javax/swing/plaf/basic/BasicBorders.java79
-rw-r--r--javax/swing/plaf/basic/BasicButtonUI.java5
-rw-r--r--javax/swing/plaf/basic/BasicCheckBoxUI.java6
-rw-r--r--javax/swing/plaf/basic/BasicComboBoxEditor.java44
-rw-r--r--javax/swing/plaf/basic/BasicComboBoxUI.java174
-rw-r--r--javax/swing/plaf/basic/BasicComboPopup.java12
-rw-r--r--javax/swing/plaf/basic/BasicEditorPaneUI.java11
-rw-r--r--javax/swing/plaf/basic/BasicFileChooserUI.java885
-rw-r--r--javax/swing/plaf/basic/BasicInternalFrameTitlePane.java22
-rw-r--r--javax/swing/plaf/basic/BasicInternalFrameUI.java35
-rw-r--r--javax/swing/plaf/basic/BasicLabelUI.java13
-rw-r--r--javax/swing/plaf/basic/BasicListUI.java179
-rw-r--r--javax/swing/plaf/basic/BasicLookAndFeel.java17
-rw-r--r--javax/swing/plaf/basic/BasicMenuItemUI.java144
-rw-r--r--javax/swing/plaf/basic/BasicMenuUI.java1
-rw-r--r--javax/swing/plaf/basic/BasicOptionPaneUI.java36
-rw-r--r--javax/swing/plaf/basic/BasicPopupMenuUI.java35
-rw-r--r--javax/swing/plaf/basic/BasicProgressBarUI.java395
-rw-r--r--javax/swing/plaf/basic/BasicRadioButtonUI.java4
-rw-r--r--javax/swing/plaf/basic/BasicScrollBarUI.java27
-rw-r--r--javax/swing/plaf/basic/BasicSplitPaneDivider.java6
-rw-r--r--javax/swing/plaf/basic/BasicSplitPaneUI.java308
-rw-r--r--javax/swing/plaf/basic/BasicTabbedPaneUI.java48
-rw-r--r--javax/swing/plaf/basic/BasicTableHeaderUI.java12
-rw-r--r--javax/swing/plaf/basic/BasicTableUI.java37
-rw-r--r--javax/swing/plaf/basic/BasicTextFieldUI.java3
-rw-r--r--javax/swing/plaf/basic/BasicTextPaneUI.java8
-rw-r--r--javax/swing/plaf/basic/BasicTextUI.java76
-rw-r--r--javax/swing/plaf/basic/BasicToolBarUI.java7
-rw-r--r--javax/swing/plaf/basic/BasicTreeUI.java556
-rw-r--r--javax/swing/plaf/metal/MetalBorders.java141
-rw-r--r--javax/swing/plaf/metal/MetalButtonUI.java45
-rw-r--r--javax/swing/plaf/metal/MetalCheckBoxIcon.java5
-rw-r--r--javax/swing/plaf/metal/MetalComboBoxEditor.java3
-rw-r--r--javax/swing/plaf/metal/MetalComboBoxUI.java53
-rw-r--r--javax/swing/plaf/metal/MetalFileChooserUI.java1076
-rw-r--r--javax/swing/plaf/metal/MetalIconFactory.java110
-rw-r--r--javax/swing/plaf/metal/MetalInternalFrameTitlePane.java24
-rw-r--r--javax/swing/plaf/metal/MetalLabelUI.java9
-rw-r--r--javax/swing/plaf/metal/MetalLookAndFeel.java40
-rw-r--r--javax/swing/plaf/metal/MetalMenuBarUI.java88
-rw-r--r--javax/swing/plaf/metal/MetalProgressBarUI.java77
-rw-r--r--javax/swing/plaf/metal/MetalRadioButtonUI.java20
-rw-r--r--javax/swing/plaf/metal/MetalScrollBarUI.java13
-rw-r--r--javax/swing/plaf/metal/MetalScrollPaneUI.java88
-rw-r--r--javax/swing/plaf/metal/MetalSplitPaneDivider.java136
-rw-r--r--javax/swing/plaf/metal/MetalSplitPaneUI.java6
-rw-r--r--javax/swing/plaf/metal/MetalTabbedPaneUI.java150
-rw-r--r--javax/swing/plaf/metal/MetalTextFieldUI.java12
-rw-r--r--javax/swing/plaf/metal/MetalToggleButtonUI.java27
-rw-r--r--javax/swing/plaf/metal/MetalToolBarUI.java68
-rw-r--r--javax/swing/plaf/metal/MetalToolTipUI.java14
-rw-r--r--javax/swing/plaf/metal/MetalTreeUI.java121
-rw-r--r--javax/swing/plaf/metal/MetalUtils.java256
-rw-r--r--javax/swing/plaf/metal/OceanTheme.java38
-rw-r--r--javax/swing/table/DefaultTableCellRenderer.java41
-rw-r--r--javax/swing/text/AbstractDocument.java39
-rw-r--r--javax/swing/text/BoxView.java36
-rw-r--r--javax/swing/text/ComponentView.java146
-rw-r--r--javax/swing/text/CompositeView.java81
-rw-r--r--javax/swing/text/DefaultCaret.java270
-rw-r--r--javax/swing/text/DefaultEditorKit.java28
-rw-r--r--javax/swing/text/DefaultStyledDocument.java854
-rw-r--r--javax/swing/text/DefaultTextUI.java61
-rw-r--r--javax/swing/text/FieldView.java14
-rw-r--r--javax/swing/text/FlowView.java4
-rw-r--r--javax/swing/text/GapContent.java36
-rw-r--r--javax/swing/text/GlyphView.java3
-rw-r--r--javax/swing/text/IconView.java49
-rw-r--r--javax/swing/text/InternationalFormatter.java2
-rw-r--r--javax/swing/text/JTextComponent.java100
-rw-r--r--javax/swing/text/MaskFormatter.java583
-rw-r--r--javax/swing/text/NumberFormatter.java86
-rw-r--r--javax/swing/text/ParagraphView.java113
-rw-r--r--javax/swing/text/PasswordView.java38
-rw-r--r--javax/swing/text/PlainDocument.java94
-rw-r--r--javax/swing/text/PlainView.java25
-rw-r--r--javax/swing/text/StyleConstants.java4
-rw-r--r--javax/swing/text/Utilities.java86
-rw-r--r--javax/swing/text/View.java48
-rw-r--r--javax/swing/text/WrappedPlainView.java140
-rw-r--r--javax/swing/tree/DefaultTreeCellEditor.java8
-rw-r--r--javax/swing/tree/DefaultTreeCellRenderer.java27
-rw-r--r--lib/.cvsignore1
-rw-r--r--native/jni/gtk-peer/Makefile.am4
-rw-r--r--native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkFontPeer.c23
-rw-r--r--native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkGraphics.c29
-rw-r--r--native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkGraphics2D.c57
-rw-r--r--native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkGraphicsEnvironment.c1
-rw-r--r--native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkPixbufDecoder.c3
-rw-r--r--native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkChoicePeer.c1
-rw-r--r--native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkClipboard.c6
-rw-r--r--native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkComponentPeer.c35
-rw-r--r--native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkListPeer.c1
-rw-r--r--native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkSelection.c6
-rw-r--r--native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkToolkit.c2
-rw-r--r--native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkWindowPeer.c2
-rw-r--r--native/jni/java-io/Makefile.am4
-rw-r--r--native/jni/java-io/java_io_VMFile.c2
-rw-r--r--native/jni/java-io/javaio.c363
-rw-r--r--native/jni/java-lang/java_lang_VMDouble.c5
-rw-r--r--native/jni/java-nio/gnu_java_nio_charset_iconv_IconvDecoder.c2
-rw-r--r--native/jni/java-nio/java_nio.c2
-rw-r--r--native/jni/midi-alsa/.cvsignore2
-rw-r--r--native/jni/midi-dssi/.cvsignore2
-rw-r--r--native/jni/midi-dssi/Makefile.am3
-rw-r--r--native/jni/qt-peer/qtmenupeer.cpp1
-rw-r--r--native/jni/xmlj/xmlj_util.h6
-rw-r--r--org/omg/CORBA/DATA_CONVERSION.java20
-rw-r--r--org/omg/CORBA/ORB.java22
-rw-r--r--org/omg/PortableInterceptor/IORInfoOperations.java52
-rw-r--r--org/omg/PortableInterceptor/IORInterceptorOperations.java6
-rw-r--r--org/omg/PortableInterceptor/IORInterceptor_3_0.java59
-rw-r--r--org/omg/PortableInterceptor/IORInterceptor_3_0Helper.java195
-rw-r--r--org/omg/PortableInterceptor/IORInterceptor_3_0Holder.java106
-rw-r--r--org/omg/PortableInterceptor/IORInterceptor_3_0Operations.java90
-rw-r--r--org/omg/PortableInterceptor/ORBInitInfoOperations.java17
-rw-r--r--org/omg/PortableInterceptor/ObjectReferenceFactory.java2
-rw-r--r--org/omg/PortableInterceptor/ObjectReferenceFactoryOperations.java11
-rw-r--r--org/omg/PortableInterceptor/ObjectReferenceTemplate.java78
-rw-r--r--org/omg/PortableInterceptor/ObjectReferenceTemplateHelper.java144
-rw-r--r--org/omg/PortableInterceptor/ObjectReferenceTemplateHolder.java103
-rw-r--r--org/omg/PortableInterceptor/ObjectReferenceTemplateSeqHelper.java169
-rw-r--r--org/omg/PortableInterceptor/ObjectReferenceTemplateSeqHolder.java104
-rw-r--r--org/omg/PortableInterceptor/ServerRequestInfoOperations.java38
-rw-r--r--org/omg/PortableInterceptor/_IORInterceptor_3_0Stub.java272
-rw-r--r--vm/reference/gnu/classpath/VMStackWalker.java16
332 files changed, 26626 insertions, 5646 deletions
diff --git a/AUTHORS b/AUTHORS
index 339138aef..04c3f0f23 100644
--- a/AUTHORS
+++ b/AUTHORS
@@ -5,18 +5,22 @@ on either list, but should, let us know. Please keep this list in
alphabetic order.
Lillian Angel (langel@redhat.com)
+Anthony Balkissoon (abalkiss@redhat.com)
Stuart Ballard (stuart.a.ballard@gmail.com)
Mark Benvenuto (mcb54@columbia.edu)
+Gary Benson (gbenson@redhat.com)
Geoff Berry (gcb@gnu.org)
James E. Blair (corvus@gnu.org)
Eric Blake (ebb9@email.byu.edu)
Sascha Brawer (brawer@acm.org)
+David Daney (ddaney@avtrex.com)
Nic Ferrier (nferrier@tapsellferrier.co.uk)
Paul Fisher (rao@gnu.org)
David Gilbert (david.gilbert@object-refinery.com)
Anthony Green (green@redhat.com)
Jochen Hoenicke (Jochen.Hoenicke@Informatik.Uni-Oldenburg.de)
Andrew John Hughes (gnu_andrew@member.fsf.org)
+Kazumitsu Ito (kaz@maczuka.gcd.org)
Brian Jones (cbj@gnu.org)
Roman Kennke (roman@kennke.org)
Michael Koch (konqueror@gmx.de)
diff --git a/ChangeLog b/ChangeLog
index 5911db063..f962d8ea7 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -72,6 +72,17 @@
(getArray): Genericized.
(getResultSet): Likewise.
+2005-11-27 Tom Tromey <tromey@redhat.com>
+
+ * java/beans/PropertyChangeSupport.java (fireIndexedPropertyChange):
+ New methods.
+ * java/beans/IndexedPropertyChangeEvent.java: New file.
+
+2005-11-26 Tom Tromey <tromey@redhat.com>
+
+ * java/lang/StackTraceElement.java (StackTraceElement): New
+ constructor.
+
2005-11-25 Tom Tromey <tromey@redhat.com>
* javax/swing/text/StyleContext.java (getStyleNames): Genericized.
@@ -247,6 +258,2949 @@
* java/security/PrivilegedExceptionAction.java: Genericized.
* java/security/PrivilegedAction.java: Genericized.
+2005-11-25 Guilhem Lavaux <guilhem@kaffe.org>
+
+ * native/jni/java-io/javaio.c, native/jni/java-io/javaio.h:
+ Removed.
+
+ * native/jni/java-io/java_io_VMFile.c: Removed dependency on
+ javaio.h
+
+ * native/jni/java-nio/gnu_java_nio_channels_FileChannelImpl.c:
+ Likewise.
+
+2005-11-25 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/plaf/metal/MetalSplitPaneDivider.java
+ (MetalDividerLayout): Fixed class name to MetalDividerLayout
+ instead of DividerLayout.
+ (MetalSplitPaneDivider): Fixed setLayout call.
+
+2005-11-25 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/plaf/metal/MetalFileChooserUI.java
+ (mouseClicked): Fixed to keep track of last object clicked,
+ instead of index. Problems arise when lists change for different
+ directories and using the index.
+ (editFile): Fixed size and location for text field. Painting is still
+ a little messed up when typing because there is no action listener yet.
+
+2005-11-26 Jan Roehrich <jan@roehrich.info>
+
+ * java/awt/datatransfer/SystemFlavorMap.java
+ (defaultFlavorMap): removed.
+ (systemFlavorMaps): added static field.
+ (getDefaultFlavorMap): reimplemented using systemFlavorMaps.
+
+2005-11-25 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/JFileChooser.java:
+ selectedFiles field should not be initialized.
+ (getSelectedFiles): Should return empty array, not null.
+ * javax/swing/plaf/metal/MetalFileChooserUI.java
+ (MetalFileChooserSelectionListener): Added comment.
+ (valueChanged): Fixed API documentation.
+ (SingleClickListener): Likewise.
+ (SingleClickListener.init): Added field initializations.
+ (mouseClicked): Implemented.
+ (editFile): Partially implemented.
+ (completeEditing): Implemented.
+ (installUI): Added call to create the action map.
+ (uninstallUI): Set actionMap to null.
+ (getActionMap): Implemented.
+ (createList): Uncommented code.
+ (removeControlButtons): Implemented.
+
+2005-11-25 Lillian Angel <langel@redhat.com>
+
+ * native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkGraphics.c:
+ Fixed typo.
+
+2005-11-25 Lillian Angel <langel@redhat.com>
+
+ * native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkGraphics.c
+ (drawString): Changed pointer to be const, and fixed check to
+ draw characters only if they are >= ' '. Handles all control
+ characters.
+
+2005-11-25 Mark Wielaard <mark@klomp.org>
+
+ Fixes bug #24981
+ * native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkSelection.c
+ (clipboard_targets_received): DeleteLocalRef of NewStringUTF.
+ (clipboard_text_received): Likewise.
+ (clipboard_uris_received): Likewise.
+
+2005-11-25 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/JList.java
+ (JList): Set default selection mode.
+ * javax/swing/plaf/basic/BasicFileChooserUI.java
+ (DoubleClickListener): No need for timer here.
+ (mouseClicked): Removed timer code, and added check for double click.
+ Problems with opening wrong directory is now fixed.
+ * javax/swing/plaf/basic/BasicListUI.java
+ (mouseDragged): Implemented.
+ * javax/swing/plaf/metal/MetalFileChooserUI.java
+ (propertyChange): Implemented MULTI_SELECTION_ENABLED_CHANGED_PROPERTY
+ property change.
+ (getListCellRendererComponent): Set opaque property, so background color
+ on cell is painted.
+ (SingleClickListener.init): Implemented.
+ (installStrings): Fixed tooltip text strings.
+
+2005-11-25 David Gilbert <david.gilbert@object-refinery.com>
+
+ * javax/swing/JFileChooser.java
+ (selectedFiles): Initialise,
+ (JFileChooser(String)): Delegate to another constructor,
+ (JFileChooser(String, FileSystemView)): Convert directory to file,
+ (setSelectedFile): Check for current selection == null,
+ (getSelectedFiles): Updated API docs,
+ (setSelectedFiles): Changed order of event generation,
+ (changeToParentDirectory): Don't check for null parent (reference
+ implementation doesn't),
+ (addChoosableFileFilter): Change handling of null filter,
+ (removeChoosableFileFilter): Handle case where removed filter is also
+ the current selection,
+ (setAcceptAllFileFilterUsed): Add or remove accept all filter as
+ appropriate,
+ (setFileFilter): Add new filter to choosable filters if necessary,
+ (accept): Reimplemented,
+ * javax/swing/plaf/basic/BasicFileChooserUI.java
+ (ApproveSelectionAction.ApproveSelectionAction): Set action name,
+ (ApproveSelectionAction.actionPerformed): Call getFileName() rather
+ than accessing JTextField directly,
+ (CancelSelectionAction.CancelSelectionAction): Set action name,
+ (ChangeToParentDirectoryAction.ChangeToParentDirectoryAction): Set
+ action name,
+ (DoubleClickListener.mouseClicked): Call setFileName rather than
+ accessing JTextField directly,
+ (GoHomeAction.GoHomeAction): Set action name,
+ (NewFolderAction.NewFolderAction): Set action name,
+ (SelectionListener.valueChanged): Get list from event,
+ (UpdateAction.UpdateAction): Set action name to null,
+ (computerIcon): Removed initialization,
+ (detailsViewIcon): Likewise,
+ (directoryIcon): Likewise,
+ (fileIcon): Likewise,
+ (floppyDriveIcon): Likewise,
+ (hardDriveIcon): Likewise,
+ (homeFolderIcon): Likewise,
+ (listViewIcon): Likewise,
+ (upFolderIcon): Likewise,
+ (fileList): Removed,
+ (filters): Removed,
+ (ICON_SIZE): Removed,
+ (parents): Removed,
+ (filename): Removed,
+ (cancel): Removed,
+ (upFolderButton): Removed,
+ (newFolderButton): Removed,
+ (homeFolderButton): Removed,
+ (approveSelectionAction): New field,
+ (cancelSelectionAction): New field,
+ (goHomeAction): New field,
+ (changeToParentDirectoryAction): New field,
+ (newFolderAction): New field,
+ (updateAction): New field,
+ (BasicFileChooserUI): Do nothing here,
+ (installUI): Initialise filechooser field,
+ (createBoxListener): Removed,
+ (createFilterListener): Removed,
+ (filterEntries): Removed,
+ (installComponents): Do nothing here,
+ (uninstallComponents): Do nothing here,
+ (installListeners): Removed component specific listeners,
+ (installIcons): Use Metal icons,
+ (unintallIcons): Clear icons,
+ (installStrings): Use fixed strings for text items that aren't defined
+ in the UI defaults - should implement localised strings later,
+ (uninstallStrings): Clear text items,
+ (createPropertyChangeListener): Return blank listener,
+ (getFileName): TODO,
+ (setFileName): TODO,
+ (rescanCurrentDirectory): Remove call on deleted filelist,
+ (getApproveButton): Just return field,
+ (getFileView): Updated API docs,
+ (getDialogTitle): Reimplemented,
+ (getApproveButtonText): Reimplemented,
+ (getNewFolderAction): Create new instance if required,
+ (getGoHomeAction): Likewise,
+ (getChangeToParentDirectoryAction): Likewise,
+ (getApproveSelectionAction): Likewise,
+ (getCancelSelectionAction): Likewise,
+ (getUpdateAction): Likewise,
+ * javax/swing/plaf/metal/MetalFileChooserUI.java
+ (MetalFileChooserPropertyChangeListener): New class,
+ (DirectoryComboBoxRenderer): New class,
+ (FilterComboBoxModel.selectedIndex): Removed field,
+ (FilterComboBoxModel.selected): New field,
+ (FilterComboBoxModel.FilterComboBoxModel): Initialise selected field,
+ (FilterComboBoxModel.propertyChange): Update filter list,
+ (FilterComboBoxModel.setSelectedItem): Reimplemented,
+ (FilterComboBoxModel.getSelectedItem): Return selected field,
+ (FilterComboBoxRenderer.getListCellRendererComponent): Call super,
+ (MetalFileChooserSelectionListener): New class,
+ (SingleClickListener): New class TODO,
+ (directoryLabel): New field,
+ (directoryComboBox): New field,
+ (fileLabel): New field,
+ (fileTextField): New field,
+ (filterLabel): New field,
+ (topPanel): New field,
+ (controls): New field,
+ (bottomPanel): New field,
+ (buttonPanel): New field,
+ (approveButton): New field,
+ (fileList): New field,
+ (fileListPanel): New field,
+ (filterModel): New field,
+ (MetalFileChooserUI): Initialise panels,
+ (installUI): TODO,
+ (uninstallUI): TODO,
+ (installComponents): Implemented,
+ (uninstallComponents): Implemented,
+ (getButtonPanel): Implemented,
+ (getBottomPanel): Implemented,
+ (installStrings): Implemented,
+ (installListeners): Implemented,
+ (uninstallListeners): Implemented,
+ (getActionMap): TODO,
+ (createActionMap): Implemented,
+ (createList): Implemented,
+ (createDetailsView): Implemented,
+ (createListSelectionListener): Implemented,
+ (getPreferredSize): Implemented badly,
+ (getMinimumSize): Likewise,
+ (getMaximumSize): Implemented,
+ (createPropertyChangeListener): Implemented,
+ (createDirectoryComboBoxRenderer): Implemented,
+ (addControlButtons): Implemented,
+ (removeControlButtons): TODO,
+ (ensureFileIsVisible): TODO,
+ (rescanCurrentDirectory): Implemented,
+ (getFileName): Implemented,
+ (setFileName): Implemented,
+ (setDirectorySelected): TODO,
+ (getDirectoryName): TODO,
+ (setDirectoryName): TODO,
+ (valueChanged): TODO,
+ (getApproveButton): Implemented,
+ (VerticalMidLayout): New support class,
+ (ButtonLayout): New support class,
+ * javax/swing/plaf/metal/MetalLookAndFeel.java
+ (initClassDefaults): Add 'FileChooserUI' default,
+ (initComponentDefaults): Added FileChooser icons.
+
+2005-11-25 Mark Wielaard <mark@klomp.org>
+
+ * native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkClipboard.c
+ (current_selection): Define as gint.
+ (clipboard_clear_func): Extract user_data with GPOINTER_TO_INT.
+ (Java_gnu_java_awt_peer_gtk_GtkClipboard_advertiseContent):
+ Convert current_selection with GINT_TO_POINTER.
+
+2005-11-25 Mark Wielaard <mark@klomp.org>
+
+ * javax/swing/plaf/basic/BasicTabbedPaneUI.java (paintIcon): Only
+ paint icon when not null.
+
+2005-11-25 Christian Thalinger <twisti@complang.tuwien.ac.at>
+
+ * native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkPixbufDecoder.c
+ (save_to_stream): Added missing DeleteLocalRef call.
+
+2005-11-24 Sven de Marothy <sven@physto.se>
+
+ * javax/print/attribute/standard/MediaName.java,
+ * javax/print/attribute/standard/MediaTray.java:
+ New files.
+ * javax/print/attribute/standard/MediaSize.java:
+ Added "ISO", "NA", "JIS" and "Other" enumerations of standard sizes.
+ * javax/print/attribute/standard/MediaSizeName.java:
+ (getEnumValueTable, getStringTable): Add stubs.
+
+2005-11-24 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/text/PasswordView.java
+ (modelToView): Overridden to correctly map between model and view
+ respecting the echo character.
+ (viewToModel): Added FIXME to show that this method also needs
+ to be adjusted like the above method.
+ * javax/swing/text/PlainView.java
+ (paint): Don't set the font here. This is already done in the
+ text component's JComponent.getComponentGraphics() method.
+ (damageLineRange): Only repaint the damaged rectangle.
+
+2005-11-24 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicLabelUI.java
+ (getPreferredSize): Don't use deprecated method to acquire
+ FontMetrics object. This can be done more elegantly using
+ Component.getFontMetrics().
+ (paint): Removed unnecessary font setting code. This is already
+ performed in JComponent.getComponentGraphics().
+
+2005-11-24 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/table/DefaultTableCellRenderer.java
+ (getTableCellRendererComponent): Don't set enabled flag on the
+ renderer. The cells are rendered normally even when the table
+ is disabled.
+
+2005-11-24 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/plaf/basic/BasicToolBarUI.java
+ (mousePressed): When using the BasicLookAndFeel, the mouse
+ should be in the center of the dragWindow while dragging.
+ * javax/swing/plaf/metal/MetalToolBarUI.java
+ (createDockingListener): Implemented.
+ (MetalDockingListener): New class.
+ (MetalDockingListener.init): Implemented.
+ (MetalDockingListener.mousePressed): Implemented. When using the
+ MetalLookAndFeel, the mouse should not be offset while dragging.
+ (MetalDockingListener.mouseDragged): Implemented. Does not do
+ anything different than dragging in the BasicLookAndFeel.
+
+2005-11-24 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/plaf/basic/BasicArrowButton.java
+ (paint): Fixed locations, so button is drawn in proper place.
+ * javax/swing/plaf/basic/BasicSplitPaneDivider.java
+ (paint): Added code to paint buttons.
+ * javax/swing/plaf/metal/MetalSplitPaneDivider.java:
+ Added new fields.
+ (MetalSplitPaneDivider): Initialized new fields, and set layout
+ to new inner class.
+ (paint): Added code to paint buttons.
+ (DividerLayout): New class implemented.
+ (DividerLayout.init): Implemented.
+ (DividerLayout.addLayoutComponent): Implemented.
+ (DividerLayout.layoutContainer): Implemented.
+ (DividerLayout.minimumLayoutSize): Implemented.
+ (DividerLayout.preferredLayoutSize): Implemented.
+ (DividerLayout.removeLayoutComponent): Implemented.
+
+2005-11-24 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/text/InternationalFormatter:
+ (InternationalFormatter<init>): Override superclass defaults for
+ commitsOnValidEdit and overwriteMode.
+ * javax/swing/text/NumberFormatter.java: New class.
+
+2005-11-23 David Gilbert <david.gilbert@object-refinery.com>
+
+ * javax/swing/plaf/metal/MetalScrollPaneUI.java
+ (installUI): Set free-standing client property on scrollbars to false,
+ (uninstallUI): Set free-standing client property on scrollbars to null.
+
+2005-11-23 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/plaf/metal/MetalIconFactory.java:
+ Added new fields to store an instance of the icons.
+ (getMenuArrowIcon): Fixed to make use of the new field.
+ (getMenuItemArrowIcon): Fixed implementation to return
+ an instance of the icon, instead of calling getMenuArrowIcon.
+ Even though, these two look identical.
+
+2005-11-23 Jan Roehrich <jan@roehrich.info>
+
+ * java/awt/datatransfer/DataFlavor.java
+ (isFlavorTextType): added method.
+
+2005-11-23 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/plaf/metal/MetalToolBarUI.java
+ (setDragOffset): Implemented.
+
+2005-11-23 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/plaf/metal/MetalLookAndFeel.java
+ (initComponentDefaults): Added defaults for menu arrow icon,
+ menu item arrow icon and menu item check icon.
+ * javax/swing/plaf/metal/MetalTabbedPaneUI.java:
+ Added new field to store graphics when painting highlight.
+ (paintTopTabBorder): Added code to fill gap if it should be
+ filled.
+ (paintBottomTabBorder): Likewise.
+ (paintTabBackground): Added call to paint the highlight below the tab.
+ (getColorForGap): Added code to return selected color, if selected.
+ (shouldFillGap): Changed to return false. With JDK, gap is never filled in
+ MetalL&F.
+ (paintHighlightBelowTab): Implemented to paint the highlight on selected tabs.
+ (calculateMaxTabHeight): Removed.
+ (getTabLabelShiftX): Removed.
+ (getTabLabelShiftY): Removed.
+ (getTabRunOverlay): Removed.
+ (paint): Removed.
+ (paintContentBorderBottomEdge): Removed.
+ (paintContentBorderLeftEdge): Removed.
+ (paintContentBorderRightEdge): Removed.
+ (paintContentBorderTopEdge): Removed.
+ (paintFocusIndicator): Removed.
+ (update): Removed.
+
+2005-11-23 David Gilbert <david.gilbert@object-refinery.com>
+
+ * javax/swing/JComponent.java
+ (getListeners): Updated API docs.
+
+2005-11-23 David Gilbert <david.gilbert@object-refinery.com>
+
+ * java/awt/Container.java
+ (getListeners): Updated API docs.
+
+2005-11-23 David Gilbert <david.gilbert@object-refinery.com>
+
+ * java/awt/Component.java
+ (getListeners): Added some details to the API docs.
+
+2005-11-23 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/text/DefaultStyledDocument.java
+ (ElementBuffer.numEndTags): New field.
+ (ElementBuffer.numStartTags): New field.
+ (ElementBuffer.elementStack): New field.
+ (ElementBuffer.ElementBuffer): Initialize element stack here.
+ (ElementBuffer.changeUpdate): Correctly perform splitting of
+ elements.
+ (ElementBuffer.split): Change to make recursive splits possible.
+ (ElementBuffer.insert): Clear and initialize elementStack and num*
+ fields.
+ (ElementBuffer.inserUpdate): Inlined the functionality for start
+ and end tags. Call endEdit on finish.
+ (ElementBuffer.endEdit): New method. Finishes off an edit run.
+ (ElementBuffer.prepareContentInsertion): New method. Prepares
+ the insertion of content.
+ (ElementBuffer.insertParagraph): New method. Inserts a new
+ paragraph at a given offset.
+ (ElementBuffer.insertContentTag): Call prepareContentInsertion first.
+ Fixed behaviour for all the different possible directions.
+ (ElementBuffer.addEdit): New method. Adds an element edit to the
+ document event and possible merges with previous edits.
+ (insert): Only fire event when something has really changed.
+ * javax/swing/text/AbstractDocument.java
+ (insertString): Only fire event when something has really changed.
+ (DefaultDocumentEvent.modified): New field.
+ (DefaultDocumentEvent.DefaultDocumentEvent): Inititialize modified
+ field.
+ (DefaultDocumentEvent.addEdit): Set modified flag to true.
+
+2005-11-23 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/text/GapContent.java
+ (getPostionsInRange): Fixed binarySearch to really find the first
+ position in this range.
+ (setPostionsInRange): Fixed binarySearch to really find the first
+ position in this range.
+ (adjustPostionsInRange): Fixed binarySearch to really find the first
+ position in this range.
+
+2005-11-23 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/text/View.java
+ (getNextVisualPositionFrom): Fixed signature and (partly)
+ implemented this method.
+ * javax/swing/text/Utilities.java
+ (getPositionAbove): Fixed to use the correct signature for the call
+ to above method.
+ (getPositionBelow): Fixed to use the correct signature for the call
+ to above method.
+ * javax/swing/text/ComponentView.java
+ (getNextVisualPositionFrom): Removed method. This is not specified
+ to be implemented.
+ * javax/swing/text/CompositeView.java
+ (getNextVisualPositionFrom): Removed method with wrong signature.
+ A method with the correct signature is already in place.
+ * javax/swing/text/FlowView.java
+ (LogicalView.getNextVisualPositionFrom): Removed method with wrong
+ signature.
+ * javax/swing/text/GlyphView.java
+ (getNextVisualPositionFrom): Removed method with wrong signature.
+ A method with the correct signature is already in place.
+ * javax/swing/text/IconView.java
+ (getNextVisualPositionFrom): Removed method. This is not specified
+ to be implemented.
+ * javax/swing/text/PlainView.java
+ (getNextVisualPositionFrom): Removed method. This is not specified
+ to be implemented.
+ * javax/swing/text/WrappedPlainView.java
+ (WrappedLine.getNextVisualPositionFrom): Removed method with wrong
+ signature.
+ * javax/swing/plaf/basic/BasicTextUI.java
+ (RootView.getNextVisualPositionFrom): Fixed signature.
+
+2005-11-22 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/JEditorPane.java
+ (JEditorPaneAccessibleHypertextSupport): Implemented.
+
+2005-11-22 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/plaf/metal/MetalTabbedPaneUI.java
+ (getColorForGap): Implemented. Background color is
+ always returned in this case.
+ (paintHighlightBelowTab): Added. Nothing to do in
+ this function as far as i can tell.
+ (shouldFillGap): Implemented. Gap should always be filled.
+ (shouldRotateTabRuns): Implemented. Tabs are not rotated
+ in Metal. False is always returned.
+ (calculateMaxTabHeight): Implemented to call super.
+ (getTabLabelShiftX): Implemented.
+ (getTabLabelShiftY): Implemented.
+ (getTabRunOverlay): Implemented.
+ (paint): Implemented to call super.
+ (paintContentBorderBottomEdge): Likewise.
+ (paintContentBorderLeftEdge): Likewise.
+ (paintContentBorderRightEdge): Likewise.
+ (paintContentBorderTopEdge): Likewise.
+ (paintFocusIndicator): Likewise.
+ (update): Likewise. Should not work any differently from
+ default implementation.
+
+2005-11-22 Christian Thalinger <twisti@complang.tuwien.ac.at>
+
+ * native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkGraphicsEnvironment.c
+ (nativeGetFontFamilies): Added missing DeleteLocalRef calls.
+ * native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkPixbufDecoder.c
+ (query_formats): Likewise.
+ * native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkChoicePeer.c
+ (append): Likewise.
+ * native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkListPeer.c
+ (append): Likewise.
+ * native/jni/qt-peer/qtmenupeer.cpp (runEvent): Likewise.
+
+2005-11-22 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/plaf/metal/MetalIconFactory.java
+ (getMenuArrowIcon): Implemented.
+ (getMenuItemArrowIcon): Implemented to call getMenuArrowIcon,
+ because both icons look the same.
+ (getMenuItemCheckIcon): Implemented.
+ * javax/swing/plaf/metal/MetalTextFieldUI.java
+ (propertyChange): Implemented to call super only, because it
+ is a hook method. It doesn't have a different purpose from
+ BasicLookAndFeel, other than allowing a subclass to override it.
+
+2005-11-22 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/text/MaskFormatter.java:
+ (convertValue): Don't check the valid/invalid character sets if we're
+ matching a literal.
+
+2005-11-22 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/plaf/metal/MetalScrollPaneUI.java
+ (installUI): Implemented.
+ (uninstallUI): Implemented.
+ (installListeners): Implemented.
+ (uninstallListeners): Implemented.
+ (createScrollBarSwapListener): Partially implemented, not sure
+ what else to do here.
+
+2005-11-22 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/text/MaskFormatter.java:
+ (convertValue): If character is a literal don't throw a ParseException
+ unless literals aren't allowd in values and this method is being
+ called from valueToString rather than stringToValue. The convert flag
+ is used to distinguish these two cases.
+
+2005-11-22 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/plaf/metal/MetalComboBoxUI.java
+ (configureEditor): Implemented.
+ (unconfigureEditor): Implemented.
+ (layoutComboBox): Implemented.
+
+2005-11-22 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/text/MaskFormatter.java: New class.
+
+2005-11-22 Lillian Angel <langel@redhat.com>
+
+ PR 24937
+ * gnu/java/awt/peer/gtk/GdkGraphics.java
+ (drawString): Removed pattern matching code. This is now
+ done in native.
+ * native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkGraphics.c
+ (Java_gnu_java_awt_peer_gtk_GdkGraphics_drawString): Added
+ a loop to filter out all non-printing characters.
+
+2005-11-22 Audrius Meskauskas <AudriusA@Bioinformatics.org>
+
+ * javax/swing/text/DefaultCaret.java (updateTimerStatus):
+ Ignore the field "visible".
+
+2005-11-22 Audrius Meskauskas <AudriusA@Bioinformatics.org>
+
+ * javax/swing/TransferHandler
+ (getClipboard): Aways check for the possibility to
+ access the system clipboard.
+
+2005-11-22 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicOptionPaneUI.java
+ (addMessageComponents): Also burst the string if there are newlines
+ in it.
+ (burstStringInto): Improved algorithm to also handle newlines.
+
+2005-11-22 Lillian Angel <langel@redhat.com>
+
+ * gnu/java/awt/peer/gtk/GdkGraphics.java
+ (drawString): Fixed regex.
+
+2005-11-22 Ito Kazumitsu <kaz@maczuka.gcd.org>
+
+ Fixes bug #22691
+ * java/io/StreamTokenizer.java(parseNumbers): Added some comment.
+
+2005-11-22 Audrius Meskauskas <AudriusA@Bioinformatics.org>
+
+ PR 24942
+ * javax/swing/text/DefaultCaret.java (focusGained):
+ Update timer status. (focusLost): Stop the timer
+ (unless the event is temporary).
+ (updateTimerStatus): New method.
+ (setVisible): Delegate timer management to the updateTimerStatus.
+
+2005-11-21 Mark Wielaard <mark@klomp.org>
+
+ * gnu/java/awt/image/ImageDecoder.java (datainput): New field.
+ (ImageDecoder(DataInput)): New constructor.
+ (startProduction): Create DataInputStreamWrapper when datainput set.
+ (DataInputStreamWrapper): New private static helper class.
+ * gnu/java/awt/peer/gtk/GdkPixbufDecoder.java
+ (GdkPixbufDecoder(DataInput)): New constructor.
+ (setInput): Check whether getInput() results in an InputStream or
+ DataInput.
+
+2005-11-21 Mark Wielaard <mark@klomp.org>
+
+ * javax/swing/plaf/basic/BasicComboBoxUI.java (cachedMinimumSize):
+ Document.
+ (isMinimumSizeDirty): Likewise. And initialize to true.
+ (getMinimumSize): Use and set cachedMinimumSize.
+ (FocusHandler.focusGained): Set isMinimumSizeDirty to true.
+ (FocusHandler.focusLost): Likewise.
+ (ItemHandler.itemStateChanged): Likewise.
+ (ListDataHandler.contentsChanged): Likewise.
+ (ListDataHandler.intervalAdded): Likewise.
+ (ListDataHandler.intervalRemoved): Likewise.
+ (PropertyChangeHandler.propertyChange): Likewise.
+
+2005-11-21 Jan Roehrich <jan@roehrich.info>
+
+ * java/awt/datatransfer/DataFlavor.java: more code style
+ fixes. Changed order to static attributes, attributes, static
+ methods, constructors, methods. Moved static part into static
+ attribute declaration.
+
+2005-11-21 Lillian Angel <langel@redhat.com>
+
+ PR classpath/PR24937
+ * gnu/java/awt/peer/gtk/GdkGraphics.java
+ (drawString): Removed most non-printable characters
+ from the string that will be drawn. Added a FIXME comment
+ because may not have filtered out all characters.
+
+2005-11-21 Mark Wielaard <mark@klomp.org>
+
+ * javax/swing/JTable.java (propertyChange): Only resize header when
+ not null.
+
+2005-11-21 Lillian Angel <langel@redhat.com>
+
+ PR classpath/PR24872
+ * javax/swing/text/DefaultEditorKit.java
+ (actionPerformed): Implemented.
+ (actionPerformed): Implemented.
+ (actionPerformed): Implemented.
+ (actionPerformed): Implemented.
+ * javax/swing/text/JTextComponent.java
+ (JTextComponent): Added key bindings for cut, copy,
+ paste, selectionBackwardAction, selectionForwardAction.
+
+2005-11-21 Anthony Balkissoon <abalkiss@redhat.com>
+
+ Fixes bug #24925
+ * javax/swing/text/DefaultEditorKit.java:
+ (DefaultKeyTypedAction.actionPeformed): Call replaceSelection here
+ instead of insertString and only do so if the text component is both
+ enabled and editable.
+
+2005-11-21 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/RepaintManager.java
+ (currentRepaintManagers): Use a WeakHashMap to avoid potential
+ memory leak.
+ (currentManager): Instantiate WeakHashMap instead of HashMap.
+ (setCurrentManager): Instantiate WeakHashMap instead of HashMap.
+
+2005-11-21 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/JViewport.java
+ (static_initializer): Initialize the defaultScrollMode here.
+ (JViewport): Set the defaultScrollMode that was initialized in
+ the static initializer.
+
+2005-11-21 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/JTable.java
+ (columnAtPoint): Removed unused code.
+ (rowAtPoint): Removed unused code.
+ (prepareRenderer): Moved renderer prepare code from the UI to this
+ method.
+ (getSelections): Removed unused code.
+ * javax/swing/plaf/basic/BasicTableUI.java
+ (paintCell): Call JTable.prepareRenderer instead of preparing
+ the renderer in the UI.
+ (paint): Removed some unused code.
+
+2005-11-21 Jan Roehrich <jan@roehrich.info>
+
+ * java/awt/datatransfer/DataFlavor.java: fixed code
+ formatting issues
+
+2005-11-20 Chris Burdess <dog@gnu.org>
+
+ * gnu/xml/transform/TransformerImpl.java: Ensure that output stream
+ is not closed if provided in the StreamResult.
+
+2005-11-19 Ito Kazumitsu <kaz@maczuka.gcd.org>
+
+ * AUTHORS: Added myself.
+
+2005-11-19 Wolfgang Baer <WBaer@gmx.de>
+
+ * javax/print/attribute/Size2DSyntax.java:
+ Added and enhanced api docs for this class.
+ (toString()): Changed to return values as ints.
+ (toString(int,String)): Changed to not append the unitsName if null.
+
+2005-11-19 Wolfgang Baer <WBaer@gmx.de>
+
+ * javax/print/attribute/ResolutionSyntax.java (toString):
+ Changed to not append the unitsName if null. Clarified api docs.
+
+2005-11-19 Wolfgang Baer <WBaer@gmx.de>
+
+ * javax/print/attribute/TextSyntax.java:
+ Added and enhanced api docs for this class.
+ (TextSyntax): If locale is null use the default locale.
+
+2005-11-19 Wolfgang Baer <WBaer@gmx.de>
+
+ * javax/print/attribute/SetOfIntegerSyntax.java:
+ Added and enhanced api docs for this class.
+ (SetOfIntegerSyntax(String)): Create empty set if given string is null.
+
+2005-11-19 Wolfgang Baer <WBaer@gmx.de>
+
+ * javax/print/attribute/ResolutionSyntax.java:
+ Added and enhanced api docs for this class.
+ (getFeedResolution): Use correct feedresolution variable
+ and do not add an additional unit to the resolution.
+ (getCrossFeedResolution): Do not add additional unit to resolution.
+
+2005-11-19 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/metal/MetalTabbedPaneUI.java
+ (paintTabBackground): Fixed colors for the tab background.
+ * javax/swing/plaf/metal/OceanTheme.java
+ (addCustomEntriesToTable): Added color modifications for
+ TabbedPane.
+
+2005-11-18 David Daney <ddaney@avtrex.com>
+
+ * AUTHORS (David Daney): New entry.
+
+2005-11-18 Roman Kennke <kennke@aicas.com>
+
+ * java/awt/Component.java
+ (setBackground): Don't inherit background from parent.
+ (addMouseMotionListener): Enable MOUSE_MOTION_EVENT_MASK instead
+ of MOUSE_EVENT_MASK.
+ (eventTypeEnabled): Handle mouse events and mouse motion events
+ separately.
+
+2005-11-18 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/metal/MetalTabbedPaneUI.java
+ (installDefaults): Added super.installDefaults().
+
+2005-11-18 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicTableHeaderUI.java
+ (installUI): Install a CellRendererPane.
+ (paint): Paint the renderer component using the rendererPane, not
+ directly.
+
+2005-11-18 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicTabbedPaneUI.java
+ (PropertyChangeHandler.propertyChange): Replaced layout() call
+ with revalidate() call.
+ (TabbedPaneLayout.calculateLayoutInfo): Added assureRectsCreated()
+ call to make sure we have the rectangles in place. Also initialize
+ the contentRect here so it can be used later.
+ (TabbedPaneLayout.calculateSize): Removed unused statement.
+ (TabbedPaneLayout.calculateTabRects): Moved assureRectsCreated call
+ to calculateLayoutInfo().
+ (TabbedPaneScrollLayout.calculateTabRects): Moved
+ assureRectsCreated call to calculateLayoutInfo(). Removed unused
+ statements.
+ (TabbedPaneScrollLayout.layoutContainer): Replaced hide() and show()
+ calls with calls to setVisible(). Especially important since
+ setVisible is handled special in Swing.
+ (BasicTabbedPaneUI): Initialize rects and tabRuns fields.
+ (installUI): Removed layout() call.
+ (paintContentBorder): Removed unused statement.
+ (assureRectsCreated): Reworked to match the JDK behaviour.
+ (getFontMetrics): Use the component getFontMetrics() instead of
+ the deprecated toolkit method.
+
+2005-11-18 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/JTable.java
+ (getCellRenderer): Replaced dataModel.getColumnClass() with
+ the shorter getColumnClass().
+ (getColumnClass): Call getModel() instead of accessing dataModel
+ directly. Important for correct operation of subclasses.
+
+2005-11-18 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/JTabbedPane.java
+ (insertTab): Don't call layout() directly, instead call
+ revalidate().
+
+2005-11-18 Roman Kennke <kennke@aicas.com>
+
+ * java/awt/Container.java
+ (findComponentForMouseEventAt): Also check for mouseMotionListeners,
+ otherwise we wouldn't dispatch mouse motion events on components
+ that have no mouse listener installed.
+
+2005-11-18 Lillian Angel <langel@redhat.com>
+
+ PR classpath/PR24754
+ * native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkFontPeer.c
+ (Java_gnu_java_awt_peer_gtk_GdkFontPeer_getTextMetrics): Fixed width
+ for the case where there is more than one line in the layout's text.
+ Otherwise, the width of the layout would be returned, which is the
+ max width of all the lines in the text. A loop was added to get the
+ extent of all the lines and add them together.
+
+2005-11-18 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/metal/MetalTabbedPaneUI.java
+ (minTabWidth): New field.
+ (selectColor): New field.
+ (selectHighlight): New field.
+ (tabAreaBackground): New field.
+ (installDefaults): Initialize new fields with values for UIManager.
+
+2005-11-18 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicInternalFrameUI.java
+ (installUI): Don't install layout here.
+ (uninstallUI): Don't uninstall layout here.
+ (installDefaults): Install layout here.
+ (uninstallDefaults): Uninstall layout here.
+ (getPreferredSize): Use getLayout() to fetch the layout of the frame
+ instead of directly accessing the corresponding field. This
+ is necessary to make subclasses work that don't use this field.
+ (getMinimumSize): Likewise.
+ (getMaximumSize): Likewise.
+
+2005-11-18 Gary Benson <gbenson@redhat.com>
+
+ * AUTHORS: Added myself.
+
+2005-11-18 David Gilbert <david.gilbert@object-refinery.com>
+
+ * javax/swing/JComponent.java
+ (setPreferredSize): Check for null argument before making a copy.
+
+2005-11-18 Gary Benson <gbenson@redhat.com>
+
+ * java/lang/SecurityManager.java (checkAccess): Correctly
+ identify system threads (and thus check permissions for them).
+
+2005-11-18 David Gilbert <david.gilbert@object-refinery.com>
+
+ * javax/swing/JComponent.java
+ (setMinimumSize): Check for null argument before making a copy.
+
+2005-11-18 Paul Jenner <psj@harker.dyndns.org>
+
+ * native/jni/xmlj/xmlj_util.h (XMLJ_64BIT_POINTER): Removed.
+
+2005-11-18 David Gilbert <david.gilbert@object-refinery.com>
+
+ * javax/swing/JComponent.java
+ (setMaximumSize): Check for null argument before making a copy.
+
+2005-11-17 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/JEditorPane.java
+ (PlainEditorKit): New inner class.
+ (createDefaultEditorKit): Return an instance of PlainEditorKit.
+ * javax/swing/JTextPane.java
+ (insertComponent): Implemented previously stubbed method.
+ (insertIcon): Implemented previously stubbed method.
+
+2005-11-17 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicEditorPaneUI.java
+ (create): Removed unneeded method.
+ * javax/swing/plaf/basic/BasicTextPaneUI.java
+ (create): Removed unneeded method.
+
+2005-11-17 Roman Kennke <kennke@aicas.com>
+
+ * java/awt/Container.java
+ (Container): Added comment.
+ (remove): Only call removeNotify if removed component is still
+ showing.
+ (paintComponents): Call paint() instead of super.paint().
+ (AccessibleContainerHandler.AccessibleContainerHandler): Added
+ comment.
+ (LightweightDispatcher.acquireComponentForMouseEvent):
+ Don't special case MOUSE_RELEASED events. They should be
+ dispatched unmodified just as MOUSE_PRESSED.
+ (LightweightDispatcher.handleEvent): Also clean up the pressCount
+ after a MOUSE_RELEASE.
+
+2005-11-17 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/text/BoxView.java:
+ (modelToView): New API method.
+
+2005-11-17 Lillian Angel <langel@redhat.com>
+
+ PR classpath/PR24721
+ * javax/swing/text/BoxView.java
+ (getViewAtPoint): Added check in to return the last view, if one exists and
+ the point was not contained in the rectangle. This is what the JDK does.
+ * javax/swing/text/CompositeView.java
+ (viewToModel): Fixed API documentation. Added check to make sure
+ x and y are greater than 0. Otherwise, 0 is returned.
+ * javax/swing/text/DefaultCaret.java
+ (moveDot): Added check to match API specs.
+ (setDot): Likewise.
+ * javax/swing/text/GlyphView.java
+ (viewToModel): Removed assert. This is not needed here. The point does not
+ need to be in the rectangle.
+
+2005-11-17 Roman Kennke <kennke@aicas.com>
+
+ Reported by Roman Schnider <schnider@aicas.com>:
+ * java/awt/Component.java
+ (reshape): Removed unused statement.
+ (repaint()): Don't forward to parent when not showing.
+ (repaint(int)): Don't forward to parent when not showing.
+ (repaint(int,int,int,int)): Don't forward to parent when not showing.
+ (repaint(float,int,int,int,int)): Don't forward to parent when not
+ showing.
+
+2005-11-17 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/text/AbstractDocument.java
+ (LeafElement.getName): If super.getName() returns something
+ non-null, then return that instead of ContentElementName.
+ * javax/swing/text/ComponentView.java
+ (comp): New field.
+ (getAlignment): Implemented previously stubbed method.
+ (getComponent): Implemented previously stubbed method.
+ (getMaximumSpan): Implemented previously stubbed method.
+ (getMinimumSpan): Implemented previously stubbed method.
+ (getPreferredSpan): Implemented previously stubbed method.
+ (modelToView): Implemented previously stubbed method.
+ (paint): Implemented previously stubbed method.
+ (setParent): Implemented previously stubbed method.
+ (setSize): Removed unneeded method.
+ (viewToModel): Implemented previously stubbed method.
+ * javax/swing/text/FlowView.java
+ (insertUpdate): Forward this event to the logical view.
+ * javax/swing/text/IconView.java
+ (paint): Implemented previously stubbed method.
+ (getPreferredSpan): Implemented previously stubbed method.
+ (modelToView): Implemented previously stubbed method.
+ (viewToModel): Implemented previously stubbed method.
+ * javax/swing/text/ParagraphView.java
+ (firstLineIndent): New field.
+ (justification): New field.
+ (lineSpacing): New field.
+ (tabSet): New field.
+ (changedUpdate): New method.
+ (setPropertiesFromAttributes): New method.
+ (setFirstLineIndent): New method.
+ (setJustification): New method.
+ (setLineSpacing): New method.
+ (getLayoutView): New method.
+ (getLayoutViewCount): New method.
+ (getTabSet): New method.
+
+2005-11-17 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/plaf/basic/BasicEditorPaneUI.java:
+ (create): Create new WrappedPlainView instance instead of PlainView.
+
+2005-11-17 Audrius Meskauskas <AudriusA@Bioinformatics.org>
+
+ PR 24911
+ * classpath/examples/Makefile.am
+ (EXAMPLE_JAVA_FILES): Extended by /*/*/*.java and /*/*/*/*.java.
+ (READMES): New category.
+ (ALL_EXAMPLE_FILES): Extended by READMES category.
+
+2004-11-17 Bryce McKinlay <mckinlay@redhat.com>
+
+ * gnu/java/net/protocol/jar/Connection.java (getHeaderField):
+ Implemented.
+ (getLastModified): Implemented.
+
+2005-11-17 Mark Wielaard <mark@klomp.org>
+
+ * java/net/URLClassLoader.java: Reindented.
+
+2005-11-17 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/JApplet.java
+ (paramString): Returns super.paramString() instead of a meaningless
+ 'JFrame'.
+ * javax/swing/JPanel.java
+ (paramString): Returns super.paramString() instead of a meaningless
+ 'JPanel'.
+
+2005-11-17 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicButtonUI.java
+ (installDefaults): Don't handle the Button.rollover property here,
+ this is Metal specific and is handled in MetalButtonUI.
+
+2005-11-17 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/JList.java
+ (locationToIndex): Clarified API comment.
+
+2005-11-17 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/tree/DefaultTreeCellEditor.java
+ (DefaultTreeCellEditor): Replaced
+ UIManager.getLookAndFeelDefaults().getXXX() with UIManager.getXXX().
+ (createTreeCellEditor): Replaced
+ UIManager.getLookAndFeelDefaults().getXXX() with UIManager.getXXX().
+ * javax/swing/tree/DefaultTreeCellRenderer.java
+ (DefaultTreeCellRenderer): Replaced
+ UIManager.getLookAndFeelDefaults().getXXX() with UIManager.getXXX().
+ (getDefaultOpenIcon): Replaced
+ UIManager.getLookAndFeelDefaults().getXXX() with UIManager.getXXX().
+ (getDefaultClosedIcon): Replaced
+ UIManager.getLookAndFeelDefaults().getXXX() with UIManager.getXXX().
+ (getDefaultLeafIcon): Replaced
+ UIManager.getLookAndFeelDefaults().getXXX() with UIManager.getXXX().
+ (getTreeCellRendererComponent): Replaced
+ UIManager.getLookAndFeelDefaults().getXXX() with UIManager.getXXX().w
+ (paint): Replaced UIManager.getLookAndFeelDefaults().getXXX()
+ with UIManager.getXXX().
+
+2005-11-17 Andrew Haley <aph@redhat.com>
+
+ * gnu/java/net/protocol/file/Connection.java (unquote): New
+ method.
+ (connect): Unquote filename.
+ * gnu/java/net/protocol/jar/Connection.java (get): Likewise.
+
+ * java/net/URL.java (URL): If the file part of a spec is absolute,
+ ignore the file part of its context.
+
+2005-11-17 Audrius Meskauskas <AudriusA@Bioinformatics.org>
+
+ * examples/gnu/classpath/examples/CORBA/swing/README.html:
+ Added note about the build.
+
+2005-11-16 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/JSplitPane.java: Reformatted file.
+ * javax/swing/plaf/basic/BasicSplitPaneUI.java: Reformatted file.
+
+2005-11-16 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/ToolTipManager.java
+ (mouseEntered): No need to start the insideTimer here,
+ already called showTip.
+
+2005-11-16 Lillian Angel <langel@redhat.com>
+
+ PR classpath/PR24763
+ * javax/swing/ToolTipManager.java
+ (mouseEntered): showTip should be called if exitTimer is running.
+ This means that the mouse has exited and re-entered a component
+ in less than 500ms.
+ (mouseExited): If enterTimer is not running, the exitTimer should
+ be started no matter what.
+ (showTip): Should not show tool tip if the currentComponent is
+ not showing.
+
+2005-11-16 Lillian Angel <langel@redhat.com>
+
+ PR classpath/PR23557 and PR classpath/PR24099
+ * native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkGraphics2D.c
+ (Java_gnu_java_awt_peer_gtk_GdkGraphics2D_gdkDrawDrawable):
+ Added check to determine if dst->drawable or src->drawable
+ are actually drawable. If not, return.
+
+2005-11-16 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/metal/MetalBorders.java
+ (ButtonBorder.paintBorder): Special case the OceanTheme.
+ (ButtonBorder.paintOceanThemeBorder): New method.
+ * javax/swing/plaf/metal/MetalButtonUI.java
+ (installDefaults): Set the rollover flag here. Don't set a special
+ border for rollover buttons.
+ (uninstallDefaults): Reset the rollover flag.
+ (update): Only paint gradient when button is enabled and not pressed.
+ * javax/swing/plaf/metal/MetalLookAndFeel.java
+ (getCurrentTheme): New method.
+
+2005-11-16 Gary Benson <gbenson@redhat.com>
+
+ * java/io/FilePermission.java (implies): Correct the sense
+ in which action checks are applied.
+
+2005-11-16 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * AUTHORS: Added myself.
+ * javax/swing/KeyboardManager.java: Changed @author tag to match the
+ other ones I have.
+ * javax/swing/text/WrappedPlainView.java: Likewise.
+
+2005-11-16 Gary Benson <gbenson@redhat.com>
+
+ * java/security/ProtectionDomain.java (toString): Use
+ gnu.classpath.SystemProperties to read line.separator
+ without security manager check.
+
+2005-11-16 Lillian Angel <langel@redhat.com>
+
+ * java/awt/image/MemoryImageSource.java
+ (startProduction): If animated, imageComplete should
+ be called with the SINGLEFRAMEDONE flag, meaning the
+ single frame is complete, but there are more frames
+ to follow.
+
+2005-11-16 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/text/PlainDocument.java:
+ (insertString): Null check fixes PR 24890.
+
+2005-11-16 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/plaf/basic/BasicTreeUI.java
+ (paintVerticalPartOfLeg): Added a check to prevent
+ ArrayOutOfBoundsException.
+
+2005-11-16 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicInternalFrameTitlePane.java
+ (paintTitleBackground): Only paint background if component is
+ opaque.
+ * javax/swing/plaf/metal/MetalInternalFrameTitlePane.java
+ (paintPalette): Added gradient painting.
+ (paintComponent): Added gradient painting.
+ * javax/swing/plaf/metal/OceanTheme.java
+ (addCustomEntriesToTable): Added gradient for
+ InternalFrama.activeTitleGradient.
+
+2005-11-16 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/ToolTipManager.java:
+ Removed unneeded fields.
+ (showTip): Re-implemented to use PopupFactory.
+ (hideTip): Likewise.
+ (adjustLocation): Fixed location.
+
+2005-11-16 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/text/PlainDocument.java:
+ (insertUpdate): The very first new element added doesn't start at the
+ start of the event, it starts at the start offset of the Element that
+ contains the start of the event.
+
+2005-11-16 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicMenuItemUI.java
+ (paintMenuItem): Always call paintBackground().
+
+2005-11-16 Lillian Angel <langel@redhat.com>
+
+ * gnu/java/awt/peer/gtk/GtkDialogPeer.java
+ (create): Since popups were changed to be JWindowPopups,
+ this code should be done in GtkWindowPeer. Code is not
+ needed.
+ * gnu/java/awt/peer/gtk/GtkWindowPeer.java
+ (create): If window is not focusable, it should not take
+ the focus away from any other window. Therefore, its
+ type should be set to GDK_WINDOW_TYPE_HINT_MENU.
+
+2005-11-16 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/metal/MetalButtonUI.java
+ (update): New method. Paints the gradient.
+ * javax/swing/plaf/metal/MetalCheckBoxIcon.java
+ (paintIcon): Paint gradient.
+ * javax/swing/plaf/metal/MetalIconFactory.java
+ (RadioButtonIcon.paintIcon): Paint gradient.
+ * javax/swing/plaf/metal/MetalLookAndFeel.java
+ (initClassDefaults): Added MetalMenuBarUI.
+ * javax/swing/plaf/metal/MetalMenuBarUI.java: New file.
+ * javax/swing/plaf/metal/MetalToggleButtonUI.java
+ (update): New method. Paints the gradient.
+ * javax/swing/plaf/metal/OceanTheme.java
+ (addCustomEntriesToTable): Added all the gradients.
+
+2005-11-16 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/JMenu.java
+ (JMenu()): Set opaque flag to false.
+ (JMenu(String)): Likewise.
+ (JMenu(Action)): Likewise.
+
+2005-11-16 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicListUI.java
+ (getRowHeight): Adjusted to deal correctly with fixed cell heights.
+ (convertYRoRow): Likewise.
+ * javax/swing/plaf/basic/BasicMenuItemUI.java
+ (installDefaults): Don't make the menu item opaque here.
+ (paintBackground): Moved background painting code from
+ paintMenuItem() to this method.
+ (paintMenuItem): Moved background painting to paintBackground().
+ (installDefaults): Don't set opaque flag here.
+
+2005-11-16 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/metal/MetalUtils.java
+ (paintGradient): New utility method(s).
+ (paintHorizontalGradient): New utility method.
+ (paintVerticalGradient): New utility method.
+
+2005-11-15 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/JComponent.java
+ (paintDoubleBuffered): Put paint() call inside a try-finally
+ block to correctly recover the double-buffering flag when
+ an exception is thrown inside the paint() call.
+
+2005-11-15 Lillian Angel <langel@redhat.com>
+
+ * native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkWindowPeer.c
+ (Java_gnu_java_awt_peer_gtk_GtkWindowPeer_gtkWindowSetResizable):
+ Needed to set allow_shrink to the same value as resizable. Other-
+ wise, it is always set to false.
+
+2005-11-15 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/plaf/basic/BasicTreeUI.java
+ (paint): Added check to prevent NPE.
+
+2005-11-15 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/JComponent.java:
+ (removeNotify): Unregister WHEN_IN_FOCUSED_WINDOW bindings from the
+ KeyboardManager.
+
+2005-11-15 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/plaf/basic/BasicLookAndFeel.java
+ (initComponentDefaults): Default rowHeight for tree's should
+ be 0. This is Sun and IBM's default.
+ * javax/swing/plaf/metal/MetalLookAndFeel.java
+ (initComponentDefaults): Default rowHeight for tree's should
+ e 0. This is Sun and IBM's default.
+ * javax/swing/plaf/basic/BasicTreeUI.java:
+ Added a default rowHeight field.
+ (setRowHeight): Set the rowHeight to the class default if parameter
+ is 0. Tree row height should never be set to 0. 20 is the minimum.
+ (installDefaults): fixed call to tree.setRowHeight
+ (shouldPaintExpandControl): Added to check to prevent NPE.
+
+2005-11-15 Audrius Meskauskas <AudriusA@Bioinformatics.org>
+
+ * examples/gnu/classpath/examples/CORBA/swing/README.html,
+ examples/gnu/classpath/examples/CORBA/swing/x5/CanvasWorld.java,
+ examples/gnu/classpath/examples/CORBA/swing/x5/ChatConstants.java,
+ examples/gnu/classpath/examples/CORBA/swing/x5/ClientFrame.java,
+ examples/gnu/classpath/examples/CORBA/swing/x5/Demo.java,
+ examples/gnu/classpath/examples/CORBA/swing/x5/GameManager.java,
+ examples/gnu/classpath/examples/CORBA/swing/x5/GameManagerImpl.java,
+ examples/gnu/classpath/examples/CORBA/swing/x5/IorReader.java,
+ examples/gnu/classpath/examples/CORBA/swing/x5/OrbStarter.java,
+ examples/gnu/classpath/examples/CORBA/swing/x5/Player.java,
+ examples/gnu/classpath/examples/CORBA/swing/x5/PlayerImpl.java,
+ examples/gnu/classpath/examples/CORBA/swing/x5/PlayingDesk.java,
+ examples/gnu/classpath/examples/CORBA/swing/x5/State.java,
+ examples/gnu/classpath/examples/CORBA/swing/x5/X5Server.java,
+ examples/gnu/classpath/examples/CORBA/swing/x5/_GameManagerImpl_Tie.java,
+ examples/gnu/classpath/examples/CORBA/swing/x5/_GameManager_Stub.java,
+ examples/gnu/classpath/examples/CORBA/swing/x5/_PlayerImpl_Tie.java,
+ examples/gnu/classpath/examples/CORBA/swing/x5/_Player_Stub.java:
+ New files.
+
+2005-11-15 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/UIManager.java
+ (userUIDefaults): New field.
+ (get(Object)): Respect the user UI settings.
+ (get(Object,Locale)): Respect the user UI settings.
+ (getBoolean(Object)): Call get() instead of
+ getLookAndFeelDefaults().get() in order to respect the user UI
+ settings.
+ (getBoolean(Object,Locale)): Call get() instead of
+ getLookAndFeelDefaults().get() in order to respect the user UI
+ settings.
+ (getBorder(Object)): Call get() instead of
+ getLookAndFeelDefaults().get() in order to respect the user UI
+ settings.
+ (getBorder(Object,Locale)): Call get() instead of
+ getLookAndFeelDefaults().get() in order to respect the user UI
+ settings.
+ (getColor(Object)): Call get() instead of
+ getLookAndFeelDefaults().get() in order to respect the user UI
+ settings.
+ (getColor(Object,Locale)): Call get() instead of
+ getLookAndFeelDefaults().get() in order to respect the user UI
+ settings.
+ (getDimension(Object)): Call get() instead of
+ getLookAndFeelDefaults().get() in order to respect the user UI
+ settings.
+ (getDimension(Object,Locale)): Call get() instead of
+ getLookAndFeelDefaults().get() in order to respect the user UI
+ settings.
+ (getFont(Object)): Call get() instead of
+ getLookAndFeelDefaults().get() in order to respect the user UI
+ settings.
+ (getFont(Object,Locale)): Call get() instead of
+ getLookAndFeelDefaults().get() in order to respect the user UI
+ settings.
+ (getIcon(Object)): Call get() instead of
+ getLookAndFeelDefaults().get() in order to respect the user UI
+ settings.
+ (getIcon(Object,Locale)): Call get() instead of
+ getLookAndFeelDefaults().get() in order to respect the user UI
+ settings.
+ (getInsets(Object)): Call get() instead of
+ getLookAndFeelDefaults().getInsets() in order to respect the user UI
+ settings.
+ (getInsets(Object,Locale)): Call get() instead of
+ getLookAndFeelDefaults().getInsets() in order to respect the user UI
+ settings.
+ (getInt(Object)): Call get() instead of
+ getLookAndFeelDefaults().get() in order to respect the user UI
+ settings.
+ (getInt(Object,Locale)): Call get() instead of
+ getLookAndFeelDefaults().get() in order to respect the user UI
+ settings.
+ (getString(Object)): Call get() instead of
+ getLookAndFeelDefaults().get() in order to respect the user UI
+ settings.
+ (getString(Object,Locale)): Call get() instead of
+ getLookAndFeelDefaults().get() in order to respect the user UI
+ settings.
+ (getUI(JComponent)): Respect the user UI settings.
+ (put): Put key/value into user UI settings.
+
+2005-11-15 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/metal/MetalBorders.java
+ (OptionDialogBorder.paintBorder): Replaced
+ UIManager.getLookAndFeelDefaults().get() with UIManager.get().
+ * javax/swing/plaf/metal/MetalButtonUI.java
+ (MetalButtonUI): Replaced UIManager.getLookAndFeelDefaults().get()
+ with UIManager.get().
+ * javax/swing/plaf/metal/MetalInternalFrameTitlePane.java
+ (installDefaults): Replaced UIManager.getLookAndFeelDefaults().get()
+ with UIManager.get().
+ * javax/swing/plaf/metal/MetalLabelUI.java
+ (paintDisabledText): Replaced UIManager.getLookAndFeelDefaults().get()
+ with UIManager.get().
+ * javax/swing/plaf/metal/MetalRadioButtonUI.java
+ (installDefaults): Replaced UIManager.getLookAndFeelDefaults().get()
+ with UIManager.get().
+ * javax/swing/plaf/metal/MetalScrollBarUI.java
+ (createDecreaseButton): Replaced
+ UIManager.getLookAndFeelDefaults().get() with UIManager.get().
+ (createIncreaseButton): Replaced
+ UIManager.getLookAndFeelDefaults().get() with UIManager.get().
+ (paintThumbHorizontal): Replaced
+ UIManager.getLookAndFeelDefaults().get() with UIManager.get().
+ (paintThumbVertical): Replaced
+ UIManager.getLookAndFeelDefaults().get() with UIManager.get().
+ * javax/swing/plaf/metal/MetalSplitPaneUI.java
+ (createDefaultDivider): Replaced
+ UIManager.getLookAndFeelDefaults().get() with UIManager.get().
+ * javax/swing/plaf/metal/MetalToggleButtonUI.java
+ (installDefaults): Replaced UIManager.getLookAndFeelDefaults().get()
+ with UIManager.get().
+ * javax/swing/plaf/metal/MetalToolTipUI.java
+ (MetalToolTipUI): Replaced UIManager.getLookAndFeelDefaults().get()
+ with UIManager.get().
+ * javax/swing/plaf/metal/MetalTreeUI.java
+ Removed all listener fields.
+ (installUI): Removed initialization and call super.installUI()
+ instead.
+ (uninstallUI): Removed initialization and call super.uninstallUI()
+ instead.
+
+2005-11-15 Audrius Meskauskas <AudriusA@Bioinformatics.org>
+
+ * gnu/CORBA/OrbFunctional.java (serveStep):
+ Returning ensure that the socket is closed.
+
+2005-11-15 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicBorders.java
+ (getButtonBorder): Replaced UIManager.getLookAndFeelDefaults().get()
+ with UIManager.get().
+ (getRadioButtonBorder): Replaced
+ UIManager.getLookAndFeelDefaults().get() with UIManager.get().
+ (getToggleButtonBorder): Replaced
+ UIManager.getLookAndFeelDefaults().get() with UIManager.get().
+ (getMenuBarBorder): Replaced
+ UIManager.getLookAndFeelDefaults().get() with UIManager.get().
+ (getSplitPaneBorder): Replaced
+ UIManager.getLookAndFeelDefaults().get() with UIManager.get().
+ (getSplitPaneDividerBorder): Replaced
+ UIManager.getLookAndFeelDefaults().get() with UIManager.get().
+ (getTextFieldBorder): Replaced
+ UIManager.getLookAndFeelDefaults().get() with UIManager.get().
+ (getInternalFrameBorder): Replaced
+ UIManager.getLookAndFeelDefaults().get() with UIManager.get().
+ * javax/swing/plaf/basic/BasicButtonUI.java
+ (paintText): Replaced UIManager.getLookAndFeelDefaults().get()
+ with UIManager.get().
+ * javax/swing/plaf/basic/BasicCheckBoxUI.java
+ (getDefaultIcon): Replaced UIManager.getLookAndFeelDefaults().get()
+ with UIManager.get().
+ * javax/swing/plaf/basic/BasicComboBoxUI.java
+ (paintCurrentValue): Replaced UIManager.getLookAndFeelDefaults().get()
+ with UIManager.get().
+ * javax/swing/plaf/basic/BasicFileChooserUI.java
+ (installStrings): Replaced UIManager.getLookAndFeelDefaults().get()
+ with UIManager.get().
+ * javax/swing/plaf/basic/BasicInternalFrameTitlePane.java
+ (installDefaults): Replaced UIManager.getLookAndFeelDefaults().get()
+ with UIManager.get().
+ * javax/swing/plaf/basic/BasicListUI.java
+ (installKeyboardActions): Replaced
+ UIManager.getLookAndFeelDefaults().get() with UIManager.get().
+ * javax/swing/plaf/basic/BasicProgressBarUI.java
+ (boxRect): Added @since tag to the API comment.
+ * javax/swing/plaf/basic/BasicRadioButtonUI.java
+ (getDefaultIcon): Replaced UIManager.getLookAndFeelDefaults().get()
+ with UIManager.get().
+ * javax/swing/plaf/basic/BasicScrollBarUI.java
+ (configureScrollBarColors): Replaced
+ UIManager.getLookAndFeelDefaults().get() with UIManager.get().
+ (calculatePreferredSize): Fetch preferred width or height from
+ UI defaults.
+ * javax/swing/plaf/basic/BasicTableUI.java
+ (installKeyboardActions): Replaced
+ UIManager.getLookAndFeelDefaults().get() with UIManager.get().
+ * javax/swing/plaf/basic/BasicTextUI.java
+ (createKeymap): Replaced
+ UIManager.getLookAndFeelDefaults().get() with UIManager.get().
+ (getInputMap): Replaced
+ UIManager.getLookAndFeelDefaults().get() with UIManager.get().
+ (getActionMap): Replaced
+ UIManager.getLookAndFeelDefaults().get() with UIManager.get().
+ * javax/swing/plaf/basic/BasicToolBarUI.java
+ (dragTo): Don't use cached* fields.
+ (installComponents): Don't use cached* fields.
+ * javax/swing/plaf/basic/BasicTreeUI.java
+ (getHashColor): Replaced
+ UIManager.getLookAndFeelDefaults().get() with UIManager.get().
+ (setHashColor): Replaced
+ UIManager.getLookAndFeelDefaults().get() with UIManager.get().
+ Added FIXME comment.
+ (installKeyboardActions): Replaced
+ UIManager.getLookAndFeelDefaults().get() with UIManager.get().
+
+2005-11-15 Christian Thalinger <twisti@complang.tuwien.ac.at>
+
+ * native/jni/java-lang/java_lang_VMDouble.c (initIDs): Register
+ clsDouble as global ref.
+ * native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkToolkit.c
+ (gtkInit): Register gtkgenericpeer as global ref.
+
+2005-11-15 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/plaf/basic/BasicTreeUI.java:
+ Removed unneeded field.
+ (getPathBounds): Reimplemented to use getNodeDimensions.
+ (getRowCount): Removed call to updateCurrentVisiblePath.
+ (uninstallKeyboardActions): Implemented.
+ (paint): Reimplemented to only paint rows contained in clip.
+ No longer uses recursion.
+ (mousePressed): If control icon is clicked, should scroll to that
+ path.
+ (getNodeDimensions): Implemented.
+ (getRowX): Implemented.
+ (getCellBounds): Removed.
+ (getCellLocation): Removed.
+ (paintRecursive): Removed.
+ (paintControlIcons): Removed.
+ (getPreviousVisibleNode): Removed call to updateCurrentVisiblePath.
+ (getLevel): Added check for invisible root.
+ (paintVerticalLine): Set graphics color.
+ (paintHorizontalLine): Likewise.
+ (drawCentered): Added negative check.
+ (drawDashedHorizontalLine): Set graphics color.
+ (drawDashedVerticalLine): Likewise.
+ (paintExpandControl): Implemented.
+ (paintHorizontalPartOfLeg): Likewise.
+ (paintVerticalPartOfLeg): Likewise.
+ (paintRow): Added call to paint the control icons.
+ (updateCurrentVisiblePath): Cleaned up function.
+
+2005-11-15 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/text/AbstractDocument.java:
+ (remove): Do not set up an ElementEdit here, this is done in the
+ Document implementation's removeUpdate method.
+ * javax/swing/text/PlainDocument.java:
+ (insertUpdate): Do not call reindex, instead, reindex the lines here
+ directly but only starting from the offset of the newly inserted text.
+ Also, if entire lines have been added or removed, set up an ElementEdit
+ and add it to the DocumentEvent. Chain BadLocationException to an
+ AssertionError and throw it in the unexpected case.
+ (removeUpdate): If entire lines have been added or removed, set up an
+ ElementEdit and add it to the DocumentEvent. Chain
+ BadLocationException to an AssertionError and throw it in the
+ unexpected case.
+ (reindex): Removed unnecessary method.
+
+2005-11-15 Wolfgang Baer <WBaer@gmx.de>
+
+ * javax/print/attribute/DateTimeSyntax.java,
+ * javax/print/attribute/EnumSyntax.java,
+ * javax/print/attribute/IntegerSyntax.java,
+ * javax/print/attribute/URISyntax.java:
+ Added and enhances some api docs.
+
+2005-11-15 Lillian Angel <langel@redhat.com>
+
+ * gnu/java/awt/peer/gtk/GtkComponentPeer.java:
+ Code written by Sven de Marothy.
+ (gtkWindowGetLocationOnScreen): Added declaration
+ for native function.
+ (getLocationOnScreen): Changed to handle 2 different cases.
+ If the component is a window, gtkWindowGetLocationOnScreen is
+ called; otherwise, gtkWidetGetLocationOnScreen.
+ * include/gnu_java_awt_peer_gtk_GtkComponentPeer.h:
+ Added signature for new function Java_gnu_java_awt_peer_
+ gtk_GtkComponentPeer_gtkWindowGetLocationOnScreen.
+ * native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkComponentPeer.c
+ (Java_gnu_java_awt_peer_gtk_GtkComponentPeer_gtkWidgetGetLocationOnScreen):
+ Implemented.
+
+2005-11-15 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/JViewport.java
+ (JViewport): Recognize setting of a system property
+ gnu.javax.swing.JViewport for the scrollMode.
+
+2005-11-15 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/metal/MetalUtils.java
+ (fillMetalPattern2D): Fixed the texture width.
+ (initializePattern): Made texture transparent.
+
+2005-11-15 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/JTextField.java
+ (createDefaultModel): Set the filterNewlines property on the created
+ model.
+
+2005-11-15 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicListUI.java
+ Fixed API docs all over to better explain the changed (but correct)
+ behaviour.
+ (convertYToRow): Added some short-circuits for special cases. Update
+ the layout state if necessary. Fixed to match the JDK behaviour.
+ Added API docs to better explain the behaviour.
+ (updateLayoutState): When a fixedCellHeight is set, then use the
+ cellHeight field, otherwise use the cellHeights array.
+ (uninstallDefaults): Removed unnecessary statement.
+ (paintBackground): Removed unnecessary method.
+ (paintCell): Removed some commented-out code.
+ (paint): Removed call to paintBackground().
+ (locationToIndex): Removed unused statement.
+
+2005-11-14 Wolfgang Baer <WBaer@gmx.de>
+
+ * javax/print/attribute/AttributeSetUtilities.java:
+ Added api docs and enhanced api docs all over the place.
+ (verifyCategoryForValue): Throw exception when arguments
+ are _not_ equal and throw NPE also if attribute is null.
+
+2005-11-14 Lillian Angel <langel@redhat.com>
+
+ * gnu/java/awt/peer/gtk/GtkComponentPeer.java
+ (getLocationOnScreen): The insets should be taken into account
+ when returning the location of an object on the screen.
+
+2005-11-14 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/JMenuBar.java:
+ (removeNotify): Unregister this JMenuBar from the KeyboardManager.
+ * javax/swing/KeyboardManager.java:
+ (unregisterJMenuBar): New implementation method.
+
+2005-11-14 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/JComponent.java:
+ (removeNotify): Removed unncessary InputMap and ActionMap inheritance
+ code. Added FIXME to remove the WHEN_IN_FOCUSED_WINDOW bindings from
+ the KeyboardManager.
+ * javax/swing/JMenuBar.java:
+ (removeNotify): Added FIXME to unregister this JMenuBar from the
+ KeyboardManager.
+
+2005-11-14 Wolfgang Baer <WBaer@gmx.de>
+
+ * javax/print/attribute/HashAttributeSet.java:
+ Added api docs to class and clarified method documentation.
+ (toArray): Get iterator from values instead of entries.
+ (hashCode): Compute hashcode according to specification.
+ (get): Throw NullPointerException if category is null.
+ (HashAttributeSet(Attribute[],Class)): Changed to allow
+ Attribute[] to be null.
+
+2005-11-14 Mark Wielaard <mark@klomp.org>
+
+ As suggested by Joao Victor <jvital@gmail.com>:
+ * javax/swing/Timer.java (Waker): Removed class.
+ (Task): New class.
+ (timer): New field.
+ (running): Removed field.
+ (waker): Likewise.
+ (task): New field.
+ (isRunning): Check whether task is null.
+ (start): Create task and schedule it with timer.
+ (stop): Cancel task and clear field.
+ (queueEvent): Synchronized on queueLock.
+
+2005-11-14 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/JTree.java
+ (expandPath): No need to get the parent path.
+ * javax/swing/event/TreeModelEvent.java:
+ Variables should be initialized to null.
+ (toString): Implemented.
+ * javax/swing/plaf/basic/BasicTreeUI.java
+ (treeStructureChanged): Implemented.
+ (getParent): Added check to avoid infinite loop.
+ (findNode): Fixed check to use getChild, instead of
+ getIndexOfChild.
+ (updateCurrentVisiblePath): Added a loop to check
+ the parent's sibling, if the current node has no
+ other siblings.
+
+2005-11-14 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/ActionMap.java:
+ (keys): Return null if the map is empty.
+ (allKeys): Likewise.
+ * javax/swing/InputMap.java:
+ (keys): Return null if the map is empty.
+ (allKeys): Likewise.
+ * javax/swing/JMenuBar:
+ (addNotify): Register the menu with the KeyboardManager.
+ (processKeyBinding): New API method.
+ (processKeyBindingHelper): New implementation method.
+ * javax/swing/JMenuItem.java:
+ (setAccelerator): Fire a PropertyChangeEvent after changing the
+ accelerator.
+ * javax/swing/KeyboardManager.java:
+ (menuBarLookup): New field, Hashtable mapping between top-level
+ containers and a Vector of the JMenuBars contained in them.
+ (getHashtableForTopLevel): Changed this public method to package
+ private.
+ (registerEntireMap): Avoid NPE by returning early if the parameter
+ is null or contains no mappings.
+ (processKeyStroke): If the mapped component doesn't consume the event,
+ let all JMenuBars in the top-level container have a chance at it.
+ (getVectorForTopLevel): New implementation method.
+ (registerJMenuBar): Likewise.
+ * javax/swing/plaf/basic/BasicMenuItemUI.java:
+ (propertyChangeListener): New field.
+ (PropertyChangeHandler): New class to handle PropertyChangeEvents on
+ the JMenuItem.
+ (ClickAction): New class to implement accelerator key handling.
+ (BasicMenuItemUI<init>): Instantiate the propertyChangeListener field.
+ (installKeyboardActions): Implemented.
+ (installListeners): Install the propertyChangeListener.
+ (installUI): Call installKeyboardAcions after installing the listeners.
+ (uninstallKeyboardActions): Implemented.
+ (uninstallListeners): Remove the propertyChangeListener.
+
+2005-11-14 Tom Tromey <tromey@redhat.com>
+
+ * java/applet/Applet.java (URLAudioClip): New class.
+ (newAudioClip): Implemented.
+ * gnu/java/beans/DummyAppletContext.java (getAudioClip): Use
+ Applet.newAudioClip.
+ (DUMMY_CLIP): Removed.
+ (DummyAudioClip): Removed.
+
+2005-11-14 Tom Tromey <tromey@redhat.com>
+
+ * javax/sound/sampled/Line.java (open): Throws
+ LineUnavailableException.
+
+2005-11-14 Roman Kennke <kennke@aicas.com>
+
+ Reported by Ingo Proetel <proetel@aicas.com>
+ * gnu/java/io/PlatformHelper.java
+ (toCanonicalForm): Remove lowercasing of paths in Windows. This
+ breaks working with URLs, like when accessing files withing JAR
+ files.
+
+2005-11-14 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/JLayeredPane.java
+ (paint): Only clear the background if the layeredPane is opaque.
+
+2005-11-14 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/RepaintManager.java
+ (globalManager): Removed obsolete field.
+ (currentRepaintManagers): New field.
+ (RepaintWorker.run): Fetch current RepaintManager for the current
+ thread group.
+ (currentManager): Return the current manager for the current thread
+ group.
+ (setCurrentManager): Set the repaint manager for the current thread
+ group.
+
+2005-11-14 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicComboPopup.java
+ (show): Instead of fiddling with the list size, set the preferredSize
+ of the scroller.
+ (configureScroller): Set border to null.
+ (configurePopup): Set border correctly.
+
+2005-11-14 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicInternalFrameTitlePane.java
+ (setButtonIcons): Only set icons if buttons are != null.
+
+2005-11-14 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicLookAndFeel.java
+ (initComponentDefaults): Fixed some UI defaults used by ProgressBar.
+
+2005-11-14 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicTextFieldUI.java
+ (propertyChange): Get new value from the PropertyChangeEvent and
+ not from the component itself (since when it receives the event,
+ the component still has the old state).
+
+2005-11-14 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicTextUI.java
+ (uninstallListeners): Uninstall the document listener here.
+ (getVisibleEditorRect): Fetch the textComponent via getComponent().
+
+2005-11-14 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/text/BoxView.java
+ (paint): Only paint child if it is inside the current clip.
+
+2005-11-14 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/AbstractButton.java
+ (setEnabled): Also set focusable flag on the button when the enabled
+ property changes.
+
+2005-11-14 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicProgressBarUI.java
+ (boxRect): New protected field.
+ (PropertyChangeHandler.propertyChange): Fixed typo in 'indeterminate'.
+ Only start animation when progressBar is actually showing. Removed
+ repaint call.
+ (AncestorHandler): New inner class. Helps starting/stopping the
+ animation when progressBar becomes showing/hidden.
+ (ComponentHandler): New inner class. Recalculates box sizes for
+ indeterminate progress bars when the size of the progress bar
+ changes.
+ (boxRect): New protected field.
+ (boxDependent): New transient field.
+ (boxIndependent): New transient field.
+ (incr): New transient field.
+ (ancestorListener): New private field.
+ (componentListener): New private field.
+ (getBox): Fixed calculation of the indeterminate progress bar box
+ to match the JDK behaviour.
+ (getMaximumSize): Implemented the maximumSize for progressBars.
+ (getMinimumSize): Implemented the minimumSize for progressBars.
+ (getPreferredInnerHorizontal): Implemented correctly.
+ (getPreferredInnerVertical): Implemented correctly.
+ (getPreferredSize): Implemented correctly using the getPreferredXXX()
+ helper methods.
+ (paintDeterminate): Fixed painting to better match the JDK behaviour.
+ (paintIndeterminate): Fixed painting to better match the JDK behaviour.
+ (paintString): Implemented 'half-dark-half-light' painted text.
+ (installListeners): Install new listeners.
+ (uninstallListeners): Uninstall new listeners.
+ * javax/swing/plaf/basic/MetalProgressBarUI.java
+ (paintDeterminate): New method.
+ (paintIndeterminate): New method.
+
+2005-11-14 Roman Kennke <kennke@aicas.com>
+
+ * examples/gnu/classpath/examples/swing/Demo.java
+ (static_initializer): Set the L&F and theme explicitly for the
+ default option, because JDK1.4 and JDK1.5 have different defaults.
+ (mkMenuBar): For the slider demo, trigger the new SliderDemo
+ class. Added ProgressBarDemo to menu.
+ (mkSliders): Removed obsolete slider demo.
+ (mkButtonBar): Added ProgressBar demo.
+ * examples/gnu/classpath/examples/swing/ProgressBarDemo.java:
+ New file. Demonstrates the JProgressBar.
+
+2005-11-13 Archie Cobbs <archie@dellroad.org>
+
+ * vm/reference/gnu/classpath/VMStackWalker.java (getClassLoader()):
+ added to fix an infinite loop bug.
+ * NEWS: note VM interface change.
+
+2005-11-13 Ito Kazumitsu <kaz@maczuka.gcd.org>
+
+ Fixes bug #23008
+ * gnu/java/nio/charset/UTF_16Decoder.java
+ MAYBE_BIG_ENDIAN, MAYBE_LITTLE_ENDIAN: New constants representing
+ such endianness which is similar to UNKNOWN_ENDIAN but defaults
+ to big/little endian without a byte order mark.
+ (decodeLoop): Handle MAYBE_BIG_ENDIAN and MAYBE_LITTLE_ENDIAN.
+ * gnu/java/nio/charset/UnicodeLittle.java
+ (newDecoder): Set the endianness to MAYBE_LITTLE_ENDIAN.
+
+2005-11-13 Audrius Meskauskas <AudriusA@Bioinformatics.org>
+
+ PR 24733
+ * javax/swing/TransferHandler.java (getClipboard): Rewritten.
+
+2005-11-13 Wolfgang Baer <WBaer@gmx.de>
+
+ * javax/print/attribute/HashDocAttributeSet.java,
+ * javax/print/attribute/HashPrintJobAttributeSet.java,
+ * javax/print/attribute/HashPrintRequestAttributeSet.java,
+ * javax/print/attribute/HashPrintServiceAttributeSet.java,
+ Added class api docs and enhanced method api docs.
+
+2005-11-13 Tom Tromey <tromey@redhat.com>
+
+ * native/jni/midi-dssi/.cvsignore: Updated.
+ * native/jni/midi-alsa/.cvsignore: New file.
+ * lib/.cvsignore: Updated.
+
+2005-11-13 Tom Tromey <tromey@redhat.com>
+
+ * javax/sound/sampled/AudioFileFormat.java: New file.
+ * javax/sound/sampled/AudioFormat.java: New file.
+ * javax/sound/sampled/AudioInputStream.java: New file.
+ * javax/sound/sampled/AudioPermission.java: New file.
+ * javax/sound/sampled/AudioSystem.java: New file.
+ * javax/sound/sampled/BooleanControl.java: New file.
+ * javax/sound/sampled/Clip.java: New file.
+ * javax/sound/sampled/CompoundControl.java: New file.
+ * javax/sound/sampled/Control.java: New file.
+ * javax/sound/sampled/DataLine.java: New file.
+ * javax/sound/sampled/EnumControl.java: New file.
+ * javax/sound/sampled/FloatControl.java: New file.
+ * javax/sound/sampled/LineEvent.java: New file.
+ * javax/sound/sampled/Line.java: New file.
+ * javax/sound/sampled/LineListener.java: New file.
+ * javax/sound/sampled/LineUnavailableException.java: New file.
+ * javax/sound/sampled/Mixer.java: New file.
+ * javax/sound/sampled/Port.java: New file.
+ * javax/sound/sampled/ReverbType.java: New file.
+ * javax/sound/sampled/SourceDataLine.java: New file.
+ * javax/sound/sampled/spi/AudioFileReader.java: New file.
+ * javax/sound/sampled/spi/AudioFileWriter.java: New file.
+ * javax/sound/sampled/spi/FormatConversionProvider.java: New file.
+ * javax/sound/sampled/spi/MixerProvider.java: New file.
+ * javax/sound/sampled/TargetDataLine.java: New file.
+ * javax/sound/sampled/UnsupportedAudioFileException.java: New file.
+
+2005-11-13 Wolfgang Baer <WBaer@gmx.de>
+
+ * javax/print/attribute/EnumSyntax.java:
+ API docs added and enhanced for class and methods.
+ (readResolve): New method.
+
+2005-11-13 Wolfgang Baer <WBaer@gmx.de>
+
+ * javax/print/attribute/Attribute.java,
+ javax/print/attribute/AttributeSet.java,
+ javax/print/attribute/DocAttribute.java,
+ javax/print/attribute/DocAttributeSet.java,
+ javax/print/attribute/PrintJobAttribute.java,
+ javax/print/attribute/PrintJobAttributeSet.java,
+ javax/print/attribute/PrintRequestAttribute.java,
+ javax/print/attribute/PrintRequestAttributeSet.java,
+ javax/print/attribute/PrintServiceAttribute.java,
+ javax/print/attribute/PrintServiceAttributeSet.java,
+ javax/print/attribute/SupportedValuesAttribute.java,
+ javax/print/attribute/UnmodifiableSetException.java:
+ Added api documentation to class and method definitions.
+ * javax/print/attribute/package.html: Included a package description.
+
+2005-11-13 Audrius Meskauskas <AudriusA@Bioinformatics.org>
+
+ * gnu/CORBA/Interceptor/gnuIorInfo.java (state): Made public.
+ * gnu/CORBA/Interceptor/gnuServerRequestInfo.java
+ (adapter_name, orb_id, server_id): New methods.
+ * org/omg/PortableInterceptor/IORInfoOperations.java
+ (state): New method.
+ * org/omg/PortableInterceptor/ServerRequestInfoOperations.java
+ (adapter_name, orb_id, server_id): New methods.
+
+2005-11-13 Audrius Meskauskas <AudriusA@Bioinformatics.org>
+
+ PR 24749
+ * javax/swing/plaf/basic/BasicTextUI.java (installDefaults):
+ Call setSelectionColor.
+
+2005-11-12 Wolfgang Baer <WBaer@gmx.de>
+
+ * java/io/ObjectInputStream.java
+ (processResolution): Pass Error, RuntimeException and
+ ObjectStreamException through to the caller.
+ (readObject): Documentation update.
+
+2005-11-11 Mark Wielaard <mark@klomp.org>
+ Anthony Green <green@redhat.com>
+
+ * java/util/Properties.java (load): Short-circuit parsing when key or
+ value doesn't contain escape character. Use StringBuilder instead of
+ StringBuffer.
+ (store): Use StringBuilder instead of StringBuffer.
+ (formatForOutput): Likewise.
+
+2005-11-11 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/plaf/basic/BasicSplitPaneUI.java
+ (getMinimumDividerLocation): Fixed to use the minimum size
+ of the correct component. Also, removed call to getAvailableSize,
+ this is not needed for the minimum location.
+
+2005-11-11 Archie Cobbs <archie@dellroad.org>
+
+ * autogen.sh: Fix broken libtool version detection on FreeBSD.
+
+2005-11-11 Lillian Angel <langel@redhat.com>
+
+ * java/awt/Container.java
+ (LightweightDispatcher.acquireComponentForMouseEvent): If the
+ event is not being dispatched, the pressCount should be reset.
+
+2005-11-11 Mark Wielaard <mark@klomp.org>
+
+ * javax/swing/text/FieldView.java (getPreferredSpan): Chain
+ BadLocationException when throwing assertion.
+
+2005-11-11 Mark Wielaard <mark@klomp.org>
+
+ Reported by john.zigman@anu.edu.au as bug #24608.
+ * gnu/java/nio/SocketChannelImpl.java (read): Put readBytes in
+ destination ByteBuffer when it doesn't have an array instead of len
+ bytes.
+
+2005-11-11 Audrius Meskauskas <AudriusA@Bioinformatics.org>
+
+ * org/omg/PortableInterceptor/IORInterceptor_3_0.java,
+ org/omg/PortableInterceptor/IORInterceptor_3_0Helper.java,
+ org/omg/PortableInterceptor/IORInterceptor_3_0Holder.java,
+ org/omg/PortableInterceptor/IORInterceptor_3_0Operations.java,
+ org/omg/PortableInterceptor/_IORInterceptor_3_0Stub.java: New files.
+ * gnu/CORBA/Interceptor/IORInterceptors.java,
+ gnu/CORBA/Interceptor/gnuIorInfo.java,
+ gnu/CORBA/OrbRestricted.java,
+ gnu/CORBA/Poa/AOM.java,
+ gnu/CORBA/Poa/ORB_1_4.java,
+ gnu/CORBA/Poa/gnuPOA.java,
+ gnu/CORBA/Poa/gnuPOAManager.java,
+ org/omg/PortableInterceptor/IORInfoOperations.java,
+ org/omg/PortableInterceptor/IORInterceptorOperations.java,
+ org/omg/PortableInterceptor/ORBInitInfoOperations.java,
+ org/omg/PortableInterceptor/ObjectReferenceFactoryOperations.java:
+ Rewritten to support the IORInterceptor_3_0.
+
+2005-11-10 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/plaf/metal/MetalRadioButtonUI.java
+ (paintFocus): Centered border around rectangle. It seemed
+ a bit offset and too small at times.
+
+2005-11-10 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicListUI.java
+ (valueChanged): Repaint list when selection changed.
+ (updateLayoutState): Reworked to correctly respect fixed cell sizes.
+ (installListeners): Create component listener before adding it.
+ (paint): Optimized to only draw the cells in the clip.
+
+2005-11-10 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/JComponent.java:
+ (processKeyEvent): Reworked this method to improve performance. Return
+ early if the event has already been handled. Don't stop climbing when
+ we hit a JInternalFrame, only stop at Applets or Windows (this fixes
+ PR 24781). Don't check WHEN_IN_FOCUSED_WINDOW bindings if there is no
+ top-level container present. If there is a top-level container, pass
+ it to KeyboardManager.processKeyStroke rather than the JComponent that
+ actually received the event, to save time in finding the top-level
+ container within KeyboardManager.
+ * javax/swing/KeyboardManager.java:
+ (findTopLevel): Changed parameter from JComponent to Component to allow
+ generality and to allow passing in of already-determined top-level
+ containers to save time.
+ (processKeyStroke): Likewise.
+
+2005-11-10 Mark Wielaard <mark@klomp.org>
+
+ Fixes bug #24731 reported by freebeans@xqb.biglobe.ne.jp.
+ * java/awt/ScrollPane.java (addNotify): Return immediately when peer
+ already set.
+
+2005-11-10 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicComboBoxUI.java
+ (installListeners): Also install focusListener on the listBox.
+ (uninstallListeners): Also uninstall focusListener from the listBox.
+ (setPopupVisible): Request focus on the listbox when making the
+ popup visible.
+
+2005-11-10 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/JComponent.java
+ (paintingTile): New field.
+ (isPaintingTile): Implemented.
+ (paintChildren): Optimized painting of overlapping children.
+
+2005-11-10 Mark Wielaard <mark@klomp.org>
+
+ Reported by Petteri <betelgeuse@gentoo.org> bug #24768 and bug #24769.
+ * configure.ac (dssi): Change accidental alsa reference to dssi.
+ * native/jni/midi-dssi/Makefile.am (libgjsmdssi_la_SOURCES): Add
+ dssi_data.h.
+
+2005-11-10 Audrius Meskauskas <AudriusA@Bioinformatics.org>
+
+ * gnu/CORBA/OrbFunctional.java (use_properties, set_parameters):
+ Rewritten to support orb and server ids.
+ * org/omg/CORBA/ORB.java,
+ org/omg/PortableInterceptor/ObjectReferenceTemplate.java:
+ Documentation update.
+
+2005-11-09 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/JComponent.java:
+ (addNotify): Unregister all WHEN_IN_FOCUSED_WINDOW bindings for this
+ JComponent and then register them with its (potentially) new top level
+ ancestor. Removed unncessary code that copied regular (WHEN_FOCUSED)
+ key bindings up the parent hierarchy.
+
+2005-11-09 Roman Kennke <kennke@aicas.com>
+
+ Reported by Friedjof Siebert <siebert@aicas.com>
+ * java/util/WeakHashMap.java
+ (WeakEntrySet.Iterator.checkMod): Improved exception message.
+ (internalRemove): Removed redundant reads of buckets[slot] and
+ prev.next and added checks to ensure that no null pointer
+ exception may occur and that this can be proved automatically.
+
+2005-11-09 Roman Kennke <kennke@aicas.com>
+
+ Reported by Friedjof Siebert <siebert@aicas.com>
+ * java/io/PrintWriter.java
+ (line_separator): Added default value for property to ensure
+ absence of null pointer exception even if property is not set.
+
+2005-11-09 Roman Kennke <kennke@aicas.com>
+
+ * java/io/InputStreamReader.java
+ (InputStreamReader(InputStream, CharsetDecoder)): Catch the case
+ when the CharsetDecoder returns a null charset and handle it like
+ US-ASCII.
+
+2005-11-09 Mark Wielaard <mark@klomp.org>
+
+ Reported by Petteri Räty <betelgeuse@gentoo.org>
+ * INSTALL: Remove double --enable-xmlj entry.
+
+2005-11-09 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/JComponent.java:
+ (processKeyEvent): Use local variables for boolean pressed and for
+ the KeyStroke. Implemented the code for WHEN_IN_FOCUSED_WINDOW
+ bindings.
+ (updateComponentInputMap): Implemented and fixed typo in docs.
+ * javax/swing/KeyboardManager.java: New class.
+
+2005-11-09 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/JTabbedPane.java
+ (setComponent): Tab should be inserted with a title, and removed from
+ the vector once set.
+ (removeTabAt): Tab should only be removed from vector.
+ remove(Component) is called to remove the tab from the JTabbedPane.
+ (remove): Added call to the component. This function should remove
+ the component as well as the tab.
+
+2005-11-09 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/JTabbedPane.java
+ (setComponent): No need to remove and add tab.
+ (remove): Fixed API documentation.
+ (remove): Fixed API documentation. Re-implemented according to API.
+
+2005-11-09 Mark Wielaard <mark@klomp.org>
+
+ * doc/www.gnu.org/cp-tools/cp-tools.wml: Add gjdoc download link.
+
+2005-11-09 Chris Burdess <dog@gnu.org>
+
+ * gnu/xml/aelfred2/SAXDriver.java: Ensure that absolutize does not
+ throw exception when custom entity resolver is set.
+
+2005-11-09 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * java/awt/event/InvocationEvent.java:
+ (exception): Replaced this field (removed yesterday) because it is
+ needed for serialization.
+ (dispatch): Save thrown exception.
+ (getException): Directly return exception, no need to cast throwable.
+
+2005-11-09 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/ComponentInputMap.java:
+ (put): Notify the component.
+ (clear): Likewise.
+ (remove): Likewise.
+ (setParent): Notify the parent. Improved the exception messages.
+ * javax/swing/JComponent.java:
+ (inputMap_whenInFocusedWindow): Changed type from InputMap to
+ ComponentInputMap.
+ (setInputMap): If we're setting the WHEN_IN_FOCUSED_WINDOW map and
+ the parameter is not a ComponentInputMap or is not associated with
+ the same Component, throw an IllegalArgumentException.
+ (getInputMap): Create a new ComponentInputMap instead of a new
+ InputMap when the WHEN_IN_FOCUSED_WINDOW map doesn't yet exist.
+ (udpateComponentInputMap): New method. This is the method that
+ ComponentInputMap calls when it is updated. Not yet completely
+ implemented.
+
+2005-11-09 Audrius Meskauskas <AudriusA@Bioinformatics.org>
+
+ * org/omg/PortableInterceptor/ObjectReferenceTemplateSeqHelper.java,
+ org/omg/PortableInterceptor/ObjectReferenceTemplateSeqHolder.java:
+ New files.
+
+2005-11-09 Audrius Meskauskas <AudriusA@Bioinformatics.org>
+
+ * org/omg/PortableInterceptor/ObjectReferenceTemplate.java,
+ org/omg/PortableInterceptor/ObjectReferenceTemplateHelper.java,
+ org/omg/PortableInterceptor/ObjectReferenceTemplateHolder.java:
+ New files.
+
+2005-11-09 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/JTabbedPane.java
+ (setComponent): Added check to prevent infinite loops.
+ * javax/swing/plaf/metal/MetalTabbedPaneUI.java
+ (createLayoutManager): Should call super here, so the layout
+ is set properly depending on the layout mode.
+
+2005-11-09 David Gilbert <david.gilbert@object-refinery.com>
+
+ * examples/gnu/classpath/examples/swing/Demo.java
+ (mkMenuBar): added file chooser item,
+ (mkButtonBar): split buttons into two rows, added 'FileChooser' button,
+ * examples/gnu/classpath/examples/swing/FileChooserDemo.java: New file.
+
+2005-11-09 Audrius Meskauskas <AudriusA@Bioinformatics.org>
+
+ * org/omg/PortableInterceptor/ObjectReferenceFactory.java: Do not
+ inherit from org.omg.CORBA.Object.
+
+2005-11-09 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/ComponentUI.java
+ (update): Restore the foreground color after filling the background.
+
+2005-11-09 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/JComponent.java
+ (paint): Fetch a new componentGraphics here instead of
+ paintComponent.
+ (paintComponent): Don't fetch the componentGraphics here. This
+ must be done in paint.
+
+2005-11-09 David Gilbert <david.gilbert@object-refinery.com>
+
+ * javax/swing/JList.java
+ (setModel): throw IllegalArgumentException for null model.
+
+2005-11-09 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicTextUI.java
+ (getVisibleEditorRect): Correctly calculate the inner rectangle.
+
+2005-11-09 Christian Thalinger <twisti@complang.tuwien.ac.at>
+
+ * native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkFontPeer.c
+ (initStaticState): Register global variable glyphVector_class
+ as global reference.
+
+2005-11-08 Audrius Meskauskas <AudriusA@Bioinformatics.org>
+
+ * javax/swing/text/DefaultCaret.java (BlinkTimerListener):
+ Added ignoreNextEvent flag and its handling.
+ (blinkListener): New field. (initBlinkTimer):
+ Initialise blinkListener field.
+ (setDot, moveDot): Call appear() instead of repaint().
+ (appear): new method.
+
+2005-11-08 Lillian Angel <langel@redhat.com>
+
+ * examples/gnu/classpath/examples/swing/GNULookAndFeel.java
+ (getDefaults): Added icons for checkboxes and radiobutton.
+ (CheckBoxIcon): New class, implemented.
+ (RadioButtonIcon): New class, implemented.
+
+2005-11-08 Tom Tromey <tromey@redhat.com>
+
+ * gnu/classpath/SystemProperties.java: Don't mention
+ gnu.java.awt.FocusManager.
+
+2005-11-08 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/text/CompositeView.java
+ (modelToView): Adjust the allocation to the child allocation before
+ forwarding to the child's modelToView. Replaced AssertionError by
+ BadLocationException, because that is the right thing to do here.
+
+2005-11-08 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicInternalFrameUI.java
+ (GlassPaneDispatcher.acquireComponentForMouseEvent): Use the
+ frame's layeredPane as parent instead of the content pane
+ when searching for the event target. This way a possibly set menubar
+ is also included in the search.
+
+2005-11-08 Lillian Angel <langel@redhat.com>
+
+ * java/awt/Window.java
+ (setLocationRelativeTo): Changed x and y to use getLocationOnScreen
+ and moved setLocation call outside of check.
+ * javax/swing/JOptionPane.java
+ (createDialog): Moved pack call and setLocationRelativeTo call here
+ and removed these calls from all other functions that call
+ createDialog. Also, removed FIXME, since call to setLocationRelativeTo
+ fixes this.
+ (showConfirmDialog): Removed pack and setLocationRelativeTo calls.
+ (showConfirmDialog): Likewise.
+ (showConfirmDialog): Likewise.
+ (showConfirmDialog): Likewise.
+ (showInputDialog): Likewise.
+ (showInputDialog): Likewise.
+ (showInputDialog): Likewise.
+ (showInputDialog): Likewise.
+ (showInputDialog): Likewise.
+ (showInputDialog): Likewise.
+ (showMessageDialog): Likewise.
+ (showMessageDialog): Likewise.
+ (showOptionDialog): Likewise.
+ * javax/swing/JTree.java
+ (JTree): Should not use a shared instance of the selection model. It
+ is a problem when one application has two different trees.
+ * javax/swing/plaf/basic/BasicTreeUI.java
+ (paintRow): Changed parameter to be the focus of the tree.
+ (updateCurrentVisiblePath): Adjusted root path incase the root is hidden.
+
+2005-11-08 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * java/awt/event/InvocationEvent.java:
+ (exception): Removed unnecessary field.
+ (dispatch): Removed reference to field exception.
+ (getException): If throwable is an Exception, return a casted version,
+ otherwise return null.
+ (getThrowable): Improved docs.
+
+2005-11-08 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/SwingUtilities.java:
+ (replaceUIActionMap): Stop climbing hierarchy once we've found an
+ ActionMapUIResource, don't keep looking until parent is null. No need
+ to check if child is null.
+ (replaceUIInputMap): Use a local variable for the parent rather than
+ 3 calls to get parent. No need to check if child is null.
+ * javax/swing/plaf/basic/BasicListUI.java:
+ * javax/swing/plaf/basic/BasicTableUI.java:
+ * javax/swing/plaf/basic/BasicTreeUI.java:
+ (installKeyboardActions): UI ActionMap should be of type
+ ActionMapUIResource, not just ActionMap.
+
+2005-11-08 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/text/DefaultStyledDocument.java:
+ (ElementBuffer.clone): New API method.
+
+2005-11-08 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * java/lang/String.java:
+ (replace): Use a StringBuilder instead of a StringBuffer because this
+ is faster and we don't need thread-safety.
+
+2005-11-08 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicTextUI.java
+ (installDefaults): Initialize background field correctly.
+
+2005-11-08 Roman Kennke <kennke@aicas.com>
+
+ * java/awt/BorderLayout.java
+ (getAlignmentX): Return 0.5F here.
+ (getAlignmentY): Return 0.5F here.
+
+2005-11-08 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/JRootPane.java
+ (RootLayout.glassPaneBounds): New field.
+ (RootLayout.layeredPaneBounds): New field.
+ (RootLayout.contentPaneBounds): New field.
+ (RootLayout.menuBarBounds): New field.
+ (RootLayout.prefSize): New field.
+ (getLayoutAlignmentX): Return 0.0F here.
+ (getLayoutAlignmentY): Return 0.0F here.
+ (invalidateLayout): Throw away cached layout information.
+ (layoutContainer): Simplified and fixed the layout. Use cache if
+ possible.
+ (preferredLayoutSize): Simplified and fixed the layout. Use cache if
+ possible.
+
+2005-11-08 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/JComponent.java
+ (alignmentX): Changed default value to -1.0.
+ (alignmentY): Changed default value to -1.0.
+ (getAlignmentX): If no value has been set, refer to the superclass
+ behaviour.
+ (getAlignmentY): If no value has been set, refer to the superclass
+ behaviour.
+ (setAlignmentX): Catch invalid values and adjust them to the nearest
+ valid value.
+ (setAlignmentY): Catch invalid values and adjust them to the nearest
+ valid value.
+
+2005-11-08 Roman Kennke <kennke@aicas.com>
+
+ * java/awt/Container.java
+ (getAlignmentX): Refer to the layout managers layoutAlignmentX
+ property if layout manager is a LayoutManager2.
+ (getAlignmentY): Refer to the layout managers layoutAlignmentY
+ property if layout manager is a LayoutManager2.
+
+2005-11-08 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/JLayeredPane.java
+ (layerToRange): Return empty array for unknown layer instead of
+ throwing an exception.
+
+2005-11-08 Roman Kennke <kennke@aicas.com>
+
+ * java/awt/Component.java
+ (invalidate): Don't invalidate invalid parents.
+
+2005-11-08 Audrius Meskauskas <AudriusA@Bioinformatics.org>
+
+ * javax/swing/JComponent.java (setMaximumSize,
+ setMinimumSize, setPreferredSize): Clone the passed parameter.
+
+2005-11-07 Roman Kennke <kennke@aicas.com>
+
+ * java/awt/Component.java
+ (invalidate): Invalidate up the whole tree, regardless if some
+ parent is already marked invalid. This is needed in some situations
+ for layout managers to throw away their cache.
+
+2005-11-07 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/JTable.java
+ (tableChanged): Cleared selection if there are no more rows. Prevents a
+ NPE.
+ * javax/swing/JTree.java
+ (scrollRectToVisible): No need to set the selection path here.
+ (expandPath): Sometimes it is required to set the state of a leaf,
+ especially if the leaf is the root node.
+ * javax/swing/plaf/basic/BasicTreeUI.java
+ (getRowCount): Added call to updateCurrentVisiblePath, so the
+ correct value is always returned.
+ (paint): No need to paint if the visible path is null.
+ (propertyChange): Implemented.
+ (paintRecursive): Added check for visibility of child. If it is
+ not visible because it was explicitly set to be hidden, no lines
+ should be drawn.
+ (paintControlIcons): Likewise.
+ (getPreviousNode): Fixed check to include root.
+ (paintRow): Set focus to be true (this will change in the future).
+ (updateCurrentVisiblePath): Fixed check to call getNextNode if
+ the current node is a leaf (more efficent than calling getNextSibling).
+ * javax/swing/tree/DefaultTreeCellRenderer.java
+ (getTreeCellRendererComponent): Changed to draw border if node has focus.
+
+2005-11-07 Ito Kazumitsu <kaz@maczuka.gcd.org>
+
+ Fixes bug #24467
+ * native/jni/java-nio/gnu_java_nio_charset_iconv_IconvDecoder.c
+ (Java_gnu_java_nio_charset_iconv_IconvDecoder_decode):
+ Do not check errno == EINVAL, which is a normal case.
+
+2005-11-07 Ito Kazumitsu <kaz@maczuka.gcd.org>
+
+ Fixes bug #22968
+ * gnu/java/nio/charset/iconv/IconvProvider.java
+ (IconvProvider): Declare the constructor public.
+
+2005-11-07 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/JApplet.java
+ (initStageDone): Removed unnecessary field.
+ (JApplet): Use rootPaneCheckingEnabled property instead of
+ initStageDone field.
+ (setLayout): Likewise.
+ (addImpl): Likewise.
+ * javax/swing/JDialog.java
+ (initStageDone): Removed unnecessary field.
+ (dialogInit): Use rootPaneCheckingEnabled property instead of
+ initStageDone field.
+ (setLayout): Likewise.
+ (addImpl): Likewise.
+ * javax/swing/JFrame.java
+ (initStageDone): Removed unnecessary field.
+ (frameInit): Use rootPaneCheckingEnabled property instead of
+ initStageDone field.
+ (setLayout): Likewise.
+ (addImpl): Likewise.
+ * javax/swing/JWindow.java
+ (initStageDone): Removed unnecessary field.
+ (windowInit): Use rootPaneCheckingEnabled property instead of
+ initStageDone field.
+ (setLayout): Likewise.
+ (addImpl): Likewise.
+ * javax/swing/JInternalFrame.java
+ (initStageDone): Removed unnecessary field.
+ (JInternalFrame): Use rootPaneCheckingEnabled property instead of
+ initStageDone field.
+ (setLayout): Likewise.
+ (addImpl): Likewise.
+ (paramString): Return superclass paramstring.
+ (reshape): Call revalidate() instead of invalidate() and doLayout().
+ (setUI): Temporarily go into init mode, so that the UI can
+ manipulate the frame directly.
+ (updateUI): Likewise.
+
+2005-11-07 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * java/lang/String.java:
+ (replace): Use a StringBuffer instead of String. Only search for new
+ occurrences of the target that occur AFTER the text just inserted, so
+ if the replacement string contains the target string we won't go into
+ an infinite loop. Use local variables instead of repeated calls to
+ length() and toString().
+
+2005-11-07 Christian Thalinger <twisti@complang.tuwien.ac.at>
+
+ * native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkClipboard.c:
+ Use long for 64-bit architectures.
+
+2005-11-07 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * java/util/Arrays.java:
+ (toString(long[])): New API method.
+ (toString(int[])): Likewise.
+ (toString(short[])): Likewise.
+ (toString(char[])): Likewise.
+ (toString(byte[])): Likewise.
+ (toString(boolean[])): Likewise.
+ (toString(float[])): Likewise.
+ (toString(double[])): Likewise.
+ (toString(Object[])): Likewise.
+
+2005-11-07 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * java/awt/event/InvocationEvent.java:
+ (throwable): New field.
+ (getThrowable): New API method.
+ (dispatch()): Catch Throwable, not Exception. Save the Throwable. If
+ it is an Exception, save the Exception.
+
+2005-11-07 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/Popup.java
+ (show): Set layout for panel. Otherwise, contents are
+ displayed at an arbitrary location.
+ * javax/swing/plaf/basic/BasicMenuItemUI.java
+ (getPreferredMenuItemSize): Took into account insets.
+ * javax/swing/plaf/metal/MetalButtonUI.java
+ (paintFocus): Don't paint focus if not enabled.
+
+2005-11-07 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * java/lang/String.java:
+ (contains): New API method.
+ (replace): New API method.
+
+2005-11-07 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * java/lang/Boolean.java:
+ (compareTo(Boolean)): New API method.
+
+2005-11-07 David Gilbert <david.gilbert@object-refinery.com>
+
+ * javax/swing/plaf/basic/BasicComboBoxUI.java
+ (installComponents): update local reference to editor component always,
+ (getDisplaySize): implement new calculation for editable combo boxes,
+ * javax/swing/plaf/metal/MetalComboBoxEditor.java
+ (editorBorderInsets): initialise with correct value,
+ * javax/swing/plaf/metal/MetalComboBoxUI.java
+ (getMinimumSize): implemented different calculation for editable combo
+ boxes.
+
+2005-11-07 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/JOptionPane.java
+ (showConfirmDialog): Added call to set the location of the
+ dialog relative to its parent.
+ (showConfirmDialog): Likewise.
+ (showConfirmDialog): Likewise.
+ (showConfirmDialog): Likewise.
+ (showInputDialog): Likewise.
+ (showInputDialog): Likewise.
+ (showInputDialog): Likewise.
+ (showInputDialog): Likewise.
+ (showMessageDialog): Likewise.
+ (showMessageDialog): Likewise.
+ (showMessageDialog): Likewise.
+ (showOptionDialog): Likewise.
+
+2005-11-07 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/plaf/basic/BasicMenuItemUI.java
+ (getPreferredMenuItemSize): Adjusted width of menu item with
+ arrow icon. If the menu item can fit in the current width of
+ the top level menu, then the width of the menu item is set to
+ the width of the popup menu. Otherwise, the width of the
+ menu item is adjusted so that the width of the popup menu
+ is increased.
+
+2005-11-07 Mark Wielaard <mark@klomp.org>
+
+ * configure.ac: Don't check or replace FREETYPE2.
+ * native/jni/gtk-peer/Makefile.am: Remove FREETYPE2_LIBS and
+ FREETYPE2_CFLAGS.
+
+2005-11-07 David Gilbert <david.gilbert@object-refinery.com>
+
+ * javax/swing/plaf/metal/MetalComboBoxEditor.java
+ (MetalComboBoxEditor): don't create new editor.
+
+2005-11-07 David Gilbert <david.gilbert@object-refinery.com>
+
+ * javax/swing/plaf/basic/BasicComboBoxEditor.java: API docs plus
+ (BasicComboBoxEditor): set border to null and columns to 9,
+ (addActionListener): implemented,
+ (removeActionListener): implemented.
+
+2005-11-07 Audrius Meskauskas <AudriusA@Bioinformatics.org>
+
+ * gnu/CORBA/IOR.java (equals, hasCode): Compare port number as well
+ and do not crash on IOR.Internet==null.
+
+2005-11-06 Mark Wielaard <mark@klomp.org>
+
+ * javax/swing/Timer.java (Waker.run): Test and set running while
+ holding queueLock.
+ (start): Set running to true.
+ (stop): Unconditionally notify queueLock.
+ (queueEvent): Only called when queueLock already held.
+
+2005-11-06 Andreas Tobler <a.tobler@schweiz.ch>
+
+ * native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkGraphics2D.c
+ (Java_gnu_java_awt_peer_gtk_GdkGraphics2D_setGradientUnlocked): Update
+ debug output to reflect actual situation.
+ (Java_gnu_java_awt_peer_gtk_GdkGraphics2D_setTexturePixelsUnlocked):
+ Likewise.
+ (Java_gnu_java_awt_peer_gtk_GdkGraphics2D_drawPixels): Adjust
+ formatting.
+ (Java_gnu_java_awt_peer_gtk_GdkGraphics2D_cairoSetMatrixUnlocked):
+ Update debug output to reflect actual situation.
+ (Java_gnu_java_awt_peer_gtk_GdkGraphics2D_cairoSetRGBAColorUnlocked):
+ Likewise.
+ (Java_gnu_java_awt_peer_gtk_GdkGraphics2D_cairoCurveTo): Adjust
+ formatting.
+ (Java_gnu_java_awt_peer_gtk_GdkGraphics2D_cairoRelCurveTo): Likewise.
+ (Java_gnu_java_awt_peer_gtk_GdkGraphics2D_cairoRectangle): Likewise.
+ (Java_gnu_java_awt_peer_gtk_GdkGraphics2D_cairoSurfaceSetFilterUnlocked):
+ Update debug output to reflect actual situation.
+
+2005-11-06 Mark Wielaard <mark@klomp.org>
+
+ * java/awt/image/AreaAveragingScaleFilter.java: Add FIXME
+ * java/awt/Image.java (getScaledInstance): In case of
+ SCALE_AREA_AVERAGING use AreaAveragingScaleFilter.
+
+2005-11-06 Wolfgang Baer <WBaer@gmx.de>
+
+ * javax/print/event/PrintEvent.java,
+ * javax/print/event/PrintJobAdapter.java,
+ * javax/print/event/PrintJobAttributeEvent.java,
+ * javax/print/event/PrintJobAttributeListener.java,
+ * javax/print/event/PrintJobEvent.java,
+ * javax/print/event/PrintJobListener.java,
+ * javax/print/event/PrintServiceAttributeEvent.java,
+ * javax/print/event/PrintServiceAttributeListener.java,
+ * javax/print/event/package.html: Added API docs all over.
+
+2005-11-06 Wolfgang Baer <WBaer@gmx.de>
+
+ * java/io/File.java
+ (getParent): If pathname is "" return null.
+ (toURI): Also append separatorChar if path equals "".
+ (getAbsolutePath): If path equals "" only return the value
+ of the user.dir system property.
+
+2005-11-06 Chris Burdess <dog@gnu.org>
+
+ * gnu/xml/stream/XMLStreamWriterImpl.java: Ensure that generated
+ prefixes do not accidentally clash, and provide documentation for
+ new virtual methods. createPrefix (new method) signature changed to
+ provide namespace URI for the benefit of subclasses.
+
+2005-11-06 Chris Burdess <dog@gnu.org>
+
+ * gnu/xml/transform/StreamSerializer.java: Avoid undeclared apos
+ entity when output mode is HTML.
+
+2005-11-06 Audrius Meskauskas <AudriusA@Bioinformatics.org>
+
+ * gnu/CORBA/IOR.java (equals, hashCode): New metods.
+ * gnu/CORBA/SimpleDelegate.java (is_equivalent): Compare IORs when applicable.
+
+2005-11-06 Audrius Meskauskas <AudriusA@Bioinformatics.org>
+
+ * gnu/CORBA/Minor.java (IOR_missing): New minor code.
+ * gnu/CORBA/NamingService/NameParser.java (corbaloc): Implemented
+ file//, ftp:// and http:// support.
+ * gnu/javax/rmi/CORBA/UtilDelegateImpl.java (mapSystemException):
+ Set the cause directly.
+ * org/omg/CORBA/DATA_CONVERSION.java,
+ org/omg/CORBA/ORB.java (string_to_object): Documentation update.
+
+2005-11-06 Chris Burdess <dog@gnu.org>
+
+ * gnu/xml/stream/XMLStreamWriterImpl.java: Fixed handling of
+ namespaces when isPrefixDefaulting is set.
+
+2005-11-04 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/text/DefaultStyledDocument.java: Reformatted.
+
+2005-11-04 Lillian Angel <langel@redhat.com>
+
+ * java/awt/Window.java
+ (setLocationRelativeTo): Implemented case when
+ component is not null.
+
+2005-11-04 Tom Tromey <tromey@redhat.com>
+
+ * java/awt/image/BufferedImage.java (BufferedImage): Implement
+ Transparency.
+ (getTransparency): New method.
+
+2005-11-04 Audrius Meskauskas <AudriusA@Bioinformatics.org>
+
+ * gnu/CORBA/SocketRepository.java (sockets): Changed type to
+ HashMap. (put_socket, get_socket, gc):
+ Always synchronize on 'sockets'.
+
+2005-11-04 Mark Wielaard <mark@klomp.org>
+
+ * configure.ac: Set version to 0.20-pre.
+
+2005-11-04 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/text/StyleConstants.java:
+ (Family): New API field.
+ (Size): New API field.
+
+2005-11-04 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/plaf/basic/BasicMenuItemUI.java
+ (paintMenuItem): Changed to use isTopLevelMenu rather than checking
+ instance of parent.
+ * javax/swing/plaf/basic/BasicPopupMenuUI.java
+ (popupMenuWillBecomeInvisible): Added check to prevent NPE.
+ * javax/swing/Popup.java:
+ Added new private field.
+ (LightweightPopup): Initialized layeredPane.
+ (show): Removed unneeded code.
+ (hide): Likewise.
+
+2005-11-04 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/table/DefaultTableCellRenderer.java
+ (updateUI): Set the background and foreground color fields to null
+ here so that installing the LabelUI does not interfere with our
+ custom set colors.
+ (getTableCellRendererComponent): Only set UI focus colors when
+ cell is actually editable. Added optimization for the case
+ when background is equal to table background.
+
+2005-11-04 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/table/DefaultTableCellRenderer.java
+ (getTableCellRendererComponent): Call super.setBackground() or
+ super.setForeground() to avoid overriding custom set background or
+ foreground colors. Set the UI focus colors when focused.
+
+2005-11-04 Roman Kennke <kennke@aicas.com>
+
+ * examples/gnu/classpath/examples/swing/TextFieldDemo.java: New file.
+ Demonstrates the JTextFields in various states.
+ * examples/gnu/classpath/examples/swing/Demo.java: Replaced the
+ old textfield demo with the new one.
+
+2005-11-04 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicTextUI.java
+ (getMinimumSize): New method.
+ * javax/swing/text/FieldView.java
+ (getPreferredSpan): Added assert that replaces a 'should never happen'
+ comment.
+
+2005-11-04 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/SizeRequirements.java
+ (getTiledSizeRequirements): Added check for overflows.
+ (adjustGreater): Fixed overflow handling through usage of long
+ instead of int.
+
+2005-11-03 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/text/DefaultCaret.java
+ (positionCaret): Call setDot instead of moveDot.
+ * javax/swing/text/PlainView.java
+ (viewToModel): Exclude the final newline character from calculation.
+
+2005-11-03 Mark Wielaard <mark@klomp.org>
+
+ * doc/www.gnu.org/announce/20051102.wml: New file.
+ * doc/www.gnu.org/newsitems.txt: Add 0.19 release announcement.
+ * doc/www.gnu.org/downloads/downloads.wml: Add 0.19.
+
+2005-11-03 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/table/DefaultTableCellRenderer.java
+ (background): New field.
+ (foreground): New field.
+ (setBackground): Store the color that is set here.
+ (setForeground): Store the color that is set here.
+ (getTableCellRendererComponent): For the unselected color, set the
+ value of the foreground or background fields if not null, otherwise
+ the value of the according table properties. Don't change
+ the color in the focused clause.
+
+2005-11-03 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/plaf/basic/BasicTreeUI.java
+ (mousePressed): If the control icon is clicked, the
+ path selected should not be changed.
+ (paintRecursively): Moved call to getChildCount before
+ loop.
+ (paintRow): Added a check to prevent NPE.
+ (updateCurrentVisiblePath): Made this slightly more efficent.
+ Instead of checking each path, we can check the siblings if the
+ current node is not expanded.
+ * javax/swing/table/DefaultTableCellRenderer.java
+ (getTableCellRendererComponent): Fixed indentation, and changed
+ to set the background color if it is not an instance of
+ ColorUIResource. Prevents overriding a user-set color.
+
+2005-11-03 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/text/WrappedPlainView.java: Fixed some > 80 chars lines.
+ (drawSelectedText): Fixed startOffset for call to
+ Utilities.drawTabbedText to make sure tabs are properly expanded.
+ (drawUnselectedText): Likewise.
+ (getMinimumSpan): New API method.
+ (getMaximumSpan): New API method.
+ (setSize): Call preferenceChanged if the width has changed.
+ (WrappedLine.determineNumLines): Move numLines=0 to the top in case
+ the early return happens, numLines will still be correct.
+ (WrappedLine.updateDamage): New implementation method called by
+ insertUpdate and removeUpdate to repaint the appropriate part of the
+ JTextArea.
+ (WrappedLine.insertUpdate): New method.
+ (WrappedLine.removeUpdate): New method.
+
+2005-11-03 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/table/DefaultTableCellRenderer.java
+ (getTableCellRendererComponent): Fixed so that the label is
+ painted with the correct background color. Does not depend on
+ type of border. Removed this code.
+
+2005-11-03 Anthony Balkissoon <abalkiss@redhat.com>
+
+ * javax/swing/text/JTextComponent.java:
+ (select): The end index cannot be smaller than the start index, changed
+ Math.max(end, 0) to Math.max(end, start).
+ * javax/swing/text/WrappedPlainView.java:
+ (selectionStart): New package private field.
+ (selectionEnd): Likewise.
+ (drawLine): Implemented to call drawUnselectedText and drawSelectedText
+ on the appropriate parts of the line. Before it just drew the whole
+ line with drawUnselectedText.
+ (paint): Store the start and end of the selection.
+ (WrappedLine.paint): Set the selected color to Color.WHITE.
+
+2005-11-03 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/table/DefaultTableCellRenderer.java
+ (getTableCellRendererComponent): Should only draw focus if the border
+ is not an empty border.
+
+2005-11-03 Audrius Meskauskas <AudriusA@Bioinformatics.org>
+
+ PR swing/24650
+ * javax/swing/text/PlainView.java (viewToModel)):
+ The end of line symbol (0xA), if being the last member in the
+ obtained text, should not be counted.
+
+2005-11-03 Lillian Angel <langel@redhat.com>
+
+ * javax/swing/plaf/basic/BasicMenuItemUI.java:
+ Changed field to be the gap between the different
+ menu's instead. defaultTextArrowGap is not needed.
+ (getPreferredMenuItemSize): Adjusted preferred size of
+ Menu Item with an arrowIcon to be the size of the
+ popupMenu. If its parent is not a popupMenu, then
+ it is a new Menu on a MenuBar.
+ * javax/swing/plaf/metal/MetalButtonUI.java
+ (paintFocus): Height of focus border should not be
+ adjusted. It was being cutoff.
+
+2005-11-03 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/plaf/basic/BasicTextUI.java
+ (RootView.getNextVisualPositionFrom): New method.
+
+2005-11-03 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/text/DefaultStyledDocument.java
+ (AttributeUndoableEdit): New inner class.
+ (StyleChangeListener): New inner class.
+ (styleChangeListener): New field.
+ (addStyle): Add styleChangeListener to new style.
+ (getStyleNames): New method.
+ (styleChanged): New method.
+ (insert): New method.
+ (create): New method.
+
+2005-11-03 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/text/DefaultTextUI.java: New file.
+
+2005-11-03 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/text/DefaultCaret.java
+ (mouseDragged): Call moveCaret.
+ (mouseClicked): Made TODO comment more precise.
+ (mouseExited): Replaced TODO comment with Nothing to do comment.
+ (mousePressed): Call positionCaret.
+ (moveCaret): Implemented.
+ (positionCaret): Implemented.
+ (moveDot): Call adjustVisibility.
+ (setDot): Call adjustVisibility.
+ (adjustVisibility): New method.
+
+2005-11-03 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/text/Utilities.java
+ (getPositionAbove): New utility method.
+ (getPositionBelow): New utility method.
+ (getParagraphElement): Special case for StyledDocuments.
+ * javax/swing/text/View.java
+ (getNextVisualPositionFrom): New abstract method.
+ * javax/swing/text/ComponentView.java
+ (getNextVisualPositionFrom): New method.
+ * javax/swing/text/CompositeView.java
+ (getNextVisualPositionFrom): New method.
+ * javax/swing/text/FlowView.java
+ (LogicalView.getNextVisualPositionFrom): New method.
+ * javax/swing/text/GlyphView.java
+ (getNextVisualPositionFrom): New method.
+ * javax/swing/text/IconView.java
+ (getNextVisualPositionFrom): New method.
+ * javax/swing/text/PlainView.java
+ (getNextVisualPositionFrom): New method.
+ * javax/swing/text/WrappedPlainView.java
+ (WrappedLine.getNextVisualPositionFrom): New method.
+
+2005-11-03 Roman Kennke <kennke@aicas.com>
+
+ * javax/swing/text/DefaultCaret.java
+ (BlinkTimerListener): New inner class. Listens for when the
+ blink timer fires and updates the visible flag accordingly.
+ (visible): Default value for visible should be false.
+ (blinkTimer): New field.
+ (Caret): New constructor.
+ (focusGained): Make the caret visible.
+ (focusLost): Make caret invisible if the focus lost is permanent.
+ (deinstall): Deinstall the blink timer.
+ (repaint): Call getComponent() instead of directly accessing the
+ textComponent field.
+ (paint): Call getComponent() instead of directly accessing the
+ textComponent field. Added an assert for the 'this should never
+ happen' comment. Update the caret rectangle if damage hasn't been
+ called before.
+ (setBlinkRate): Set the blink rate in the timer if there is already
+ a timer present.
+ (setVisible): Call damage on the caret's location. Start/Stop blink
+ timer.
+ (damage): New method. Updates the caret's bounds.
+ * javax/swing/text/JTextComponent.java
+ (CaretBlinkTimer): Removed unneeded inner class.
+ (caretBlinkTimer): Removed unneeded field.
+ (JTextComponent): Removed initialization of blink timer.
+ (setEditable): Removed starting of blink timer.
+ (setCaret): Likewise.
+ * javax/swing/text/Utilities.java
+ (getParagraphElement): New utility method.
+
2005-11-02 Mark Wielaard <mark@klomp.org>
* gnu/java/awt/peer/gtk/GdkGraphics.java (initComponentGraphics): Set
diff --git a/INSTALL b/INSTALL
index c6ce1d1bc..7da236669 100644
--- a/INSTALL
+++ b/INSTALL
@@ -127,8 +127,7 @@ gives a complete list.
--enable-Werror whether to compile C code with -Werror which turns
any compiler warning into a compilation failure
default=no
- --enable-xmlj compile native libxml/xslt library default=no
- --with-gjdoc generate documentation using gjdoc default=no
+ --with-gjdoc generate documentation using gjdoc default=no
--with-jay Regenerate the parsers with jay must be given the
path to the jay executable
diff --git a/NEWS b/NEWS
index 5a15a09fa..778369385 100644
--- a/NEWS
+++ b/NEWS
@@ -1,3 +1,10 @@
+New in release 0.20
+
+Runtime interface changes:
+
+* New method VMStackWalker.getClassLoader() was added to avoid an infinite
+ loop between getCallingClassLoader() and Class.getClassLoader().
+
New in release 0.19 (Nov 2, 2005)
* The Swing RepaintManager has been reworked for more efficient painting,
diff --git a/autogen.sh b/autogen.sh
index e20cc3869..babfa4e5d 100755
--- a/autogen.sh
+++ b/autogen.sh
@@ -16,7 +16,7 @@ LIBTOOLIZE=libtoolize
have_libtool=false
if ${LIBTOOLIZE} --version < /dev/null > /dev/null 2>&1 ; then
- libtool_version=`${LIBTOOLIZE} --version | sed 's/^[^0-9]*\([0-9.][0-9.]*\).*/\1/'`
+ libtool_version=`${LIBTOOLIZE} --version | sed 's/^.*[^0-9.]\([0-9]\{1,\}\.[0-9.]\{1,\}\).*/\1/'`
case $libtool_version in
1.5*)
have_libtool=true
diff --git a/configure.ac b/configure.ac
index 2e6778a08..ce9449a25 100644
--- a/configure.ac
+++ b/configure.ac
@@ -6,7 +6,7 @@ dnl -----------------------------------------------------------
dnl define([AC_CACHE_LOAD], )dnl
dnl define([AC_CACHE_SAVE], )dnl
-AC_INIT([GNU Classpath],[0.19-generics],[classpath@gnu.org],[classpath])
+AC_INIT([GNU Classpath],[0.20-generics-pre],[classpath@gnu.org],[classpath])
AC_CONFIG_SRCDIR(java/lang/System.java)
AC_CANONICAL_TARGET
@@ -118,7 +118,7 @@ AM_CONDITIONAL(CREATE_ALSA_LIBRARIES, test "x${COMPILE_ALSA}" = xyes)
dnl -----------------------------------------------------------
dnl DSSI code (enabled by default)
dnl -----------------------------------------------------------
-AC_ARG_ENABLE([alsa],
+AC_ARG_ENABLE([dssi],
[AS_HELP_STRING(--disable-dssi,compile DSSI providers (enable by --enable-dssi) [default=yes])],
[case "${enableval}" in
yes) COMPILE_DSSI=yes ;;
@@ -353,7 +353,6 @@ if test "x${COMPILE_JNI}" = xyes; then
fi
PKG_CHECK_MODULES(PANGOFT2, pangoft2)
- PKG_CHECK_MODULES(FREETYPE2, freetype2)
AC_SUBST(GTK_CFLAGS)
AC_SUBST(GTK_LIBS)
@@ -361,8 +360,6 @@ if test "x${COMPILE_JNI}" = xyes; then
AC_SUBST(CAIRO_CFLAGS)
AC_SUBST(PANGOFT2_LIBS)
AC_SUBST(PANGOFT2_CFLAGS)
- AC_SUBST(FREETYPE2_LIBS)
- AC_SUBST(FREETYPE2_CFLAGS)
fi
dnl Check for AWT related Qt4
diff --git a/doc/www.gnu.org/announce/20051102.wml b/doc/www.gnu.org/announce/20051102.wml
new file mode 100644
index 000000000..e39a4eaa5
--- /dev/null
+++ b/doc/www.gnu.org/announce/20051102.wml
@@ -0,0 +1,247 @@
+#!wml --include=..
+
+#use wml::std::page
+#use wml::std::lang
+#use wml::fmt::isolatin
+#use wml::std::case global=upper
+
+<lang:star:slice:>
+
+<set-var last-modified-author="mjw">
+
+#include <include/macros.wml>
+
+<header title="GNU Classpath 0.19 Announcement (2005-11-02)">
+<pre>
+GNU Classpath "95% and counting" 0.19 released
+
+GNU Classpath, essential libraries for java, is a project to create
+free core class libraries for use with runtimes, compilers and tools
+for the java programming language.
+
+The GNU Classpath developer snapshot releases are not directly aimed
+at the end user but are meant to be integrated into larger development
+platforms. For example the GCC (gcj) and Kaffe projects will use the
+developer snapshots as a base for future versions.
+
+Some highlights of changes in this release (more extensive list below):
+
+ Much more efficient painting for large Free Swing GUIs. Improved
+ accessibility support. HttpURLConnection rewrite. Official CORBA
+ VMCID assigned. Start of RMI over IIOP support. Qt4 support for
+ OS-X. Much improved Free Swing Metal theme. Free Swing Demo includes
+ theme switcher example (Metal, Ocean, GNU). JBoss now starts up and
+ Jonas testsuite passes for 95%. Support for the javax.sound.midi
+ framework and experimental DSSI and ALSA service providers. Early
+ version of the popular StAX API. Now has 96% coverage of 1.4 API.
+
+This is the first time we also have a pre-release of our 1.5 generics
+work. classpath-0.19-generics contains a version of the core library
+that uses the new 1.5 language features such as generics and
+enumerations. ECJ and JamVM are known to support the generics release
+out of the box. And you should be able to run Eclipse 3.1 with it to
+develop programs that use the new 1.5 language and core library
+additions. classpath-generics is a work in progress and not as
+extensively tested as our regular releases. But please try it out if
+you want to help us test the new 1.5 support of the core libraries.
+
+For this release we setup a Free Swing Test Application page
+http://developer.classpath.org/mediation/FreeSwingTestApps
+Please see that page for showcases of applications that work with this
+release and to help test other applications.
+
+It is also the first release that has GNU Classpath promotion banners.
+http://developer.classpath.org/mediation/ClasspathBanners
+Please feel free to add them to your project pages if your project is
+known to work with GNU Classpath or just to promote the project.
+
+32 people actively contributed to this release and made
+787 CVS commits during the last two months of development
+(excluding the generics branch work). diffstat since 0.18:
+ 1158 files changed, 93916 insertions(+), 36407 deletions(-)
+
+More details about the various changes and contributions below.
+
+A full list of bug reports fixed for this release can be found at:
+http://gcc.gnu.org/bugzilla/buglist.cgi?product=classpath&target_milestone=0.19
+
+This release depends on gtk+ 2.4 for AWT support. But gtk+ 2.6 or
+higher is recommended. Included, but not activated by default in this
+release is a Graphics2D implementation based on the Cairo Graphics
+framework (http://www.cairographics.org). Enabling this makes programs
+like JFreeChart and JEdit start up on GNU Classpath based runtimes.
+To enable this support install the cairo 0.5.x snapshot, configure GNU
+Classpath with --enable-gtk-cairo.
+
+One of the major focuses of the GNU Classpath project is expanding and
+using the Mauve test suite for Compatibility, Completeness and
+Correctness checking. Various groups around GNU Classpath collaborate
+on the free software Mauve test suite which contains around 34.000
+core library tests. Mauve has various modules for testing core class
+library implementations, byte code verifiers, source to byte code and
+native code compiler tests. Mauve also contains the Wonka visual test
+suite and the Jacks Compiler Killer Suite.
+See for more information: http://www.sourceware.org/mauve/
+This release passes 33.381 out of 34.262 Mauve core library tests.
+
+Conformance reports for the included jaxp support can be found in the
+doc/README.jaxp file.
+
+GNU Classpath 0.19 can be downloaded from
+ftp://ftp.gnu.org/pub/gnu/classpath/
+or one of the ftp.gnu.org mirrors
+http://www.gnu.org/order/ftp.html
+
+File: classpath-0.19.tar.gz
+MD5sum: 0b93b1c1dd3d33ef7fb6a47dbb29e41d
+SHA1sum: 43d499e8b83e04a7fc4a1d4d301638c5cec6c679
+
+File: classpath-0.19-generics.tar.gz (EXPERIMENTAL)
+MD5sum: 4c0ccc91a147af4010d19f48dbf441b3
+SHA1sum: b2a2b968523b3af35cd7e44bcc4f940621b3ca66
+
+The GNU Classpath developers site http://developer.classpath.org/
+provides detailed information on how to start with helping the GNU
+Classpath project and gives an overview of the core class library
+packages currently provided. For each snapshot release generated
+documentation is provided through the GNU Classpath Tools gjdoc
+project. A documentation generation framework for java source
+files used by the GNU project. Full documentation on the currently
+implementated packages and classes can be found at:
+http://developer.classpath.org/doc/
+
+New in release 0.19 (Nov 2, 2005)
+(See the ChangeLog file for a full list of changes.)
+
+* The Swing RepaintManager has been reworked for more efficient
+ painting, especially for large GUIs.
+
+* The Swing layout manager OverlayLayout has been implemented, the
+ BoxLayout has been rewritten to make use of the SizeRequirements
+ utility class and caching for more efficient layout.
+
+* Improved accessibility support for Swing.
+
+* The java.net.HttpURLConnection implementation no longer buffers the
+ entire response body in memory. This means that response bodies
+ larger than available memory can now be handled.
+
+* The Andrew Watson, Vice President and Technical Director of the
+ Object Management Group, has officially assigned us 20 bit Vendor
+ Minor Code Id: 0x47430 ("GC") that will mark remote Classpath -
+ specific system exceptions. Obtaining the VMCID means that GNU
+ Classpath now is a recogniseable type of node in a highly
+ interoperable CORBA world.
+
+* Classpath now includes the first working draft to support the RMI
+ over IIOP protocol. The current implementation is capable for remote
+ invocations, transferring various Serializables and Externalizables
+ via RMI-IIOP protocol. It can flatten graphs and, at least for the
+ simple cases, is interoperable with Sun's jdk 1.5.
+
+* Qt4 configury switches for OS-X. Additional to the --enable-qt-peer,
+ OS-X users with a Qt4 installation can build the qt-peers with the
+ argument --with-qt4dir=<Qt4-installation-dir>.
+
+* Significant progress has been made in the implementation of the
+ javax.swing.plaf.metal.* package, with most UI delegates in a
+ working state now. Please test this with your own applications and
+ provide feedback that will help us to improve this package.
+
+* The GUI demo (gnu.classpath.examples.swing.Demo) has been extended
+ to highlight various features in our free-swing implementation. And
+ includes a look and feel switcher (Metal default, Ocean or GNU).
+
+Runtime interface changes:
+
+* Changed implementation of VMClassLoader.getPackage(s) : new method
+ VMClassLoader.getBootPackages should be implemented by the vm, and
+ sould return a string array of boot package names ("java.lang",
+ "java.net", ...). Feedback from vm implementors for usability and
+ relevance of the getBootPackages method would be greatly
+ appreciated.
+
+New Untested/Disabled Features:
+
+ The following new features are included, but not ready for
+ production yet. They are explicitly disabled and not supported. But
+ if you want to help with the development of these new features we
+ are interested in feedback. You will have to explicitly enable them
+ to try them out (and they will most likely contain bugs). If you are
+ interested in any of these then please join the mailing-list and
+ follow development in CVS.
+
+* Cairo Gtk+ Graphics2D support, enabled by giving configure
+ --enable-gtk-cairo.
+* QT4 AWT peers, enable by giving configure --enable-qt-peer.
+
+The following people helped with this release:
+
+Andreas Tobler
+ Qt4 support for Darwin/OSX, Graphics2D support, gtk+ updates.
+Andrew Haley
+ Serialization and URLClassLoader fixes.
+Andrew John Hughes
+ Serialization fixes, Properties XML support and generic branch work.
+Anthony Balkissoon
+ Lots of Free Swing additions.
+Anthony Green
+ MIDI framework, ALSA and DSSI providers.
+Audrius Meskauskas
+ Lots of new CORBA and RMI work and bugfixes.
+Casey Marshall
+ Crypto algorithm fixes.
+Chris Burdess
+ StAX and dom xml:id support.
+Christian Thalinger
+ Configuration and VM inteface fixes and CACAO integration.
+Dalibor Topic
+ Build cleanups and Kaffe integration.
+David Daney
+ HttpURLConnection rewrite and improvements.
+David Gilbert
+ Lots of Free Swing and metal theme additions.
+David Lichteblau
+ JCL support library global/local reference cleanups.
+Gael Thomas
+ VMClassLoader boot packages support sugestions.
+Guilhem Lavaux
+ Configuration, thread and channel fixes and Kaffe integration.
+Jan Roehrich
+ BasicTreeUI fixes.
+Jeroen Frijters
+ Serialization fixes, better Proxy support, bug fixes and IKVM integration.
+Julian Scheid
+ Documentation updates and gjdoc support.
+Keith Seitz
+ JDWP support.
+Lillian Angel
+ Lots of Free Swing additions.
+Mark Wielaard
+ Bug fixes, packaging and release management
+Martin Cordova
+ Suggestions for better SocketTimeoutException.
+Michael Koch
+ Configuration fixes.
+Nicolas Geoffray
+ VMClassLoader and AccessController improvements.
+Paul Jenner
+ Better -Werror support.
+Robert Schuster
+ XML and URL, AWT and Free Swing bug fixes
+Roman Kennke
+ Lots of Free Swing additions.
+Santiago Gala
+ AccessControlContext fixes.
+Stuart Ballard
+ RMI constant fixes.
+Sven de Marothy
+ BMP imageio support, CSS and TextLayout fixes.
+Thomas Fitzsimmons
+ Lots of imageio framework additions, lots of AWT and Free Swing bug fixes.
+Tom Tromey
+ Eclipse integration, generics work, lots of bug fixes and gcj integration.
+
+We would also like to thank the numerous bug reporters and testers!
+</pre>
+<footer>
diff --git a/doc/www.gnu.org/cp-tools/cp-tools.wml b/doc/www.gnu.org/cp-tools/cp-tools.wml
index 902544fbe..a5139fbd5 100755
--- a/doc/www.gnu.org/cp-tools/cp-tools.wml
+++ b/doc/www.gnu.org/cp-tools/cp-tools.wml
@@ -35,6 +35,15 @@ page describing them in more detail:
</box>
<box>
+<boxtitle><a name="Development">GNU Classpath::Tools::Downloads</a></boxtitle>
+<boxitem>
+At the moment there are only official releases of gjdoc on
+<createlink url="ftp://ftp.gnu.org/gnu/classpath/" name="ftp.gnu.org"/>.
+All other tools are available from CVS from the savannah project page below.
+</boxitem>
+</box>
+
+<box>
<boxtitle><a name="Development">GNU Classpath::Tools::Development</a></boxtitle>
<boxitem>
GNU Classpath Tools is part of the GNU Classpath project which is hosted at
diff --git a/doc/www.gnu.org/downloads/downloads.wml b/doc/www.gnu.org/downloads/downloads.wml
index cd5d092d7..96018f603 100644
--- a/doc/www.gnu.org/downloads/downloads.wml
+++ b/doc/www.gnu.org/downloads/downloads.wml
@@ -77,10 +77,10 @@ sub mylink {
<download-block>
<download
- date="06 September 2005"
- version="0.18"
- url="ftp://ftp.gnu.org/gnu/classpath/classpath-0.18.tar.gz"
- notes="http://www.gnu.org/software/classpath/announce/20050906.html"
+ date="02 November 2005"
+ version="0.19"
+ url="ftp://ftp.gnu.org/gnu/classpath/classpath-0.19.tar.gz"
+ notes="http://www.gnu.org/software/classpath/announce/20051102.html"
>
<!-- download
@@ -100,6 +100,12 @@ sub mylink {
<download-block>
<download
+ date="06 September 2005"
+ version="0.18"
+ url="ftp://ftp.gnu.org/gnu/classpath/classpath-0.18.tar.gz"
+ notes="http://www.gnu.org/software/classpath/announce/20050906.html"
+>
+<download
date="15 July 2005"
version="0.17"
url="ftp://ftp.gnu.org/gnu/classpath/classpath-0.17.tar.gz"
diff --git a/doc/www.gnu.org/newsitems.txt b/doc/www.gnu.org/newsitems.txt
index 709f29108..dbfcfd2ce 100644
--- a/doc/www.gnu.org/newsitems.txt
+++ b/doc/www.gnu.org/newsitems.txt
@@ -1,3 +1,8 @@
+<newsitem date="02 Nov 2005">
+<createlink name="GNU Classpath 0.19"
+ url="announce/20051102.html">
+</newsitem>
+
<newsitem date="06 Sep 2005">
<createlink name="GNU Classpath 0.18"
url="announce/20050906.html">
diff --git a/examples/Makefile.am b/examples/Makefile.am
index 3a2aec86d..53960f008 100644
--- a/examples/Makefile.am
+++ b/examples/Makefile.am
@@ -20,7 +20,7 @@ endif
endif
# All our example java source files
-EXAMPLE_JAVA_FILES = $(srcdir)/gnu/classpath/examples/*/*.java
+EXAMPLE_JAVA_FILES = $(srcdir)/gnu/classpath/examples/*/*.java $(srcdir)/gnu/classpath/examples/*/*/*.java $(srcdir)/gnu/classpath/examples/*/*/*/*.java
# The example C source files
EXAMPLE_C_FILES = $(srcdir)/gnu/classpath/examples/*/*.c
@@ -34,8 +34,11 @@ BUILT_SOURCES = $(EXAMPLE_ZIP)
# the png icons we use in some of the examples.
EXAMPLE_ICONS = $(srcdir)/gnu/classpath/examples/icons/*.png
+# The example specific README files.
+READMES = $(srcdir)/gnu/classpath/examples/CORBA/swing/README.html
+
# All the files we find "interesting"
-ALL_EXAMPLE_FILES = $(EXAMPLE_JAVA_FILES) $(EXAMPLE_C_FILES) $(EXAMPLE_ICONS)
+ALL_EXAMPLE_FILES = $(EXAMPLE_JAVA_FILES) $(EXAMPLE_C_FILES) $(EXAMPLE_ICONS) $(READMES)
# Some architecture independent data to be installed.
example_DATA = $(EXAMPLE_ZIP) README
diff --git a/examples/gnu/classpath/examples/CORBA/swing/README.html b/examples/gnu/classpath/examples/CORBA/swing/README.html
new file mode 100644
index 000000000..a3a9e6282
--- /dev/null
+++ b/examples/gnu/classpath/examples/CORBA/swing/README.html
@@ -0,0 +1,493 @@
+<html>
+ <head>
+ <title>Five-in-a-row v 0.0</title>
+ </head>
+ <body LANG="en-US">
+ <h1>
+ <i>Five-in-a-row
+ </i> 0.0 supplementary documentation
+ </h1>
+ <h3>Introduction and rules
+ </h3>
+ <p>
+ <i>Five-in-a-row
+ </i> is a two player strategy game. The players
+ are connected via network using CORBA-based RMI/IIOP protocol and
+ make they moves with the help of the Swing-based
+ interface. While playing, the users can also chat.
+ </p>
+ <p>The system consists of the single server and any number of
+ interconnected players. The person, willing to play, starts the
+ client and connects the server. The server redirects call to the
+ partner that has previously connected the same server, also willing
+ to play.
+ </p>
+ <p>The game desk is a field where it is possible to set O's
+ and X'es, one per move. The goal is to get five O's in a row while
+ preventing your partner from getting five X's in a row. Vertical,
+ horizontal and diagonal rows are allowed. The system detects the
+ loss-victory situation on the desk, but currently does not serve as a
+ playing partner, requiring at least two human players for this game.
+ </p>
+ <p>Both players can at any time reset the game (restarting it with
+ the same player) or leave the game (disconnecting). The disconnected
+ player can contact the game manager again, requesting to find another
+ partner.
+ </p>
+ <p>Simple as it is, the application has some features of the typical
+ role playing game that frequently just has more states, actions,
+ possible moves and also provides far richer graphics environment. The
+ game manger serves as a World-Wide-Pub where you can always find a
+ partner to play.
+
+ The players can made both unsynchronized (chatting, game reset and
+ leaving) and synchronized (moves) actions. The game state changes
+ while playing, and the set of the available actions depends on the
+ current state. Finally, the mouse and canvas are involved. However
+ using RMI/IIOP machinery allowed to implement all this functionality
+ with just 13 classes (plus 4 generated), all of them being rather
+ simple.
+
+ This example refers to the standard classes only and must be buildable
+ from your IDE as long as it has any java 1.4 compiler.
+ </p>
+ <p>
+ The used IIOP protocol must ensure interoperability, allowing players
+ to use different java virtual machines and operating systems.
+ The processors may have the opposite byte order.
+ </p>
+ <h3>Configuration and run
+ </h3>
+ <p>The game manager server executable class is
+ <i>gnu.classpath.examples.CORBA.swing.x5.X5Server
+ </i>. After start,
+ it will print to console the Internet address that must be entered to
+ the client to reach the manager.
+ </p>
+ <p>The client executable class it
+ <i>gnu.classpath.examples.CORBA.swing.x5.Demo
+ </i>.
+ </p>
+ <p>The game should run with GNU Classpath
+ 0.19 and Sun Microsystems java 1.5.0_04. Due later fixed bugs it will
+ not run with the older versions of these two implementations.
+ </p>
+ <p>The game manager HTTP server uses port
+ 1500. Hence all firewalls between the server and the player must be
+ configured to allow HTTP on 1500. The ports, used by the RMI/IIOP are
+ not persistent. GNU Classpath is configured to take ports 1501, 1502
+ and 1503 (the firewalls must allow to use them for RMI/IIOP). The
+ CORBA implementation other than Classpath may use different port
+ values. Unfortunately, there is no standard method to configure the
+ used port range in a vendor-independent way.
+ </p>
+ <h3>The game server
+ </h3>
+ <p>The game manager is first reachable via http:// protocol (for
+ instance http://123.456.7.89:1500). The simple server at this port
+ always serves much longer string, representing the CORBA stringified
+ object reference (IOR). The
+ <i>Five-in-a-row&nbsp;
+ </i>client uses
+ this reference to find and access the remote game server object.
+ </p>
+ <p>If the server player queue is empty, it simply queues this player.
+ If the queue is not empty, the server introduces the arrived player
+ and queued player to each other as leaves the them alone. When
+ playing, the two clients communicate with each other directly, so the
+ server is just a &ldquo;meeting point&rdquo; where the players can
+ find each other. The game server is a console-only application.
+ </p>
+ <p>The initial server http:// address must be transferred to players
+ by some other means of communication (web chat, E-mail, link in a web
+ site and so on). The server writes this address to the specified
+ file, and the client can also take the default value from the same
+ file. This is convenient when all applications run on a single
+ machine, but also may be used to transfer the address via shared
+ filesystem.
+ </p>
+ <h3>The game client
+ </h3>
+ <p>The clients are Swing-based GUI applications, capable for remote
+ communication with each other and with the game manager. They have a
+ set of predefined states and switch between these states in
+ accordance to the preprogrammed logic. The client states are defined
+ in the
+ <i>State
+ </i> interface. They are displayed in the bottom left
+ corner of the window and are summarized in the following table:
+ </p>
+ <table BORDER=1 CELLPADDING=4 CELLSPACING=0 WIDTH="100%">
+ <thead>
+ <tr BGCOLOR="#ccccff">
+ <th BGCOLOR="#e6e6ff">
+ Our state
+ </th>
+ <th BGCOLOR="#e6e6ff">
+ Partner state
+ </th>
+ <th BGCOLOR="#e6e6ff">
+ Possible actions
+ </th>
+ <th BGCOLOR="#e6e6ff">
+ Comment
+ </th>
+ </tr>
+ </thead>
+ <tbody>
+ <tr>
+ <td>
+ Disconnected
+ </td>
+ <td>
+ Partner not accessible
+ </td>
+ <td>
+ Connect
+ </td>
+ <td>
+ Initial state.
+ </td>
+ </tr>
+ <tr>
+ <td>
+ Queued
+ </td>
+ <td>
+ Partner not accessible
+ </td>
+ <td>
+ Leave
+ </td>
+ <td>
+ Queued by the game manager.
+ </td>
+ </tr>
+ <tr>
+ <td>
+ I think.
+ </td>
+ <td>
+ I wait for your move
+ </td>
+ <td>
+ Make move, reset game, leave, chat.
+ </td>
+ <td>
+ The person who waited for another player to come starts
+ the game first.
+ </td>
+ </tr>
+ <tr>
+ <td>
+ I wait for your move
+ </td>
+ <td>
+ I think
+ </td>
+ <td>
+ Chat, reset game, leave.
+ </td>
+ <td>
+ After the partner makes the move, the state changes to
+ <i>I think
+ </i>, unless the end of game situation is detected by
+ the desk analyzer.
+ </td>
+ </tr>
+ <tr>
+ <td>
+ I have lost
+ </td>
+ <td>
+ I have won
+ </td>
+ <td>
+ Chat, reset game, leave.
+ </td>
+ <td>
+ Can be entered with the help of the desk analyzer only.
+ </td>
+ </tr>
+ <tr>
+ <td>
+ I have won
+ </td>
+ <td>
+ I have lost
+ </td>
+ <td>
+ Chat, reset game, leave
+ </td>
+ <td>
+ Can be entered with the help of the desk analyzer only.
+ </td>
+ </tr>
+ <tr>
+ <td>
+ Error
+ </td>
+ <td>
+ Any
+ </td>
+ <td>
+ Chat, leave
+ </td>
+ <td>
+ This should never happen under normal work, but the demo
+ program may be modified by the user.
+ </td>
+ </tr>
+ </tbody>
+ </table>
+ <br>
+ <br>
+ As it is seen, being in one of the states, the client expects to
+ be the partner client in a certain defined state, and both clients
+ change they states in a synchronized manner. Each state has its own
+ set of the available actions and each action either preserves the
+ current state (chat, reset) or changes it following the rules. For
+ this simple example, the state change rules are obvious.
+ <h3>The used RMI-IIOP architecture
+ </h3>
+ Both player and game manager servants are derived from the
+ <i>org.omg.PortableServer.Servant
+ </i> and, being servants, are simply
+ connected to the
+ <i>POA
+ </i>with
+ <i>POA.servant_to_reference
+ </i>. The
+ first remote object (game manager) is found using the stringified
+ object reference. No naming service is involved.
+</p>
+Where required, the CORBA objects are narrowed into required
+player and game manager interfaces using method
+<i>PortableRemoteObject.narrow(org.omg.CORBA.Object object, Class
+ interface_class)
+</i>, passing the actual interface of the object as
+the second parameter. After narrowing, the remote side obtains
+possibility to invoke remote methods, defined in the interface of
+this object. After the first remote object is found, other objects
+can be simply passed as the method parameters. For instance, the game
+manager introduces another player by passing its reference as a
+parameter to the method
+<i>Player.start_game.
+</i>
+<h3>Class and interface summary
+</h3>
+<table BORDER=1 CELLPADDING=3 CELLSPACING=0 WIDTH="100%">
+ <col>
+ <col>
+ <tr>
+ <th COLSPAN=2 BGCOLOR="#e6e6ff">
+ Executables classes
+ </th>
+ </tr>
+ <tr>
+ <td>
+ Demo
+ </td>
+ <td>
+ The main executable class of the game client.
+ </td>
+ </tr>
+ <tr>
+ <td>
+ X5Server
+ </td>
+ <td>
+ The main executable class of the game manager server.
+ </td>
+ </tr>
+</table>
+<p></p>
+<table BORDER=1 CELLPADDING=3 CELLSPACING=0 WIDTH="100%">
+ <tr BGCOLOR="#ccccff">
+ <th COLSPAN=2 BGCOLOR="#e6e6ff">
+ Interface Summary
+ </th>
+ </tr>
+ <tr>
+ <td>
+ GameManager
+ </td>
+ <td>
+ The game manager interface.
+ </td>
+ </tr>
+ <tr>
+ <td>
+ Player
+ </td>
+ <td>
+ Defines remote methods that are invoked by another player or by
+ the challenge server.
+ </td>
+ </tr>
+ <tr>
+ <td>
+ State
+ </td>
+ <td>
+ Defines the states in that the player can be.
+ </td>
+ </tr>
+</table>
+&nbsp;
+<table BORDER=1 CELLPADDING=3 CELLSPACING=0 WIDTH="100%">
+ <col>
+ <col>
+ <tr BGCOLOR="#ccccff">
+ <th COLSPAN=2 BGCOLOR="#e6e6ff">
+ Class Summary
+ </th>
+ </tr>
+ <tr>
+ <td>
+ _GameManager_Stub
+ </td>
+ <td>
+ Normally generated with rmic compiler, this class represents
+ the GameManager Stub on the client side.
+ </td>
+ </tr>
+ <tr>
+ <td>
+ _GameManagerImpl_Tie
+ </td>
+ <td>
+ Normally generated with rmic compiler, this class represents
+ the GameManager Tie on the client side.
+ </td>
+ </tr>
+ <tr>
+ <td>
+ _Player_Stub
+ </td>
+ <td>
+ Generate with rmic, command line rmic -iiop -poa -keep
+ gnu.classpath.examples.CORBA.swing.x5.PlayerImpl (the compiled
+ package must be present in the current folder).
+ </td>
+ </tr>
+ <tr>
+ <td>
+ _PlayerImpl_Tie
+ </td>
+ <td>
+ Generate with rmic, command line rmic -iiop -poa -keep
+ gnu.classpath.examples.CORBA.swing.x5.PlayerImpl (the compiled
+ package must be present in the current folder).
+ </td>
+ </tr>
+ <tr>
+ <td>
+ ChatConstants
+ </td>
+ <td>
+ The chat color code constants, used to indicate who is talking.
+ </td>
+ </tr>
+ <tr>
+ <td>
+ ClientFrame
+ </td>
+ <td>
+ The JFrame of the GUI client.
+ </td>
+ </tr>
+ <tr>
+ <td>
+ GameManagerImpl
+ </td>
+ <td>
+ The manager connects two players into the game.
+ </td>
+ </tr>
+ <tr>
+ <td>
+ IorReader
+ </td>
+ <td>
+ Reads the remote URL.
+ </td>
+ </tr>
+ <tr>
+ <td>
+ OrbStarter
+ </td>
+ <td>
+ Starts the ORBs, involved into this application.
+ </td>
+ </tr>
+ <tr>
+ <td>
+ PlayerImpl
+ </td>
+ <td>
+ The implementation of the PlayerCommunicator, providing the
+ local functionality.
+ </td>
+ </tr>
+ <tr>
+ <td>
+ PlayingDesk
+ </td>
+ <td>
+ Manages actions, related to the game rules and also does all
+ painting.
+ </td>
+ </tr>
+</table>
+<h3>See also
+</h3>
+<p>
+ <a HREF="http://www.javascripter.net/games/xo/xo.htm">http://www.javascripter.net/games/xo/xo.htm
+ </a>
+</p>
+<p>
+ <a HREF="http://www.leepoint.net/notes-java/45examples/55games/five/five.html">http://www.leepoint.net/notes-java/45examples/55games/five/five.html
+ </a>
+</p>
+<p>Copyright
+</p>
+<p>
+ <font COLOR="#b3b3b3">Copyright (C) 2005 Free Software Foundation,
+ Inc. This file is part of GNU Classpath. GNU Classpath is free
+ software; you can redistribute it and/or modify it under the terms of
+ the GNU General Public License as published by the Free Software
+ Foundation; either version 2, or (at your option) any later version.
+ GNU Classpath is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details. You should have received a
+ copy of the GNU General Public License along with GNU Classpath; see
+ the file COPYING. If not, write to the Free Software Foundation,
+ Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
+ Linking this library statically or dynamically with other modules is
+ making a combined work based on this library. Thus, the terms and
+ conditions of the GNU General Public License cover the whole
+ combination. As a special exception, the copyright holders of this
+ library give you permission to link this library with independent
+ modules to produce an executable, regardless of the license terms of
+ these independent modules, and to copy and distribute the resulting
+ executable under terms of your choice, provided that you also meet,
+ for each linked independent module, the terms and conditions of the
+ license of that module. An independent module is a module which is
+ not derived from or based on this library. If you modify this
+ library, you may extend this exception to your version of the
+ library, but you are not obligated to do so. If you do not wish to do
+ so, delete this exception statement from your version.
+ </font>
+</p>
+<p>
+ <br>
+ <br>
+</p>
+<p>
+First version written by <a href="http://savannah.gnu.org/users/audriusa">
+Audrius Me&scaron;kauskas</a>
+</p>
+</body>
+</html>
diff --git a/examples/gnu/classpath/examples/CORBA/swing/x5/CanvasWorld.java b/examples/gnu/classpath/examples/CORBA/swing/x5/CanvasWorld.java
new file mode 100644
index 000000000..9e1a70fcc
--- /dev/null
+++ b/examples/gnu/classpath/examples/CORBA/swing/x5/CanvasWorld.java
@@ -0,0 +1,307 @@
+/* CanvasWorld.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+ This file is part of GNU Classpath.
+
+ GNU Classpath is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2, or (at your option)
+ any later version.
+
+ GNU Classpath is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with GNU Classpath; see the file COPYING. If not, write to the
+ Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ 02110-1301 USA.
+
+ Linking this library statically or dynamically with other modules is
+ making a combined work based on this library. Thus, the terms and
+ conditions of the GNU General Public License cover the whole
+ combination.
+
+ As a special exception, the copyright holders of this library give you
+ permission to link this library with independent modules to produce an
+ executable, regardless of the license terms of these independent
+ modules, and to copy and distribute the resulting executable under
+ terms of your choice, provided that you also meet, for each linked
+ independent module, the terms and conditions of the license of that
+ module. An independent module is a module which is not derived from
+ or based on this library. If you modify this library, you may extend
+ this exception to your version of the library, but you are not
+ obligated to do so. If you do not wish to do so, delete this
+ exception statement from your version. */
+
+
+package gnu.classpath.examples.CORBA.swing.x5;
+
+import java.awt.Color;
+import java.awt.Dimension;
+import java.awt.Graphics;
+import java.awt.Point;
+import java.awt.event.MouseEvent;
+import java.awt.event.MouseListener;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Iterator;
+
+import javax.swing.JComponent;
+import javax.swing.JFrame;
+import javax.swing.JScrollPane;
+
+/**
+ * The purpose of this simple example is to check if the mouse events are
+ * correctly received in a scrollable canvas and also if the canvas are
+ * correctly repainted. The similar canvas are used in various games and
+ * interactive demonstrations.
+ *
+ * The user can set one of the three possible figures with the different
+ * mouse buttons. The figure must be set where the user have clicked the
+ * mouse.
+ *
+ * @author Audrius Meskauskas (AudriusA@Bioinformatics.org)
+ */
+public class CanvasWorld
+ extends JComponent
+ implements MouseListener, State
+{
+ /**
+ * Use serialVersionUID for interoperability.
+ */
+ private static final long serialVersionUID = 1;
+
+ /**
+ * Red oval, set by the left mouse button.
+ */
+ public static final int RED = 0;
+
+ /**
+ * Black cross, set by the right mouse button.
+ */
+ public static final int BLACK = 1;
+
+ /**
+ * Blue and smaller oval, set by the middle mouse button.
+ */
+ public static final int HINT = 2;
+
+ /**
+ * The message string is displayed at the top of the window.
+ */
+ String message = "Click left, right or middle button in to set the figure";
+
+ /**
+ * The additinal message, related to the mouse events.
+ */
+ String mouse = "No mouse event so far";
+
+ /**
+ * The grid spacing.
+ */
+ static int W = 16;
+
+ /**
+ * The radius of the dots being painted.
+ */
+ static int R = W / 3;
+
+ /**
+ * The collection of the red dots.
+ */
+ ArrayList reds = new ArrayList();
+
+ /**
+ * The collection of the black crosses.
+ */
+ ArrayList blacks = new ArrayList();
+
+ /**
+ * The collection of the smaller blue crosses.
+ */
+ ArrayList hints = new ArrayList();
+
+ public CanvasWorld()
+ {
+ try
+ {
+ addMouseListener(this);
+ }
+ catch (Exception e)
+ {
+ throw new AssertionError(e);
+ }
+ }
+
+ /**
+ * Paint this component.
+ */
+ public void paintComponent(Graphics g)
+ {
+ int w = getWidth();
+ int h = getHeight();
+
+ g.setColor(Color.white);
+ g.fillRect(0, 0, w, h);
+
+ drawGrid(w, h, g);
+
+ g.setColor(Color.black);
+
+ g.drawString(message, W, W);
+ g.drawString(mouse, W, 2*W);
+
+ drawFigures(g);
+ }
+
+ /**
+ * Check for the presence of the given point in the collection.
+ */
+ public final boolean pointPresent(int x, int y, Collection in)
+ {
+ Iterator iter = in.iterator();
+ Point p;
+ while (iter.hasNext())
+ {
+ p = (Point) iter.next();
+ if (p.x == x && p.y == y)
+ return true;
+ }
+ return false;
+ }
+
+ public void drawGrid(int w, int h, Graphics g)
+ {
+ g.setColor(Color.lightGray);
+
+ int xs = 2*W+W/2;
+
+ // Draw vertical lines:
+ for (int x = 0; x < w; x += W)
+ {
+ g.drawLine(x, xs, x, h);
+ }
+
+ // Draw horizontal lines:
+ for (int y = 3*W; y < h; y += W)
+ {
+ g.drawLine(0, y, w, y);
+ }
+
+ g.setColor(Color.gray);
+ }
+
+ public void drawFigures(Graphics g)
+ {
+ g.setColor(Color.red);
+ drawDots(reds, g, RED);
+
+ g.setColor(Color.black);
+ drawDots(blacks, g, BLACK);
+
+ g.setColor(Color.blue);
+ drawDots(hints, g, HINT);
+ }
+
+ public Point makePoint(int x, int y)
+ {
+ return new Point(x / W, y / W);
+ }
+
+ /**
+ * Draw a collection of dots (the collor must be set before calling the
+ * method).
+ */
+ public void drawDots(Collection dots, Graphics g, int mode)
+ {
+ Iterator iter = dots.iterator();
+ int x;
+ int y;
+
+ int hW = W / 2;
+ int RR = R * 2;
+ int hR = R / 2;
+ Point p;
+ while (iter.hasNext())
+ {
+ p = (Point) iter.next();
+ x = p.x * W + hW;
+ y = p.y * W + hW;
+
+ if (mode == RED)
+ g.drawOval(x - R, y - R, RR, RR);
+ else if (mode == BLACK)
+ {
+ g.drawLine(x - R, y - R, x + R, y + R);
+ g.drawLine(x - R, y + R, x + R, y - R);
+ }
+ else
+ {
+ // Hint.
+ g.drawOval(x - hR, y - hR, R, R);
+ }
+ }
+ }
+
+ public void mouseClicked(MouseEvent e)
+ {
+ int x = e.getX();
+ int y = e.getY();
+
+ Point p = makePoint(x, y);
+
+ // Ignore clicks on the occupied cells.
+ if (pointPresent(p.x, p.y, reds) || (pointPresent(p.x, p.y, blacks)))
+ {
+ message = "Clicked on the occupied cell.";
+ return;
+ }
+ else
+ message = "Figure set at ["+p.x+","+p.y+"]";
+
+ if (e.getButton() == MouseEvent.BUTTON1)
+ reds.add(p);
+ else if (e.getButton() == MouseEvent.BUTTON3)
+ blacks.add(p);
+ else if (e.getButton() == MouseEvent.BUTTON2)
+ hints.add(p);
+ repaint();
+ }
+
+ public void mouseEntered(MouseEvent m)
+ {
+ mouse = "Mouse entered.";
+ repaint();
+ }
+
+ public void mousePressed(MouseEvent m)
+ {
+ mouse = "Mouse pressed at "+m.getX()+","+m.getY();
+ repaint();
+ }
+
+ public void mouseReleased(MouseEvent m)
+ {
+ mouse = "Mouse released at "+m.getX()+","+m.getY();
+ repaint();
+ }
+
+ public void mouseExited(MouseEvent m)
+ {
+ mouse = "Mouse exited";
+ repaint();
+ }
+
+ public static void main(String[] args)
+ {
+ JFrame frame = new JFrame();
+ CanvasWorld world = new CanvasWorld();
+ world.setPreferredSize(new Dimension(1000,1000));
+ frame.add(new JScrollPane(world));
+ frame.setSize(400, 200);
+ frame.setVisible(true);
+ }
+
+} \ No newline at end of file
diff --git a/examples/gnu/classpath/examples/CORBA/swing/x5/ChatConstants.java b/examples/gnu/classpath/examples/CORBA/swing/x5/ChatConstants.java
new file mode 100644
index 000000000..b0552b439
--- /dev/null
+++ b/examples/gnu/classpath/examples/CORBA/swing/x5/ChatConstants.java
@@ -0,0 +1,80 @@
+/* ChatConstants.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+ This file is part of GNU Classpath.
+
+ GNU Classpath is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2, or (at your option)
+ any later version.
+
+ GNU Classpath is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with GNU Classpath; see the file COPYING. If not, write to the
+ Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ 02110-1301 USA.
+
+ Linking this library statically or dynamically with other modules is
+ making a combined work based on this library. Thus, the terms and
+ conditions of the GNU General Public License cover the whole
+ combination.
+
+ As a special exception, the copyright holders of this library give you
+ permission to link this library with independent modules to produce an
+ executable, regardless of the license terms of these independent
+ modules, and to copy and distribute the resulting executable under
+ terms of your choice, provided that you also meet, for each linked
+ independent module, the terms and conditions of the license of that
+ module. An independent module is a module which is not derived from
+ or based on this library. If you modify this library, you may extend
+ this exception to your version of the library, but you are not
+ obligated to do so. If you do not wish to do so, delete this
+ exception statement from your version. */
+
+
+package gnu.classpath.examples.CORBA.swing.x5;
+
+import java.awt.Color;
+
+/**
+ * The chat color code constants, used to indicate who is talking.
+ * Additionally, the red color is reseved for the most important messages,
+ * related to the start and end of the game.
+ *
+ * @author Audrius Meskauskas (AudriusA@Bioinformatics.org)
+ */
+public class ChatConstants
+{
+ /**
+ * Messages from the local system.
+ */
+ public static byte SYSTEM = 0;
+
+ /**
+ * Mirrored messsages from the local player.
+ */
+ public static byte SELF = 1;
+
+ /**
+ * Messages from the remote player.
+ */
+ public static byte REMOTE_PLAYER = 2;
+
+ /**
+ * Messages from the game server/
+ */
+ public static byte GAME_SERVER = 3;
+
+ /**
+ * The array of the used colors.
+ */
+ public static Color[] colors =
+ new Color[]
+ {
+ Color.black, new Color(0, 80, 0), new Color(0, 0, 128), Color.blue
+ };
+} \ No newline at end of file
diff --git a/examples/gnu/classpath/examples/CORBA/swing/x5/ClientFrame.java b/examples/gnu/classpath/examples/CORBA/swing/x5/ClientFrame.java
new file mode 100644
index 000000000..c3d8300b7
--- /dev/null
+++ b/examples/gnu/classpath/examples/CORBA/swing/x5/ClientFrame.java
@@ -0,0 +1,417 @@
+/* ClientFrame.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+ This file is part of GNU Classpath.
+
+ GNU Classpath is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2, or (at your option)
+ any later version.
+
+ GNU Classpath is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with GNU Classpath; see the file COPYING. If not, write to the
+ Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ 02110-1301 USA.
+
+ Linking this library statically or dynamically with other modules is
+ making a combined work based on this library. Thus, the terms and
+ conditions of the GNU General Public License cover the whole
+ combination.
+
+ As a special exception, the copyright holders of this library give you
+ permission to link this library with independent modules to produce an
+ executable, regardless of the license terms of these independent
+ modules, and to copy and distribute the resulting executable under
+ terms of your choice, provided that you also meet, for each linked
+ independent module, the terms and conditions of the license of that
+ module. An independent module is a module which is not derived from
+ or based on this library. If you modify this library, you may extend
+ this exception to your version of the library, but you are not
+ obligated to do so. If you do not wish to do so, delete this
+ exception statement from your version. */
+
+package gnu.classpath.examples.CORBA.swing.x5;
+
+import java.awt.BorderLayout;
+import java.awt.Color;
+import java.awt.GridLayout;
+import java.awt.event.*;
+import java.io.BufferedWriter;
+import java.io.File;
+import java.io.FileWriter;
+
+import java.rmi.RemoteException;
+
+import javax.rmi.PortableRemoteObject;
+
+import javax.swing.*;
+import java.awt.Dimension;
+
+/**
+ * The JFrame of the GUI client.
+ *
+ * @author Audrius Meskauskas (AudriusA@Bioinformatics.org)
+ */
+public class ClientFrame
+ extends JFrame
+{
+ /**
+ * The size of the playing field.
+ */
+ public final Dimension DESK_SIZE =
+ new Dimension(624, 352-PlayingDesk.W);
+
+ /**
+ * Use serialVersionUID for interoperability.
+ */
+ private static final long serialVersionUID = 1;
+
+ // Define the application components:
+
+ /**
+ * Central panel where the main action takes place.
+ */
+ PlayingDesk desk = new PlayingDesk();
+
+ /**
+ * The scroll pane for canvas.
+ */
+ JScrollPane scroll = new JScrollPane();
+
+ /**
+ * Will remember the manager IOR.
+ */
+ String mior = "";
+
+ // The bottom panel contains the area that is used both to enter URL and
+ // for chatting.
+ JPanel pnBottom = new JPanel();
+
+ BorderLayout layBottom = new BorderLayout();
+
+ JTextField taUrl = new JTextField();
+
+ // The top primitive chatting panel, composed from labels.
+ JPanel pnChat = new JPanel();
+
+ GridLayout layChat = new GridLayout();
+
+ JLabel lbC3 = new JLabel();
+
+ JLabel lbC2 = new JLabel();
+
+ JLabel lbC1 = new JLabel();
+
+ // The button panel.
+ JPanel pnButtons = new JPanel();
+
+ GridLayout layButtons = new GridLayout();
+
+ JButton bLeave = new JButton();
+
+ JButton bConnect = new JButton();
+
+ JButton bExit = new JButton();
+
+ JButton bReset = new JButton();
+
+ JLabel lbState = new JLabel();
+
+ JButton bChat = new JButton();
+
+ JButton bPaste = new JButton();
+
+ public ClientFrame()
+ {
+ try
+ {
+ jbInit();
+ }
+ catch (Exception e)
+ {
+ e.printStackTrace();
+ }
+ }
+
+ private void jbInit()
+ throws Exception
+ {
+ desk.frame = this;
+
+ pnBottom.setLayout(layBottom);
+
+ pnChat.setLayout(layChat);
+ layChat.setColumns(1);
+ layChat.setRows(3);
+
+ lbC1.setText("This program needs the game server (see README on how to start it).");
+ lbC2.setText("Enter the game server address (host:port)");
+ lbC3.setText("Pressing \'Connect\' with the empty address will start the server on "
+ + "the local machine.");
+ bLeave.setEnabled(true);
+ bLeave.setToolTipText("Leave if either you have lost or do not want longer to play with "
+ + "this partner.");
+ bLeave.setText("Leave game");
+ bLeave.addActionListener(new java.awt.event.ActionListener()
+ {
+ public void actionPerformed(ActionEvent e)
+ {
+ bLeave_actionPerformed(e);
+ }
+ });
+ bConnect.setToolTipText("Connect your playing partner");
+ bConnect.setText("Connect");
+ bConnect.addActionListener(new java.awt.event.ActionListener()
+ {
+ public void actionPerformed(ActionEvent e)
+ {
+ bConnect_actionPerformed(e);
+ }
+ });
+ pnButtons.setLayout(layButtons);
+ bExit.setToolTipText("Exit this program");
+ bExit.setText("Exit");
+ bExit.addActionListener(new java.awt.event.ActionListener()
+ {
+ public void actionPerformed(ActionEvent e)
+ {
+ bExit_actionPerformed(e);
+ }
+ });
+ layButtons.setHgap(2);
+ bReset.setToolTipText("Restart the game. The partner may choose to exit!");
+ bReset.setText("Reset game");
+ bReset.addActionListener(new java.awt.event.ActionListener()
+ {
+ public void actionPerformed(ActionEvent e)
+ {
+ bReset_actionPerformed(e);
+ }
+ });
+ lbState.setText("Disconnected");
+ bChat.setToolTipText("Send message to player. Reuse the address "+
+ "field to enter the message.");
+ bChat.setText("Chat");
+ bChat.addActionListener(new java.awt.event.ActionListener()
+ {
+ public void actionPerformed(ActionEvent e)
+ {
+ bChat_actionPerformed(e);
+ }
+ });
+
+ bPaste.setText("Paste");
+ bPaste.setToolTipText("Paste, same as Ctrl-V");
+ bPaste.addActionListener(new java.awt.event.ActionListener()
+ {
+ public void actionPerformed(ActionEvent e)
+ {
+ bPaste_actionPerformed(e);
+ }
+ });
+
+ desk.setMaximumSize(DESK_SIZE);
+ desk.setPreferredSize(DESK_SIZE);
+
+ scroll.getViewport().add(desk, null);
+ getContentPane().add(scroll, BorderLayout.CENTER);
+ getContentPane().add(pnBottom, BorderLayout.SOUTH);
+
+ pnBottom.add(taUrl, BorderLayout.CENTER);
+ pnBottom.add(pnChat, BorderLayout.NORTH);
+
+ pnChat.add(lbC1, null);
+ pnChat.add(lbC2, null);
+ pnChat.add(lbC3, null);
+ pnBottom.add(pnButtons, BorderLayout.SOUTH);
+ pnButtons.add(lbState, null);
+ pnButtons.add(bConnect, null);
+ pnButtons.add(bChat, null);
+ pnButtons.add(bLeave, null);
+ pnButtons.add(bReset, null);
+ pnButtons.add(bExit, null);
+ pnButtons.add(bPaste, null);
+
+ desk.player.set_current_state(State.DISCONNECTED);
+ }
+
+ /**
+ * Handles exit procedure.
+ */
+ protected void processWindowEvent(WindowEvent e)
+ {
+ super.processWindowEvent(e);
+ if (e.getID() == WindowEvent.WINDOW_CLOSING)
+ {
+ bExit_actionPerformed(null);
+ }
+ }
+
+ /**
+ * Handles the connection procedure.
+ */
+ void bConnect_actionPerformed(ActionEvent e)
+ {
+ try
+ {
+ int state = desk.player.get_current_state();
+
+ if (state == State.DISCONNECTED || state == State.ERROR)
+ {
+ talk(ChatConstants.colors[0], "Connecting...");
+
+ if (desk.manager == null)
+ {
+ mior = taUrl.getText().trim();
+
+ // Obtain the manager object:
+ org.omg.CORBA.Object object = null;
+
+ try
+ {
+ object = desk.orb.string_to_object(mior);
+ }
+ catch (Exception exc)
+ {
+ // Maybe CORBA 3.0.3 is not completely implemented?
+ if (mior.startsWith("http://") || mior.startsWith("ftp://")
+ || mior.startsWith("file://"))
+ object = desk.orb.string_to_object(IorReader.readUrl(mior));
+ else
+ throw exc;
+ }
+
+ desk.manager = (GameManager) PortableRemoteObject.narrow(
+ object, GameManager.class);
+
+ // Export the desk.player as a remote object.
+ PortableRemoteObject.exportObject(desk.player);
+ }
+
+ desk.player.set_current_state(State.QUEUED);
+ desk.manager.requestTheGame(desk.player);
+ }
+
+ // Save the specified IOR for the future use:
+ File gmf = new File(OrbStarter.WRITE_URL_TO_FILE);
+ FileWriter f = new FileWriter(gmf);
+ BufferedWriter b = new BufferedWriter(f);
+
+ b.write(mior);
+ b.close();
+ }
+ catch (Exception ex)
+ {
+ talk(Color.red, "The manager is not reachable by this address.");
+ talk(Color.red, ex.getMessage());
+ desk.player.set_current_state(State.DISCONNECTED);
+ }
+ }
+
+ /**
+ * Display the new message with the given color. Shift the other messages over
+ * the labels.
+ */
+ public void talk(Color color, String text)
+ {
+ lbC1.setText(lbC2.getText());
+ lbC1.setForeground(lbC2.getForeground());
+
+ lbC2.setText(lbC3.getText());
+ lbC2.setForeground(lbC3.getForeground());
+
+ lbC3.setText(text);
+ lbC3.setForeground(color);
+ }
+
+ /**
+ * Exit this program.
+ */
+ void bExit_actionPerformed(ActionEvent e)
+ {
+ try
+ {
+ if (desk.player.get_current_state() != State.DISCONNECTED
+ && desk.player.partner != null)
+ {
+ desk.player.partner.receive_chat(ChatConstants.REMOTE_PLAYER,
+ "I close the program!");
+ desk.player.partner.disconnect();
+ }
+ }
+ catch (RemoteException ex)
+ {
+ // We will print the exception because this is a demo application that
+ // may be modified for learning purposes.
+ ex.printStackTrace();
+ }
+ System.exit(0);
+ }
+
+ void bReset_actionPerformed(ActionEvent e)
+ {
+ if (desk.player.partner != null)
+ {
+ try
+ {
+ desk.player.partner.receive_chat(ChatConstants.REMOTE_PLAYER,
+ "Your partner restarted the game.");
+
+ desk.player.start_game(desk.player.partner, false);
+ desk.player.partner.start_game(desk.player, true);
+ }
+ catch (RemoteException ex)
+ {
+ // We will print the exception because this is a demo application
+ // that
+ // may be modified for learning purposes.
+ ex.printStackTrace();
+ }
+ }
+ else
+ talk(Color.black, "You have not started the game yet.");
+ }
+
+ void bLeave_actionPerformed(ActionEvent e)
+ {
+ desk.player.leave();
+ }
+
+ void bChat_actionPerformed(ActionEvent e)
+ {
+ try
+ {
+ if (desk.player.partner != null)
+ {
+ String message = taUrl.getText();
+ desk.player.partner.receive_chat(ChatConstants.REMOTE_PLAYER, message);
+ talk(ChatConstants.colors[ChatConstants.SELF], message);
+ taUrl.setText("");
+ }
+ else
+ {
+ talk(Color.black, "Sorry, not connected to anybody");
+ }
+ }
+ catch (RemoteException ex)
+ {
+ // We will print the exception because this is a demo application that
+ // may be modified for learning purposes.
+ ex.printStackTrace();
+ }
+ }
+
+ /**
+ * Work around our keyboard shortcut handling that is still not working
+ * properly.
+ */
+ void bPaste_actionPerformed(ActionEvent e)
+ {
+ taUrl.paste();
+ }
+} \ No newline at end of file
diff --git a/examples/gnu/classpath/examples/CORBA/swing/x5/Demo.java b/examples/gnu/classpath/examples/CORBA/swing/x5/Demo.java
new file mode 100644
index 000000000..b83217896
--- /dev/null
+++ b/examples/gnu/classpath/examples/CORBA/swing/x5/Demo.java
@@ -0,0 +1,99 @@
+/* Demo.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+ This file is part of GNU Classpath.
+
+ GNU Classpath is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2, or (at your option)
+ any later version.
+
+ GNU Classpath is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with GNU Classpath; see the file COPYING. If not, write to the
+ Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ 02110-1301 USA.
+
+ Linking this library statically or dynamically with other modules is
+ making a combined work based on this library. Thus, the terms and
+ conditions of the GNU General Public License cover the whole
+ combination.
+
+ As a special exception, the copyright holders of this library give you
+ permission to link this library with independent modules to produce an
+ executable, regardless of the license terms of these independent
+ modules, and to copy and distribute the resulting executable under
+ terms of your choice, provided that you also meet, for each linked
+ independent module, the terms and conditions of the license of that
+ module. An independent module is a module which is not derived from
+ or based on this library. If you modify this library, you may extend
+ this exception to your version of the library, but you are not
+ obligated to do so. If you do not wish to do so, delete this
+ exception statement from your version. */
+
+
+package gnu.classpath.examples.CORBA.swing.x5;
+
+import java.awt.Dimension;
+import java.awt.Toolkit;
+import java.io.BufferedReader;
+import java.io.File;
+import java.io.FileReader;
+
+/**
+ * The main executable class of the game client.
+ *
+ * @author Audrius Meskauskas (AudriusA@Bioinformatics.org)
+ */
+public class Demo
+{
+
+ public static void main(String[] args)
+ {
+ ClientFrame frame = new ClientFrame();
+ frame.setSize(new Dimension(640, 480));
+ frame.setTitle("Make vertical, horizontal or diagonal line of 5 dots. "
+ + "Click mouse to set the dot.");
+ frame.validate();
+
+ // Center the window
+ Dimension screenSize = Toolkit.getDefaultToolkit().getScreenSize();
+ Dimension frameSize = frame.getSize();
+ if (frameSize.height > screenSize.height)
+ {
+ frameSize.height = screenSize.height;
+ }
+ if (frameSize.width > screenSize.width)
+ {
+ frameSize.width = screenSize.width;
+ }
+ frame.setLocation((screenSize.width - frameSize.width) / 2,
+ (screenSize.height - frameSize.height) / 2);
+ frame.setVisible(true);
+
+ // Set the ior.
+ try
+ {
+ if (OrbStarter.WRITE_URL_TO_FILE != null)
+ {
+ File saved_ior = new File(OrbStarter.WRITE_URL_TO_FILE);
+ if (saved_ior.exists())
+ {
+ FileReader f = new FileReader(saved_ior);
+ String s = new BufferedReader(f).readLine();
+ frame.taUrl.setText(s);
+ }
+ }
+ }
+ catch (Exception e)
+ {
+ // We will print the exception, because this is a demo program -
+ // expected to be modified by user.
+ e.printStackTrace();
+ }
+ }
+} \ No newline at end of file
diff --git a/examples/gnu/classpath/examples/CORBA/swing/x5/GameManager.java b/examples/gnu/classpath/examples/CORBA/swing/x5/GameManager.java
new file mode 100644
index 000000000..4d632e8bf
--- /dev/null
+++ b/examples/gnu/classpath/examples/CORBA/swing/x5/GameManager.java
@@ -0,0 +1,68 @@
+/* GameManager.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+ This file is part of GNU Classpath.
+
+ GNU Classpath is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2, or (at your option)
+ any later version.
+
+ GNU Classpath is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with GNU Classpath; see the file COPYING. If not, write to the
+ Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ 02110-1301 USA.
+
+ Linking this library statically or dynamically with other modules is
+ making a combined work based on this library. Thus, the terms and
+ conditions of the GNU General Public License cover the whole
+ combination.
+
+ As a special exception, the copyright holders of this library give you
+ permission to link this library with independent modules to produce an
+ executable, regardless of the license terms of these independent
+ modules, and to copy and distribute the resulting executable under
+ terms of your choice, provided that you also meet, for each linked
+ independent module, the terms and conditions of the license of that
+ module. An independent module is a module which is not derived from
+ or based on this library. If you modify this library, you may extend
+ this exception to your version of the library, but you are not
+ obligated to do so. If you do not wish to do so, delete this
+ exception statement from your version. */
+
+
+package gnu.classpath.examples.CORBA.swing.x5;
+
+import java.rmi.Remote;
+import java.rmi.RemoteException;
+
+/**
+ * The game manager interface.
+ *
+ * Defines the operations of the game server that connects two players into
+ * the game. The game server does not participate in the game itself.
+ *
+ * @author Audrius Meskauskas (AudriusA@Bioinformatics.org)
+ */
+public interface GameManager extends Remote
+{
+ /**
+ * Register the newPlayer as the person who is willing to play. When another
+ * player calls this method, the Manager connects them by calling
+ * {@link PlayerCommunicator#start_game}. The manager provides the partner
+ * and sets (randomly) the starting side.
+ */
+ void requestTheGame(Player newPlayer) throws RemoteException;
+
+ /**
+ * Unregister the player that left and is no longer waiting for a playing
+ * partner to come.
+ * @throws RemoteException
+ */
+ void unregister(Player player) throws RemoteException;
+} \ No newline at end of file
diff --git a/examples/gnu/classpath/examples/CORBA/swing/x5/GameManagerImpl.java b/examples/gnu/classpath/examples/CORBA/swing/x5/GameManagerImpl.java
new file mode 100644
index 000000000..fc449bc50
--- /dev/null
+++ b/examples/gnu/classpath/examples/CORBA/swing/x5/GameManagerImpl.java
@@ -0,0 +1,135 @@
+/* GameManagerImpl.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+ This file is part of GNU Classpath.
+
+ GNU Classpath is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2, or (at your option)
+ any later version.
+
+ GNU Classpath is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with GNU Classpath; see the file COPYING. If not, write to the
+ Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ 02110-1301 USA.
+
+ Linking this library statically or dynamically with other modules is
+ making a combined work based on this library. Thus, the terms and
+ conditions of the GNU General Public License cover the whole
+ combination.
+
+ As a special exception, the copyright holders of this library give you
+ permission to link this library with independent modules to produce an
+ executable, regardless of the license terms of these independent
+ modules, and to copy and distribute the resulting executable under
+ terms of your choice, provided that you also meet, for each linked
+ independent module, the terms and conditions of the license of that
+ module. An independent module is a module which is not derived from
+ or based on this library. If you modify this library, you may extend
+ this exception to your version of the library, but you are not
+ obligated to do so. If you do not wish to do so, delete this
+ exception statement from your version. */
+
+package gnu.classpath.examples.CORBA.swing.x5;
+
+import java.rmi.RemoteException;
+
+import org.omg.CORBA.ORB;
+import org.omg.CORBA.Object;
+
+/**
+ * The manager connects two players into the game.
+ *
+ * @author Audrius Meskauskas (AudriusA@Bioinformatics.org)
+ */
+public class GameManagerImpl
+ implements GameManager
+{
+ /**
+ * The game manager IOR.
+ */
+ static String ior;
+
+ /**
+ * The game manager ORB.
+ */
+ static ORB orb;
+
+ /**
+ * True if the manager started ok.
+ */
+ static boolean ok;
+
+ /**
+ * Another player that is already waiting for the game.
+ */
+ Player queuedPlayer = null;
+
+ public synchronized void requestTheGame(Player newPlayer)
+ throws RemoteException
+ {
+ System.out.println("Game requested");
+
+ if (queuedPlayer == null)
+ {
+ // No other player so far.
+ newPlayer.receive_chat(ChatConstants.GAME_SERVER,
+ "Request registered, waiting for the other player to come...");
+ System.out.println("Player queued.");
+ queuedPlayer = newPlayer;
+ }
+ else if (queuedPlayer.equals(newPlayer))
+ {
+ // The same player applies again.
+ newPlayer.receive_chat(ChatConstants.GAME_SERVER,
+ "No other player so far... Please wait.");
+ }
+ else
+ {
+ // As the queued player waited for the game, we allow him/her
+ // to start the game. This is a reward for waiting.
+ newPlayer.receive_chat(ChatConstants.GAME_SERVER,
+ "The other player is waiting. The game started, your "
+ + "partner begins...");
+ queuedPlayer.receive_chat(ChatConstants.GAME_SERVER,
+ "The other player arrived. Lets play, you begin the game now...");
+
+ newPlayer.start_game(queuedPlayer, false);
+ queuedPlayer.start_game(newPlayer, true);
+
+ queuedPlayer = null;
+ System.out.println("Players connected.");
+ }
+ }
+
+ /**
+ * Unregister the player who left and is no longer waiting for another side.
+ */
+ public void unregister(Player player)
+ throws RemoteException
+ {
+ if (queuedPlayer != null)
+ {
+ // We need to verify the identity of the player being unregistered.
+ // The stubs, being derived from the org.omg.CORBA.Object, have the
+ // method for this. This method compares the player host address,
+ // used port and the object key.
+ if (player instanceof Object && queuedPlayer instanceof Object)
+ {
+ Object a = (Object) player;
+ Object b = (Object) queuedPlayer;
+
+ if (a._is_equivalent(b))
+ queuedPlayer = null;
+ }
+ else
+ queuedPlayer = null;
+ }
+ System.out.println("Unregistering player");
+ }
+} \ No newline at end of file
diff --git a/examples/gnu/classpath/examples/CORBA/swing/x5/IorReader.java b/examples/gnu/classpath/examples/CORBA/swing/x5/IorReader.java
new file mode 100644
index 000000000..a976def74
--- /dev/null
+++ b/examples/gnu/classpath/examples/CORBA/swing/x5/IorReader.java
@@ -0,0 +1,124 @@
+/* IorReader.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+ This file is part of GNU Classpath.
+
+ GNU Classpath is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2, or (at your option)
+ any later version.
+
+ GNU Classpath is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with GNU Classpath; see the file COPYING. If not, write to the
+ Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ 02110-1301 USA.
+
+ Linking this library statically or dynamically with other modules is
+ making a combined work based on this library. Thus, the terms and
+ conditions of the GNU General Public License cover the whole
+ combination.
+
+ As a special exception, the copyright holders of this library give you
+ permission to link this library with independent modules to produce an
+ executable, regardless of the license terms of these independent
+ modules, and to copy and distribute the resulting executable under
+ terms of your choice, provided that you also meet, for each linked
+ independent module, the terms and conditions of the license of that
+ module. An independent module is a module which is not derived from
+ or based on this library. If you modify this library, you may extend
+ this exception to your version of the library, but you are not
+ obligated to do so. If you do not wish to do so, delete this
+ exception statement from your version. */
+
+
+package gnu.classpath.examples.CORBA.swing.x5;
+
+import java.io.File;
+import java.io.FileReader;
+import java.io.IOException;
+import java.io.InputStreamReader;
+import java.net.MalformedURLException;
+import java.net.URL;
+
+import org.omg.CORBA.BAD_PARAM;
+import org.omg.CORBA.DATA_CONVERSION;
+
+/**
+ * Reads the remote URL. Following formal/04-03-12, CORBA should be able to do
+ * this without the help of this class. However some popular class libraries
+ * are written using the older CORBA specifications and may not handle
+ * functionality, require by this game. This class substitutes the functionality,
+ * ensuring that these implementations will also start and we will be able
+ * to test the interoperability.
+ *
+ * @author Audrius Meskauskas (AudriusA@Bioinformatics.org)
+ */
+public class IorReader
+{
+ /**
+ * Read IOR from the remote URL.
+ */
+ public static String readUrl(String url)
+ {
+ URL u;
+ try
+ {
+ u = new URL(url);
+ }
+ catch (MalformedURLException mex)
+ {
+ throw new BAD_PARAM("Malformed URL: '" + url + "'");
+ }
+
+ try
+ {
+ InputStreamReader r = new InputStreamReader(u.openStream());
+
+ StringBuffer b = new StringBuffer();
+ int c;
+
+ while ((c = r.read()) > 0)
+ b.append((char) c);
+
+ return b.toString().trim();
+ }
+ catch (Exception exc)
+ {
+ DATA_CONVERSION d = new DATA_CONVERSION("Reading " + url + " failed.");
+ throw d;
+ }
+ }
+
+ /**
+ * Read IOR from the file in the local file system.
+ */
+ public static String readFile(String file)
+ {
+ File f = new File(file);
+ if (!f.exists())
+ {
+ DATA_CONVERSION err = new DATA_CONVERSION(f.getAbsolutePath()
+ + " does not exist.");
+ throw err;
+ }
+ try
+ {
+ char[] c = new char[(int) f.length()];
+ FileReader fr = new FileReader(f);
+ fr.read(c);
+ fr.close();
+ return new String(c).trim();
+ }
+ catch (IOException ex)
+ {
+ DATA_CONVERSION d = new DATA_CONVERSION();
+ d.initCause(ex);
+ throw (d);
+ }
+ }
+}
diff --git a/examples/gnu/classpath/examples/CORBA/swing/x5/OrbStarter.java b/examples/gnu/classpath/examples/CORBA/swing/x5/OrbStarter.java
new file mode 100644
index 000000000..3852945c6
--- /dev/null
+++ b/examples/gnu/classpath/examples/CORBA/swing/x5/OrbStarter.java
@@ -0,0 +1,236 @@
+/* OrbStarter.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+ This file is part of GNU Classpath.
+
+ GNU Classpath is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2, or (at your option)
+ any later version.
+
+ GNU Classpath is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with GNU Classpath; see the file COPYING. If not, write to the
+ Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ 02110-1301 USA.
+
+ Linking this library statically or dynamically with other modules is
+ making a combined work based on this library. Thus, the terms and
+ conditions of the GNU General Public License cover the whole
+ combination.
+
+ As a special exception, the copyright holders of this library give you
+ permission to link this library with independent modules to produce an
+ executable, regardless of the license terms of these independent
+ modules, and to copy and distribute the resulting executable under
+ terms of your choice, provided that you also meet, for each linked
+ independent module, the terms and conditions of the license of that
+ module. An independent module is a module which is not derived from
+ or based on this library. If you modify this library, you may extend
+ this exception to your version of the library, but you are not
+ obligated to do so. If you do not wish to do so, delete this
+ exception statement from your version. */
+
+
+package gnu.classpath.examples.CORBA.swing.x5;
+
+import java.rmi.RemoteException;
+import java.util.Properties;
+
+import javax.rmi.PortableRemoteObject;
+import javax.rmi.CORBA.Tie;
+
+import org.omg.CORBA.ORB;
+import org.omg.PortableServer.POA;
+import org.omg.PortableServer.POAHelper;
+import org.omg.PortableServer.Servant;
+
+/**
+ * Starts the ORBs, involved into this application.
+ *
+ * @author Audrius Meskauskas (AudriusA@Bioinformatics.org)
+ */
+public class OrbStarter
+{
+ /**
+ * The game manager name server port. This server allows to access the game
+ * manager by host (IP) and port rather than by the rather long IOR string.
+ */
+ static int MANAGER_NAMER_PORT = 1500;
+
+ /**
+ * The used port range (understood and used by GNU Classpath only).
+ */
+ static String USED_PORT_RANGE = "1501-1503";
+
+ /**
+ * Specify the file where under start the game manager writes its IOR.
+ * You may specify the path if the game manager and player clients have
+ * access to some share file system or if you prefer to write IOR to
+ * floppy and then read from the floppy on the client side. Both clients
+ * and server will use this constant. Set to null not to write the IOR.
+ */
+ static String WRITE_URL_TO_FILE = "game_manager_ior.txt";
+
+ /**
+ * Start the manager ORB.
+ * @return the manager URL if it starts.
+ */
+ public static String startManager(final String[] args)
+ {
+ GameManagerImpl.ior = null;
+ GameManagerImpl.ok = false;
+
+ final Properties p = new Properties();
+ p.put("gnu.CORBA.ListenerPort", USED_PORT_RANGE);
+
+ try
+ {
+ new Thread()
+ {
+ public void run()
+ {
+ try
+ {
+ GameManagerImpl.orb = ORB.init(args, p);
+
+ // Obtain the root poa:
+ POA rootPOA = POAHelper.narrow(GameManagerImpl.orb.resolve_initial_references("RootPOA"));
+
+ GameManagerImpl impl = new GameManagerImpl();
+
+ PortableRemoteObject.exportObject(impl);
+
+ // Construct the tie that is also the servant.
+ Tie tie = new _GameManagerImpl_Tie();
+
+ // Set the invocation target for this tie.
+ tie.setTarget(impl);
+
+ // Obtain the reference to the corresponding CORBA object:
+ org.omg.CORBA.Object object = rootPOA.servant_to_reference((Servant) tie);
+
+ GameManagerImpl.ok = true;
+
+ // Activate the root POA.
+ rootPOA.the_POAManager().activate();
+
+ // Get the IOR URL that must be passed to clients.
+ GameManagerImpl.ior = GameManagerImpl.orb.object_to_string(object);
+
+ GameManagerImpl.orb.run();
+ }
+ catch (Exception exc)
+ {
+ exc.printStackTrace();
+ GameManagerImpl.ior = "Unable to start the ORB: " + exc;
+ }
+ }
+ }.start();
+
+ // Wait the thread to enter orb.run.
+ long t = System.currentTimeMillis();
+ while (GameManagerImpl.ior == null
+ && System.currentTimeMillis() - t < 20000)
+ {
+ Thread.sleep(100);
+ }
+
+ return GameManagerImpl.ior;
+ }
+ catch (Exception e)
+ {
+ e.printStackTrace();
+ return "Exception: " + e;
+ }
+ }
+
+ /**
+ * Start the client ORB.
+ */
+ public static String startPlayer(final Player player, final PlayingDesk desk)
+ {
+ desk.ior = null;
+ desk.ok = false;
+
+ final Properties p = new Properties();
+ p.put("gnu.CORBA.ListenerPort", USED_PORT_RANGE);
+
+ try
+ {
+ new Thread()
+ {
+ public void run()
+ {
+ try
+ {
+ desk.orb = ORB.init(new String[0], p);
+
+ POA rootPOA = POAHelper.narrow(desk.orb.resolve_initial_references("RootPOA"));
+ rootPOA.the_POAManager().activate();
+
+ // Construct the tie.
+ Tie tie = new _PlayerImpl_Tie();
+
+ // Set the implementing class (invocation target).
+ tie.setTarget(new PlayerImpl());
+
+ // Connect the tie as POA servant.
+ org.omg.CORBA.Object object = rootPOA.servant_to_reference((Servant) tie);
+
+ // Get the stringified reference.
+ desk.ior = desk.orb.object_to_string(object);
+
+ // Mark that the object was created OK.
+ desk.ok = true;
+ desk.orb.run();
+ }
+ catch (Exception exc)
+ {
+ exc.printStackTrace();
+ desk.ior = "Unable to start the ORB: " + exc;
+ }
+ }
+ }.start();
+
+ long t = System.currentTimeMillis();
+ while (desk.ior == null && System.currentTimeMillis() - t < 20000)
+ {
+ Thread.sleep(100);
+ }
+ }
+ catch (Exception e)
+ {
+ e.printStackTrace();
+ return "Exception: " + e;
+ }
+
+ // Add shutdown hook to unregister from the manager.
+ Runtime.getRuntime().addShutdownHook(new Thread()
+ {
+ public void run()
+ {
+ if (desk.manager != null && player != null)
+ {
+ try
+ {
+ desk.manager.unregister(player);
+ }
+ catch (RemoteException ex)
+ {
+ // We will print the exception because this is a demo
+ // application that
+ // may be modified for learning purposes.
+ ex.printStackTrace();
+ }
+ desk.manager = null;
+ }
+ }
+ });
+ return desk.ior;
+ }
+}
diff --git a/examples/gnu/classpath/examples/CORBA/swing/x5/Player.java b/examples/gnu/classpath/examples/CORBA/swing/x5/Player.java
new file mode 100644
index 000000000..ff5624b79
--- /dev/null
+++ b/examples/gnu/classpath/examples/CORBA/swing/x5/Player.java
@@ -0,0 +1,96 @@
+/* Player.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+ This file is part of GNU Classpath.
+
+ GNU Classpath is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2, or (at your option)
+ any later version.
+
+ GNU Classpath is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with GNU Classpath; see the file COPYING. If not, write to the
+ Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ 02110-1301 USA.
+
+ Linking this library statically or dynamically with other modules is
+ making a combined work based on this library. Thus, the terms and
+ conditions of the GNU General Public License cover the whole
+ combination.
+
+ As a special exception, the copyright holders of this library give you
+ permission to link this library with independent modules to produce an
+ executable, regardless of the license terms of these independent
+ modules, and to copy and distribute the resulting executable under
+ terms of your choice, provided that you also meet, for each linked
+ independent module, the terms and conditions of the license of that
+ module. An independent module is a module which is not derived from
+ or based on this library. If you modify this library, you may extend
+ this exception to your version of the library, but you are not
+ obligated to do so. If you do not wish to do so, delete this
+ exception statement from your version. */
+
+package gnu.classpath.examples.CORBA.swing.x5;
+
+import java.awt.Point;
+
+import java.rmi.Remote;
+import java.rmi.RemoteException;
+
+/**
+ * Defines remote methods that are invoked by another player or by the
+ * challenge server.
+ *
+ * @author Audrius Meskauskas (AudriusA@Bioinformatics.org)
+ */
+public interface Player extends Remote
+{
+ /**
+ * Receive the invitation to play from the patner or the game manager.
+ *
+ * @param address the address (host and port) of the remote partner.
+ * @param youStart if true, the game manager instructs to start
+ * the game first (another side is instructed to start the game second).
+ *
+ * @return true on success.
+ */
+ boolean start_game(Player otherPlayer, boolean youStart)
+ throws RemoteException;
+
+ /**
+ * Get the state of the local player (one of the constants, defined
+ * in this interface).
+ */
+ int get_current_state() throws RemoteException;
+
+ /**
+ * Receive the chat message from the friend or challenge server (remote).
+ * Possible at any state, always remote.
+ *
+ * @param color the color code, used to highlight the message.
+ * @param text the message text.
+ */
+ void receive_chat(byte color, String test) throws RemoteException;
+
+ /**
+ * Indicated that the remote side leaves the game (capitulating).
+ */
+ void disconnect() throws RemoteException;
+
+ /**
+ * Receive friends move (possible at I_WAIT_FOR_YOUR_MOVE).
+ *
+ * @param x grid position.
+ * @param y grid position.
+ *
+ * @param sessionId the session id, must match (otherwise the call is ignored).
+ * @param victory if not a null, the friend thinks that it has won, the parameter
+ * containing the ends of the builded line.
+ */
+ void receive_move(int x, int y, Point[] victory) throws RemoteException;
+} \ No newline at end of file
diff --git a/examples/gnu/classpath/examples/CORBA/swing/x5/PlayerImpl.java b/examples/gnu/classpath/examples/CORBA/swing/x5/PlayerImpl.java
new file mode 100644
index 000000000..c30f7d51a
--- /dev/null
+++ b/examples/gnu/classpath/examples/CORBA/swing/x5/PlayerImpl.java
@@ -0,0 +1,275 @@
+/* PlayerImpl.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+ This file is part of GNU Classpath.
+
+ GNU Classpath is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2, or (at your option)
+ any later version.
+
+ GNU Classpath is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with GNU Classpath; see the file COPYING. If not, write to the
+ Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ 02110-1301 USA.
+
+ Linking this library statically or dynamically with other modules is
+ making a combined work based on this library. Thus, the terms and
+ conditions of the GNU General Public License cover the whole
+ combination.
+
+ As a special exception, the copyright holders of this library give you
+ permission to link this library with independent modules to produce an
+ executable, regardless of the license terms of these independent
+ modules, and to copy and distribute the resulting executable under
+ terms of your choice, provided that you also meet, for each linked
+ independent module, the terms and conditions of the license of that
+ module. An independent module is a module which is not derived from
+ or based on this library. If you modify this library, you may extend
+ this exception to your version of the library, but you are not
+ obligated to do so. If you do not wish to do so, delete this
+ exception statement from your version. */
+
+
+package gnu.classpath.examples.CORBA.swing.x5;
+
+import java.awt.Color;
+import java.awt.Point;
+
+import java.rmi.RemoteException;
+
+/**
+ * The implementation of the PlayerCommunicator, providing the local
+ * functionality. Apart remote methods, the class also defines some local
+ * methods, needed for the co-ordinated work with the game user interface.
+ *
+ * @author Audrius Meskauskas (AudriusA@Bioinformatics.org)
+ */
+public class PlayerImpl
+ implements Player, State
+{
+ /**
+ * The playing table.
+ */
+ PlayingDesk desk;
+
+ /**
+ * The state of this player (one of the constants, defined in the player
+ * interface.
+ */
+ private int state = DISCONNECTED;
+
+ /**
+ * The other player.
+ */
+ Player partner;
+
+ /**
+ * Called when the local player refuses to continue the game.
+ */
+ public void leave()
+ {
+ try
+ {
+ if (state == I_THINK || state == I_WAIT_FOR_YOUR_MOVE)
+ {
+ partner.receive_chat(ChatConstants.REMOTE_PLAYER,
+ "Your partner has left the game.");
+ partner.disconnect();
+ }
+ else if (state == State.QUEUED)
+ {
+ if (desk.manager != null)
+ desk.manager.unregister(desk.player);
+ receive_chat(ChatConstants.SYSTEM,
+ "Do not be so pessimistic, try to play first!");
+ }
+ set_current_state(State.DISCONNECTED);
+
+ desk.frame.bChat.setEnabled(false);
+ desk.frame.bLeave.setEnabled(false);
+ desk.frame.bConnect.setEnabled(true);
+ desk.frame.taUrl.setText(desk.frame.mior);
+ }
+ catch (RemoteException ex)
+ {
+ // We will print the exception because this is a demo application that
+ // may be modified for learning purposes.
+ ex.printStackTrace();
+ }
+ }
+
+ /**
+ * Called when we make the move. The PlayingTable is responsible for checking
+ * the correctness of the move and detecting the victory.
+ *
+ * @param x x position of the new dot.
+ * @param y y position of the new dot.
+ *
+ * @param victory array of two memebers, representing the endpoints of the
+ * drawn line (victory detected) or null if no such yet exists.
+ */
+ public void we_move(int x, int y, Point[] victory)
+ {
+ try
+ {
+ set_current_state(I_WAIT_FOR_YOUR_MOVE);
+ partner.receive_move(x, y, victory);
+ }
+ catch (RemoteException ex)
+ {
+ // We will print the exception because this is a demo application that
+ // may be modified for learning purposes.
+ ex.printStackTrace();
+
+ state = ERROR;
+ }
+ }
+
+ /**
+ * Set the current state.
+ */
+ public void set_current_state(int new_state)
+ {
+ state = new_state;
+
+ if (state == DISCONNECTED)
+ {
+ setStatus("Disconnected");
+ }
+ else if (state == I_THINK)
+ {
+ setStatus("Our move");
+ }
+ else if (state == I_WAIT_FOR_YOUR_MOVE)
+ {
+ setStatus("Partner's move");
+ }
+ else if (state == ERROR)
+ {
+ setStatus("Error.");
+ }
+ else if (state == I_HAVE_LOST)
+ {
+ setStatus("We lost");
+ }
+ else if (state == I_HAVE_WON)
+ {
+ setStatus("Victory");
+ }
+ else if (state == QUEUED)
+ {
+ setStatus("Queued");
+ }
+ else
+ {
+ setStatus("State " + state);
+ }
+
+ boolean connected = state != State.DISCONNECTED;
+
+ desk.frame.bConnect.setEnabled(!connected && state != State.QUEUED);
+ desk.frame.bReset.setEnabled(connected);
+ desk.frame.bLeave.setEnabled(connected);
+ desk.frame.bChat.setEnabled(connected);
+ }
+
+ /**
+ * Show the state in the status line.
+ */
+ public void setStatus(String status)
+ {
+ desk.frame.lbState.setText(status);
+ }
+
+ /**
+ * Receive the invitation to play from the patner or the game manager.
+ *
+ * @param address the address (host and port) of the remote partner.
+ * @param youStart if true, the game manager instructs to start the game first
+ * (another side is instructed to start the game second).
+ *
+ * Game server may also chat a little bit with both players, saying that the
+ * game has started.
+ *
+ * @return true on success.
+ */
+ public boolean start_game(Player otherPlayer, boolean youStart)
+ throws RemoteException
+ {
+ partner = otherPlayer;
+ desk.reset();
+
+ if (youStart)
+ {
+ set_current_state(I_THINK);
+ }
+ else
+ {
+ set_current_state(I_WAIT_FOR_YOUR_MOVE);
+ }
+
+ desk.frame.taUrl.setText("");
+
+ return true;
+ }
+
+ /**
+ * Get the state of the local player (one of the constants, defined in this
+ * interface).
+ */
+ public int get_current_state()
+ throws RemoteException
+ {
+ return state;
+ }
+
+ /**
+ * Receive the chat message from the friend or challenge server (remote).
+ * Possible at any state, always remote.
+ *
+ * @param color the color code, used to highlight the message.
+ * @param text the message text.
+ */
+ public void receive_chat(byte color, String text)
+ throws RemoteException
+ {
+ if (color >= ChatConstants.colors.length)
+ color = ChatConstants.REMOTE_PLAYER;
+
+ desk.frame.talk(ChatConstants.colors[color], text);
+ }
+
+ /**
+ * Indicated that the remote side leaves the game (capitulating).
+ */
+ public void disconnect()
+ throws RemoteException
+ {
+ desk.frame.talk(Color.red, "The partner leaves the game.");
+ partner = null;
+ set_current_state(DISCONNECTED);
+
+ desk.frame.taUrl.setText(desk.frame.mior);
+ }
+
+ /**
+ * Receive friends move (possible at I_WAIT_FOR_YOUR_MOVE).
+ *
+ * @param x grid position.
+ * @param y grid position.
+ * @param victory if not a null, the friend thinks that it has won, the
+ * parameter containing the ends of the builded line.
+ */
+ public void receive_move(int x, int y, Point[] victory)
+ throws RemoteException
+ {
+ // The state changes are handled by the PlayingTable
+ desk.friendsMove(x, y, victory);
+ }
+} \ No newline at end of file
diff --git a/examples/gnu/classpath/examples/CORBA/swing/x5/PlayingDesk.java b/examples/gnu/classpath/examples/CORBA/swing/x5/PlayingDesk.java
new file mode 100644
index 000000000..83178f936
--- /dev/null
+++ b/examples/gnu/classpath/examples/CORBA/swing/x5/PlayingDesk.java
@@ -0,0 +1,512 @@
+/* PlayingDesk.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+ This file is part of GNU Classpath.
+
+ GNU Classpath is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2, or (at your option)
+ any later version.
+
+ GNU Classpath is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with GNU Classpath; see the file COPYING. If not, write to the
+ Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ 02110-1301 USA.
+
+ Linking this library statically or dynamically with other modules is
+ making a combined work based on this library. Thus, the terms and
+ conditions of the GNU General Public License cover the whole
+ combination.
+
+ As a special exception, the copyright holders of this library give you
+ permission to link this library with independent modules to produce an
+ executable, regardless of the license terms of these independent
+ modules, and to copy and distribute the resulting executable under
+ terms of your choice, provided that you also meet, for each linked
+ independent module, the terms and conditions of the license of that
+ module. An independent module is a module which is not derived from
+ or based on this library. If you modify this library, you may extend
+ this exception to your version of the library, but you are not
+ obligated to do so. If you do not wish to do so, delete this
+ exception statement from your version. */
+
+
+package gnu.classpath.examples.CORBA.swing.x5;
+
+import java.awt.Color;
+import java.awt.Graphics;
+import java.awt.Point;
+import java.awt.event.MouseEvent;
+import java.awt.event.MouseListener;
+import java.rmi.RemoteException;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Iterator;
+
+import javax.swing.JComponent;
+
+import org.omg.CORBA.ORB;
+
+/**
+ * Manages actions, related to the game rules and also does all painting.
+ *
+ * @author Audrius Meskauskas, Lithuania (AudriusA@Bioinformatics.org)
+ */
+public class PlayingDesk
+ extends JComponent
+ implements MouseListener, State
+{
+ /**
+ * Use serialVersionUID for interoperability.
+ */
+ private static final long serialVersionUID = 1;
+
+ /**
+ * Indicates that the field point state is the red oval.
+ */
+ public static final int RED = 0;
+
+ /**
+ * Indicates that the field point state is the black cross.
+ */
+ public static final int BLACK = 1;
+
+ /**
+ * Indicates that the field point state is the hint, suggested by the fan.
+ */
+ public static final int HINT = 2;
+
+ /**
+ * The access to the main frame methods.
+ */
+ ClientFrame frame;
+
+ /**
+ * The access to the player communicator.
+ */
+ PlayerImpl player;
+
+ /**
+ * The game manager.
+ */
+ GameManager manager;
+
+ /**
+ * The player ORB.
+ */
+ ORB orb;
+
+ /**
+ * The player IOR.
+ */
+ String ior;
+
+ /**
+ * True if the player ORB started ok.
+ */
+ boolean ok;
+
+ /**
+ * The grid spacing.
+ */
+ static int W = 16;
+
+ /**
+ * The radius of the dots being painted.
+ */
+ static int R = W / 3;
+
+ /**
+ * The collection of the red dots.
+ */
+ ArrayList reds = new ArrayList();
+
+ /**
+ * The collection of the black dots.
+ */
+ ArrayList blacks = new ArrayList();
+
+ /**
+ * The array of hints.
+ */
+ ArrayList hints = new ArrayList();
+
+ /**
+ * When the game is completed, obtains the value of the two end points of the
+ * created line.
+ */
+ Point[] endOfGame;
+
+ public PlayingDesk()
+ {
+ try
+ {
+ player = new PlayerImpl();
+ player.desk = this;
+
+ OrbStarter.startPlayer(player, this);
+
+ jbInit();
+ }
+ catch (Exception e)
+ {
+ e.printStackTrace();
+ }
+ }
+
+ /**
+ * Paint this component.
+ */
+ public void paintComponent(Graphics g)
+ {
+ int w = getWidth();
+ int h = getHeight();
+
+ g.setColor(Color.white);
+ g.fillRect(0, 0, w, h);
+
+ drawGrid(w, h, g);
+ drawFigures(g);
+ }
+
+ /**
+ * Check maybe a game is finished after setting the point N
+ */
+ public Point[] checkFinished(Collection x, Point N)
+ {
+ Iterator iter = x.iterator();
+ Point p;
+
+ // The victory, if happens, must occur inside these boundaries:
+ int ax = N.x - 5;
+ int bx = N.x + 5;
+
+ int ay = N.y - 5;
+ int by = N.y + 5;
+
+ while (iter.hasNext())
+ {
+ p = (Point) iter.next();
+
+ if (p.x > ax && p.x < bx && p.y > ay && p.y < by)
+ {
+ // Check the vertical line down
+ if (pointPresent(p.x, p.y + 1, x))
+ if (pointPresent(p.x, p.y + 2, x))
+ if (pointPresent(p.x, p.y + 3, x))
+ if (pointPresent(p.x, p.y + 4, x))
+ return new Point[] { p, new Point(p.x, p.y + 4) };
+
+ // Check the horizontal line left
+ if (pointPresent(p.x + 1, p.y, x))
+ if (pointPresent(p.x + 2, p.y, x))
+ if (pointPresent(p.x + 3, p.y, x))
+ if (pointPresent(p.x + 4, p.y, x))
+ return new Point[] { p, new Point(p.x + 4, p.y) };
+
+ // Check the diagonal line right down.
+ if (pointPresent(p.x + 1, p.y + 1, x))
+ if (pointPresent(p.x + 2, p.y + 2, x))
+ if (pointPresent(p.x + 3, p.y + 3, x))
+ if (pointPresent(p.x + 4, p.y + 4, x))
+ return new Point[] { p, new Point(p.x + 4, p.y + 4) };
+
+ // Check the diagonal line left down.
+ if (pointPresent(p.x - 1, p.y + 1, x))
+ if (pointPresent(p.x - 2, p.y + 2, x))
+ if (pointPresent(p.x - 3, p.y + 3, x))
+ if (pointPresent(p.x - 4, p.y + 4, x))
+ return new Point[] { p, new Point(p.x - 4, p.y + 4) };
+ }
+ }
+ return null;
+ }
+
+ /**
+ * Called when the "end of the game" situation is detected.
+ */
+ public void drawFinishLine(int xa, int ya, int xb, int yb, Graphics g)
+ {
+ g.setColor(Color.blue);
+
+ int hW = W / 2;
+ g.drawLine(xa * W + hW, ya * W + hW, xb * W + hW, yb * W + hW);
+ }
+
+ /**
+ * Check for the presence of the given point in the collection.
+ */
+ public final boolean pointPresent(int x, int y, Collection in)
+ {
+ Iterator iter = in.iterator();
+ Point p;
+ while (iter.hasNext())
+ {
+ p = (Point) iter.next();
+ if (p.x == x && p.y == y)
+ return true;
+ }
+ return false;
+ }
+
+ public void drawGrid(int w, int h, Graphics g)
+ {
+ g.setColor(Color.lightGray);
+
+ // Draw vertical lines:
+ for (int x = 0; x < w; x += W)
+ {
+ g.drawLine(x, 0, x, h);
+ }
+
+ // Draw horizontal lines:
+ for (int y = 0; y < h; y += W)
+ {
+ g.drawLine(0, y, w, y);
+ }
+
+ g.setColor(Color.gray);
+ g.drawRect(0,0, frame.DESK_SIZE.width, frame.DESK_SIZE.height);
+ g.drawRect(0,0, frame.DESK_SIZE.width+3, frame.DESK_SIZE.height+3);
+ }
+
+ public void drawFigures(Graphics g)
+ {
+ g.setColor(Color.red);
+ drawDots(reds, g, RED);
+
+ g.setColor(Color.black);
+ drawDots(blacks, g, BLACK);
+
+ g.setColor(Color.lightGray);
+ drawDots(hints, g, HINT);
+
+ if (endOfGame != null)
+ drawFinishLine(endOfGame[0].x, endOfGame[0].y, endOfGame[1].x,
+ endOfGame[1].y, g);
+ }
+
+ public Point makePoint(int x, int y)
+ {
+ return new Point(x / W, y / W);
+ }
+
+ /**
+ * Draw a collection of dots (the collor must be set before calling the
+ * method).
+ */
+ public void drawDots(Collection dots, Graphics g, int mode)
+ {
+ Iterator iter = dots.iterator();
+ int x;
+ int y;
+
+ int hW = W / 2;
+ int RR = R * 2;
+ int hR = R / 2;
+ Point p;
+ while (iter.hasNext())
+ {
+ p = (Point) iter.next();
+ x = p.x * W + hW;
+ y = p.y * W + hW;
+
+ if (mode == RED)
+ g.drawOval(x - R, y - R, RR, RR);
+ else if (mode == BLACK)
+ {
+ g.drawLine(x - R, y - R, x + R, y + R);
+ g.drawLine(x - R, y + R, x + R, y - R);
+ }
+ else
+ {
+ // Hint.
+ g.drawOval(x - hR, y - hR, R, R);
+ }
+ }
+ }
+
+ private void jbInit()
+ throws Exception
+ {
+ addMouseListener(this);
+ }
+
+ public void mouseClicked(MouseEvent e)
+ {
+ try
+ {
+ int state = player.get_current_state();
+
+ // Check if the state is correct.
+ if (state == I_WAIT_FOR_YOUR_MOVE)
+ {
+ frame.talk(Color.black,
+ "It is now time for our partner's move, not ours. Please wait.");
+ }
+ else if (state == DISCONNECTED)
+ {
+ frame.talk(Color.black,
+ "We are not connected to the playing partner yet.");
+ }
+ else if (state == I_HAVE_LOST)
+ {
+ frame.talk(Color.black,
+ "We have already lost this battle, but why not to try again?");
+ }
+ else if (state == I_HAVE_WON)
+ {
+ frame.talk(Color.black,
+ "The victory is ours, nothing more to do here.");
+ }
+ else if (player.partner == null)
+ frame.talk(Color.black, "No other player so far.");
+ else
+ {
+ int x = e.getX();
+ int y = e.getY();
+
+ if (x>frame.DESK_SIZE.width ||
+ y>frame.DESK_SIZE.height)
+ {
+ frame.talk(Color.black,"Outside the game area.");
+ return;
+ }
+
+ Point p = makePoint(x, y);
+
+ // Ignore clicks on the occupied cells.
+ if (pointPresent(p.x, p.y, reds)
+ || (pointPresent(p.x, p.y, blacks)))
+ {
+ frame.talk(Color.black,
+ "This is against the rules, select the unoccupied cell.");
+ return;
+ }
+
+ reds.add(p);
+
+ endOfGame = checkFinished(reds, p);
+ repaint();
+
+ if (endOfGame != null)
+ {
+ frame.talk(Color.red, "Our move " + p.x + "-" + p.y
+ + " and we win!");
+ player.set_current_state(I_HAVE_WON);
+ }
+ else
+ {
+ frame.talk(Color.black, "Our move " + p.x + "-" + p.y
+ + ". Waiting for the other side move...");
+ player.set_current_state(I_WAIT_FOR_YOUR_MOVE);
+ }
+
+ player.partner.receive_move(p.x, p.y, endOfGame);
+ }
+ }
+ catch (RemoteException ex)
+ {
+ // We will print the exception because this is a demo application
+ // that may be modified for learning purposes.
+ ex.printStackTrace();
+ }
+ }
+
+ /**
+ * Handle the move of the other playing side.
+ */
+ public void friendsMove(int x, int y, Point[] victory)
+ {
+ try
+ {
+ int state = player.get_current_state();
+ if (state != I_WAIT_FOR_YOUR_MOVE || pointPresent(x, y, blacks))
+ {
+ stateFailed("Move " + x + "-" + y);
+ }
+ else
+ {
+ blacks.add(new Point(x, y));
+ repaint();
+
+ if (victory != null)
+ {
+ frame.talk(Color.red,
+ " We have lost this time, unfortunately..");
+ player.set_current_state(I_HAVE_LOST);
+ endOfGame = victory;
+ }
+ else
+ {
+ frame.talk(Color.black, "Partner goes " + x + "-" + y
+ + ". Your move?");
+ player.set_current_state(I_THINK);
+ }
+ }
+ }
+ catch (RemoteException rex)
+ {
+ rex.printStackTrace();
+ }
+ }
+
+ /**
+ * Prepare for the new game.
+ */
+ public void reset()
+ {
+ blacks.clear();
+ reds.clear();
+ hints.clear();
+ endOfGame = null;
+ repaint();
+ }
+
+ public void mouseEntered(MouseEvent m)
+ {
+ // Nothing to do.
+ }
+
+ public void mousePressed(MouseEvent m)
+ {
+ // Nothing to do.
+ }
+
+ public void mouseReleased(MouseEvent m)
+ {
+ // Nothing to do.
+ }
+
+ public void mouseExited(MouseEvent m)
+ {
+ // Nothing to do.
+ }
+
+ /**
+ * The systems detected the error conditions. The game cannot continue (the
+ * chat is still possible).
+ */
+ public void stateFailed(String reason)
+ {
+ try
+ {
+ player.receive_chat(ChatConstants.REMOTE_PLAYER,
+ "Wrong move, game cannot continue (our state was "
+ + player.get_current_state() + ")");
+ frame.talk(Color.red, "The remote side violates communicating rules.");
+ player.set_current_state(State.ERROR);
+ }
+ catch (RemoteException ex)
+ {
+ // We will print the exception because this is a demo application
+ // that may be modified for learning purposes.
+ ex.printStackTrace();
+ }
+ }
+} \ No newline at end of file
diff --git a/examples/gnu/classpath/examples/CORBA/swing/x5/State.java b/examples/gnu/classpath/examples/CORBA/swing/x5/State.java
new file mode 100644
index 000000000..7285396cd
--- /dev/null
+++ b/examples/gnu/classpath/examples/CORBA/swing/x5/State.java
@@ -0,0 +1,82 @@
+/* State.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+ This file is part of GNU Classpath.
+
+ GNU Classpath is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2, or (at your option)
+ any later version.
+
+ GNU Classpath is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with GNU Classpath; see the file COPYING. If not, write to the
+ Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ 02110-1301 USA.
+
+ Linking this library statically or dynamically with other modules is
+ making a combined work based on this library. Thus, the terms and
+ conditions of the GNU General Public License cover the whole
+ combination.
+
+ As a special exception, the copyright holders of this library give you
+ permission to link this library with independent modules to produce an
+ executable, regardless of the license terms of these independent
+ modules, and to copy and distribute the resulting executable under
+ terms of your choice, provided that you also meet, for each linked
+ independent module, the terms and conditions of the license of that
+ module. An independent module is a module which is not derived from
+ or based on this library. If you modify this library, you may extend
+ this exception to your version of the library, but you are not
+ obligated to do so. If you do not wish to do so, delete this
+ exception statement from your version. */
+
+
+package gnu.classpath.examples.CORBA.swing.x5;
+
+/**
+ * Defines the states in that the player can be.
+ *
+ * @author Audrius Meskauskas (AudriusA@Bioinformatics.org)
+ */
+public interface State {
+ /**
+ * The initial ("disconnected") state.
+ */
+ int DISCONNECTED = 0;
+
+ /**
+ * The state, indicating that the player has been queued for the game and
+ * waiting for the partner to come.
+ */
+ int QUEUED = 1;
+
+ /**
+ * The "my move" state.
+ */
+ int I_THINK = 2;
+
+ /**
+ * The "friend's move" state.
+ */
+ int I_WAIT_FOR_YOUR_MOVE = 3;
+
+ /**
+ * States that we have won.
+ */
+ int I_HAVE_WON = 4;
+
+ /**
+ * States that we have lost.
+ */
+ int I_HAVE_LOST = 5;
+
+ /**
+ * The "inconsistent" state when it is not possible to continue the game.
+ */
+ int ERROR = -1;
+} \ No newline at end of file
diff --git a/examples/gnu/classpath/examples/CORBA/swing/x5/X5Server.java b/examples/gnu/classpath/examples/CORBA/swing/x5/X5Server.java
new file mode 100644
index 000000000..2ef9241c5
--- /dev/null
+++ b/examples/gnu/classpath/examples/CORBA/swing/x5/X5Server.java
@@ -0,0 +1,175 @@
+/* GameManagerAddressServer.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+ This file is part of GNU Classpath.
+
+ GNU Classpath is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2, or (at your option)
+ any later version.
+
+ GNU Classpath is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with GNU Classpath; see the file COPYING. If not, write to the
+ Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ 02110-1301 USA.
+
+ Linking this library statically or dynamically with other modules is
+ making a combined work based on this library. Thus, the terms and
+ conditions of the GNU General Public License cover the whole
+ combination.
+
+ As a special exception, the copyright holders of this library give you
+ permission to link this library with independent modules to produce an
+ executable, regardless of the license terms of these independent
+ modules, and to copy and distribute the resulting executable under
+ terms of your choice, provided that you also meet, for each linked
+ independent module, the terms and conditions of the license of that
+ module. An independent module is a module which is not derived from
+ or based on this library. If you modify this library, you may extend
+ this exception to your version of the library, but you are not
+ obligated to do so. If you do not wish to do so, delete this
+ exception statement from your version. */
+
+
+package gnu.classpath.examples.CORBA.swing.x5;
+
+import java.io.BufferedWriter;
+import java.io.File;
+import java.io.FileWriter;
+import java.io.IOException;
+import java.io.OutputStream;
+import java.net.InetAddress;
+import java.net.ServerSocket;
+import java.net.Socket;
+
+/**
+ * The main executable class of the game manager server.
+ *
+ * The manager address server returns the IOR address string of the game
+ * manager. Hence the user does not need to enter the rather long IOR address
+ * string and only needs to specify the host and port of the machine where the
+ * game manager is running.
+ *
+ * The manager address server starts the main game manager as well.
+ *
+ * This server acts as a HTTP server that always returns the same response. This
+ * primitive functionality is sufficient for its task.
+ *
+ * The more complex CORBA applications should use the name service instead. We
+ * do not use the name service as this would require to start additional
+ * external application, specific for the different java platforms.
+ *
+ * @author Audrius Meskauskas (AudriusA@Bioinformatics.org)
+ */
+public class X5Server
+{
+ /**
+ * Start the game manager.
+ */
+ public static void main(String[] args)
+ {
+ // Start the game manager, write the IOR to the agreed location.
+ OrbStarter.startManager(args);
+
+ if (!GameManagerImpl.ok)
+ {
+ System.out.println("Unable to start the game manager:");
+ System.exit(1);
+ }
+
+ // Print the IOR.
+ System.out.println(GameManagerImpl.ior);
+
+ String manager_address = null;
+
+ // Start the game manager server.
+ ServerSocket nameServer = null;
+ try
+ {
+ nameServer = new ServerSocket(OrbStarter.MANAGER_NAMER_PORT);
+
+ System.out.println("The game manager is listening at:");
+ manager_address = "http://"
+ + InetAddress.getLocalHost().getHostAddress() + ":"
+ + nameServer.getLocalPort();
+
+ System.out.println(manager_address);
+
+ System.out.println("Enter this address to the "
+ + "input field of the game client.");
+
+ System.out.println("Use ^C to stop the manager.");
+ }
+ catch (Exception ex)
+ {
+ System.out.println("The port " + OrbStarter.MANAGER_NAMER_PORT
+ + " is not available. The game manager namer will not start.");
+ System.exit(1);
+ }
+
+ // Write the IOR to the local file system.
+ if (OrbStarter.WRITE_URL_TO_FILE != null)
+ {
+ try
+ {
+ File gmf = new File(OrbStarter.WRITE_URL_TO_FILE);
+ FileWriter f = new FileWriter(gmf);
+ BufferedWriter b = new BufferedWriter(f);
+
+ b.write(manager_address);
+ b.close();
+ }
+ catch (IOException e)
+ {
+ System.out.println("Local filesystem not accessible."
+ + "Read IOR from console.");
+ }
+ }
+
+ // Do forever.
+ while (true)
+ {
+ try
+ {
+ Socket socket = nameServer.accept();
+
+ System.out.println("Connected.");
+
+ // Set the two minutes timeout.
+ socket.setSoTimeout(1000 * 120);
+
+ OutputStream out = socket.getOutputStream();
+
+ int length = GameManagerImpl.ior.length();
+
+ StringBuffer b = new StringBuffer();
+ b.append("HTTP/1.0 200 OK\r\n");
+ b.append("Content-Length: " + length + "\r\n");
+ b.append("Connection: close\r\n");
+ b.append("Content-Type: text/plain; charset=UTF-8\r\n");
+ b.append("\r\n");
+
+ b.append(GameManagerImpl.ior);
+
+ out.write(b.toString().getBytes("UTF-8"));
+
+ socket.shutdownOutput();
+
+ if (!socket.isClosed())
+ socket.close();
+
+ System.out.println("Completed.");
+ }
+ catch (Exception exc)
+ {
+ exc.printStackTrace();
+ System.out.println("Network problem.");
+ }
+ }
+ }
+}
diff --git a/examples/gnu/classpath/examples/CORBA/swing/x5/_GameManagerImpl_Tie.java b/examples/gnu/classpath/examples/CORBA/swing/x5/_GameManagerImpl_Tie.java
new file mode 100644
index 000000000..17a62600c
--- /dev/null
+++ b/examples/gnu/classpath/examples/CORBA/swing/x5/_GameManagerImpl_Tie.java
@@ -0,0 +1,214 @@
+/* _GameManagerImpl_Tie.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+ This file is part of GNU Classpath.
+
+ GNU Classpath is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2, or (at your option)
+ any later version.
+
+ GNU Classpath is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with GNU Classpath; see the file COPYING. If not, write to the
+ Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ 02110-1301 USA.
+
+ Linking this library statically or dynamically with other modules is
+ making a combined work based on this library. Thus, the terms and
+ conditions of the GNU General Public License cover the whole
+ combination.
+
+ As a special exception, the copyright holders of this library give you
+ permission to link this library with independent modules to produce an
+ executable, regardless of the license terms of these independent
+ modules, and to copy and distribute the resulting executable under
+ terms of your choice, provided that you also meet, for each linked
+ independent module, the terms and conditions of the license of that
+ module. An independent module is a module which is not derived from
+ or based on this library. If you modify this library, you may extend
+ this exception to your version of the library, but you are not
+ obligated to do so. If you do not wish to do so, delete this
+ exception statement from your version. */
+
+
+package gnu.classpath.examples.CORBA.swing.x5;
+
+import java.rmi.Remote;
+
+import javax.rmi.PortableRemoteObject;
+import javax.rmi.CORBA.Tie;
+
+import org.omg.CORBA.BAD_OPERATION;
+import org.omg.CORBA.ORB;
+import org.omg.CORBA.SystemException;
+import org.omg.CORBA.portable.InputStream;
+import org.omg.CORBA.portable.OutputStream;
+import org.omg.CORBA.portable.ResponseHandler;
+import org.omg.CORBA.portable.UnknownException;
+import org.omg.PortableServer.Servant;
+
+/**
+ * Normally generated with rmic compiler, this class represents the GameManager
+ * Tie on the client side. The Game Manager methods contain the code for remote
+ * invocation.
+ *
+ * This class is normally generated with rmic from the {@link GameManagerImpl}:
+ *
+ * <pre>
+ * rmic -iiop -poa -keep gnu.classpath.examples.CORBA.swing.x5.GameManagerImpl
+ * </pre>
+ *
+ * (the compiled package must be present in the current folder).
+ *
+ * In this example the class was manually edited and commented for better
+ * understanding of functionality.
+ *
+ * @author Audrius Meskauskas (AudriusA@Bioinformatics.org)
+ */
+public class _GameManagerImpl_Tie
+ extends Servant
+ implements Tie
+{
+ /**
+ * The target, where remote invocations are forwarded.
+ */
+ private GameManagerImpl target = null;
+
+ /**
+ * The GameManager repository Id.
+ */
+ private static final String[] _type_ids =
+ { "RMI:gnu.classpath.examples.CORBA.swing.x5.GameManager:0000000000000000" };
+
+ /**
+ * Set the target where the remote invocations are forwarded.
+ */
+ public void setTarget(Remote a_target)
+ {
+ this.target = (GameManagerImpl) a_target;
+ }
+
+ /**
+ * Get the target where the remote invocations are forwarded.
+ */
+ public Remote getTarget()
+ {
+ return target;
+ }
+
+ /**
+ * Get the CORBA object for that this Tie is currently serving the request.
+ * The same tie may serve multiple requests for the different objects in
+ * parallel threads.
+ */
+ public org.omg.CORBA.Object thisObject()
+ {
+ return _this_object();
+ }
+
+ /**
+ * Deactivate this object.
+ */
+ public void deactivate()
+ {
+ try
+ {
+ _poa().deactivate_object(_poa().servant_to_id(this));
+ }
+ catch (org.omg.PortableServer.POAPackage.WrongPolicy exception)
+ {
+ }
+ catch (org.omg.PortableServer.POAPackage.ObjectNotActive exception)
+ {
+ }
+ catch (org.omg.PortableServer.POAPackage.ServantNotActive exception)
+ {
+ }
+ }
+
+ /**
+ * Get the ORB for this tie.
+ */
+ public ORB orb()
+ {
+ return _orb();
+ }
+
+ /**
+ * Set the ORB for this tie.
+ */
+ public void orb(ORB orb)
+ {
+ try
+ {
+ ((org.omg.CORBA_2_3.ORB) orb).set_delegate(this);
+ }
+ catch (ClassCastException e)
+ {
+ throw new org.omg.CORBA.BAD_PARAM(
+ "POA Servant requires an instance of org.omg.CORBA_2_3.ORB");
+ }
+ }
+
+ /**
+ * Return all interfaces, supported by this method.
+ */
+ public String[] _all_interfaces(org.omg.PortableServer.POA poa,
+ byte[] objectId)
+ {
+ return _type_ids;
+ }
+
+ /**
+ * This method is invoked by CORBA system to handle the remote invocation.
+ *
+ * @param method the name of the method being invoked.
+ * @param _in the stream to read the method parameters.
+ * @param reply the responsed handler that can create the output stream to
+ * write the parameters being returned.
+ */
+ public OutputStream _invoke(String method, InputStream _in,
+ ResponseHandler reply)
+ throws SystemException
+ {
+ try
+ {
+ org.omg.CORBA_2_3.portable.InputStream in =
+ (org.omg.CORBA_2_3.portable.InputStream) _in;
+ if (method.equals("requestTheGame"))
+ {
+ Player p = (Player) PortableRemoteObject.narrow(
+ in.read_Object(), Player.class);
+ target.requestTheGame(p);
+
+ OutputStream out = reply.createReply();
+ return out;
+ }
+ else if (method.equals("unregister"))
+ {
+ Player p = (Player) PortableRemoteObject.narrow(
+ in.read_Object(), Player.class);
+ target.unregister(p);
+
+ OutputStream out = reply.createReply();
+ return out;
+ }
+ else
+ throw new BAD_OPERATION();
+ }
+ catch (SystemException ex)
+ {
+ throw ex;
+ }
+ catch (Throwable ex)
+ {
+ ex.printStackTrace();
+ throw new UnknownException(ex);
+ }
+ }
+} \ No newline at end of file
diff --git a/examples/gnu/classpath/examples/CORBA/swing/x5/_GameManager_Stub.java b/examples/gnu/classpath/examples/CORBA/swing/x5/_GameManager_Stub.java
new file mode 100644
index 000000000..e9279963a
--- /dev/null
+++ b/examples/gnu/classpath/examples/CORBA/swing/x5/_GameManager_Stub.java
@@ -0,0 +1,207 @@
+/* _GameManager_Stub.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+ This file is part of GNU Classpath.
+
+ GNU Classpath is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2, or (at your option)
+ any later version.
+
+ GNU Classpath is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with GNU Classpath; see the file COPYING. If not, write to the
+ Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ 02110-1301 USA.
+
+ Linking this library statically or dynamically with other modules is
+ making a combined work based on this library. Thus, the terms and
+ conditions of the GNU General Public License cover the whole
+ combination.
+
+ As a special exception, the copyright holders of this library give you
+ permission to link this library with independent modules to produce an
+ executable, regardless of the license terms of these independent
+ modules, and to copy and distribute the resulting executable under
+ terms of your choice, provided that you also meet, for each linked
+ independent module, the terms and conditions of the license of that
+ module. An independent module is a module which is not derived from
+ or based on this library. If you modify this library, you may extend
+ this exception to your version of the library, but you are not
+ obligated to do so. If you do not wish to do so, delete this
+ exception statement from your version. */
+
+
+package gnu.classpath.examples.CORBA.swing.x5;
+
+import java.rmi.RemoteException;
+import java.rmi.UnexpectedException;
+
+import javax.rmi.CORBA.Stub;
+import javax.rmi.CORBA.Util;
+
+import org.omg.CORBA.SystemException;
+import org.omg.CORBA.portable.ApplicationException;
+import org.omg.CORBA.portable.OutputStream;
+import org.omg.CORBA.portable.RemarshalException;
+import org.omg.CORBA.portable.ServantObject;
+
+/**
+ * Normally generated with rmic compiler, this class represents the GameManager
+ * Stub on the client side. The Game Manager methods contain the code for
+ * remote invocation.
+ *
+ * This class is normally generated with rmic from the {@link GameManagerImpl}:
+ * <pre>
+ * rmic -iiop -poa -keep gnu.classpath.examples.CORBA.swing.x5.GameManagerImpl
+ * </pre>
+ * (the compiled package must be present in the current folder).
+ *
+ * @author Audrius Meskauskas (AudriusA@Bioinformatics.org)
+ */
+public class _GameManager_Stub extends Stub implements GameManager
+{
+ /**
+ * Use serialVersionUID for interoperability.
+ */
+ private static final long serialVersionUID = 1;
+
+ private static final String[] _type_ids =
+ { "RMI:gnu.classpath.examples.CORBA.swing.x5.GameManager:0000000000000000" };
+
+ public String[] _ids()
+ {
+ return _type_ids;
+ }
+
+ /**
+ * Notify the manager that the player is no longer willing to play and
+ * should be removed from the queue.
+ */
+ public void unregister(Player p)
+ throws RemoteException
+ {
+ if (!Util.isLocal(this))
+ {
+ try
+ {
+ org.omg.CORBA.portable.InputStream in = null;
+ try
+ {
+ OutputStream out = _request("unregister", true);
+ Util.writeRemoteObject(out, p);
+ _invoke(out);
+ }
+ catch (ApplicationException ex)
+ {
+ in = ex.getInputStream();
+
+ String id = in.read_string();
+ throw new UnexpectedException(id);
+ }
+ catch (RemarshalException ex)
+ {
+ unregister(p);
+ }
+ finally
+ {
+ _releaseReply(in);
+ }
+ }
+ catch (SystemException ex)
+ {
+ throw Util.mapSystemException(ex);
+ }
+ }
+ else
+ {
+ ServantObject so =
+ _servant_preinvoke("requestTheGame", GameManager.class);
+ if (so == null)
+ {
+ unregister(p);
+ return;
+ }
+ try
+ {
+ ((GameManager) so.servant).unregister(p);
+ }
+ catch (Throwable ex)
+ {
+ Throwable exCopy = (Throwable) Util.copyObject(ex, _orb());
+ throw Util.wrapException(exCopy);
+ }
+ finally
+ {
+ _servant_postinvoke(so);
+ }
+ }
+ }
+
+ /**
+ * The method that the user should invoke.
+ */
+ public void requestTheGame(Player arg0) throws RemoteException
+ {
+ if (!Util.isLocal(this))
+ {
+ try
+ {
+ org.omg.CORBA.portable.InputStream in = null;
+ try
+ {
+ OutputStream out = _request("requestTheGame", true);
+ Util.writeRemoteObject(out, arg0);
+ _invoke(out);
+ }
+ catch (ApplicationException ex)
+ {
+ in = ex.getInputStream();
+
+ String id = in.read_string();
+ throw new UnexpectedException(id);
+ }
+ catch (RemarshalException ex)
+ {
+ requestTheGame(arg0);
+ }
+ finally
+ {
+ _releaseReply(in);
+ }
+ }
+ catch (SystemException ex)
+ {
+ throw Util.mapSystemException(ex);
+ }
+ }
+ else
+ {
+ ServantObject so =
+ _servant_preinvoke("requestTheGame", GameManager.class);
+ if (so == null)
+ {
+ requestTheGame(arg0);
+ return;
+ }
+ try
+ {
+ Player arg0Copy = (Player) Util.copyObject(arg0, _orb());
+ ((GameManager) so.servant).requestTheGame(arg0Copy);
+ }
+ catch (Throwable ex)
+ {
+ Throwable exCopy = (Throwable) Util.copyObject(ex, _orb());
+ throw Util.wrapException(exCopy);
+ }
+ finally
+ {
+ _servant_postinvoke(so);
+ }
+ }
+ }
+} \ No newline at end of file
diff --git a/examples/gnu/classpath/examples/CORBA/swing/x5/_PlayerImpl_Tie.java b/examples/gnu/classpath/examples/CORBA/swing/x5/_PlayerImpl_Tie.java
new file mode 100644
index 000000000..730c6f469
--- /dev/null
+++ b/examples/gnu/classpath/examples/CORBA/swing/x5/_PlayerImpl_Tie.java
@@ -0,0 +1,212 @@
+/* _PlayerImpl_Tie.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+ This file is part of GNU Classpath.
+
+ GNU Classpath is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2, or (at your option)
+ any later version.
+
+ GNU Classpath is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with GNU Classpath; see the file COPYING. If not, write to the
+ Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ 02110-1301 USA.
+
+ Linking this library statically or dynamically with other modules is
+ making a combined work based on this library. Thus, the terms and
+ conditions of the GNU General Public License cover the whole
+ combination.
+
+ As a special exception, the copyright holders of this library give you
+ permission to link this library with independent modules to produce an
+ executable, regardless of the license terms of these independent
+ modules, and to copy and distribute the resulting executable under
+ terms of your choice, provided that you also meet, for each linked
+ independent module, the terms and conditions of the license of that
+ module. An independent module is a module which is not derived from
+ or based on this library. If you modify this library, you may extend
+ this exception to your version of the library, but you are not
+ obligated to do so. If you do not wish to do so, delete this
+ exception statement from your version. */
+
+
+package gnu.classpath.examples.CORBA.swing.x5;
+
+import java.awt.Point;
+import java.rmi.Remote;
+
+import javax.rmi.PortableRemoteObject;
+import javax.rmi.CORBA.Tie;
+
+import org.omg.CORBA.BAD_OPERATION;
+import org.omg.CORBA.ORB;
+import org.omg.CORBA.SystemException;
+import org.omg.CORBA.portable.InputStream;
+import org.omg.CORBA.portable.OutputStream;
+import org.omg.CORBA.portable.ResponseHandler;
+import org.omg.CORBA.portable.UnknownException;
+import org.omg.PortableServer.Servant;
+
+/**
+ * Generate with rmic, command line
+ * rmic -iiop -poa -keep gnu.classpath.examples.CORBA.swing.x5.PlayerImpl
+ * (the compiled package must be present in the current folder).
+ *
+ * This class is normally generated with rmic from the {@link PlayerImpl}:
+ * <pre>
+ * rmic -iiop -poa -keep gnu.classpath.examples.CORBA.swing.x5.PlayerImpl
+ * </pre>
+ * (the compiled package must be present in the current folder).
+ *
+ * In this example the class was manually edited and commented for better
+ * understanding of functionality.
+ *
+ * @author Audrius Meskauskas (AudriusA@Bioinformatics.org)
+ */
+public class _PlayerImpl_Tie extends Servant implements Tie
+{
+ private PlayerImpl target = null;
+ private static final String[] _type_ids =
+ { "RMI:gnu.classpath.examples.CORBA.swing.x5.Player:0000000000000000" };
+
+ public void setTarget(Remote a_target)
+ {
+ this.target = (PlayerImpl) a_target;
+ }
+
+ public Remote getTarget()
+ {
+ return target;
+ }
+
+ public org.omg.CORBA.Object thisObject()
+ {
+ return _this_object();
+ }
+
+ public void deactivate()
+ {
+ try
+ {
+ _poa().deactivate_object(_poa().servant_to_id(this));
+ }
+ catch (org.omg.PortableServer.POAPackage.WrongPolicy exception)
+ {
+ }
+ catch (org.omg.PortableServer.POAPackage.ObjectNotActive exception)
+ {
+ }
+ catch (org.omg.PortableServer.POAPackage.ServantNotActive exception)
+ {
+ }
+ }
+
+ public ORB orb()
+ {
+ return _orb();
+ }
+
+ public void orb(ORB orb)
+ {
+ try
+ {
+ ((org.omg.CORBA_2_3.ORB) orb).set_delegate(this);
+ }
+ catch (ClassCastException e)
+ {
+ throw new org.omg.CORBA.BAD_PARAM(
+ "POA Servant requires an instance of org.omg.CORBA_2_3.ORB"
+ );
+ }
+ }
+
+ public String[] _all_interfaces(org.omg.PortableServer.POA poa,
+ byte[] objectId
+ )
+ {
+ return _type_ids;
+ }
+
+ public OutputStream _invoke(String method, InputStream _in,
+ ResponseHandler reply
+ ) throws SystemException
+ {
+ try
+ {
+ org.omg.CORBA_2_3.portable.InputStream in =
+ (org.omg.CORBA_2_3.portable.InputStream) _in;
+ switch (method.charAt(9))
+ {
+ case 101 :
+ if (method.equals("start_game"))
+ {
+ Player arg0 =
+ (Player) PortableRemoteObject.narrow(in.read_Object(),
+ Player.class
+ );
+ boolean arg1 = in.read_boolean();
+ boolean result = target.start_game(arg0, arg1);
+ OutputStream out = reply.createReply();
+ out.write_boolean(result);
+ return out;
+ }
+
+ case 104 :
+ if (method.equals("receive_chat"))
+ {
+ byte arg0 = in.read_octet();
+ String arg1 = (String) in.read_value(String.class);
+ target.receive_chat(arg0, arg1);
+
+ OutputStream out = reply.createReply();
+ return out;
+ }
+
+ case 111 :
+ if (method.equals("receive_move"))
+ {
+ int arg0 = in.read_long();
+ int arg1 = in.read_long();
+ Point[] arg2 = (Point[]) in.read_value(Point[].class);
+ target.receive_move(arg0, arg1, arg2);
+
+ OutputStream out = reply.createReply();
+ return out;
+ }
+
+ case 114 :
+ if (method.equals("_get_J_current_state"))
+ {
+ int result = target.get_current_state();
+ OutputStream out = reply.createReply();
+ out.write_long(result);
+ return out;
+ }
+
+ case 116 :
+ if (method.equals("disconnect"))
+ {
+ target.disconnect();
+
+ OutputStream out = reply.createReply();
+ return out;
+ }
+ }
+ throw new BAD_OPERATION("No such method: '"+method+"'");
+ }
+ catch (SystemException ex)
+ {
+ throw ex;
+ }
+ catch (Throwable ex)
+ {
+ throw new UnknownException(ex);
+ }
+ }
+} \ No newline at end of file
diff --git a/examples/gnu/classpath/examples/CORBA/swing/x5/_Player_Stub.java b/examples/gnu/classpath/examples/CORBA/swing/x5/_Player_Stub.java
new file mode 100644
index 000000000..eeb5cf0da
--- /dev/null
+++ b/examples/gnu/classpath/examples/CORBA/swing/x5/_Player_Stub.java
@@ -0,0 +1,397 @@
+/* _Player_Stub.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+ This file is part of GNU Classpath.
+
+ GNU Classpath is free software; you can redistribute it and/or modify
+ it under the terms of the GNU General Public License as published by
+ the Free Software Foundation; either version 2, or (at your option)
+ any later version.
+
+ GNU Classpath is distributed in the hope that it will be useful, but
+ WITHOUT ANY WARRANTY; without even the implied warranty of
+ MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ General Public License for more details.
+
+ You should have received a copy of the GNU General Public License
+ along with GNU Classpath; see the file COPYING. If not, write to the
+ Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+ 02110-1301 USA.
+
+ Linking this library statically or dynamically with other modules is
+ making a combined work based on this library. Thus, the terms and
+ conditions of the GNU General Public License cover the whole
+ combination.
+
+ As a special exception, the copyright holders of this library give you
+ permission to link this library with independent modules to produce an
+ executable, regardless of the license terms of these independent
+ modules, and to copy and distribute the resulting executable under
+ terms of your choice, provided that you also meet, for each linked
+ independent module, the terms and conditions of the license of that
+ module. An independent module is a module which is not derived from
+ or based on this library. If you modify this library, you may extend
+ this exception to your version of the library, but you are not
+ obligated to do so. If you do not wish to do so, delete this
+ exception statement from your version. */
+
+
+package gnu.classpath.examples.CORBA.swing.x5;
+
+import java.awt.Point;
+import java.io.Serializable;
+import java.rmi.RemoteException;
+import java.rmi.UnexpectedException;
+
+import javax.rmi.CORBA.Stub;
+import javax.rmi.CORBA.Util;
+
+import org.omg.CORBA.SystemException;
+import org.omg.CORBA.portable.ApplicationException;
+import org.omg.CORBA.portable.OutputStream;
+import org.omg.CORBA.portable.RemarshalException;
+import org.omg.CORBA.portable.ServantObject;
+
+/**
+ * Generate with rmic, command line
+ * rmic -iiop -poa -keep gnu.classpath.examples.CORBA.swing.x5.PlayerImpl
+ * (the compiled package must be present in the current folder).
+ *
+ * This class is normally generated with rmic from the {@link GameManagerImpl}:
+ * <pre>
+ * rmic -iiop -poa -keep gnu.classpath.examples.CORBA.swing.x5.GameManagerImpl
+ * </pre>
+ * (the compiled package must be present in the current folder).
+ *
+ * In this example the class was manually edited and commented for better
+ * understanding of functionality.
+ *
+ * @author Audrius Meskauskas (AudriusA@Bioinformatics.org)
+ */
+public class _Player_Stub extends Stub implements Player
+{
+ /**
+ * Use serialVersionUID for interoperability.
+ */
+ private static final long serialVersionUID = 1;
+
+ private static final String[] _type_ids =
+ { "RMI:gnu.classpath.examples.CORBA.swing.x5.Player:0000000000000000" };
+
+ public String[] _ids()
+ {
+ return _type_ids;
+ }
+
+ public boolean start_game(Player arg0, boolean arg1)
+ throws RemoteException
+ {
+ if (!Util.isLocal(this))
+ {
+ try
+ {
+ org.omg.CORBA.portable.InputStream in = null;
+ try
+ {
+ OutputStream out = _request("start_game", true);
+ Util.writeRemoteObject(out, arg0);
+ out.write_boolean(arg1);
+ in = _invoke(out);
+ return in.read_boolean();
+ }
+ catch (ApplicationException ex)
+ {
+ in = ex.getInputStream();
+
+ String id = in.read_string();
+ throw new UnexpectedException(id);
+ }
+ catch (RemarshalException ex)
+ {
+ return start_game(arg0, arg1);
+ }
+ finally
+ {
+ _releaseReply(in);
+ }
+ }
+ catch (SystemException ex)
+ {
+ throw Util.mapSystemException(ex);
+ }
+ }
+ else
+ {
+ ServantObject so = _servant_preinvoke("start_game", Player.class);
+ if (so == null)
+ {
+ return start_game(arg0, arg1);
+ }
+ try
+ {
+ Player arg0Copy = (Player) Util.copyObject(arg0, _orb());
+ return ((Player) so.servant).start_game(arg0Copy, arg1);
+ }
+ catch (Throwable ex)
+ {
+ Throwable exCopy = (Throwable) Util.copyObject(ex, _orb());
+ throw Util.wrapException(exCopy);
+ }
+ finally
+ {
+ _servant_postinvoke(so);
+ }
+ }
+ }
+
+ public int get_current_state() throws RemoteException
+ {
+ if (!Util.isLocal(this))
+ {
+ try
+ {
+ org.omg.CORBA.portable.InputStream in = null;
+ try
+ {
+ OutputStream out = _request("_get_J_current_state", true);
+ in = _invoke(out);
+ return in.read_long();
+ }
+ catch (ApplicationException ex)
+ {
+ in = ex.getInputStream();
+
+ String id = in.read_string();
+ throw new UnexpectedException(id);
+ }
+ catch (RemarshalException ex)
+ {
+ return get_current_state();
+ }
+ finally
+ {
+ _releaseReply(in);
+ }
+ }
+ catch (SystemException ex)
+ {
+ throw Util.mapSystemException(ex);
+ }
+ }
+ else
+ {
+ ServantObject so =
+ _servant_preinvoke("_get_J_current_state", Player.class);
+ if (so == null)
+ {
+ return get_current_state();
+ }
+ try
+ {
+ return ((Player) so.servant).get_current_state();
+ }
+ catch (Throwable ex)
+ {
+ Throwable exCopy = (Throwable) Util.copyObject(ex, _orb());
+ throw Util.wrapException(exCopy);
+ }
+ finally
+ {
+ _servant_postinvoke(so);
+ }
+ }
+ }
+
+ public void receive_chat(byte arg0, String arg1) throws RemoteException
+ {
+ if (!Util.isLocal(this))
+ {
+ try
+ {
+ org.omg.CORBA_2_3.portable.InputStream in = null;
+ try
+ {
+ org.omg.CORBA_2_3.portable.OutputStream out =
+ (org.omg.CORBA_2_3.portable.OutputStream) _request("receive_chat",
+ true
+ );
+ out.write_octet(arg0);
+ out.write_value(arg1, String.class);
+ _invoke(out);
+ }
+ catch (ApplicationException ex)
+ {
+ in =
+ (org.omg.CORBA_2_3.portable.InputStream) ex.getInputStream();
+
+ String id = in.read_string();
+ throw new UnexpectedException(id);
+ }
+ catch (RemarshalException ex)
+ {
+ receive_chat(arg0, arg1);
+ }
+ finally
+ {
+ _releaseReply(in);
+ }
+ }
+ catch (SystemException ex)
+ {
+ throw Util.mapSystemException(ex);
+ }
+ }
+ else
+ {
+ ServantObject so = _servant_preinvoke("receive_chat", Player.class);
+ if (so == null)
+ {
+ receive_chat(arg0, arg1);
+ return;
+ }
+ try
+ {
+ ((Player) so.servant).receive_chat(arg0, arg1);
+ }
+ catch (Throwable ex)
+ {
+ Throwable exCopy = (Throwable) Util.copyObject(ex, _orb());
+ throw Util.wrapException(exCopy);
+ }
+ finally
+ {
+ _servant_postinvoke(so);
+ }
+ }
+ }
+
+ public void disconnect() throws RemoteException
+ {
+ if (!Util.isLocal(this))
+ {
+ try
+ {
+ org.omg.CORBA.portable.InputStream in = null;
+ try
+ {
+ OutputStream out = _request("disconnect", true);
+ _invoke(out);
+ }
+ catch (ApplicationException ex)
+ {
+ in = ex.getInputStream();
+
+ String id = in.read_string();
+ throw new UnexpectedException(id);
+ }
+ catch (RemarshalException ex)
+ {
+ disconnect();
+ }
+ finally
+ {
+ _releaseReply(in);
+ }
+ }
+ catch (SystemException ex)
+ {
+ throw Util.mapSystemException(ex);
+ }
+ }
+ else
+ {
+ ServantObject so = _servant_preinvoke("disconnect", Player.class);
+ if (so == null)
+ {
+ disconnect();
+ return;
+ }
+ try
+ {
+ ((Player) so.servant).disconnect();
+ }
+ catch (Throwable ex)
+ {
+ Throwable exCopy = (Throwable) Util.copyObject(ex, _orb());
+ throw Util.wrapException(exCopy);
+ }
+ finally
+ {
+ _servant_postinvoke(so);
+ }
+ }
+ }
+
+ public void receive_move(int arg0, int arg1, Point[] arg2)
+ throws RemoteException
+ {
+ if (!Util.isLocal(this))
+ {
+ try
+ {
+ org.omg.CORBA_2_3.portable.InputStream in = null;
+ try
+ {
+ org.omg.CORBA_2_3.portable.OutputStream out =
+ (org.omg.CORBA_2_3.portable.OutputStream) _request("receive_move",
+ true
+ );
+ out.write_long(arg0);
+ out.write_long(arg1);
+ out.write_value(cast_array(arg2), Point[].class);
+ _invoke(out);
+ }
+ catch (ApplicationException ex)
+ {
+ in =
+ (org.omg.CORBA_2_3.portable.InputStream) ex.getInputStream();
+
+ String id = in.read_string();
+ throw new UnexpectedException(id);
+ }
+ catch (RemarshalException ex)
+ {
+ receive_move(arg0, arg1, arg2);
+ }
+ finally
+ {
+ _releaseReply(in);
+ }
+ }
+ catch (SystemException ex)
+ {
+ throw Util.mapSystemException(ex);
+ }
+ }
+ else
+ {
+ ServantObject so = _servant_preinvoke("receive_move", Player.class);
+ if (so == null)
+ {
+ receive_move(arg0, arg1, arg2);
+ return;
+ }
+ try
+ {
+ Point[] arg2Copy = (Point[]) Util.copyObject(arg2, _orb());
+ ((Player) so.servant).receive_move(arg0, arg1, arg2Copy);
+ }
+ catch (Throwable ex)
+ {
+ Throwable exCopy = (Throwable) Util.copyObject(ex, _orb());
+ throw Util.wrapException(exCopy);
+ }
+ finally
+ {
+ _servant_postinvoke(so);
+ }
+ }
+ }
+
+ // This method is required as a work-around for
+ // a bug in the JDK 1.1.6 verifier.
+ private Serializable cast_array(Object obj)
+ {
+ return (Serializable) obj;
+ }
+} \ No newline at end of file
diff --git a/examples/gnu/classpath/examples/swing/Demo.java b/examples/gnu/classpath/examples/swing/Demo.java
index 6e71af3c8..549a42e4b 100644
--- a/examples/gnu/classpath/examples/swing/Demo.java
+++ b/examples/gnu/classpath/examples/swing/Demo.java
@@ -29,6 +29,7 @@ import javax.swing.*;
import javax.swing.tree.*;
import javax.swing.border.*;
+import javax.swing.plaf.metal.DefaultMetalTheme;
import javax.swing.plaf.metal.MetalLookAndFeel;
import javax.swing.plaf.metal.OceanTheme;
@@ -72,10 +73,15 @@ public class Demo
JOptionPane.OK_OPTION,
JOptionPane.QUESTION_MESSAGE,
null, lafs, DEFAULT);
+ if (laf == 0)
+ {
+ MetalLookAndFeel.setCurrentTheme(new DefaultMetalTheme());
+ UIManager.setLookAndFeel(new MetalLookAndFeel());
+ }
if (laf == 1)
{
- MetalLookAndFeel.setCurrentTheme(new OceanTheme());
- UIManager.setLookAndFeel(new MetalLookAndFeel());
+ MetalLookAndFeel.setCurrentTheme(new OceanTheme());
+ UIManager.setLookAndFeel(new MetalLookAndFeel());
}
else if (laf == 2)
UIManager.setLookAndFeel(new GNULookAndFeel());
@@ -171,9 +177,13 @@ public class Demo
examples);
new PopUpAction("Slider",
- mkSliders(),
+ (new SliderDemo("Slider Demo")).createContent(),
examples);
+ new PopUpAction("ProgressBar",
+ ProgressBarDemo.createContent(),
+ examples);
+
new PopUpAction("List",
mkListPanel(new String[] { "hello",
"this",
@@ -208,9 +218,13 @@ public class Demo
examples);
new PopUpAction("TextField",
- mkTextField("Hello, World!"),
+ (new TextFieldDemo("TextField Demo")).createContent(),
examples);
+ new PopUpAction("FileChooser",
+ (new FileChooserDemo("FileChooser Demo")).createContent(),
+ examples);
+
new PopUpAction("ColorChooser",
mkColorChooser(),
examples);
@@ -688,26 +702,6 @@ public class Demo
return tabs;
}
- static JComponent mkSliders()
- {
- JSlider slider = new JSlider();
- slider.setPaintTrack(true);
- slider.setPaintTicks(true);
- slider.setMajorTickSpacing(30);
- slider.setMinorTickSpacing(5);
- slider.setPaintLabels(true);
- slider.setInverted(false);
- JProgressBar progress = new JProgressBar();
- BoundedRangeModel model = new DefaultBoundedRangeModel(10, 1, 0, 100);
- progress.setModel(model);
- slider.setModel(model);
- JPanel panel = new JPanel();
- panel.setLayout(new GridLayout(1, 2));
- panel.add(slider);
- panel.add(progress);
- return panel;
- }
-
public Demo()
{
frame = new JFrame("Swing Activity Board");
@@ -1018,28 +1012,34 @@ public class Demo
private JPanel mkButtonBar()
{
- JPanel panel = new JPanel ();
- panel.setLayout(new FlowLayout());
+ JPanel panel = new JPanel (new GridLayout(2, 1));
+ JPanel panelA = new JPanel(new FlowLayout());
+ JPanel panelB = new JPanel(new FlowLayout());
new PopUpAction("Buttons",
(new ButtonDemo("Button Demo")).createContent(),
- panel);
+ panelA);
new PopUpAction("Toggles",
mkToggle("cool and refreshing"),
- panel);
+ panelA);
new PopUpAction("Checkbox",
mkCheckbox("ice cold"),
- panel);
+ panelA);
new PopUpAction("Radio",
mkRadio("delicious"),
- panel);
+ panelA);
new PopUpAction("Slider",
(new SliderDemo("Slider Demo")).createContent(),
- panel);
+ panelA);
+
+ new PopUpAction("ProgressBar",
+ ProgressBarDemo.createContent(),
+ panelA);
+
new PopUpAction("List",
mkListPanel(new String[] { "hello",
@@ -1050,56 +1050,60 @@ public class Demo
"that",
"wraps",
"over"}),
- panel);
+ panelA);
new PopUpAction("Scrollbar",
(new ScrollBarDemo("ScrollBar Demo")).createContent(),
- panel);
+ panelA);
new PopUpAction("Viewport",
mkViewportBox(mkBigButton("View Me!")),
- panel);
+ panelA);
new PopUpAction("ScrollPane",
mkScrollPane(mkBigButton("Scroll Me!")),
- panel);
+ panelA);
new PopUpAction("TabPane",
mkTabs(new String[] {"happy",
"sad",
"indifferent"}),
- panel);
+ panelB);
new PopUpAction("Spinner",
mkSpinner(),
- panel);
+ panelB);
new PopUpAction("TextField",
- mkTextField("Hello, World!"),
- panel);
+ (new TextFieldDemo("TextField Demo")).createContent(),
+ panelB);
+
+ new PopUpAction("FileChooser",
+ (new FileChooserDemo("FileChooser Demo")).createContent(),
+ panelB);
new PopUpAction("ColorChooser",
mkColorChooser(),
- panel);
+ panelB);
new PopUpAction("ComboBox",
(new ComboBoxDemo("ComboBox Demo")).createContent(),
- panel);
+ panelB);
new PopUpAction("Editor",
mkEditorPane(),
- panel);
+ panelB);
new PopUpAction("Tree",
mkTree(),
- panel);
+ panelB);
new PopUpAction("Table",
mkTable(),
- panel);
+ panelB);
JButton exitDisposer = mkDisposerButton(frame);
- panel.add(exitDisposer);
+ panelB.add(exitDisposer);
exitDisposer.addActionListener(new ActionListener()
{
public void actionPerformed(ActionEvent e)
@@ -1107,11 +1111,8 @@ public class Demo
System.exit(1);
}
});
+ panel.add(panelA);
+ panel.add(panelB);
return panel;
}
-
- public static JTextField mkTextField(String sometext)
- {
- return new JTextField(sometext, 40);
- }
}
diff --git a/examples/gnu/classpath/examples/swing/FileChooserDemo.java b/examples/gnu/classpath/examples/swing/FileChooserDemo.java
new file mode 100644
index 000000000..70bb56d66
--- /dev/null
+++ b/examples/gnu/classpath/examples/swing/FileChooserDemo.java
@@ -0,0 +1,228 @@
+/* FileChooserDemo.java -- An example showing file choosers in Swing.
+ Copyright (C) 2005, Free Software Foundation, Inc.
+
+This file is part of GNU Classpath examples.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+*/
+
+package gnu.classpath.examples.swing;
+
+import java.awt.BorderLayout;
+import java.awt.GridLayout;
+import java.awt.event.ActionEvent;
+import java.awt.event.ActionListener;
+import java.io.File;
+
+import javax.swing.BorderFactory;
+import javax.swing.DefaultListModel;
+import javax.swing.JButton;
+import javax.swing.JFileChooser;
+import javax.swing.JFrame;
+import javax.swing.JLabel;
+import javax.swing.JList;
+import javax.swing.JPanel;
+import javax.swing.JScrollPane;
+import javax.swing.filechooser.FileFilter;
+
+/**
+ * A simple demo showing the {@link JFileChooser} component used in different
+ * ways.
+ */
+public class FileChooserDemo extends JFrame implements ActionListener
+{
+ /**
+ * A file filter for Java source files.
+ */
+ static class JavaFileFilter extends FileFilter
+ {
+ public String getDescription()
+ {
+ return "Java Source Files (.java)";
+ }
+ public boolean accept(File f)
+ {
+ if (f != null)
+ {
+ return f.getName().endsWith(".java") || f.isDirectory();
+ }
+ else
+ return false;
+ }
+ }
+
+ /** A label to display the selected file. */
+ JLabel selectedFileLabel;
+
+ /**
+ * A list showing the selected files (where multi selections are
+ * allowed).
+ */
+ JList selectedFilesList;
+
+ /** A label to display the return code for the JFileChooser. */
+ JLabel returnCodeLabel;
+
+ /**
+ * Creates a new demo instance.
+ *
+ * @param frameTitle the frame title.
+ */
+ public FileChooserDemo(String frameTitle)
+ {
+ super(frameTitle);
+ JPanel content = createContent();
+ JPanel closePanel = new JPanel();
+ JButton closeButton = new JButton("Close");
+ closeButton.setActionCommand("CLOSE");
+ closeButton.addActionListener(this);
+ closePanel.add(closeButton);
+ content.add(closePanel, BorderLayout.SOUTH);
+ getContentPane().add(content);
+ }
+
+ /**
+ * Returns a panel with the demo content. The panel
+ * uses a BorderLayout(), and the BorderLayout.SOUTH area
+ * is empty, to allow callers to add controls to the
+ * bottom of the panel if they want to (a close button is
+ * added if this demo is being run as a standalone demo).
+ */
+ JPanel createContent()
+ {
+ JPanel panel = new JPanel(new BorderLayout());
+
+ // create a panel of buttons to select the different styles of file
+ // chooser...
+ JPanel buttonPanel = new JPanel(new GridLayout(5, 1));
+ JButton openButton = new JButton("Open...");
+ openButton.setActionCommand("OPEN");
+ openButton.addActionListener(this);
+ buttonPanel.add(openButton);
+ JButton saveButton = new JButton("Save...");
+ saveButton.setActionCommand("SAVE");
+ saveButton.addActionListener(this);
+ buttonPanel.add(saveButton);
+ JButton queryButton = new JButton("Select Directory...");
+ queryButton.setActionCommand("SELECT_DIRECTORY");
+ queryButton.addActionListener(this);
+ buttonPanel.add(queryButton);
+ JButton openJavaButton = new JButton("Open Java file...");
+ openJavaButton.setActionCommand("OPEN_JAVA");
+ openJavaButton.addActionListener(this);
+ buttonPanel.add(openJavaButton);
+ JButton openMultiButton = new JButton("Open multiple files...");
+ openMultiButton.setActionCommand("OPEN_MULTI");
+ openMultiButton.addActionListener(this);
+ buttonPanel.add(openMultiButton);
+ panel.add(buttonPanel, BorderLayout.WEST);
+
+ // create a panel to display the selected file(s) and the return code
+ JPanel displayPanel = new JPanel(new BorderLayout());
+
+ selectedFileLabel = new JLabel("-");
+ selectedFileLabel.setBorder(BorderFactory.createTitledBorder("Selected File/Directory: "));
+ displayPanel.add(selectedFileLabel, BorderLayout.NORTH);
+
+ selectedFilesList = new JList();
+ JScrollPane sp = new JScrollPane(selectedFilesList);
+ sp.setBorder(BorderFactory.createTitledBorder("Selected Files: "));
+ displayPanel.add(sp);
+
+ returnCodeLabel = new JLabel("0");
+ returnCodeLabel.setBorder(BorderFactory.createTitledBorder("Return Code:"));
+ displayPanel.add(returnCodeLabel, BorderLayout.SOUTH);
+
+ panel.add(displayPanel);
+ return panel;
+ }
+
+ /**
+ * When the user clicks on a button, launch the appropriate file chooser
+ * and report the results.
+ *
+ * @param e the event.
+ */
+ public void actionPerformed(ActionEvent e)
+ {
+ int option = 0;
+ File selectedFile = null;
+ File[] selectedFiles = new File[0];
+
+ if (e.getActionCommand().equals("CLOSE"))
+ {
+ System.exit(0);
+ }
+ else if (e.getActionCommand().equals("OPEN"))
+ {
+ JFileChooser chooser = new JFileChooser();
+ option = chooser.showOpenDialog(this);
+ selectedFile = chooser.getSelectedFile();
+ selectedFiles = chooser.getSelectedFiles();
+ }
+ else if (e.getActionCommand().equals("OPEN_MULTI"))
+ {
+ JFileChooser chooser = new JFileChooser();
+ chooser.setMultiSelectionEnabled(true);
+ option = chooser.showOpenDialog(this);
+ selectedFile = chooser.getSelectedFile();
+ selectedFiles = chooser.getSelectedFiles();
+ }
+ else if (e.getActionCommand().equals("OPEN_JAVA"))
+ {
+ JFileChooser chooser = new JFileChooser();
+ chooser.setAcceptAllFileFilterUsed(false);
+ chooser.setFileFilter(new JavaFileFilter());
+ option = chooser.showOpenDialog(this);
+ selectedFile = chooser.getSelectedFile();
+ selectedFiles = chooser.getSelectedFiles();
+ }
+ else if (e.getActionCommand().equals("SAVE"))
+ {
+ JFileChooser chooser = new JFileChooser();
+ option = chooser.showSaveDialog(this);
+ selectedFile = chooser.getSelectedFile();
+ selectedFiles = chooser.getSelectedFiles();
+ }
+ else if (e.getActionCommand().equals("SELECT_DIRECTORY"))
+ {
+ JFileChooser chooser = new JFileChooser();
+ chooser.setFileSelectionMode(JFileChooser.DIRECTORIES_ONLY);
+ option = chooser.showDialog(this, "Select");
+ selectedFile = chooser.getSelectedFile();
+ selectedFiles = chooser.getSelectedFiles();
+ }
+
+ // display the selection and return code
+ if (selectedFile != null)
+ selectedFileLabel.setText(selectedFile.toString());
+ else
+ selectedFileLabel.setText("null");
+ DefaultListModel listModel = new DefaultListModel();
+ for (int i = 0; i < selectedFiles.length; i++)
+ listModel.addElement(selectedFiles[i]);
+ selectedFilesList.setModel(listModel);
+ returnCodeLabel.setText(Integer.toString(option));
+ }
+
+ public static void main(String[] args)
+ {
+ FileChooserDemo app = new FileChooserDemo("File Chooser Demo");
+ app.pack();
+ app.setVisible(true);
+ }
+
+}
diff --git a/examples/gnu/classpath/examples/swing/GNULookAndFeel.java b/examples/gnu/classpath/examples/swing/GNULookAndFeel.java
index 97e91a89f..c8fd09d74 100644
--- a/examples/gnu/classpath/examples/swing/GNULookAndFeel.java
+++ b/examples/gnu/classpath/examples/swing/GNULookAndFeel.java
@@ -22,8 +22,13 @@ Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
package gnu.classpath.examples.swing;
import java.awt.Color;
+import java.awt.Component;
+import java.awt.Graphics;
+import javax.swing.Icon;
import javax.swing.ImageIcon;
+import javax.swing.JCheckBox;
+import javax.swing.JRadioButton;
import javax.swing.UIDefaults;
import javax.swing.plaf.ColorUIResource;
import javax.swing.plaf.IconUIResource;
@@ -64,8 +69,10 @@ public class GNULookAndFeel extends BasicLookAndFeel
"MenuBar.background", new ColorUIResource(blueGray),
"MenuItem.background", new ColorUIResource(blueGray),
"ScrollBar.background", new ColorUIResource(blueGray),
-
- "Tree.closedIcon",
+ "CheckBox.icon", new CheckBoxIcon(),
+ "RadioButton.icon", new RadioButtonIcon(),
+
+ "Tree.closedIcon",
new IconUIResource(new ImageIcon
(getClass().getResource
(iconspath + "TreeClosed.png"))),
@@ -82,4 +89,177 @@ public class GNULookAndFeel extends BasicLookAndFeel
}
return LAF_defaults;
}
+
+ /**
+ * The icon used for CheckBoxes in the BasicLookAndFeel. This is an empty
+ * icon with a size of 13x13 pixels.
+ */
+ static class CheckBoxIcon
+ implements Icon
+ {
+ /**
+ * Returns the height of the icon. The BasicLookAndFeel CheckBox icon
+ * has a height of 13 pixels.
+ *
+ * @return the height of the icon
+ */
+ public int getIconHeight()
+ {
+ return 13;
+ }
+
+ /**
+ * Returns the width of the icon. The BasicLookAndFeel CheckBox icon
+ * has a width of 13 pixels.
+ *
+ * @return the height of the icon
+ */
+ public int getIconWidth()
+ {
+ return 13;
+ }
+
+ /**
+ * Paints the icon. The BasicLookAndFeel CheckBox icon is empty and does
+ * not need to be painted.
+ *
+ * @param c the component to be painted
+ * @param g the Graphics context to be painted with
+ * @param x the x position of the icon
+ * @param y the y position of the icon
+ */
+ public void paintIcon(Component c, Graphics g, int x, int y)
+ {
+ Color save = g.getColor();
+ g.setColor(c.getForeground());
+ g.drawRect(x, y, getIconWidth(), getIconHeight());
+
+ JCheckBox item = (JCheckBox) c;
+ if (item.isSelected())
+ {
+ g.drawLine(3 + x, 5 + y, 3 + x, 9 + y);
+ g.drawLine(4 + x, 5 + y, 4 + x, 9 + y);
+ g.drawLine(5 + x, 7 + y, 9 + x, 3 + y);
+ g.drawLine(5 + x, 8 + y, 9 + x, 4 + y);
+ }
+
+ g.setColor(save);
+ }
+ }
+
+ /**
+ * The icon used for RadioButtons in the GNULookAndFeel. This is an empty
+ * icon with a size of 13x13 pixels.
+ */
+ static class RadioButtonIcon
+ implements Icon
+ {
+ /**
+ * Returns the height of the icon. The GNULookAndFeel RadioButton icon
+ * has a height of 13 pixels.
+ *
+ * @return the height of the icon
+ */
+ public int getIconHeight()
+ {
+ return 13;
+ }
+
+ /**
+ * Returns the width of the icon. The GNULookAndFeel RadioButton icon
+ * has a width of 13 pixels.
+ *
+ * @return the height of the icon
+ */
+ public int getIconWidth()
+ {
+ return 13;
+ }
+
+ /**
+ * Paints the icon. The GNULookAndFeel RadioButton icon is empty and does
+ * not need to be painted.
+ *
+ * @param c the component to be painted
+ * @param g the Graphics context to be painted with
+ * @param x the x position of the icon
+ * @param y the y position of the icon
+ */
+ public void paintIcon(Component c, Graphics g, int x, int y)
+ {
+ Color savedColor = g.getColor();
+ JRadioButton b = (JRadioButton) c;
+
+ // draw outer circle
+ if (b.isEnabled())
+ g.setColor(Color.GRAY);
+ else
+ g.setColor(Color.GRAY);
+ g.drawLine(x + 2, y + 1, x + 3, y + 1);
+ g.drawLine(x + 4, y, x + 7, y);
+ g.drawLine(x + 8, y + 1, x + 9, y + 1);
+ g.drawLine(x + 10, y + 2, x + 10, y + 3);
+ g.drawLine(x + 11, y + 4, x + 11, y + 7);
+ g.drawLine(x + 10, y + 8, x + 10, y + 9);
+ g.drawLine(x + 8, y + 10, x + 9, y + 10);
+ g.drawLine(x + 4, y + 11, x + 7, y + 11);
+ g.drawLine(x + 2, y + 10, x + 3, y + 10);
+ g.drawLine(x + 1, y + 9, x + 1, y + 8);
+ g.drawLine(x, y + 7, x, y + 4);
+ g.drawLine(x + 1, y + 2, x + 1, y + 3);
+
+ if (b.getModel().isArmed())
+ {
+ g.setColor(Color.GRAY);
+ g.drawLine(x + 4, y + 1, x + 7, y + 1);
+ g.drawLine(x + 4, y + 10, x + 7, y + 10);
+ g.drawLine(x + 1, y + 4, x + 1, y + 7);
+ g.drawLine(x + 10, y + 4, x + 10, y + 7);
+ g.fillRect(x + 2, y + 2, 8, 8);
+ }
+ else
+ {
+ // only draw inner highlight if not filled
+ if (b.isEnabled())
+ {
+ g.setColor(Color.WHITE);
+
+ g.drawLine(x + 2, y + 8, x + 2, y + 9);
+ g.drawLine(x + 1, y + 4, x + 1, y + 7);
+ g.drawLine(x + 2, y + 2, x + 2, y + 3);
+ g.drawLine(x + 3, y + 2, x + 3, y + 2);
+ g.drawLine(x + 4, y + 1, x + 7, y + 1);
+ g.drawLine(x + 8, y + 2, x + 9, y + 2);
+ }
+ }
+
+ // draw outer highlight
+ if (b.isEnabled())
+ {
+ g.setColor(Color.WHITE);
+
+ // outer
+ g.drawLine(x + 10, y + 1, x + 10, y + 1);
+ g.drawLine(x + 11, y + 2, x + 11, y + 3);
+ g.drawLine(x + 12, y + 4, x + 12, y + 7);
+ g.drawLine(x + 11, y + 8, x + 11, y + 9);
+ g.drawLine(x + 10, y + 10, x + 10, y + 10);
+ g.drawLine(x + 8, y + 11, x + 9, y + 11);
+ g.drawLine(x + 4, y + 12, x + 7, y + 12);
+ g.drawLine(x + 2, y + 11, x + 3, y + 11);
+ }
+
+ if (b.isSelected())
+ {
+ if (b.isEnabled())
+ g.setColor(Color.BLACK);
+ else
+ g.setColor(Color.GRAY);
+ g.drawLine(x + 4, y + 3, x + 7, y + 3);
+ g.fillRect(x + 3, y + 4, 6, 4);
+ g.drawLine(x + 4, y + 8, x + 7, y + 8);
+ }
+ g.setColor(savedColor);
+ }
+ }
}
diff --git a/examples/gnu/classpath/examples/swing/ProgressBarDemo.java b/examples/gnu/classpath/examples/swing/ProgressBarDemo.java
new file mode 100644
index 000000000..d62175bcd
--- /dev/null
+++ b/examples/gnu/classpath/examples/swing/ProgressBarDemo.java
@@ -0,0 +1,219 @@
+/* ProgressBarDemo.java -- A demonstration of JProgressBars
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package gnu.classpath.examples.swing;
+
+import java.awt.BorderLayout;
+import java.awt.event.ActionEvent;
+import java.awt.event.ActionListener;
+
+import javax.swing.Box;
+import javax.swing.BoxLayout;
+import javax.swing.JButton;
+import javax.swing.JFrame;
+import javax.swing.JPanel;
+import javax.swing.JProgressBar;
+import javax.swing.JSlider;
+import javax.swing.SwingUtilities;
+import javax.swing.event.ChangeEvent;
+import javax.swing.event.ChangeListener;
+
+public class ProgressBarDemo
+ extends JFrame
+ implements ActionListener
+{
+
+ /**
+ * Creates a new ProgressBarDemo window with the specified title.
+ *
+ * @param title the title of the program window
+ */
+ ProgressBarDemo(String title)
+ {
+ super(title);
+ JPanel content = createContent();
+ JPanel closePanel = new JPanel();
+ JButton closeButton = new JButton("Close");
+ closeButton.setActionCommand("CLOSE");
+ closeButton.addActionListener(this);
+ closePanel.add(closeButton);
+ getContentPane().add(content);
+ getContentPane().add(closePanel, BorderLayout.SOUTH);
+ }
+
+ static JPanel createContent()
+ {
+ JPanel content = new JPanel();
+ content.setLayout(new BoxLayout(content, BoxLayout.Y_AXIS));
+ JPanel horizontalProgressBar = createHorizontalProgressBar();
+ content.add(horizontalProgressBar);
+ content.add(Box.createVerticalStrut(10));
+ JPanel verticalProgressBar = createVerticalProgressBar();
+ content.add(verticalProgressBar);
+ return content;
+ }
+
+ private static JPanel createHorizontalProgressBar()
+ {
+ JPanel panel = new JPanel();
+ panel.setLayout(new BoxLayout(panel, BoxLayout.Y_AXIS));
+
+ // Plain progress bar.
+ final JProgressBar hor1 = new JProgressBar(JProgressBar.HORIZONTAL, 0, 100);
+ panel.add(hor1);
+ final JSlider slider1 = new JSlider(JSlider.HORIZONTAL, 0, 100, 0);
+ slider1.addChangeListener(new ChangeListener()
+ {
+ public void stateChanged(ChangeEvent event)
+ {
+ hor1.setValue(slider1.getValue());
+ }
+ });
+ panel.add(slider1);
+
+ panel.add(Box.createVerticalStrut(5));
+
+ // Plain progress bar with some text.
+ final JProgressBar hor2 = new JProgressBar(JProgressBar.HORIZONTAL, 0, 100);
+ hor2.setString("ProgressBar Demo");
+ hor2.setStringPainted(true);
+ panel.add(hor2);
+ final JSlider slider2 = new JSlider(JSlider.HORIZONTAL, 0, 100, 0);
+ slider2.addChangeListener(new ChangeListener()
+ {
+ public void stateChanged(ChangeEvent event)
+ {
+ hor2.setValue(slider2.getValue());
+ }
+ });
+ panel.add(slider2);
+
+ panel.add(Box.createVerticalStrut(5));
+
+ // Indeterminate progress bar.
+ final JProgressBar hor3 = new JProgressBar(JProgressBar.HORIZONTAL, 0, 100);
+ hor3.setIndeterminate(true);
+ panel.add(hor3);
+
+ panel.add(Box.createVerticalStrut(5));
+
+ // Indeterminate progress bar with text.
+ final JProgressBar hor4 = new JProgressBar(JProgressBar.HORIZONTAL, 0, 100);
+ hor4.setIndeterminate(true);
+ hor4.setString("Indeterminate ProgressBar");
+ hor4.setStringPainted(true);
+ panel.add(hor4);
+
+ return panel;
+ }
+
+ private static JPanel createVerticalProgressBar()
+ {
+ JPanel panel = new JPanel();
+ panel.setLayout(new BoxLayout(panel, BoxLayout.X_AXIS));
+ final JProgressBar vert = new JProgressBar(JProgressBar.VERTICAL, 0, 100);
+ panel.add(vert);
+ final JSlider slider = new JSlider(JSlider.VERTICAL, 0, 100, 0);
+ slider.addChangeListener(new ChangeListener()
+ {
+ public void stateChanged(ChangeEvent event)
+ {
+ vert.setValue(slider.getValue());
+ }
+ });
+ panel.add(slider);
+
+ panel.add(Box.createHorizontalStrut(5));
+
+ final JProgressBar vert2 = new JProgressBar(JProgressBar.VERTICAL, 0, 100);
+ vert2.setString("ProgressBar Demo");
+ panel.add(vert2);
+ vert2.setStringPainted(true);
+ final JSlider slider2 = new JSlider(JSlider.VERTICAL, 0, 100, 0);
+ slider2.addChangeListener(new ChangeListener()
+ {
+ public void stateChanged(ChangeEvent event)
+ {
+ vert2.setValue(slider2.getValue());
+ }
+ });
+ panel.add(slider2);
+
+ panel.add(Box.createHorizontalStrut(5));
+
+ // Indeterminate progress bar.
+ final JProgressBar vert3 = new JProgressBar(JProgressBar.VERTICAL, 0, 100);
+ vert3.setIndeterminate(true);
+ panel.add(vert3);
+
+ panel.add(Box.createHorizontalStrut(5));
+
+ // Indeterminate progress bar with text.
+ final JProgressBar vert4 = new JProgressBar(JProgressBar.VERTICAL, 0, 100);
+ vert4.setIndeterminate(true);
+ vert4.setString("Indeterminate ProgressBar");
+ vert4.setStringPainted(true);
+ panel.add(vert4);
+ return panel;
+ }
+
+ public void actionPerformed(ActionEvent event)
+ {
+ // TODO Auto-generated method stub
+
+ }
+
+ /**
+ * The entry point when running as a standalone program.
+ *
+ * @param args command line arguments
+ */
+ public static void main(String[] args)
+ {
+ SwingUtilities.invokeLater(
+ new Runnable()
+ {
+ public void run()
+ {
+ ProgressBarDemo app = new ProgressBarDemo("ProgressBar Demo");
+ app.pack();
+ app.setVisible(true);
+ }
+ });
+ }
+}
diff --git a/examples/gnu/classpath/examples/swing/TextFieldDemo.java b/examples/gnu/classpath/examples/swing/TextFieldDemo.java
new file mode 100644
index 000000000..5ddf11680
--- /dev/null
+++ b/examples/gnu/classpath/examples/swing/TextFieldDemo.java
@@ -0,0 +1,488 @@
+/* TextFieldDemo.java -- An example showing various textfields in Swing.
+ Copyright (C) 2005, Free Software Foundation, Inc.
+
+This file is part of GNU Classpath examples.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+*/
+
+
+package gnu.classpath.examples.swing;
+
+import java.awt.BorderLayout;
+import java.awt.Color;
+import java.awt.Font;
+import java.awt.Graphics;
+import java.awt.GridLayout;
+import java.awt.Rectangle;
+import java.awt.event.ActionEvent;
+import java.awt.event.ActionListener;
+
+import javax.swing.BorderFactory;
+import javax.swing.Box;
+import javax.swing.BoxLayout;
+import javax.swing.JButton;
+import javax.swing.JCheckBox;
+import javax.swing.JFrame;
+import javax.swing.JPanel;
+import javax.swing.JTextField;
+import javax.swing.text.BadLocationException;
+import javax.swing.text.DefaultCaret;
+import javax.swing.text.JTextComponent;
+
+/**
+ * A simple textfield demo showing various textfields in different states.
+ */
+public class TextFieldDemo
+ extends JFrame
+ implements ActionListener
+{
+
+ /**
+ * A custom caret for demonstration purposes. This class is inspired by the
+ * CornerCaret from the OReilly Swing book.
+ *
+ * @author Roman Kennke (kennke@aicas.com)
+ */
+ static class CornerCaret extends DefaultCaret
+ {
+ public CornerCaret()
+ {
+ super();
+ setBlinkRate(500);
+ }
+
+ protected synchronized void damage(Rectangle r)
+ {
+ if (r == null) return;
+ x = r.x;
+ y = r.y + (r.height * 4 / 5 - 3);
+ width = 5;
+ height = 5;
+ repaint();
+ }
+
+ public void paint(Graphics g)
+ {
+ JTextComponent comp = getComponent();
+ if (comp == null) return;
+ int dot = getDot();
+ Rectangle r = null;
+ try
+ {
+ r = comp.modelToView(dot);
+ }
+ catch (BadLocationException e)
+ {
+ return;
+ }
+ if (r == null) return;
+ int dist = r.height * 4 / 5 - 3;
+ if ((x != r.x) || (y != r.y + dist))
+ {
+ repaint();
+ x = r.x;
+ y = r.y + dist;
+ width = 5;
+ height = 5;
+ }
+ if (isVisible())
+ {
+ g.drawLine(r.x, r.y + dist, r.x, r.y + dist + 4);
+ g.drawLine(r.x, r.y + dist + 4, r.x + 4, r.y + dist + 4);
+ }
+ }
+ }
+
+ /**
+ * The left aligned textfields and state buttons.
+ */
+ JTextField textfield1;
+ JTextField textfield2;
+ JTextField textfield3;
+ JCheckBox enabled1;
+ JCheckBox editable1;
+JPanel textFieldPanel1;
+ /**
+ * The right aligned textfields and state buttons.
+ */
+ JTextField textfield4;
+ JTextField textfield5;
+ JTextField textfield6;
+ JCheckBox enabled2;
+ JCheckBox editable2;
+
+ /**
+ * The centered textfields and state buttons.
+ */
+ JTextField textfield7;
+ JTextField textfield8;
+ JTextField textfield9;
+ JCheckBox enabled3;
+ JCheckBox editable3;
+
+ /**
+ * The custom colored textfields and state buttons.
+ */
+ JTextField textfield10;
+ JTextField textfield11;
+ JTextField textfield12;
+ JTextField textfield13;
+ JTextField textfield14;
+ JCheckBox enabled4;
+ JCheckBox editable4;
+
+ /**
+ * Some miscallenous textfield demos.
+ */
+ JTextField textfield15;
+ JTextField textfield16;
+ JCheckBox enabled5;
+ JCheckBox editable5;
+
+ /**
+ * Creates a new demo instance.
+ *
+ * @param title the frame title.
+ */
+ public TextFieldDemo(String title)
+ {
+ super(title);
+ JPanel content = createContent();
+ JPanel closePanel = new JPanel();
+ JButton closeButton = new JButton("Close");
+ closeButton.setActionCommand("CLOSE");
+ closeButton.addActionListener(this);
+ closePanel.add(closeButton);
+ content.add(closePanel, BorderLayout.SOUTH);
+ getContentPane().add(content);
+ }
+
+ /**
+ * Returns a panel with the demo content. The panel
+ * uses a BorderLayout(), and the BorderLayout.SOUTH area
+ * is empty, to allow callers to add controls to the
+ * bottom of the panel if they want to (a close button is
+ * added if this demo is being run as a standalone demo).
+ */
+ JPanel createContent()
+ {
+ JPanel content = new JPanel(new BorderLayout());
+ JPanel panel = new JPanel(new GridLayout(5, 1));
+ panel.add(createLeftAlignedPanel());
+ panel.add(createRightAlignedPanel());
+ panel.add(createCenteredPanel());
+ panel.add(createCustomColoredPanel());
+ panel.add(createMiscPanel());
+ content.add(panel);
+ //content.setPreferredSize(new Dimension(400, 300));
+ return content;
+ }
+
+ private JPanel createLeftAlignedPanel()
+ {
+ JPanel panel = new JPanel(new BorderLayout());
+ panel.setBorder(BorderFactory.createTitledBorder("Left aligned"));
+
+ textFieldPanel1 = new JPanel();
+ textFieldPanel1.setLayout(new BoxLayout(textFieldPanel1, BoxLayout.X_AXIS));
+
+ textfield1 = new JTextField("Hello World!");
+ textfield1.setHorizontalAlignment(JTextField.LEFT);
+ textfield1.setFont(new Font("Dialog", Font.PLAIN, 8));
+ textFieldPanel1.add(textfield1);
+
+ textfield2 = new JTextField("Hello World!");
+ textfield2.setHorizontalAlignment(JTextField.LEFT);
+ textfield2.setFont(new Font("Dialog", Font.ITALIC, 12));
+ textFieldPanel1.add(textfield2);
+
+ textfield3 = new JTextField("Hello World!");
+ textfield3.setHorizontalAlignment(JTextField.LEFT);
+ textfield3.setFont(new Font("Dialog", Font.BOLD, 14));
+ textFieldPanel1.add(textfield3);
+
+ panel.add(textFieldPanel1);
+
+ JPanel statePanel = new JPanel();
+ statePanel.setLayout(new BoxLayout(statePanel, BoxLayout.Y_AXIS));
+ statePanel.add(Box.createVerticalGlue());
+ enabled1 = new JCheckBox("enabled");
+ enabled1.setSelected(true);
+ enabled1.addActionListener(this);
+ enabled1.setActionCommand("ENABLED1");
+ statePanel.add(enabled1);
+ editable1 = new JCheckBox("editable");
+ editable1.setSelected(true);
+ editable1.addActionListener(this);
+ editable1.setActionCommand("EDITABLE1");
+ statePanel.add(editable1);
+ statePanel.add(Box.createVerticalGlue());
+ panel.add(statePanel, BorderLayout.EAST);
+
+ return panel;
+ }
+
+ private JPanel createRightAlignedPanel()
+ {
+ JPanel panel = new JPanel(new BorderLayout());
+ panel.setBorder(BorderFactory.createTitledBorder("Right aligned"));
+
+ JPanel textFieldPanel = new JPanel();
+ textFieldPanel.setLayout(new BoxLayout(textFieldPanel, BoxLayout.X_AXIS));
+
+ textfield4 = new JTextField("Hello World!");
+ textfield4.setHorizontalAlignment(JTextField.RIGHT);
+ textfield4.setFont(new Font("Dialog", Font.PLAIN, 8));
+ textFieldPanel.add(textfield4);
+
+ textfield5 = new JTextField("Hello World!");
+ textfield5.setHorizontalAlignment(JTextField.RIGHT);
+ textfield5.setFont(new Font("Dialog", Font.ITALIC, 12));
+ textFieldPanel.add(textfield5);
+
+ textfield6 = new JTextField("Hello World!");
+ textfield6.setHorizontalAlignment(JTextField.RIGHT);
+ textfield6.setFont(new Font("Dialog", Font.BOLD, 14));
+ textFieldPanel.add(textfield6);
+
+ panel.add(textFieldPanel);
+
+ JPanel statePanel = new JPanel();
+ statePanel.setLayout(new BoxLayout(statePanel, BoxLayout.Y_AXIS));
+ statePanel.add(Box.createVerticalGlue());
+ enabled2 = new JCheckBox("enabled");
+ enabled2.setSelected(true);
+ enabled2.addActionListener(this);
+ enabled2.setActionCommand("ENABLED2");
+ statePanel.add(enabled2);
+ editable2 = new JCheckBox("editable");
+ editable2.setSelected(true);
+ editable2.addActionListener(this);
+ editable2.setActionCommand("EDITABLE2");
+ statePanel.add(editable2);
+ statePanel.add(Box.createVerticalGlue());
+ panel.add(statePanel, BorderLayout.EAST);
+
+ return panel;
+ }
+
+ private JPanel createCenteredPanel()
+ {
+ JPanel panel = new JPanel(new BorderLayout());
+ panel.setBorder(BorderFactory.createTitledBorder("Centered"));
+
+ JPanel textFieldPanel = new JPanel();
+ textFieldPanel.setLayout(new BoxLayout(textFieldPanel, BoxLayout.X_AXIS));
+
+ textfield7 = new JTextField("Hello World!");
+ textfield7.setHorizontalAlignment(JTextField.CENTER);
+ textfield7.setFont(new Font("Dialog", Font.PLAIN, 8));
+ textFieldPanel.add(textfield7);
+
+ textfield8 = new JTextField("Hello World!");
+ textfield8.setHorizontalAlignment(JTextField.CENTER);
+ textfield8.setFont(new Font("Dialog", Font.ITALIC, 12));
+ textFieldPanel.add(textfield8);
+
+ textfield9 = new JTextField("Hello World!");
+ textfield9.setHorizontalAlignment(JTextField.CENTER);
+ textfield9.setFont(new Font("Dialog", Font.BOLD, 14));
+ textFieldPanel.add(textfield9);
+
+ panel.add(textFieldPanel);
+
+ JPanel statePanel = new JPanel();
+ statePanel.setLayout(new BoxLayout(statePanel, BoxLayout.Y_AXIS));
+ statePanel.add(Box.createVerticalGlue());
+ enabled3 = new JCheckBox("enabled");
+ enabled3.setSelected(true);
+ enabled3.addActionListener(this);
+ enabled3.setActionCommand("ENABLED3");
+ statePanel.add(enabled3);
+ editable3 = new JCheckBox("editable");
+ editable3.setSelected(true);
+ editable3.addActionListener(this);
+ editable3.setActionCommand("EDITABLE3");
+ statePanel.add(editable3);
+ statePanel.add(Box.createVerticalGlue());
+ panel.add(statePanel, BorderLayout.EAST);
+
+ return panel;
+ }
+
+ private JPanel createCustomColoredPanel()
+ {
+ JPanel panel = new JPanel(new BorderLayout());
+
+ JPanel textFieldPanel = new JPanel();
+ panel.setBorder(BorderFactory.createTitledBorder("Custom colors"));
+ textFieldPanel.setLayout(new BoxLayout(textFieldPanel, BoxLayout.X_AXIS));
+
+ textfield10 = new JTextField("custom foreground");
+ textfield10.setForeground(Color.GREEN);
+ textFieldPanel.add(textfield10);
+
+ textfield11 = new JTextField("custom background");
+ textfield11.setForeground(Color.YELLOW);
+ textFieldPanel.add(textfield11);
+
+ textfield12 = new JTextField("custom disabled textcolor");
+ textfield12.setDisabledTextColor(Color.BLUE);
+ textFieldPanel.add(textfield12);
+
+ textfield13 = new JTextField("custom selected text color");
+ textfield13.setSelectedTextColor(Color.RED);
+ textFieldPanel.add(textfield13);
+
+ textfield14 = new JTextField("custom selection color");
+ textfield14.setSelectionColor(Color.CYAN);
+ textFieldPanel.add(textfield14);
+
+ panel.add(textFieldPanel);
+
+ JPanel statePanel = new JPanel();
+ statePanel.setLayout(new BoxLayout(statePanel, BoxLayout.Y_AXIS));
+ statePanel.add(Box.createVerticalGlue());
+ enabled4 = new JCheckBox("enabled");
+ enabled4.setSelected(true);
+ enabled4.addActionListener(this);
+ enabled4.setActionCommand("ENABLED4");
+ statePanel.add(enabled4);
+ editable4 = new JCheckBox("editable");
+ editable4.setSelected(true);
+ editable4.addActionListener(this);
+ editable4.setActionCommand("EDITABLE4");
+ statePanel.add(editable4);
+ statePanel.add(Box.createVerticalGlue());
+ panel.add(statePanel, BorderLayout.EAST);
+
+ return panel;
+ }
+
+ private JPanel createMiscPanel()
+ {
+ JPanel panel = new JPanel(new BorderLayout());
+ panel.setBorder(BorderFactory.createTitledBorder("Miscallenous"));
+
+ JPanel textFieldPanel = new JPanel();
+ textFieldPanel.setLayout(new BoxLayout(textFieldPanel, BoxLayout.X_AXIS));
+
+ textfield15 = new JTextField("Custom Caret");
+ textfield15.setCaret(new CornerCaret());
+ textFieldPanel.add(textfield15);
+
+ textfield16 = new JTextField("Custom Caret color");
+ textfield16.setCaretColor(Color.MAGENTA);
+ textFieldPanel.add(textfield16);
+
+ panel.add(textFieldPanel);
+
+ JPanel statePanel = new JPanel();
+ statePanel.setLayout(new BoxLayout(statePanel, BoxLayout.Y_AXIS));
+ statePanel.add(Box.createVerticalGlue());
+ enabled5 = new JCheckBox("enabled");
+ enabled5.setSelected(true);
+ enabled5.addActionListener(this);
+ enabled5.setActionCommand("ENABLED5");
+ statePanel.add(enabled5);
+ editable5 = new JCheckBox("editable");
+ editable5.setSelected(true);
+ editable5.addActionListener(this);
+ editable5.setActionCommand("EDITABLE5");
+ statePanel.add(editable5);
+ statePanel.add(Box.createVerticalGlue());
+ panel.add(statePanel, BorderLayout.EAST);
+
+ return panel;
+ }
+
+ public void actionPerformed(ActionEvent e)
+ {
+ if (e.getActionCommand().equals("CLOSE"))
+ {
+ System.exit(0);
+ }
+ else if (e.getActionCommand().equals("ENABLED1"))
+ {
+ boolean enabled = enabled1.isSelected();
+ textfield1.setEnabled(enabled);
+ textfield2.setEnabled(enabled);
+ textfield3.setEnabled(enabled);
+ }
+ else if (e.getActionCommand().equals("EDITABLE1"))
+ {
+ boolean editable = editable1.isSelected();
+ textfield1.setEditable(editable);
+ textfield2.setEditable(editable);
+ textfield3.setEditable(editable);
+ }
+ else if (e.getActionCommand().equals("ENABLED2"))
+ {
+ boolean enabled = enabled2.isSelected();
+ textfield4.setEnabled(enabled);
+ textfield5.setEnabled(enabled);
+ textfield6.setEnabled(enabled);
+ }
+ else if (e.getActionCommand().equals("EDITABLE2"))
+ {
+ boolean editable = editable2.isSelected();
+ textfield4.setEditable(editable);
+ textfield5.setEditable(editable);
+ textfield6.setEditable(editable);
+ }
+ else if (e.getActionCommand().equals("ENABLED3"))
+ {
+ boolean enabled = enabled3.isSelected();
+ textfield7.setEnabled(enabled);
+ textfield8.setEnabled(enabled);
+ textfield9.setEnabled(enabled);
+ }
+ else if (e.getActionCommand().equals("EDITABLE3"))
+ {
+ boolean editable = editable3.isSelected();
+ textfield7.setEditable(editable);
+ textfield8.setEditable(editable);
+ textfield9.setEditable(editable);
+ }
+ else if (e.getActionCommand().equals("ENABLED4"))
+ {
+ boolean enabled = enabled4.isSelected();
+ textfield10.setEnabled(enabled);
+ textfield11.setEnabled(enabled);
+ textfield12.setEnabled(enabled);
+ textfield13.setEnabled(enabled);
+ textfield14.setEnabled(enabled);
+ }
+ else if (e.getActionCommand().equals("EDITABLE4"))
+ {
+ boolean editable = editable4.isSelected();
+ textfield10.setEditable(editable);
+ textfield11.setEditable(editable);
+ textfield12.setEditable(editable);
+ textfield13.setEditable(editable);
+ textfield14.setEditable(editable);
+ }
+ }
+
+ public static void main(String[] args)
+ {
+ TextFieldDemo app = new TextFieldDemo("TextField Demo");
+ app.pack();
+ app.setVisible(true);
+ }
+
+}
diff --git a/gnu/CORBA/IOR.java b/gnu/CORBA/IOR.java
index 4f724e8a1..5d6d3152f 100644
--- a/gnu/CORBA/IOR.java
+++ b/gnu/CORBA/IOR.java
@@ -59,6 +59,8 @@ import org.omg.IOP.TaggedProfileHelper;
import java.io.ByteArrayOutputStream;
import java.io.IOException;
import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.zip.Adler32;
/**
* The implementaton of the Interoperable Object Reference (IOR). IOR can be
@@ -716,4 +718,51 @@ public class IOR
// The future supported tagged profiles should be added here.
throw new BAD_PARAM("Unsupported profile type " + profile.tag);
}
+
+ /**
+ * Checks for equality.
+ */
+ public boolean equals(Object x)
+ {
+ if (x instanceof IOR)
+ {
+ boolean keys;
+ boolean hosts = true;
+
+ IOR other = (IOR) x;
+
+ if (Internet==null || other.Internet==null)
+ return Internet == other.Internet;
+
+ if (key != null && other.key != null)
+ keys = Arrays.equals(key, other.key);
+ else
+ keys = key == other.key;
+
+ if (Internet != null && Internet.host != null)
+ if (other.Internet != null && other.Internet.host != null)
+ hosts = other.Internet.host.equals(Internet.host);
+
+ return keys & hosts && Internet.port==other.Internet.port;
+ }
+ else
+ return false;
+ }
+
+ /**
+ * Get the hashcode of this IOR.
+ */
+ public int hashCode()
+ {
+ Adler32 adler = new Adler32();
+ if (key != null)
+ adler.update(key);
+ if (Internet != null)
+ {
+ if (Internet.host != null)
+ adler.update(Internet.host.getBytes());
+ adler.update(Internet.port);
+ }
+ return (int) adler.getValue();
+ }
} \ No newline at end of file
diff --git a/gnu/CORBA/Interceptor/IORInterceptors.java b/gnu/CORBA/Interceptor/IORInterceptors.java
index 88756988c..2b77de58e 100644
--- a/gnu/CORBA/Interceptor/IORInterceptors.java
+++ b/gnu/CORBA/Interceptor/IORInterceptors.java
@@ -38,16 +38,20 @@ exception statement from your version. */
package gnu.CORBA.Interceptor;
+import org.omg.CORBA.OBJ_ADAPTER;
+import org.omg.CORBA.OMGVMCID;
import org.omg.PortableInterceptor.IORInfo;
import org.omg.PortableInterceptor.IORInterceptor;
import org.omg.PortableInterceptor.IORInterceptorOperations;
+import org.omg.PortableInterceptor.IORInterceptor_3_0Operations;
+import org.omg.PortableInterceptor.ObjectReferenceTemplate;
/**
* A block of the all registered IOR interceptors.
*
* @author Audrius Meskauskas, Lithuania (AudriusA@Bioinformatics.org)
*/
-public class IORInterceptors implements IORInterceptorOperations
+public class IORInterceptors implements IORInterceptor_3_0Operations
{
/**
* The array of all registered IOR interceptors.
@@ -106,4 +110,81 @@ public class IORInterceptors implements IORInterceptorOperations
{
return getClass().getName();
}
+
+ /**
+ * Call this method for all registered CORBA 3.0 interceptors.
+ */
+ public void adapter_manager_state_changed(int adapterManagerId, short adapterState)
+ {
+ for (int i = 0; i < interceptors.length; i++)
+ {
+ try
+ {
+ if (interceptors[i] instanceof IORInterceptor_3_0Operations)
+ {
+ ((IORInterceptor_3_0Operations) interceptors[i]).
+ adapter_manager_state_changed(adapterManagerId, adapterState);
+ }
+ }
+ catch (Exception exc)
+ {
+ OBJ_ADAPTER oa = new OBJ_ADAPTER("components_established failed");
+ oa.initCause(exc);
+ oa.minor = 6 | OMGVMCID.value;
+ throw oa;
+ }
+ }
+ }
+
+ /**
+ * Call this method for all registered CORBA 3.0 interceptors.
+ */
+ public void adapter_state_changed(ObjectReferenceTemplate[] adapters, short adaptersState)
+ {
+ for (int i = 0; i < interceptors.length; i++)
+ {
+ try
+ {
+ if (interceptors[i] instanceof IORInterceptor_3_0Operations)
+ {
+ ((IORInterceptor_3_0Operations) interceptors[i]).
+ adapter_state_changed(adapters, adaptersState);
+ }
+ }
+ catch (Exception exc)
+ {
+ OBJ_ADAPTER oa = new OBJ_ADAPTER("components_established failed");
+ oa.initCause(exc);
+ oa.minor = 6 | OMGVMCID.value;
+ throw oa;
+ }
+ }
+ }
+
+ /**
+ * Call this method for all registered CORBA 3.0 interceptors.
+ *
+ * @throws OBJ_ADAPTER minor 6 on any failure (as defined by OMG specs).
+ */
+ public void components_established(IORInfo info)
+ {
+ for (int i = 0; i < interceptors.length; i++)
+ {
+ try
+ {
+ if (interceptors[i] instanceof IORInterceptor_3_0Operations)
+ {
+ ((IORInterceptor_3_0Operations) interceptors[i]).
+ components_established(info);
+ }
+ }
+ catch (Exception exc)
+ {
+ OBJ_ADAPTER oa = new OBJ_ADAPTER("components_established failed");
+ oa.initCause(exc);
+ oa.minor = 6 | OMGVMCID.value;
+ throw oa;
+ }
+ }
+ }
} \ No newline at end of file
diff --git a/gnu/CORBA/Interceptor/gnuIorInfo.java b/gnu/CORBA/Interceptor/gnuIorInfo.java
index 1c406cb5e..256a28cb5 100644
--- a/gnu/CORBA/Interceptor/gnuIorInfo.java
+++ b/gnu/CORBA/Interceptor/gnuIorInfo.java
@@ -40,12 +40,14 @@ package gnu.CORBA.Interceptor;
import gnu.CORBA.IOR;
import gnu.CORBA.Poa.ORB_1_4;
+import gnu.CORBA.Poa.gnuPOA;
import org.omg.CORBA.LocalObject;
import org.omg.CORBA.Policy;
import org.omg.IOP.TaggedComponent;
import org.omg.PortableInterceptor.IORInfo;
-import org.omg.PortableServer.POA;
+import org.omg.PortableInterceptor.ObjectReferenceFactory;
+import org.omg.PortableInterceptor.ObjectReferenceTemplate;
/**
* Implements IORInfo.
@@ -67,7 +69,7 @@ public class gnuIorInfo extends LocalObject implements IORInfo
/**
* The POA, to that IOR is related.
*/
- public final POA poa;
+ public final gnuPOA poa;
/**
* The IOR itself.
@@ -77,7 +79,7 @@ public class gnuIorInfo extends LocalObject implements IORInfo
/**
* Create an instance.
*/
- public gnuIorInfo(ORB_1_4 an_orb, POA a_poa, IOR an_ior)
+ public gnuIorInfo(ORB_1_4 an_orb, gnuPOA a_poa, IOR an_ior)
{
orb = an_orb;
poa = a_poa;
@@ -113,8 +115,42 @@ public class gnuIorInfo extends LocalObject implements IORInfo
/**
* Return the state of the object POA.
*/
- short state()
+ public short state()
{
return (short) poa.the_POAManager().get_state().value();
}
+
+ /**
+ * Get the adapter template, associated with this poa.
+ */
+ public ObjectReferenceTemplate adapter_template()
+ {
+ return poa.getReferenceTemplate();
+ }
+
+ /**
+ * Get the object factory of the current POA.
+ */
+ public ObjectReferenceFactory current_factory()
+ {
+ return poa.getReferenceFactory();
+ }
+
+ /**
+ * Set the object factory of the current POA.
+ */
+ public void current_factory(ObjectReferenceFactory factory)
+ {
+ poa.setReferenceFactory(factory);
+ }
+
+ /**
+ * The method currently uses system identity hashcode that should be
+ * different for each object.
+ */
+ public int manager_id()
+ {
+ // The System.identityHashCode is also called in gnuPoaManager.
+ return System.identityHashCode(poa.the_POAManager());
+ }
} \ No newline at end of file
diff --git a/gnu/CORBA/Interceptor/gnuServerRequestInfo.java b/gnu/CORBA/Interceptor/gnuServerRequestInfo.java
index 5f75f7687..8d5c681e7 100644
--- a/gnu/CORBA/Interceptor/gnuServerRequestInfo.java
+++ b/gnu/CORBA/Interceptor/gnuServerRequestInfo.java
@@ -42,6 +42,7 @@ import gnu.CORBA.GIOP.ReplyHeader;
import gnu.CORBA.GIOP.RequestHeader;
import gnu.CORBA.ObjectCreator;
import gnu.CORBA.Poa.gnuServantObject;
+import gnu.CORBA.OrbFunctional;
import gnu.CORBA.Unexpected;
import gnu.CORBA.gnuRequest;
@@ -453,4 +454,23 @@ public class gnuServerRequestInfo extends LocalObject
}
return p;
}
+
+ /** @inheritDoc */
+ public String[] adapter_name()
+ {
+ return m_object.poa.getReferenceTemplate().adapter_name();
+ }
+
+ /** @inheritDoc */
+ public String orb_id()
+ {
+ return m_object.orb.orb_id;
+ }
+
+ /** @inheritDoc */
+ public String server_id()
+ {
+ return OrbFunctional.server_id;
+ }
+
} \ No newline at end of file
diff --git a/gnu/CORBA/Minor.java b/gnu/CORBA/Minor.java
index fb5991dc9..511a34d55 100644
--- a/gnu/CORBA/Minor.java
+++ b/gnu/CORBA/Minor.java
@@ -272,5 +272,11 @@ public interface Minor
* submitting large number of requests.
*/
int Threads = 21 | vendor;
+
+ /**
+ * The IOR starts with file://, http:// or ftp://, but this local or remote
+ * resource is not accessible.
+ */
+ int Missing_IOR = 22 | vendor;
}
diff --git a/gnu/CORBA/NamingService/NameParser.java b/gnu/CORBA/NamingService/NameParser.java
index 8fc75c6a5..422db1c58 100644
--- a/gnu/CORBA/NamingService/NameParser.java
+++ b/gnu/CORBA/NamingService/NameParser.java
@@ -38,6 +38,7 @@ exception statement from your version. */
package gnu.CORBA.NamingService;
+import gnu.CORBA.Minor;
import gnu.CORBA.OrbFunctional;
import gnu.CORBA.IOR;
import gnu.CORBA.Unexpected;
@@ -53,7 +54,13 @@ import org.omg.CORBA.portable.ObjectImpl;
import org.omg.CosNaming.NamingContext;
import org.omg.CosNaming._NamingContextStub;
+import java.io.File;
+import java.io.FileReader;
+import java.io.IOException;
+import java.io.InputStreamReader;
import java.io.UnsupportedEncodingException;
+import java.net.MalformedURLException;
+import java.net.URL;
import java.net.URLDecoder;
import java.util.ArrayList;
import java.util.StringTokenizer;
@@ -88,6 +95,21 @@ public class NameParser
* The IOR prefix.
*/
public static final String pxIOR = "ior";
+
+ /**
+ * The file:// prefix.
+ */
+ public static final String pxFILE = "file://";
+
+ /**
+ * The ftp:// prefix.
+ */
+ public static final String pxFTP = "ftp://";
+
+ /**
+ * The http:// prefix.
+ */
+ public static final String pxHTTP = "http://";
/**
* Marks iiop protocol.
@@ -132,6 +154,9 @@ public class NameParser
* 2. corbaloc:rir:[/key] <br>
* 3. corbaname:[iiop][version.subversion@]:host[:port]/key <br>
* 4. corbaname:rir:[/key] <br>
+ * 5. file://[file name]<br>
+ * 6. http://[url]<br>
+ * 7. ftp://[url]<br>
*
* Protocol defaults to IOP, the object key defaults to the NameService.
*
@@ -144,6 +169,28 @@ public class NameParser
OrbFunctional orb)
throws BAD_PARAM
{
+ return corbaloc(corbaloc, orb, 0);
+ }
+
+ /**
+ * Parse controlling against the infinite recursion loop.
+ */
+ private org.omg.CORBA.Object corbaloc(String corbaloc,
+ OrbFunctional orb, int recursion)
+ {
+ // The used CORBA specification does not state how many times we should to
+ //redirect, but the infinite loop may be used to knock out the system.
+ // by malicious attempt.
+ if (recursion > 10)
+ throw new DATA_CONVERSION("More than 10 redirections");
+
+ if (corbaloc.startsWith(pxFILE))
+ return corbaloc(readFile(corbaloc.substring(pxFILE.length())), orb, recursion+1);
+ else if (corbaloc.startsWith(pxHTTP))
+ return corbaloc(readUrl(corbaloc), orb, recursion+1);
+ else if (corbaloc.startsWith(pxFTP))
+ return corbaloc(readUrl(corbaloc), orb, recursion+1);
+
boolean corbaname;
// The alternative addresses, if given.
@@ -302,6 +349,70 @@ public class NameParser
else
throw new DATA_CONVERSION("Unsupported protocol '" + t[p] + "'");
}
+
+ /**
+ * Read IOR from the file in the local file system.
+ */
+ String readFile(String file)
+ {
+ File f = new File(file);
+ if (!f.exists())
+ {
+ DATA_CONVERSION err = new DATA_CONVERSION(f.getAbsolutePath()
+ + " does not exist.");
+ err.minor = Minor.Missing_IOR;
+ }
+ try
+ {
+ char[] c = new char[(int) f.length()];
+ FileReader fr = new FileReader(f);
+ fr.read(c);
+ fr.close();
+ return new String(c).trim();
+ }
+ catch (IOException ex)
+ {
+ DATA_CONVERSION d = new DATA_CONVERSION();
+ d.initCause(ex);
+ d.minor = Minor.Missing_IOR;
+ throw (d);
+ }
+ }
+
+ /**
+ * Read IOR from the remote URL.
+ */
+ String readUrl(String url)
+ {
+ URL u;
+ try
+ {
+ u = new URL(url);
+ }
+ catch (MalformedURLException mex)
+ {
+ throw new BAD_PARAM("Malformed URL: '" + url + "'");
+ }
+
+ try
+ {
+ InputStreamReader r = new InputStreamReader(u.openStream());
+
+ StringBuffer b = new StringBuffer();
+ int c;
+
+ while ((c = r.read()) > 0)
+ b.append((char) c);
+
+ return b.toString().trim();
+ }
+ catch (Exception exc)
+ {
+ DATA_CONVERSION d = new DATA_CONVERSION("Reading " + url + " failed.");
+ d.minor = Minor.Missing_IOR;
+ throw d;
+ }
+ }
private org.omg.CORBA.Object resolve(org.omg.CORBA.Object object)
{
diff --git a/gnu/CORBA/OrbFunctional.java b/gnu/CORBA/OrbFunctional.java
index dd9dcb831..7b9c34ada 100644
--- a/gnu/CORBA/OrbFunctional.java
+++ b/gnu/CORBA/OrbFunctional.java
@@ -298,6 +298,17 @@ public class OrbFunctional extends OrbRestricted
public static final String NAME_SERVICE = "NameService";
/**
+ * Defines the ORB ID that is accessible by IOR interceptors.
+ */
+ public static final String ORB_ID = "org.omg.CORBA.ORBid";
+
+
+ /**
+ * Defines the SERVER ID that is accessible by IOR interceptors.
+ */
+ public static final String SERVER_ID = "org.omg.CORBA.ServerId";
+
+ /**
* The if the client has once opened a socket, it should start sending the
* message header in a given time. Otherwise the server will close the socket.
* This prevents server hang when the client opens the socket, but does not
@@ -370,6 +381,17 @@ public class OrbFunctional extends OrbRestricted
* seven seconds.
*/
public static int TANDEM_REQUESTS = 7000;
+
+ /**
+ * The Id of this ORB.
+ */
+ public String orb_id = "orb_"+hashCode();
+
+ /**
+ * The Id of this Server. This field is defined static to ensure it has
+ * the same value over all ORB's in this machine.
+ */
+ public static String server_id = "server_"+OrbFunctional.class.hashCode();
/**
* The map of the already conncted objects.
@@ -1093,9 +1115,9 @@ public class OrbFunctional extends OrbRestricted
/**
* Set the ORB parameters. This method is normally called from
* {@link #init(Applet, Properties)}.
- *
+ *
* @param app the current applet.
- *
+ *
* @param props application specific properties, passed as the second
* parameter in {@link #init(Applet, Properties)}. Can be <code>null</code>.
*/
@@ -1108,37 +1130,39 @@ public class OrbFunctional extends OrbRestricted
{
for (int i = 0; i < para.length; i++)
{
- if (para [ i ] [ 0 ].equals(LISTEN_ON))
- Port = Integer.parseInt(para [ i ] [ 1 ]);
- if (para [ i ] [ 0 ].equals(REFERENCE))
+ if (para[i][0].equals(LISTEN_ON))
+ Port = Integer.parseInt(para[i][1]);
+ if (para[i][0].equals(REFERENCE))
{
- StringTokenizer st =
- new StringTokenizer(para [ i ] [ 1 ], "=");
+ StringTokenizer st = new StringTokenizer(para[i][1], "=");
initial_references.put(st.nextToken(),
- string_to_object(st.nextToken())
- );
+ string_to_object(st.nextToken()));
}
- if (para [ i ] [ 0 ].equals(NS_HOST))
- ns_host = para [ i ] [ 1 ];
- if (para [ i ] [ 0 ].equals(START_READING_MESSAGE))
- TOUT_START_READING_MESSAGE = Integer.parseInt(para [ i ] [ 1 ]);
- if (para [ i ] [ 0 ].equals(WHILE_READING))
- TOUT_WHILE_READING = Integer.parseInt(para [ i ] [ 1 ]);
- if (para [ i ] [ 0 ].equals(AFTER_RECEIVING))
- TOUT_AFTER_RECEIVING = Integer.parseInt(para [ i ] [ 1 ]);
+ if (para[i][0].equals(ORB_ID))
+ orb_id = para[i][1];
+
+ if (para[i][0].equals(SERVER_ID))
+ server_id = para[i][1];
+
+ if (para[i][0].equals(NS_HOST))
+ ns_host = para[i][1];
+ if (para[i][0].equals(START_READING_MESSAGE))
+ TOUT_START_READING_MESSAGE = Integer.parseInt(para[i][1]);
+ if (para[i][0].equals(WHILE_READING))
+ TOUT_WHILE_READING = Integer.parseInt(para[i][1]);
+ if (para[i][0].equals(AFTER_RECEIVING))
+ TOUT_AFTER_RECEIVING = Integer.parseInt(para[i][1]);
try
{
- if (para [ i ] [ 0 ].equals(NS_PORT))
- ns_port = Integer.parseInt(para [ i ] [ 1 ]);
+ if (para[i][0].equals(NS_PORT))
+ ns_port = Integer.parseInt(para[i][1]);
}
catch (NumberFormatException ex)
{
- BAD_PARAM bad =
- new BAD_PARAM("Invalid " + NS_PORT +
- "property, unable to parse '" +
- props.getProperty(NS_PORT) + "'"
- );
+ BAD_PARAM bad = new BAD_PARAM("Invalid " + NS_PORT
+ + "property, unable to parse '" + props.getProperty(NS_PORT)
+ + "'");
bad.initCause(ex);
throw bad;
}
@@ -1149,11 +1173,11 @@ public class OrbFunctional extends OrbRestricted
/**
* Set the ORB parameters. This method is normally called from
* {@link #init(String[], Properties)}.
- *
+ *
* @param para the parameters, that were passed as the parameters to the
* <code>main(String[] args)</code> method of the current standalone
* application.
- *
+ *
* @param props application specific properties that were passed as a second
* parameter in {@link init(String[], Properties)}). Can be <code>null</code>.
*/
@@ -1163,29 +1187,33 @@ public class OrbFunctional extends OrbRestricted
{
for (int i = 0; i < para.length - 1; i++)
{
- if (para [ i ].endsWith("ListenOn"))
- Port = Integer.parseInt(para [ i + 1 ]);
- if (para [ i ].endsWith("ORBInitRef"))
+ if (para[i].endsWith("ListenOn"))
+ Port = Integer.parseInt(para[i + 1]);
+ if (para[i].endsWith("ORBInitRef"))
{
- StringTokenizer st = new StringTokenizer(para [ i + 1 ], "=");
+ StringTokenizer st = new StringTokenizer(para[i + 1], "=");
initial_references.put(st.nextToken(),
- string_to_object(st.nextToken())
- );
+ string_to_object(st.nextToken()));
}
- if (para [ i ].endsWith("ORBInitialHost"))
- ns_host = para [ i + 1 ];
+ if (para[i].endsWith("ORBInitialHost"))
+ ns_host = para[i + 1];
+
+ if (para[i].endsWith("ServerId"))
+ server_id = para[i++];
+ else if (para[i].endsWith("ORBid"))
+ orb_id = para[i++];
+
try
{
- if (para [ i ].endsWith("ORBInitialPort"))
- ns_port = Integer.parseInt(para [ i + 1 ]);
+ if (para[i].endsWith("ORBInitialPort"))
+ ns_port = Integer.parseInt(para[i + 1]);
}
catch (NumberFormatException ex)
{
- throw new BAD_PARAM("Invalid " + para [ i ] +
- "parameter, unable to parse '" +
- props.getProperty(para [ i + 1 ]) + "'"
- );
+ throw new BAD_PARAM("Invalid " + para[i]
+ + "parameter, unable to parse '"
+ + props.getProperty(para[i + 1]) + "'");
}
}
}
@@ -1584,6 +1612,18 @@ public class OrbFunctional extends OrbRestricted
// TODO log it.
return;
}
+ finally
+ {
+ try
+ {
+ if (service!=null && !service.isClosed())
+ service.close();
+ }
+ catch (IOException ioex)
+ {
+ // OK.
+ }
+ }
}
/**
@@ -1641,6 +1681,12 @@ public class OrbFunctional extends OrbRestricted
}
}
+ if (props.containsKey(ORB_ID))
+ orb_id = props.getProperty(ORB_ID);
+
+ if (props.containsKey(SERVER_ID))
+ server_id = props.getProperty(SERVER_ID);
+
Enumeration en = props.elements();
while (en.hasMoreElements())
{
diff --git a/gnu/CORBA/OrbRestricted.java b/gnu/CORBA/OrbRestricted.java
index 783ced080..c0401800a 100644
--- a/gnu/CORBA/OrbRestricted.java
+++ b/gnu/CORBA/OrbRestricted.java
@@ -64,6 +64,7 @@ import org.omg.CORBA.portable.OutputStream;
import org.omg.CORBA.portable.ValueFactory;
import org.omg.PortableInterceptor.ClientRequestInterceptorOperations;
import org.omg.PortableInterceptor.IORInterceptorOperations;
+import org.omg.PortableInterceptor.IORInterceptor_3_0Operations;
import org.omg.PortableInterceptor.ServerRequestInterceptorOperations;
import java.applet.Applet;
@@ -97,7 +98,7 @@ public class OrbRestricted extends org.omg.CORBA_2_3.ORB
* The cumulated listener for all IOR interceptors. Interceptors are used by
* {@link gnu.CORBA.Poa.ORB_1_4}.
*/
- public IORInterceptorOperations iIor;
+ public IORInterceptor_3_0Operations iIor;
/**
* The cumulated listener for all server request interceptors. Interceptors
diff --git a/gnu/CORBA/Poa/AOM.java b/gnu/CORBA/Poa/AOM.java
index db98043d0..9faf0883d 100644
--- a/gnu/CORBA/Poa/AOM.java
+++ b/gnu/CORBA/Poa/AOM.java
@@ -40,7 +40,6 @@ package gnu.CORBA.Poa;
import gnu.CORBA.ByteArrayComparator;
-import org.omg.PortableServer.POA;
import org.omg.PortableServer.Servant;
import java.util.Iterator;
@@ -67,7 +66,7 @@ public class AOM
/**
* Create an initialised instance.
*/
- Obj(org.omg.CORBA.Object _object, byte[] _key, Servant _servant, POA _poa)
+ Obj(org.omg.CORBA.Object _object, byte[] _key, Servant _servant, gnuPOA _poa)
{
object = _object;
key = _key;
@@ -96,7 +95,7 @@ public class AOM
/**
* The POA, where the object is connected.
*/
- public final POA poa;
+ public final gnuPOA poa;
/**
* The object key.
@@ -258,7 +257,7 @@ public class AOM
*
* @return the newly created object record.
*/
- public Obj add(org.omg.CORBA.Object object, Servant servant, POA poa)
+ public Obj add(org.omg.CORBA.Object object, Servant servant, gnuPOA poa)
{
return add(generateObjectKey(object), object, servant, poa);
}
@@ -272,7 +271,7 @@ public class AOM
* @param poa the POA, where the object is connected.
*/
public Obj add(byte[] key, org.omg.CORBA.Object object, Servant servant,
- POA poa
+ gnuPOA poa
)
{
Obj rec = new Obj(object, key, servant, poa);
diff --git a/gnu/CORBA/Poa/ORB_1_4.java b/gnu/CORBA/Poa/ORB_1_4.java
index b2451b337..4fc51ff15 100644
--- a/gnu/CORBA/Poa/ORB_1_4.java
+++ b/gnu/CORBA/Poa/ORB_1_4.java
@@ -58,7 +58,6 @@ import org.omg.CORBA.Policy;
import org.omg.CORBA.PolicyError;
import org.omg.CORBA.portable.ObjectImpl;
import org.omg.PortableInterceptor.PolicyFactory;
-import org.omg.PortableServer.POA;
import org.omg.PortableServer.Servant;
import org.omg.PortableServer.POAManagerPackage.State;
import org.omg.PortableServer.POAPackage.InvalidPolicy;
@@ -206,7 +205,7 @@ public class ORB_1_4
{
AOM.Obj obj = rootPOA.findIorKey(ior.key);
- POA poa;
+ gnuPOA poa;
// Null means that the object was connected to the ORB directly.
if (obj == null)
@@ -218,6 +217,7 @@ public class ORB_1_4
// This may modify the ior.
iIor.establish_components(info);
+ iIor.components_established(info);
}
return ior;
}
diff --git a/gnu/CORBA/Poa/gnuPOA.java b/gnu/CORBA/Poa/gnuPOA.java
index 4c1826a81..aa313c4b4 100644
--- a/gnu/CORBA/Poa/gnuPOA.java
+++ b/gnu/CORBA/Poa/gnuPOA.java
@@ -49,10 +49,15 @@ import org.omg.CORBA.LocalObject;
import org.omg.CORBA.NO_IMPLEMENT;
import org.omg.CORBA.OBJ_ADAPTER;
import org.omg.CORBA.ORB;
+import org.omg.CORBA.Object;
import org.omg.CORBA.Policy;
import org.omg.CORBA.SetOverrideType;
import org.omg.CORBA.TRANSIENT;
import org.omg.CORBA.portable.ObjectImpl;
+import org.omg.PortableInterceptor.NON_EXISTENT;
+import org.omg.PortableInterceptor.ObjectReferenceFactory;
+import org.omg.PortableInterceptor.ObjectReferenceTemplate;
+import org.omg.PortableInterceptor.ObjectReferenceTemplateHelper;
import org.omg.PortableServer.AdapterActivator;
import org.omg.PortableServer.ForwardRequest;
import org.omg.PortableServer.IdAssignmentPolicy;
@@ -87,6 +92,8 @@ import org.omg.PortableServer.POAPackage.ServantAlreadyActive;
import org.omg.PortableServer.POAPackage.ServantNotActive;
import org.omg.PortableServer.POAPackage.WrongAdapter;
import org.omg.PortableServer.POAPackage.WrongPolicy;
+
+import gnu.CORBA.OrbFunctional;
import gnu.CORBA.CDR.BufferredCdrInput;
import gnu.CORBA.CDR.BufferedCdrOutput;
@@ -97,9 +104,105 @@ import gnu.CORBA.CDR.BufferedCdrOutput;
*/
public class gnuPOA
extends LocalObject
- implements POA
+ implements POA, ObjectReferenceFactory
{
/**
+ * The object reference template, associated with this POA.
+ *
+ * @since 1.5
+ */
+ class RefTemplate implements ObjectReferenceTemplate
+ {
+ /**
+ * Use serialVersionUID for interoperability.
+ */
+ private static final long serialVersionUID = 1;
+
+ RefTemplate()
+ {
+ // The adapter name is computed once.
+ ArrayList names = new ArrayList();
+ names.add(the_name());
+
+ POA poa = the_parent();
+ while (poa != null)
+ {
+ names.add(poa.the_name());
+ poa = poa.the_parent();
+ }
+
+ // Fill in the string array in reverse (more natural) order,
+ // root POA first.
+ m_adapter_name = new String[names.size()];
+
+ for (int i = 0; i < m_adapter_name.length; i++)
+ m_adapter_name[i] = (String) names.get(m_adapter_name.length - i - 1);
+ }
+
+ /**
+ * The adapter name
+ */
+ final String[] m_adapter_name;
+
+ /**
+ * Get the name of this POA.
+ */
+ public String[] adapter_name()
+ {
+ return (String[]) m_adapter_name.clone();
+ }
+
+ /**
+ * Get the ORB id.
+ */
+ public String orb_id()
+ {
+ return m_orb.orb_id;
+ }
+
+ /**
+ * Get the server id.
+ */
+ public String server_id()
+ {
+ return OrbFunctional.server_id;
+ }
+
+ /**
+ * Create the object.
+ */
+ public Object make_object(String repositoryId, byte[] objectId)
+ {
+ return create_reference_with_id(objectId, repositoryId);
+ }
+
+ /**
+ * Get the array of truncatible repository ids.
+ */
+ public String[] _truncatable_ids()
+ {
+ return ref_template_ids;
+ }
+ }
+
+ /**
+ * Use serialVersionUID for interoperability.
+ */
+ private static final long serialVersionUID = 1;
+
+ /**
+ * The adapter reference template.
+ */
+ ObjectReferenceTemplate refTemplate;
+
+ /**
+ * The reference template repository ids. Defined outside the class as it
+ * cannot have static members.
+ */
+ final static String[] ref_template_ids =
+ new String[] { ObjectReferenceTemplateHelper.id() };
+
+ /**
* The active object map, mapping between object keys, objects and servants.
*/
public final AOM aom = new AOM();
@@ -182,6 +285,12 @@ public class gnuPOA
* necessity of the frequent checks.
*/
public final boolean retain_servant;
+
+ /**
+ * The object reference factory, used to create the new object
+ * references.
+ */
+ ObjectReferenceFactory m_object_factory = this;
/**
* Create a new abstract POA.
@@ -228,6 +337,8 @@ public class gnuPOA
retain_servant = applies(ServantRetentionPolicyValue.RETAIN);
validatePolicies(a_policies);
+
+ refTemplate = new RefTemplate();
}
/**
@@ -422,24 +533,24 @@ public class gnuPOA
}
/**
- * Generate the Object Id for the given servant and add the servant to
- * the Active Object Map using this Id a a key. If the servant
- * activator is set, its incarnate method will be called.
- *
- * @param a_servant a servant that would serve the object with the
- * returned Object Id. If null is passed, under apporoprate policies the
- * servant activator is invoked.
- *
+ * Generate the Object Id for the given servant and add the servant to the
+ * Active Object Map using this Id a a key. If the servant activator is set,
+ * its incarnate method will be called.
+ *
+ * @param a_servant a servant that would serve the object with the returned
+ * Object Id. If null is passed, under apporoprate policies the servant
+ * activator is invoked.
+ *
* @return the generated objert Id for the given servant.
- *
- * @throws ServantAlreadyActive if this servant is already in the
- * Active Object Map and the UNIQUE_ID policy applies.
- *
- * @throws WrongPolicy if the required policies SYSTEM_ID and RETAIN
- * do not apply to this POA.
+ *
+ * @throws ServantAlreadyActive if this servant is already in the Active
+ * Object Map and the UNIQUE_ID policy applies.
+ *
+ * @throws WrongPolicy if the required policies SYSTEM_ID and RETAIN do not
+ * apply to this POA.
*/
public byte[] activate_object(Servant a_servant)
- throws ServantAlreadyActive, WrongPolicy
+ throws ServantAlreadyActive, WrongPolicy
{
checkDiscarding();
required(ServantRetentionPolicyValue.RETAIN);
@@ -465,27 +576,29 @@ public class gnuPOA
}
byte[] object_key = AOM.getFreeId();
- ServantDelegateImpl delegate = new ServantDelegateImpl(a_servant, this, object_key);
- connectDelegate(object_key, delegate);
+ ServantDelegateImpl delegate = new ServantDelegateImpl(a_servant, this,
+ object_key);
+ create_and_connect(object_key,
+ a_servant._all_interfaces(this, object_key)[0], delegate);
return object_key;
}
/**
- * Add the given servant to the Active Object Map as a servant for the
- * object with the provided Object Id. If the servant activator is
- * set, its incarnate method will be called.
- *
+ * Add the given servant to the Active Object Map as a servant for the object
+ * with the provided Object Id. If the servant activator is set, its incarnate
+ * method will be called.
+ *
* @param an_Object_Id an object id for the given object.
- * @param a_servant a servant that will serve the object with the given
- * Object Id. If null is passed, under apporoprate policies the
- * servant activator is invoked.
- *
- * @throws ObjectAlreadyActive if the given object id is already in the
- * Active Object Map.
- * @throws ServantAlreadyActive if the UNIQUE_ID policy applies and
- * this servant is already in use.
- * @throws WrongPolicy if the required RETAIN policy does not apply to
- * this POA.
+ * @param a_servant a servant that will serve the object with the given Object
+ * Id. If null is passed, under apporoprate policies the servant activator is
+ * invoked.
+ *
+ * @throws ObjectAlreadyActive if the given object id is already in the Active
+ * Object Map.
+ * @throws ServantAlreadyActive if the UNIQUE_ID policy applies and this
+ * servant is already in use.
+ * @throws WrongPolicy if the required RETAIN policy does not apply to this
+ * POA.
* @throws BAD_PARAM if the passed object id is invalid due any reason.
*/
public void activate_object_with_id(byte[] an_Object_Id, Servant a_servant)
@@ -496,16 +609,14 @@ public class gnuPOA
}
/**
- * Same as activate_object_with_id, but permits gnuForwardRequest
- * forwarding exception. This is used when the activation is called
- * from the remote invocation context and we have possibility
- * to return the forwarding message.
+ * Same as activate_object_with_id, but permits gnuForwardRequest forwarding
+ * exception. This is used when the activation is called from the remote
+ * invocation context and we have possibility to return the forwarding
+ * message.
*/
public void activate_object_with_id(byte[] an_Object_Id, Servant a_servant,
- boolean use_forwarding
- )
- throws ServantAlreadyActive, ObjectAlreadyActive,
- WrongPolicy
+ boolean use_forwarding)
+ throws ServantAlreadyActive, ObjectAlreadyActive, WrongPolicy
{
checkDiscarding();
required(ServantRetentionPolicyValue.RETAIN);
@@ -537,23 +648,24 @@ public class gnuPOA
}
else
{
- ServantDelegateImpl delegate =
- new ServantDelegateImpl(a_servant, this, an_Object_Id);
- connectDelegate(an_Object_Id, delegate);
+ ServantDelegateImpl delegate = new ServantDelegateImpl(a_servant, this,
+ an_Object_Id);
+ create_and_connect(an_Object_Id, a_servant._all_interfaces(this,
+ an_Object_Id)[0], delegate);
}
}
/**
* Locate the servant for this object Id and connect it to ORB.
- *
+ *
* @param an_Object_Id the object id.
* @param a_servant the servant (may be null).
* @param exists an existing active object map entry.
- * @param use_forwarding allow to throw the gnuForwardRequest
- * if the activator throws ForwardRequest.
- *
- * @throws OBJ_ADAPTER minor 4 if the servant cannot be located
- * (the required servant manager may be missing).
+ * @param use_forwarding allow to throw the gnuForwardRequest if the activator
+ * throws ForwardRequest.
+ *
+ * @throws OBJ_ADAPTER minor 4 if the servant cannot be located (the required
+ * servant manager may be missing).
*/
private void locateServant(byte[] an_Object_Id, Servant a_servant,
AOM.Obj exists, boolean use_forwarding
@@ -662,8 +774,8 @@ public class gnuPOA
* servant.
*/
public org.omg.CORBA.Object create_reference_with_id(byte[] an_object_id,
- String a_repository_id
- )
+ String a_repository_id
+ )
{
String[] ids;
if (a_repository_id == null)
@@ -1047,27 +1159,27 @@ public class gnuPOA
}
/**
- * <p>Converts the given servant to the object reference.
- * The servant will serve all methods, invoked on the returned object.
- * The returned object reference can be passed to the remote client,
- * enabling remote invocations.
- * </p><p>
- * If the specified servant is active, it is returned. Otherwise,
- * if the POA has the IMPLICIT_ACTIVATION policy the method activates
- * the servant. In this case, if the servant activator is set,
- * the {@link ServantActivatorOperations#incarnate} method will be called.
+ * <p>
+ * Converts the given servant to the object reference. The servant will serve
+ * all methods, invoked on the returned object. The returned object reference
+ * can be passed to the remote client, enabling remote invocations.
* </p>
- *
+ * <p>
+ * If the specified servant is active, it is returned. Otherwise, if the POA
+ * has the IMPLICIT_ACTIVATION policy the method activates the servant. In
+ * this case, if the servant activator is set, the
+ * {@link ServantActivatorOperations#incarnate} method will be called.
+ * </p>
+ *
* @throws ServantNotActive if the servant is inactive and no
* IMPLICIT_ACTIVATION policy applies.
* @throws WrongPolicy This method needs the RETAIN policy and either the
* UNIQUE_ID or IMPLICIT_ACTIVATION policies.
- *
+ *
* @return the object, exposing the given servant in the context of this POA.
*/
public org.omg.CORBA.Object servant_to_reference(Servant the_Servant)
- throws ServantNotActive,
- WrongPolicy
+ throws ServantNotActive, WrongPolicy
{
required(ServantRetentionPolicyValue.RETAIN);
@@ -1092,17 +1204,17 @@ public class gnuPOA
else
return exists.object;
}
- if (exists == null &&
- applies(ImplicitActivationPolicyValue.IMPLICIT_ACTIVATION)
- )
+ if (exists == null
+ && applies(ImplicitActivationPolicyValue.IMPLICIT_ACTIVATION))
{
checkDiscarding();
byte[] object_key = AOM.getFreeId();
- ServantDelegateImpl delegate =
- new ServantDelegateImpl(the_Servant, this, object_key);
- connectDelegate(object_key, delegate);
+ ServantDelegateImpl delegate = new ServantDelegateImpl(the_Servant,
+ this, object_key);
+ create_and_connect(object_key, the_Servant._all_interfaces(this,
+ object_key)[0], delegate);
return delegate.object;
}
@@ -1111,20 +1223,20 @@ public class gnuPOA
}
/**
- * Incarnate in cases when request forwarding is not expected
- * because the servant must be provided by the servant activator.
- *
- * @param x the aom entry, where the object is replaced by
- * value, returned by servant activator (if not null).
- *
+ * Incarnate in cases when request forwarding is not expected because the
+ * servant must be provided by the servant activator.
+ *
+ * @param x the aom entry, where the object is replaced by value, returned by
+ * servant activator (if not null).
+ *
* @param key the object key.
- *
+ *
* @param a_servant the servant that was passed as a parameter in the
* activation method.
- *
- * @param use_forwarding if true, the gnuForwardRequest is throw
- * under the forwarding exception (for remote client). Otherwise, the
- * request is internally redirected (for local invocation).
+ *
+ * @param use_forwarding if true, the gnuForwardRequest is throw under the
+ * forwarding exception (for remote client). Otherwise, the request is
+ * internally redirected (for local invocation).
*/
private Servant incarnate(AOM.Obj x, byte[] object_key,
Servant a_servant, boolean use_forwarding
@@ -1281,34 +1393,46 @@ public class gnuPOA
}
/**
- * <p> Destroy this POA and all descendant POAs. The destroyed POAs can be
- * later re-created via {@link AdapterActivator} or by invoking
- * {@link #create_POA}.
- * This differs from {@link PoaManagerOperations#deactivate} that does
- * not allow recreation of the deactivated POAs. After deactivation,
- * recreation is only possible if the POAs were later destroyed.
- * </p><p>
- * The remote invocation on the target, belonging to the POA that is
- * currently destroyed return the remote exception ({@link TRANSIENT},
- * minor code 4).
+ * <p>
+ * Destroy this POA and all descendant POAs. The destroyed POAs can be later
+ * re-created via {@link AdapterActivator} or by invoking {@link #create_POA}.
+ * This differs from {@link PoaManagerOperations#deactivate} that does not
+ * allow recreation of the deactivated POAs. After deactivation, recreation is
+ * only possible if the POAs were later destroyed.
+ * </p>
+ * <p>
+ * The remote invocation on the target, belonging to the POA that is currently
+ * destroyed return the remote exception ({@link TRANSIENT}, minor code 4).
* </p>
+ *
* @param etherealize_objects if true, and POA has RETAIN policy, and the
* servant manager is available, the servant manager method
- * {@link ServantActivatorOperations#etherealize} is called for each
- * <i>active</i> object in the Active Object Map. This method should not
- * try to access POA being destroyed. If <code>destroy</code> is called
- * multiple times before the destruction completes,
- * the etherialization should be invoked only once.
- *
+ * {@link ServantActivatorOperations#etherealize} is called for each <i>active</i>
+ * object in the Active Object Map. This method should not try to access POA
+ * being destroyed. If <code>destroy</code> is called multiple times before
+ * the destruction completes, the etherialization should be invoked only once.
+ *
* @param wait_for_completion if true, the method waits till the POA being
- * destroyed completes all current requests and etherialization. If false,
- * the method returns immediately.
+ * destroyed completes all current requests and etherialization. If false, the
+ * method returns immediately.
*/
public void destroy(boolean etherealize_objects, boolean wait_for_completion)
{
+ // Notify the IOR interceptors about that the POA is destroyed.
+ if (m_orb.iIor != null)
+ m_orb.iIor.adapter_state_changed(
+ new ObjectReferenceTemplate[] { getReferenceTemplate() },
+ NON_EXISTENT.value);
+
if (wait_for_completion)
waitWhileRunning();
+ // Nofify the IOR interceptors that the POA is destroyed.
+ if (m_manager instanceof gnuPOAManager)
+ {
+ ((gnuPOAManager) m_manager).poaDestroyed(this);
+ }
+
// Put the brake instead of manager, preventing the subsequent
// requests.
gnuPOAManager g = new gnuPOAManager();
@@ -1348,7 +1472,7 @@ public class gnuPOA
POA[] ch = the_children();
for (int i = 0; i < ch.length; i++)
{
- ch [ i ].destroy(etherealize_objects, wait_for_completion);
+ ch[i].destroy(etherealize_objects, wait_for_completion);
}
}
@@ -1430,13 +1554,14 @@ public class gnuPOA
}
/**
- * Connect the given delegate under the given key, also calling
- * incarnate.
+ * Connect the given delegate under the given key, also calling incarnate.
*/
- private void connectDelegate(byte[] object_key, ServantDelegateImpl delegate)
+ private void create_and_connect(byte[] object_key, String repository_id,
+ ServantDelegateImpl delegate)
{
aom.add(delegate);
- connect_to_orb(object_key, delegate.object);
+ connect_to_orb(object_key, getReferenceFactory().make_object(repository_id,
+ object_key));
if (servant_activator != null)
incarnate(null, object_key, delegate.servant, false);
}
@@ -1631,5 +1756,51 @@ public class gnuPOA
}
}
return h;
- }
+ }
+
+ /**
+ * Get the object reference template of this POA.
+ * Instantiate a singleton instance, if required.
+ */
+ public ObjectReferenceTemplate getReferenceTemplate()
+ {
+ if (refTemplate == null)
+ refTemplate = new RefTemplate();
+
+ return refTemplate;
+ }
+
+ public ObjectReferenceFactory getReferenceFactory()
+ {
+ return m_object_factory;
+ }
+
+ public void setReferenceFactory(ObjectReferenceFactory factory)
+ {
+ m_object_factory = factory;
+ }
+
+ /**
+ * Create the object (needed by the factory interface).
+ */
+ public Object make_object(String a_repository_id, byte[] an_object_id)
+ {
+ AOM.Obj existing = aom.get(an_object_id);
+ // The object may already exist. In this case, it is just returned.
+ if (existing != null && existing.object != null)
+ return existing.object;
+ else
+ {
+ return new gnuServantObject(new String[] { a_repository_id },
+ an_object_id, this, m_orb);
+ }
+ }
+
+ /**
+ * Required by object reference factory ops.
+ */
+ public String[] _truncatable_ids()
+ {
+ return ref_template_ids;
+ }
}
diff --git a/gnu/CORBA/Poa/gnuPOAManager.java b/gnu/CORBA/Poa/gnuPOAManager.java
index 6c1b5644f..7710306b7 100644
--- a/gnu/CORBA/Poa/gnuPOAManager.java
+++ b/gnu/CORBA/Poa/gnuPOAManager.java
@@ -40,6 +40,8 @@ package gnu.CORBA.Poa;
import org.omg.CORBA.BAD_INV_ORDER;
import org.omg.CORBA.LocalObject;
+import org.omg.PortableInterceptor.NON_EXISTENT;
+import org.omg.PortableInterceptor.ObjectReferenceTemplate;
import org.omg.PortableServer.POAManager;
import org.omg.PortableServer.POAManagerPackage.AdapterInactive;
import org.omg.PortableServer.POAManagerPackage.State;
@@ -59,18 +61,22 @@ public class gnuPOAManager
extends LocalObject
implements POAManager
{
+ /**
+ * Use serialVersionUID for interoperability.
+ */
+ private static final long serialVersionUID = 1;
+
/**
- * The POAs, controlled by this manager. The members must be instances of
- * the gnuAbstractPOA.
+ * The POAs, controlled by this manager.
*/
- HashSet POAs = new HashSet();
+ private HashSet POAs = new HashSet();
/**
* The state of the manager. The newly created manager is always
* in the holding state.
*/
State state = State.HOLDING;
-
+
/**
* Get the state of the POA manager.
*/
@@ -94,6 +100,8 @@ public class gnuPOAManager
state = State.ACTIVE;
else
throw new AdapterInactive();
+
+ notifyInterceptors(state.value());
}
/**
@@ -113,6 +121,9 @@ public class gnuPOAManager
state = State.HOLDING;
else
throw new AdapterInactive();
+
+ notifyInterceptors(state.value());
+
if (wait_for_completion)
waitForIdle();
}
@@ -144,6 +155,9 @@ public class gnuPOAManager
if (state == State.INACTIVE)
throw new AdapterInactive("Repetetive inactivation");
state = State.INACTIVE;
+
+ notifyInterceptors(state.value());
+
if (wait_for_completion)
waitForIdle();
@@ -178,6 +192,9 @@ public class gnuPOAManager
state = State.DISCARDING;
else
throw new AdapterInactive();
+
+ notifyInterceptors(state.value());
+
if (wait_for_completion)
waitForIdle();
}
@@ -193,11 +210,13 @@ public class gnuPOAManager
{
if (state == State.ACTIVE)
throw new BAD_INV_ORDER("The state is active");
-
+
+ gnuPOA poa;
Iterator iter = POAs.iterator();
+
while (iter.hasNext())
{
- gnuPOA poa = (gnuPOA) iter.next();
+ poa = (gnuPOA) iter.next();
poa.waitWhileRunning();
}
}
@@ -222,4 +241,33 @@ public class gnuPOAManager
{
POAs.remove(poa);
}
+
+ /**
+ * This method is called when POA is destryed. The interceptors are
+ * notified.
+ */
+ public void poaDestroyed(gnuPOA poa)
+ {
+ notifyInterceptors(NON_EXISTENT.value);
+ }
+
+ /**
+ * Notify CORBA 3.0 interceptors about the status change.
+ */
+ public synchronized void notifyInterceptors(int new_state)
+ {
+ gnuPOA poa;
+ Iterator iter = POAs.iterator();
+
+ // The System.identityHashCode is also called in gnuIorInfo.
+ while (iter.hasNext())
+ {
+ poa = (gnuPOA) iter.next();
+ if (poa.m_orb.iIor != null)
+ {
+ poa.m_orb.iIor.adapter_manager_state_changed(
+ System.identityHashCode(this), (short) new_state);
+ }
+ }
+ }
} \ No newline at end of file
diff --git a/gnu/CORBA/SimpleDelegate.java b/gnu/CORBA/SimpleDelegate.java
index 3b5e1d81c..c6e20e173 100644
--- a/gnu/CORBA/SimpleDelegate.java
+++ b/gnu/CORBA/SimpleDelegate.java
@@ -196,13 +196,11 @@ public class SimpleDelegate
}
/**
- * Returns true if the objects are the same of have
- * the same delegate set. All objects in this implementation
- * have a separate delegate.
+ * Returns true if the objects are the same or have the same delegate set. All
+ * objects in this implementation have a separate delegate.
*/
public boolean is_equivalent(org.omg.CORBA.Object target,
- org.omg.CORBA.Object other
- )
+ org.omg.CORBA.Object other)
{
if (target == other)
return true;
@@ -210,14 +208,26 @@ public class SimpleDelegate
{
try
{
- org.omg.CORBA.portable.Delegate a =
- ((ObjectImpl) target)._get_delegate();
- org.omg.CORBA.portable.Delegate b =
- ((ObjectImpl) other)._get_delegate();
+ org.omg.CORBA.portable.Delegate a = ((ObjectImpl) target)._get_delegate();
+ org.omg.CORBA.portable.Delegate b = ((ObjectImpl) other)._get_delegate();
if (a == b)
{
return true;
}
+ else
+ {
+ // We compere the IOR's in this case.
+ if (a instanceof IorProvider && b instanceof IorProvider)
+ {
+ IOR ia = ((IorProvider) a).getIor();
+ IOR ib = ((IorProvider) b).getIor();
+
+ if (ia != null && ib != null)
+ return (ia.equals(ib));
+ else
+ return ia == ib;
+ }
+ }
if (a != null && b != null)
{
return a.equals(b);
diff --git a/gnu/CORBA/SocketRepository.java b/gnu/CORBA/SocketRepository.java
index cac4ad65f..e48a9a5da 100644
--- a/gnu/CORBA/SocketRepository.java
+++ b/gnu/CORBA/SocketRepository.java
@@ -40,7 +40,7 @@ package gnu.CORBA;
import java.net.Socket;
import java.net.SocketException;
-import java.util.Hashtable;
+import java.util.HashMap;
import java.util.Iterator;
import java.util.Map;
@@ -56,7 +56,7 @@ public class SocketRepository
/**
* The socket map.
*/
- private static Hashtable sockets = new Hashtable();
+ private static HashMap sockets = new HashMap();
/**
* Put a socket. This method also discards all not reusable sockets from
@@ -68,14 +68,18 @@ public class SocketRepository
*/
public static void put_socket(Object key, Socket s)
{
- sockets.put(key, s);
- gc();
+ synchronized (sockets)
+ {
+ sockets.put(key, s);
+ gc();
+ }
}
/**
- * Removes all non reusable sockets.
+ * Removes all non reusable sockets. As it is private,
+ * we know we call from the synchronized code already.
*/
- public static void gc()
+ private static void gc()
{
Iterator iter = sockets.entrySet().iterator();
@@ -107,38 +111,41 @@ public class SocketRepository
* @param key a socket key.
*
* @return an opened socket for reuse, null if no such available or it is
- * closed, its input or output has been shutown or otherwise the socket
- * is not reuseable.
+ * closed, its input or output has been shutown or otherwise the socket is not
+ * reuseable.
*/
public static Socket get_socket(Object key)
{
if (true)
return null;
-
- Socket s = (Socket) sockets.get(key);
- if (s == null)
- return null;
-
- // Ensure that the socket is fully reusable.
- else if (not_reusable(s))
- {
- sockets.remove(key);
- return null;
- }
- else
+
+ synchronized (sockets)
{
- try
+ Socket s = (Socket) sockets.get(key);
+ if (s == null)
+ return null;
+
+ // Ensure that the socket is fully reusable.
+ else if (not_reusable(s))
{
- // Set one minute time out that will be changed later.
- s.setSoTimeout(60*1000);
+ sockets.remove(key);
+ return null;
}
- catch (SocketException e)
+ else
{
- s = null;
+ try
+ {
+ // Set one minute time out that will be changed later.
+ s.setSoTimeout(60 * 1000);
+ }
+ catch (SocketException e)
+ {
+ s = null;
+ }
+
+ sockets.remove(key);
+ return s;
}
-
- sockets.remove(key);
- return s;
}
}
} \ No newline at end of file
diff --git a/gnu/classpath/SystemProperties.java b/gnu/classpath/SystemProperties.java
index 17f8ebdb7..0c2d0e8de 100644
--- a/gnu/classpath/SystemProperties.java
+++ b/gnu/classpath/SystemProperties.java
@@ -106,12 +106,6 @@ public class SystemProperties
if (defaultProperties.get("file.encoding") == null)
defaultProperties.put("file.encoding", "8859_1");
- // Default to the Swing FocusManager so that the old-style Swing API
- // for FocusManager can be supported without hardcoding it in AWT.
- if (defaultProperties.get("gnu.java.awt.FocusManager") == null)
- defaultProperties.put("gnu.java.awt.FocusManager",
- "gnu.java.awt.FocusManager");
-
// XXX FIXME - Temp hack for old systems that set the wrong property
if (defaultProperties.get("java.io.tmpdir") == null)
defaultProperties.put("java.io.tmpdir",
diff --git a/gnu/java/awt/image/ImageDecoder.java b/gnu/java/awt/image/ImageDecoder.java
index 141c85417..8e8eecb25 100644
--- a/gnu/java/awt/image/ImageDecoder.java
+++ b/gnu/java/awt/image/ImageDecoder.java
@@ -40,6 +40,8 @@ package gnu.java.awt.image;
import java.awt.image.ImageConsumer;
import java.awt.image.ImageProducer;
import java.io.ByteArrayInputStream;
+import java.io.DataInput;
+import java.io.EOFException;
import java.io.FileInputStream;
import java.io.IOException;
import java.io.InputStream;
@@ -55,6 +57,7 @@ public abstract class ImageDecoder implements ImageProducer
int offset;
int length;
InputStream input;
+ DataInput datainput;
static
{
@@ -79,6 +82,11 @@ public abstract class ImageDecoder implements ImageProducer
this.input = is;
}
+ public ImageDecoder (DataInput datainput)
+ {
+ this.datainput = datainput;
+ }
+
public ImageDecoder (byte[] imagedata, int imageoffset, int imagelength)
{
data = imagedata;
@@ -119,6 +127,8 @@ public abstract class ImageDecoder implements ImageProducer
{
if (url != null)
input = url.openStream();
+ else if (datainput != null)
+ input = new DataInputStreamWrapper(datainput);
else
{
if (filename != null)
@@ -153,4 +163,26 @@ public abstract class ImageDecoder implements ImageProducer
}
public abstract void produce (Vector v, InputStream is) throws IOException;
+
+ private static class DataInputStreamWrapper extends InputStream
+ {
+ private final DataInput datainput;
+
+ DataInputStreamWrapper(DataInput datainput)
+ {
+ this.datainput = datainput;
+ }
+
+ public int read() throws IOException
+ {
+ try
+ {
+ return datainput.readByte() & 0xFF;
+ }
+ catch (EOFException eofe)
+ {
+ return -1;
+ }
+ }
+ }
}
diff --git a/gnu/java/awt/peer/gtk/GdkGraphics.java b/gnu/java/awt/peer/gtk/GdkGraphics.java
index d80306c8a..84fb1371e 100644
--- a/gnu/java/awt/peer/gtk/GdkGraphics.java
+++ b/gnu/java/awt/peer/gtk/GdkGraphics.java
@@ -48,9 +48,9 @@ import java.awt.Graphics;
import java.awt.Image;
import java.awt.Rectangle;
import java.awt.Shape;
-import java.awt.SystemColor;
import java.awt.image.ImageObserver;
import java.text.AttributedCharacterIterator;
+import java.util.regex.*;
public class GdkGraphics extends Graphics
{
@@ -248,9 +248,8 @@ public class GdkGraphics extends Graphics
public void drawString (String str, int x, int y)
{
drawString(getFontPeer(), str, x, y);
- }
+ }
-
public void drawString (AttributedCharacterIterator ci, int x, int y)
{
throw new Error ("not implemented");
diff --git a/gnu/java/awt/peer/gtk/GdkPixbufDecoder.java b/gnu/java/awt/peer/gtk/GdkPixbufDecoder.java
index 85cb1e47a..054ebaaae 100644
--- a/gnu/java/awt/peer/gtk/GdkPixbufDecoder.java
+++ b/gnu/java/awt/peer/gtk/GdkPixbufDecoder.java
@@ -47,6 +47,7 @@ import java.awt.image.ImageConsumer;
import java.awt.image.ImageProducer;
import java.awt.image.Raster;
import java.awt.image.RenderedImage;
+import java.io.DataInput;
import java.io.DataOutput;
import java.io.IOException;
import java.io.InputStream;
@@ -102,6 +103,11 @@ public class GdkPixbufDecoder extends gnu.java.awt.image.ImageDecoder
0x00ff0000,
0x0000ff00,
0x000000ff);
+ public GdkPixbufDecoder (DataInput datainput)
+ {
+ super (datainput);
+ }
+
public GdkPixbufDecoder (InputStream in)
{
super (in);
@@ -630,7 +636,14 @@ public class GdkPixbufDecoder extends gnu.java.awt.image.ImageDecoder
boolean ignoreMetadata)
{
super.setInput(input, seekForwardOnly, ignoreMetadata);
- dec = new GdkPixbufDecoder((InputStream) getInput());
+ Object get = getInput();
+ if (get instanceof InputStream)
+ dec = new GdkPixbufDecoder((InputStream) get);
+ else if (get instanceof DataInput)
+ dec = new GdkPixbufDecoder((DataInput) get);
+ else
+ throw new IllegalArgumentException("input object not supported: "
+ + get);
}
public BufferedImage read(int imageIndex, ImageReadParam param)
diff --git a/gnu/java/awt/peer/gtk/GtkComponentPeer.java b/gnu/java/awt/peer/gtk/GtkComponentPeer.java
index 60e837127..fe0dae70d 100644
--- a/gnu/java/awt/peer/gtk/GtkComponentPeer.java
+++ b/gnu/java/awt/peer/gtk/GtkComponentPeer.java
@@ -71,6 +71,7 @@ import java.awt.image.ImageProducer;
import java.awt.image.VolatileImage;
import java.awt.peer.ComponentPeer;
import java.awt.peer.ContainerPeer;
+import java.awt.peer.WindowPeer;
import java.util.Timer;
import java.util.TimerTask;
@@ -98,6 +99,7 @@ public class GtkComponentPeer extends GtkGenericPeer
native int[] gtkWidgetGetBackground ();
native void gtkWidgetGetDimensions (int[] dim);
native void gtkWidgetGetPreferredDimensions (int[] dim);
+ native void gtkWindowGetLocationOnScreen (int[] point);
native void gtkWidgetGetLocationOnScreen (int[] point);
native void gtkWidgetSetCursor (int type);
native void gtkWidgetSetCursorUnlocked (int type);
@@ -270,7 +272,10 @@ public class GtkComponentPeer extends GtkGenericPeer
public Point getLocationOnScreen ()
{
int point[] = new int[2];
- gtkWidgetGetLocationOnScreen (point);
+ if( this instanceof WindowPeer )
+ gtkWindowGetLocationOnScreen (point);
+ else
+ gtkWidgetGetLocationOnScreen (point);
return new Point (point[0], point[1]);
}
diff --git a/gnu/java/awt/peer/gtk/GtkDialogPeer.java b/gnu/java/awt/peer/gtk/GtkDialogPeer.java
index f5ba3ad2c..3e3125a2b 100644
--- a/gnu/java/awt/peer/gtk/GtkDialogPeer.java
+++ b/gnu/java/awt/peer/gtk/GtkDialogPeer.java
@@ -44,10 +44,6 @@ import java.awt.Rectangle;
import java.awt.event.PaintEvent;
import java.awt.peer.DialogPeer;
-import javax.swing.JDialog;
-import javax.swing.JPopupMenu;
-import javax.swing.JToolTip;
-
public class GtkDialogPeer extends GtkWindowPeer
implements DialogPeer
{
@@ -87,27 +83,9 @@ public class GtkDialogPeer extends GtkWindowPeer
void create ()
{
Dialog dialog = (Dialog) awtComponent;
- int type = GDK_WINDOW_TYPE_HINT_DIALOG;
-
- if (dialog instanceof JDialog)
- {
- Class heavyWeightClass;
- try
- {
- heavyWeightClass = Class.forName("javax.swing.Popup$JWindowPopup");
- }
- catch (ClassNotFoundException e)
- {
- throw new AssertionError(e);
- }
-
- if (dialog.getClass() == heavyWeightClass
- || ((JDialog) dialog).getContentPane() instanceof JToolTip)
- type = GDK_WINDOW_TYPE_HINT_MENU;
- }
// Create a decorated dialog window.
- create (type, !((Dialog) awtComponent).isUndecorated ());
+ create (GDK_WINDOW_TYPE_HINT_DIALOG, !((Dialog) awtComponent).isUndecorated ());
gtkWindowSetModal (dialog.isModal ());
setTitle (dialog.getTitle ());
diff --git a/gnu/java/awt/peer/gtk/GtkWindowPeer.java b/gnu/java/awt/peer/gtk/GtkWindowPeer.java
index c84d51037..57fb87f37 100644
--- a/gnu/java/awt/peer/gtk/GtkWindowPeer.java
+++ b/gnu/java/awt/peer/gtk/GtkWindowPeer.java
@@ -41,7 +41,6 @@ package gnu.java.awt.peer.gtk;
import java.awt.Component;
import java.awt.Frame;
import java.awt.Window;
-import java.awt.event.ComponentEvent;
import java.awt.event.WindowEvent;
import java.awt.peer.WindowPeer;
@@ -80,12 +79,16 @@ public class GtkWindowPeer extends GtkContainerPeer
void create (int type, boolean decorated)
{
+ Window window = (Window) awtComponent;
GtkWindowPeer parent_peer = null;
Component parent = awtComponent.getParent();
-
+
+ if (!window.isFocusableWindow())
+ type = GDK_WINDOW_TYPE_HINT_MENU;
+
if (parent != null)
parent_peer = (GtkWindowPeer) awtComponent.getParent().getPeer();
-
+
create (type, decorated, parent_peer);
}
diff --git a/gnu/java/beans/DummyAppletContext.java b/gnu/java/beans/DummyAppletContext.java
index 4facb470d..583d2f5cb 100644
--- a/gnu/java/beans/DummyAppletContext.java
+++ b/gnu/java/beans/DummyAppletContext.java
@@ -63,7 +63,6 @@ import java.util.Iterator;
class DummyAppletContext implements AppletContext
{
private static final Enumeration EMPTY_ENUMERATION = Collections.enumeration(Collections.EMPTY_SET);
- private static final AudioClip DUMMY_CLIP = new DummyAudioClip();
DummyAppletContext()
{
@@ -80,14 +79,7 @@ class DummyAppletContext implements AppletContext
*/
public AudioClip getAudioClip(URL url)
{
- try
- {
- return (url.openConnection() != null ? DUMMY_CLIP : null);
- }
- catch (IOException ioe)
- {
- return null;
- }
+ return Applet.newAudioClip(url);
}
/** Loads the <code>Image</code> instance by delegating to
@@ -170,31 +162,4 @@ class DummyAppletContext implements AppletContext
{
return Collections.EMPTY_SET.iterator();
}
-
- /** Dummy <code>AudioClip</code> implementation that does nothing but
- * preventing <code>NullPointerException</code>S being thrown in programs
- * that expect a valid <code>AudioClip</code> instance to be returned by
- * their Applet.
- *
- * @author Robert Schuster
- */
- static class DummyAudioClip implements AudioClip
- {
- public void play()
- {
- }
-
- public void stop()
- {
- }
-
- public void loop()
- {
- }
-
- public String toString()
- {
- return "DummyAudioClip never plays anything - implement javax.sound and make us happy :)";
- }
- }
}
diff --git a/gnu/java/io/PlatformHelper.java b/gnu/java/io/PlatformHelper.java
index d2c601231..79ce6e8f4 100644
--- a/gnu/java/io/PlatformHelper.java
+++ b/gnu/java/io/PlatformHelper.java
@@ -109,11 +109,6 @@ public class PlatformHelper
String tmppath = path.replace('/', separatorChar);
StringBuffer canonpath;
- // We found it'll be more efficient and easy to handle to
- // return a lowercased canonical path
- if(isWindows)
- tmppath = tmppath.toLowerCase();
-
int i;
if ((i = beginWithRootPathPrefix(tmppath)) == 0 )
diff --git a/gnu/java/net/protocol/file/Connection.java b/gnu/java/net/protocol/file/Connection.java
index 52bd04845..8e4a41366 100644
--- a/gnu/java/net/protocol/file/Connection.java
+++ b/gnu/java/net/protocol/file/Connection.java
@@ -59,6 +59,7 @@ import java.security.Permission;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Locale;
+import java.net.MalformedURLException;
/**
* This subclass of java.net.URLConnection models a URLConnection via
@@ -125,6 +126,54 @@ public class Connection extends URLConnection
}
/**
+ * Unquote "%" + hex quotes characters
+ *
+ * @param str The string to unquote or null.
+ *
+ * @return The unquoted string or null if str was null.
+ *
+ * @exception MalformedURLException If the given string contains invalid
+ * escape sequences.
+ *
+ * Sadly the same as URI.unquote, but there's nothing we can do to
+ * make it accessible.
+ *
+ */
+ public static String unquote(String str) throws MalformedURLException
+ {
+ if (str == null)
+ return null;
+ byte[] buf = new byte[str.length()];
+ int pos = 0;
+ for (int i = 0; i < str.length(); i++)
+ {
+ char c = str.charAt(i);
+ if (c > 127)
+ throw new MalformedURLException(str + " : Invalid character");
+ if (c == '%')
+ {
+ if (i + 2 >= str.length())
+ throw new MalformedURLException(str + " : Invalid quoted character");
+ int hi = Character.digit(str.charAt(++i), 16);
+ int lo = Character.digit(str.charAt(++i), 16);
+ if (lo < 0 || hi < 0)
+ throw new MalformedURLException(str + " : Invalid quoted character");
+ buf[pos++] = (byte) (hi * 16 + lo);
+ }
+ else
+ buf[pos++] = (byte) c;
+ }
+ try
+ {
+ return new String(buf, 0, pos, "utf-8");
+ }
+ catch (java.io.UnsupportedEncodingException x2)
+ {
+ throw (Error) new InternalError().initCause(x2);
+ }
+ }
+
+ /**
* "Connects" to the file by opening it.
*/
public void connect() throws IOException
@@ -134,7 +183,7 @@ public class Connection extends URLConnection
return;
// If not connected, then file needs to be openned.
- file = new File (getURL().getFile());
+ file = new File (unquote(getURL().getFile()));
if (! file.isDirectory())
{
diff --git a/gnu/java/net/protocol/jar/Connection.java b/gnu/java/net/protocol/jar/Connection.java
index e85487420..e2a052ef5 100644
--- a/gnu/java/net/protocol/jar/Connection.java
+++ b/gnu/java/net/protocol/jar/Connection.java
@@ -47,7 +47,10 @@ import java.net.MalformedURLException;
import java.net.ProtocolException;
import java.net.URL;
import java.net.URLConnection;
+import java.text.SimpleDateFormat;
+import java.util.Date;
import java.util.Hashtable;
+import java.util.Locale;
import java.util.jar.JarEntry;
import java.util.jar.JarFile;
import java.util.zip.ZipFile;
@@ -60,6 +63,12 @@ import java.util.zip.ZipFile;
*/
public final class Connection extends JarURLConnection
{
+ /**
+ * HTTP-style DateFormat, used to format the last-modified header.
+ * Lazy initialized since jar files are used during bootstrapping.
+ */
+ private static SimpleDateFormat dateFormat;
+
private JarFile jar_file;
private JarEntry jar_entry;
private URL jar_url;
@@ -82,7 +91,9 @@ public final class Connection extends JarURLConnection
if ("file".equals (url.getProtocol()))
{
- File f = new File (url.getFile());
+ String fn = url.getFile();
+ fn = gnu.java.net.protocol.file.Connection.unquote(fn);
+ File f = new File (fn);
jf = new JarFile (f, true, ZipFile.OPEN_READ);
}
else
@@ -165,6 +176,38 @@ public final class Connection extends JarURLConnection
return jar_file;
}
+ public String getHeaderField(String field)
+ {
+ try
+ {
+ if (!connected)
+ connect();
+
+ if (field.equals("content-type"))
+ return guessContentTypeFromName(getJarEntry().getName());
+ else if (field.equals("content-length"))
+ return Long.toString(getJarEntry().getSize());
+ else if (field.equals("last-modified"))
+ {
+ // Both creating and manipulating dateFormat need synchronization.
+ synchronized (this.getClass())
+ {
+ if (dateFormat == null)
+ dateFormat = new SimpleDateFormat
+ ("EEE, dd MMM yyyy hh:mm:ss 'GMT'",
+ new Locale ("En", "Us", "Unix"));
+
+ return dateFormat.format(new Date(getJarEntry().getTime()));
+ }
+ }
+ }
+ catch (IOException e)
+ {
+ // Fall through.
+ }
+ return null;
+ }
+
public int getContentLength()
{
if (!connected)
@@ -172,4 +215,19 @@ public final class Connection extends JarURLConnection
return (int) jar_entry.getSize();
}
+
+ public long getLastModified()
+ {
+ if (!connected)
+ return -1;
+
+ try
+ {
+ return getJarEntry().getTime();
+ }
+ catch (IOException e)
+ {
+ return -1;
+ }
+ }
}
diff --git a/gnu/java/nio/SocketChannelImpl.java b/gnu/java/nio/SocketChannelImpl.java
index 9fb71c1ae..fcddbd6c3 100644
--- a/gnu/java/nio/SocketChannelImpl.java
+++ b/gnu/java/nio/SocketChannelImpl.java
@@ -258,7 +258,7 @@ public final class SocketChannelImpl extends SocketChannel
}
else
{
- dst.put (data, offset, len);
+ dst.put (data, offset, readBytes);
}
return readBytes;
diff --git a/gnu/java/nio/charset/UTF_16Decoder.java b/gnu/java/nio/charset/UTF_16Decoder.java
index e3927d994..fa1dbc412 100644
--- a/gnu/java/nio/charset/UTF_16Decoder.java
+++ b/gnu/java/nio/charset/UTF_16Decoder.java
@@ -54,6 +54,8 @@ final class UTF_16Decoder extends CharsetDecoder
static final int BIG_ENDIAN = 0;
static final int LITTLE_ENDIAN = 1;
static final int UNKNOWN_ENDIAN = 2;
+ static final int MAYBE_BIG_ENDIAN = 3;
+ static final int MAYBE_LITTLE_ENDIAN = 4;
private static final char BYTE_ORDER_MARK = 0xFEFF;
private static final char REVERSED_BYTE_ORDER_MARK = 0xFFFE;
@@ -81,26 +83,37 @@ final class UTF_16Decoder extends CharsetDecoder
byte b2 = in.get ();
// handle byte order mark
- if (byteOrder == UNKNOWN_ENDIAN)
+ if (byteOrder == UNKNOWN_ENDIAN ||
+ byteOrder == MAYBE_BIG_ENDIAN ||
+ byteOrder == MAYBE_LITTLE_ENDIAN)
{
char c = (char) (((b1 & 0xFF) << 8) | (b2 & 0xFF));
if (c == BYTE_ORDER_MARK)
{
+ if (byteOrder == MAYBE_LITTLE_ENDIAN)
+ {
+ return CoderResult.malformedForLength (2);
+ }
byteOrder = BIG_ENDIAN;
inPos += 2;
continue;
}
else if (c == REVERSED_BYTE_ORDER_MARK)
{
+ if (byteOrder == MAYBE_BIG_ENDIAN)
+ {
+ return CoderResult.malformedForLength (2);
+ }
byteOrder = LITTLE_ENDIAN;
inPos += 2;
continue;
}
else
{
- // assume big endian, do not consume bytes,
+ // assume big or little endian, do not consume bytes,
// continue with normal processing
- byteOrder = BIG_ENDIAN;
+ byteOrder = (byteOrder == MAYBE_LITTLE_ENDIAN ?
+ LITTLE_ENDIAN : BIG_ENDIAN);
}
}
diff --git a/gnu/java/nio/charset/UnicodeLittle.java b/gnu/java/nio/charset/UnicodeLittle.java
index d354e04e5..63f2855d5 100644
--- a/gnu/java/nio/charset/UnicodeLittle.java
+++ b/gnu/java/nio/charset/UnicodeLittle.java
@@ -64,7 +64,7 @@ final class UnicodeLittle extends Charset
public CharsetDecoder newDecoder ()
{
- return new UTF_16Decoder (this, UTF_16Decoder.UNKNOWN_ENDIAN);
+ return new UTF_16Decoder (this, UTF_16Decoder.MAYBE_LITTLE_ENDIAN);
}
public CharsetEncoder newEncoder ()
diff --git a/gnu/java/nio/charset/iconv/IconvProvider.java b/gnu/java/nio/charset/iconv/IconvProvider.java
index 58eaa85ba..873e9ecda 100644
--- a/gnu/java/nio/charset/iconv/IconvProvider.java
+++ b/gnu/java/nio/charset/iconv/IconvProvider.java
@@ -62,7 +62,11 @@ public final class IconvProvider extends CharsetProvider
}
}
- private IconvProvider()
+ // Declaring the construtor public may violate the use of singleton.
+ // But it must be public so that an instance of this class can be
+ // created by Class.newInstance(), which is the case when this provider is
+ // defined in META-INF/services/java.nio.charset.spi.CharsetProvider.
+ public IconvProvider()
{
IconvMetaData.setup();
}
diff --git a/gnu/javax/rmi/CORBA/UtilDelegateImpl.java b/gnu/javax/rmi/CORBA/UtilDelegateImpl.java
index f37f18c24..66a4e24ff 100644
--- a/gnu/javax/rmi/CORBA/UtilDelegateImpl.java
+++ b/gnu/javax/rmi/CORBA/UtilDelegateImpl.java
@@ -518,7 +518,7 @@ public class UtilDelegateImpl
else if (ex instanceof INV_OBJREF)
{
rex = new NoSuchObjectException(message);
- rex.initCause(ex);
+ rex.detail = ex;
}
else if (ex instanceof NO_PERMISSION)
rex = new AccessException(message, ex);
@@ -529,22 +529,22 @@ public class UtilDelegateImpl
else if (ex instanceof OBJECT_NOT_EXIST)
{
rex = new NoSuchObjectException(message);
- rex.initCause(ex);
+ rex.detail = ex;
}
else if (ex instanceof TRANSACTION_REQUIRED)
{
rex = new TransactionRequiredException(message);
- rex.initCause(ex);
+ rex.detail = ex;
}
else if (ex instanceof TRANSACTION_ROLLEDBACK)
{
rex = new TransactionRolledbackException(message);
- rex.initCause(ex);
+ rex.detail = ex;
}
else if (ex instanceof INVALID_TRANSACTION)
{
rex = new InvalidTransactionException(message);
- rex.initCause(ex);
+ rex.detail = ex;
}
else if (ex instanceof UNKNOWN)
rex = wrapException(ex.getCause());
diff --git a/gnu/xml/aelfred2/SAXDriver.java b/gnu/xml/aelfred2/SAXDriver.java
index 7e950ce04..6864ff659 100644
--- a/gnu/xml/aelfred2/SAXDriver.java
+++ b/gnu/xml/aelfred2/SAXDriver.java
@@ -717,7 +717,9 @@ final public class SAXDriver
}
else
{
- in.setSystemId(absolutize(baseURI, in.getSystemId(), false));
+ in.setSystemId(absolutize(baseURI,
+ in.getSystemId(),
+ entityResolver != base));
source = entityResolver.resolveEntity(in.getPublicId(),
in.getSystemId());
if (source == null)
diff --git a/gnu/xml/stream/XMLStreamWriterImpl.java b/gnu/xml/stream/XMLStreamWriterImpl.java
index 9ac0abe27..d677048cf 100644
--- a/gnu/xml/stream/XMLStreamWriterImpl.java
+++ b/gnu/xml/stream/XMLStreamWriterImpl.java
@@ -39,7 +39,10 @@ package gnu.xml.stream;
import java.io.IOException;
import java.io.Writer;
+import java.util.Enumeration;
+import java.util.HashSet;
import java.util.LinkedList;
+import java.util.Set;
import javax.xml.XMLConstants;
import javax.xml.namespace.NamespaceContext;
@@ -57,16 +60,56 @@ public class XMLStreamWriterImpl
implements XMLStreamWriter
{
+ /**
+ * The underlying character stream to write to.
+ */
protected final Writer writer;
+
+ /**
+ * The encoding being used.
+ * Note that this must match the encoding of the character stream.
+ */
protected final String encoding;
+
+ /**
+ * Whether prefix defaulting is being used.
+ * If true and a prefix has not been defined for a namespace specified on
+ * an element or an attribute, a new prefix and namespace declaration will
+ * be created.
+ */
protected final boolean prefixDefaulting;
+
+ /**
+ * The namespace context used to determine the namespace-prefix mappings
+ * in scope.
+ */
protected NamespaceContext namespaceContext;
+ /**
+ * The stack of elements in scope.
+ * Used to close the remaining elements.
+ */
private LinkedList elements;
+
+ /**
+ * Whether a start element has been opened but not yet closed.
+ */
private boolean inStartElement;
+
+ /**
+ * Whether we are in an empty element.
+ */
private boolean emptyElement;
+
private NamespaceSupport namespaces;
-
+ private int count = 0;
+
+ /**
+ * Constructor.
+ * @see #writer
+ * @see #encoding
+ * @see #prefixDefaulting
+ */
protected XMLStreamWriterImpl(Writer writer, String encoding,
boolean prefixDefaulting)
{
@@ -77,6 +120,10 @@ public class XMLStreamWriterImpl
namespaces = new NamespaceSupport();
}
+ /**
+ * Write the end of a start-element event.
+ * This will close the element if it was defined to be an empty element.
+ */
private void endStartElement()
throws IOException
{
@@ -128,7 +175,7 @@ public class XMLStreamWriterImpl
if (!isDeclared)
{
if (prefixDefaulting)
- prefix = XMLConstants.DEFAULT_NS_PREFIX;
+ prefix = createPrefix(namespaceURI);
else
throw new XMLStreamException("namespace " + namespaceURI +
" has not been declared");
@@ -140,13 +187,13 @@ public class XMLStreamWriterImpl
writer.write(':');
}
writer.write(localName);
- if (prefixDefaulting && !isDeclared)
+ inStartElement = true;
+ if (!isDeclared)
{
writeNamespace(prefix, namespaceURI);
}
elements.addLast(new String[] { prefix, localName });
- inStartElement = true;
}
catch (IOException e)
{
@@ -156,6 +203,26 @@ public class XMLStreamWriterImpl
}
}
+ /**
+ * Creates a new unique prefix in the document.
+ * Subclasses may override this method to provide a suitably unique prefix
+ * for the given namespace.
+ * @param namespaceURI the namespace URI
+ */
+ protected String createPrefix(String namespaceURI)
+ {
+ Set prefixes = new HashSet();
+ for (Enumeration e = namespaces.getPrefixes(); e.hasMoreElements(); )
+ prefixes.add(e.nextElement());
+ String ret;
+ do
+ {
+ ret = "ns" + (count++);
+ }
+ while (prefixes.contains(ret));
+ return ret;
+ }
+
public void writeStartElement(String prefix, String localName,
String namespaceURI)
throws XMLStreamException
@@ -656,6 +723,12 @@ public class XMLStreamWriterImpl
throw new IllegalArgumentException(name);
}
+ /**
+ * Write the specified text, ensuring that the content is suitably encoded
+ * for XML.
+ * @param text the text to write
+ * @param inAttr whether we are in an attribute value
+ */
private void writeEncoded(String text, boolean inAttr)
throws IOException
{
diff --git a/gnu/xml/transform/StreamSerializer.java b/gnu/xml/transform/StreamSerializer.java
index eb045393d..74b10057c 100644
--- a/gnu/xml/transform/StreamSerializer.java
+++ b/gnu/xml/transform/StreamSerializer.java
@@ -694,7 +694,11 @@ public class StreamSerializer
{
buf = new StringBuffer(text.substring(0, i));
}
- buf.append("&apos;");
+ if (mode == Stylesheet.OUTPUT_HTML)
+ // HTML does not define &apos;, use character entity ref
+ buf.append("&#x27;");
+ else
+ buf.append("&apos;");
}
else if (c == '"' && inAttr)
{
diff --git a/gnu/xml/transform/TransformerImpl.java b/gnu/xml/transform/TransformerImpl.java
index cf4048847..78bca52d3 100644
--- a/gnu/xml/transform/TransformerImpl.java
+++ b/gnu/xml/transform/TransformerImpl.java
@@ -487,6 +487,7 @@ class TransformerImpl
throws IOException
{
OutputStream out = null;
+ boolean created = false;
try
{
out = sr.getOutputStream();
@@ -523,6 +524,7 @@ class TransformerImpl
URL url = new URL(systemId);
out = new FileOutputStream(url.getPath());
}
+ created = true;
}
out = new BufferedOutputStream(out);
StreamSerializer serializer =
@@ -539,7 +541,7 @@ class TransformerImpl
{
try
{
- if (out != null)
+ if (out != null && created)
{
out.close();
}
diff --git a/include/gnu_java_awt_peer_gtk_GtkComponentPeer.h b/include/gnu_java_awt_peer_gtk_GtkComponentPeer.h
index 2c32e3f6c..da86e23a8 100644
--- a/include/gnu_java_awt_peer_gtk_GtkComponentPeer.h
+++ b/include/gnu_java_awt_peer_gtk_GtkComponentPeer.h
@@ -16,6 +16,7 @@ JNIEXPORT jintArray JNICALL Java_gnu_java_awt_peer_gtk_GtkComponentPeer_gtkWidge
JNIEXPORT jintArray JNICALL Java_gnu_java_awt_peer_gtk_GtkComponentPeer_gtkWidgetGetBackground (JNIEnv *env, jobject);
JNIEXPORT void JNICALL Java_gnu_java_awt_peer_gtk_GtkComponentPeer_gtkWidgetGetDimensions (JNIEnv *env, jobject, jintArray);
JNIEXPORT void JNICALL Java_gnu_java_awt_peer_gtk_GtkComponentPeer_gtkWidgetGetPreferredDimensions (JNIEnv *env, jobject, jintArray);
+JNIEXPORT void JNICALL Java_gnu_java_awt_peer_gtk_GtkComponentPeer_gtkWindowGetLocationOnScreen (JNIEnv *env, jobject, jintArray);
JNIEXPORT void JNICALL Java_gnu_java_awt_peer_gtk_GtkComponentPeer_gtkWidgetGetLocationOnScreen (JNIEnv *env, jobject, jintArray);
JNIEXPORT void JNICALL Java_gnu_java_awt_peer_gtk_GtkComponentPeer_gtkWidgetSetCursor (JNIEnv *env, jobject, jint);
JNIEXPORT void JNICALL Java_gnu_java_awt_peer_gtk_GtkComponentPeer_gtkWidgetSetCursorUnlocked (JNIEnv *env, jobject, jint);
diff --git a/java/applet/Applet.java b/java/applet/Applet.java
index d0610ba0e..bb855351b 100644
--- a/java/applet/Applet.java
+++ b/java/applet/Applet.java
@@ -54,6 +54,10 @@ import javax.accessibility.AccessibleContext;
import javax.accessibility.AccessibleRole;
import javax.accessibility.AccessibleState;
import javax.accessibility.AccessibleStateSet;
+import javax.sound.sampled.AudioSystem;
+import javax.sound.sampled.Clip;
+import javax.sound.sampled.LineUnavailableException;
+import javax.sound.sampled.UnsupportedAudioFileException;
/**
* This is the base applet class. An applet is a Java program that
@@ -257,8 +261,6 @@ public class Applet extends Panel
* Returns an audio clip from the specified URL. This clip is not tied to
* any particular applet.
*
- * XXX Classpath does not yet implement this.
- *
* @param url the URL of the audio clip
* @return the retrieved audio clip
* @throws NullPointerException if url is null
@@ -267,8 +269,7 @@ public class Applet extends Panel
*/
public static final AudioClip newAudioClip(URL url)
{
- // This requires an implementation of AudioClip in gnu.java.applet.
- throw new Error("Not implemented");
+ return new URLAudioClip(url);
}
/**
@@ -521,4 +522,71 @@ public class Applet extends Panel
return s;
}
} // class AccessibleApplet
+
+ private static class URLAudioClip implements AudioClip
+ {
+ // The URL we will try to play.
+ // This is null if we have already tried to create an
+ // audio input stream from this URL.
+ private URL url;
+
+ // The real audio clip. This is null before the URL is read,
+ // and might be null afterward if we were unable to read the URL
+ // for some reason.
+ private Clip clip;
+
+ public URLAudioClip(URL url)
+ {
+ this.url = url;
+ }
+
+ private synchronized Clip getClip()
+ {
+ if (url == null)
+ return clip;
+ try
+ {
+ clip = AudioSystem.getClip();
+ clip.open(AudioSystem.getAudioInputStream(url));
+ }
+ catch (LineUnavailableException _)
+ {
+ // Ignore.
+ }
+ catch (IOException _)
+ {
+ // Ignore.
+ }
+ catch (UnsupportedAudioFileException _)
+ {
+ // Ignore.
+ }
+ url = null;
+ return clip;
+ }
+
+ public void loop()
+ {
+ Clip myclip = getClip();
+ if (myclip != null)
+ myclip.loop(Clip.LOOP_CONTINUOUSLY);
+ }
+
+ public void play()
+ {
+ Clip myclip = getClip();
+ if (myclip != null)
+ myclip.start();
+ }
+
+ public void stop()
+ {
+ Clip myclip = getClip();
+ if (myclip != null)
+ {
+ myclip.stop();
+ myclip.setFramePosition(0);
+ }
+ }
+ }
} // class Applet
diff --git a/java/awt/BorderLayout.java b/java/awt/BorderLayout.java
index 0e626bbb1..1b67c01cf 100644
--- a/java/awt/BorderLayout.java
+++ b/java/awt/BorderLayout.java
@@ -430,7 +430,7 @@ public class BorderLayout implements LayoutManager2, java.io.Serializable
*/
public float getLayoutAlignmentX(Container parent)
{
- return(parent.getAlignmentX());
+ return 0.5F;
}
/**
@@ -445,7 +445,7 @@ public class BorderLayout implements LayoutManager2, java.io.Serializable
*/
public float getLayoutAlignmentY(Container parent)
{
- return(parent.getAlignmentY());
+ return 0.5F;
}
/**
diff --git a/java/awt/Component.java b/java/awt/Component.java
index 91b47f71b..dfc49f386 100644
--- a/java/awt/Component.java
+++ b/java/awt/Component.java
@@ -1038,14 +1038,10 @@ public abstract class Component
if ((c != null) && c.equals(background))
return;
- // If c is null, inherit from closest ancestor whose bg is set.
- if (c == null && parent != null)
- c = parent.getBackground();
- if (peer != null && c != null)
- peer.setBackground(c);
-
Color previous = background;
background = c;
+ if (peer != null && c != null)
+ peer.setBackground(c);
firePropertyChange("background", previous, c);
}
@@ -1409,7 +1405,6 @@ public abstract class Component
{
if (parent != null)
{
- Rectangle parentBounds = parent.getBounds();
Rectangle oldBounds = new Rectangle(oldx, oldy, oldwidth,
oldheight);
Rectangle newBounds = new Rectangle(x, y, width, height);
@@ -1720,7 +1715,7 @@ public abstract class Component
valid = false;
prefSize = null;
minSize = null;
- if (parent != null && parent.valid)
+ if (parent != null && parent.isValid())
parent.invalidate();
}
@@ -1887,13 +1882,7 @@ public abstract class Component
*/
public void repaint()
{
- if(!isShowing())
- {
- Component p = parent;
- if (p != null)
- p.repaint(0, getX(), getY(), width, height);
- }
- else
+ if (isShowing())
repaint(0, 0, 0, width, height);
}
@@ -1908,13 +1897,7 @@ public abstract class Component
*/
public void repaint(long tm)
{
- if(!isShowing())
- {
- Component p = parent;
- if (p != null)
- p.repaint(tm, getX(), getY(), width, height);
- }
- else
+ if (isShowing())
repaint(tm, 0, 0, width, height);
}
@@ -1932,13 +1915,7 @@ public abstract class Component
*/
public void repaint(int x, int y, int w, int h)
{
- if(!isShowing())
- {
- Component p = parent;
- if (p != null)
- p.repaint(0, x + getX(), y + getY(), width, height);
- }
- else
+ if (isShowing())
repaint(0, x, y, w, h);
}
@@ -1957,13 +1934,7 @@ public abstract class Component
*/
public void repaint(long tm, int x, int y, int width, int height)
{
- if(!isShowing())
- {
- Component p = parent;
- if (p != null)
- p.repaint(tm, x + getX(), y + getY(), width, height);
- }
- else
+ if (isShowing())
{
ComponentPeer p = peer;
if (p != null)
@@ -2667,7 +2638,7 @@ public abstract class Component
{
mouseMotionListener = AWTEventMulticaster.add(mouseMotionListener, listener);
if (mouseMotionListener != null)
- enableEvents(AWTEvent.MOUSE_EVENT_MASK);
+ enableEvents(AWTEvent.MOUSE_MOTION_EVENT_MASK);
}
/**
@@ -2800,10 +2771,19 @@ public abstract class Component
}
/**
- * Returns all registered EventListers of the given listenerType.
+ * Returns all registered {@link EventListener}s of the given
+ * <code>listenerType</code>.
*
- * @param listenerType the class of listeners to filter
- * @return an array of registered listeners
+ * @param listenerType the class of listeners to filter (<code>null</code>
+ * not permitted).
+ *
+ * @return An array of registered listeners.
+ *
+ * @throws ClassCastException if <code>listenerType</code> does not implement
+ * the {@link EventListener} interface.
+ * @throws NullPointerException if <code>listenerType</code> is
+ * <code>null</code>.
+ *
* @see #getComponentListeners()
* @see #getFocusListeners()
* @see #getHierarchyListeners()
@@ -4879,11 +4859,12 @@ p * <li>the set of backward traversal keys
case MouseEvent.MOUSE_EXITED:
case MouseEvent.MOUSE_PRESSED:
case MouseEvent.MOUSE_RELEASED:
- case MouseEvent.MOUSE_MOVED:
- case MouseEvent.MOUSE_DRAGGED:
return (mouseListener != null
- || mouseMotionListener != null
|| (eventMask & AWTEvent.MOUSE_EVENT_MASK) != 0);
+ case MouseEvent.MOUSE_MOVED:
+ case MouseEvent.MOUSE_DRAGGED:
+ return (mouseMotionListener != null
+ || (eventMask & AWTEvent.MOUSE_MOTION_EVENT_MASK) != 0);
case FocusEvent.FOCUS_GAINED:
case FocusEvent.FOCUS_LOST:
diff --git a/java/awt/Container.java b/java/awt/Container.java
index 0f571e291..35c281a65 100644
--- a/java/awt/Container.java
+++ b/java/awt/Container.java
@@ -125,6 +125,7 @@ public class Container extends Component
*/
public Container()
{
+ // Nothing to do here.
}
/**
@@ -429,7 +430,8 @@ public class Container extends Component
for (int j = 0; j < list.length; j++)
r.removeComponentListener(list[j]);
- r.removeNotify();
+ if (r.isShowing())
+ r.removeNotify();
System.arraycopy(component, index + 1, component, index,
ncomponents - index - 1);
@@ -740,7 +742,16 @@ public class Container extends Component
*/
public float getAlignmentX()
{
- return super.getAlignmentX();
+ LayoutManager layout = getLayout();
+ float alignmentX = 0.0F;
+ if (layout != null && layout instanceof LayoutManager2)
+ {
+ LayoutManager2 lm2 = (LayoutManager2) layout;
+ alignmentX = lm2.getLayoutAlignmentX(this);
+ }
+ else
+ alignmentX = super.getAlignmentX();
+ return alignmentX;
}
/**
@@ -752,7 +763,16 @@ public class Container extends Component
*/
public float getAlignmentY()
{
- return super.getAlignmentY();
+ LayoutManager layout = getLayout();
+ float alignmentY = 0.0F;
+ if (layout != null && layout instanceof LayoutManager2)
+ {
+ LayoutManager2 lm2 = (LayoutManager2) layout;
+ alignmentY = lm2.getLayoutAlignmentY(this);
+ }
+ else
+ alignmentY = super.getAlignmentY();
+ return alignmentY;
}
/**
@@ -830,7 +850,7 @@ public class Container extends Component
*/
public void paintComponents(Graphics g)
{
- super.paint(g);
+ paint(g);
visitChildren(g, GfxPaintAllVisitor.INSTANCE, true);
}
@@ -878,13 +898,21 @@ public class Container extends Component
}
/**
- * Returns an array of all the objects currently registered as FooListeners
- * upon this Container. FooListeners are registered using the addFooListener
- * method.
- *
- * @exception ClassCastException If listenerType doesn't specify a class or
- * interface that implements @see java.util.EventListener.
+ * Returns all registered {@link EventListener}s of the given
+ * <code>listenerType</code>.
*
+ * @param listenerType the class of listeners to filter (<code>null</code>
+ * not permitted).
+ *
+ * @return An array of registered listeners.
+ *
+ * @throws ClassCastException if <code>listenerType</code> does not implement
+ * the {@link EventListener} interface.
+ * @throws NullPointerException if <code>listenerType</code> is
+ * <code>null</code>.
+ *
+ * @see #getContainerListeners()
+ *
* @since 1.3
*/
public <T extends EventListener> T[] getListeners(Class<T> listenerType)
@@ -1076,7 +1104,7 @@ public class Container extends Component
{
if (!contains(x, y))
return null;
-
+
for (int i = 0; i < ncomponents; ++i)
{
// Ignore invisible children...
@@ -1099,7 +1127,8 @@ public class Container extends Component
}
//don't return transparent components with no MouseListeners
- if (this.getMouseListeners().length == 0)
+ if (getMouseListeners().length == 0
+ && getMouseMotionListeners().length == 0)
return null;
return this;
}
@@ -1958,6 +1987,7 @@ public class Container extends Component
*/
protected AccessibleContainerHandler()
{
+ // Nothing to do here.
}
/**
@@ -2025,8 +2055,7 @@ class LightweightDispatcher implements Serializable
* location, otherwise the appropriate component from the conditions
* above.
*/
- Component getDeepestComponentForMouseEventAt (
- Component parent, int x, int y)
+ Component getDeepestComponentForMouseEventAt(Component parent, int x, int y)
{
if (parent == null || (! parent.contains(x, y)))
return null;
@@ -2050,8 +2079,7 @@ class LightweightDispatcher implements Serializable
Point p = me.getPoint();
while (candidate == null && parent != null)
{
- candidate =
- getDeepestComponentForMouseEventAt(parent, p.x, p.y);
+ candidate = getDeepestComponentForMouseEventAt(parent, p.x, p.y);
if (candidate == null || (candidate.eventMask & me.getID()) == 0)
{
candidate = null;
@@ -2133,14 +2161,12 @@ class LightweightDispatcher implements Serializable
break;
}
- if (me.getID() == MouseEvent.MOUSE_RELEASED
- || me.getID() == MouseEvent.MOUSE_PRESSED && modifiers > 0
+ if (me.getID() == MouseEvent.MOUSE_PRESSED && modifiers > 0
|| me.getID() == MouseEvent.MOUSE_DRAGGED)
{
// If any of the following events occur while a button is held down,
// they should be dispatched to the same component to which the
// original MOUSE_PRESSED event was dispatched:
- // - MOUSE_RELEASED
// - MOUSE_PRESSED: another button pressed while the first is held
// down
// - MOUSE_DRAGGED
@@ -2152,7 +2178,10 @@ class LightweightDispatcher implements Serializable
// Don't dispatch CLICKED events whose target is not the same as the
// target for the original PRESSED event.
if (candidate != pressedComponent)
- mouseEventTarget = null;
+ {
+ mouseEventTarget = null;
+ pressCount = 0;
+ }
else if (pressCount == 0)
pressedComponent = null;
}
@@ -2187,7 +2216,10 @@ class LightweightDispatcher implements Serializable
// there is a CLICKED event after this, it will do clean up.
if (--pressCount == 0
&& mouseEventTarget != pressedComponent)
- pressedComponent = null;
+ {
+ pressedComponent = null;
+ pressCount = 0;
+ }
break;
}
diff --git a/java/awt/Image.java b/java/awt/Image.java
index 642131eba..93c2c4790 100644
--- a/java/awt/Image.java
+++ b/java/awt/Image.java
@@ -38,7 +38,9 @@ exception statement from your version. */
package java.awt;
+import java.awt.image.AreaAveragingScaleFilter;
import java.awt.image.FilteredImageSource;
+import java.awt.image.ImageFilter;
import java.awt.image.ImageObserver;
import java.awt.image.ImageProducer;
import java.awt.image.ReplicateScaleFilter;
@@ -178,20 +180,25 @@ public abstract class Image
*/
public Image getScaledInstance(int width, int height, int flags)
{
+ ImageFilter filter;
switch (flags)
{
case SCALE_DEFAULT:
case SCALE_FAST:
case SCALE_REPLICATE:
- ImageProducer producer =
- new FilteredImageSource(this.getSource(),
- new ReplicateScaleFilter(width, height));
- return Toolkit.getDefaultToolkit().createImage(producer);
- case SCALE_SMOOTH:
+ filter = new ReplicateScaleFilter(width, height);
+ break;
case SCALE_AREA_AVERAGING:
+ filter = new AreaAveragingScaleFilter(width, height);
+ break;
+ case SCALE_SMOOTH:
+ throw new Error("SCALE_SMOOTH: not implemented");
default:
- throw new Error("not implemented");
+ throw new Error("Unknown flag or not implemented: " + flags);
}
+
+ ImageProducer producer = new FilteredImageSource(getSource(), filter);
+ return Toolkit.getDefaultToolkit().createImage(producer);
}
/**
diff --git a/java/awt/ScrollPane.java b/java/awt/ScrollPane.java
index d35d9490d..525d9d3e7 100644
--- a/java/awt/ScrollPane.java
+++ b/java/awt/ScrollPane.java
@@ -401,7 +401,7 @@ setScrollPosition(int x, int y)
public void
addNotify()
{
- if (!isDisplayable ())
+ if (peer != null)
return;
setPeer((ComponentPeer)getToolkit().createScrollPane(this));
diff --git a/java/awt/Window.java b/java/awt/Window.java
index ccc609596..61b380edf 100644
--- a/java/awt/Window.java
+++ b/java/awt/Window.java
@@ -809,20 +809,81 @@ public class Window extends Container implements Accessible
return isVisible();
}
- public void setLocationRelativeTo (Component c)
+ public void setLocationRelativeTo(Component c)
{
- if (c == null || !c.isShowing ())
+ int x = 0;
+ int y = 0;
+
+ if (c == null || !c.isShowing())
{
- int x = 0;
- int y = 0;
-
- GraphicsEnvironment ge = GraphicsEnvironment.getLocalGraphicsEnvironment ();
- Point center = ge.getCenterPoint ();
+ GraphicsEnvironment ge = GraphicsEnvironment.getLocalGraphicsEnvironment();
+ Point center = ge.getCenterPoint();
x = center.x - (width / 2);
y = center.y - (height / 2);
- setLocation (x, y);
}
- // FIXME: handle case where component is non-null.
+ else
+ {
+ int cWidth = c.getWidth();
+ int cHeight = c.getHeight();
+ Dimension screenSize = getToolkit().getScreenSize();
+
+ x = c.getLocationOnScreen().x;
+ y = c.getLocationOnScreen().y;
+
+ // If bottom of component is cut off, window placed
+ // on the left or the right side of component
+ if ((y + cHeight) > screenSize.height)
+ {
+ // If the right side of the component is closer to the center
+ if ((screenSize.width / 2 - x) <= 0)
+ {
+ if ((x - width) >= 0)
+ x -= width;
+ else
+ x = 0;
+ }
+ else
+ {
+ if ((x + cWidth + width) <= screenSize.width)
+ x += cWidth;
+ else
+ x = screenSize.width - width;
+ }
+
+ y = screenSize.height - height;
+ }
+ else if (cWidth > width || cHeight > height)
+ {
+ // If right side of component is cut off
+ if ((x + width) > screenSize.width)
+ x = screenSize.width - width;
+ // If left side of component is cut off
+ else if (x < 0)
+ x = 0;
+ else
+ x += (cWidth - width) / 2;
+
+ y += (cHeight - height) / 2;
+ }
+ else
+ {
+ // If right side of component is cut off
+ if ((x + width) > screenSize.width)
+ x = screenSize.width - width;
+ // If left side of component is cut off
+ else if (x < 0 || (x - (width - cWidth) / 2) < 0)
+ x = 0;
+ else
+ x -= (width - cWidth) / 2;
+
+ if ((y - (height - cHeight) / 2) > 0)
+ y -= (height - cHeight) / 2;
+ else
+ y = 0;
+ }
+ }
+
+ setLocation(x, y);
}
/**
diff --git a/java/awt/datatransfer/DataFlavor.java b/java/awt/datatransfer/DataFlavor.java
index 189920f96..606cfe035 100644
--- a/java/awt/datatransfer/DataFlavor.java
+++ b/java/awt/datatransfer/DataFlavor.java
@@ -1,5 +1,5 @@
/* DataFlavor.java -- A type of data to transfer via the clipboard.
- Copyright (C) 1999, 2001, 2004 Free Software Foundation, Inc.
+ Copyright (C) 1999, 2001, 2004, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -49,6 +49,7 @@ import java.io.StringReader;
import java.io.UnsupportedEncodingException;
import java.nio.ByteBuffer;
import java.nio.CharBuffer;
+import java.nio.charset.Charset;
import java.rmi.Remote;
/**
@@ -63,78 +64,65 @@ public class DataFlavor implements java.io.Externalizable, Cloneable
// FIXME: Serialization: Need to write methods for.
-/**
- * This is the data flavor used for tranferring plain text. The MIME
- * type is "text/plain; charset=unicode". The representation class
- * is <code>java.io.InputStream</code>.
- *
- * @deprecated The charset unicode is platform specific and InputStream
- * deals with bytes not chars. Use <code>getRederForText()</code>.
- */
-public static final DataFlavor plainTextFlavor;
-
-/**
- * This is the data flavor used for transferring Java strings. The
- * MIME type is "application/x-java-serialized-object" and the
- * representation class is <code>java.lang.String</code>.
- */
-public static final DataFlavor stringFlavor;
-
-/**
- * This is a data flavor used for transferring lists of files. The
- * representation type is a <code>java.util.List</code>, with each element of
- * the list being a <code>java.io.File</code>.
- */
-public static final DataFlavor javaFileListFlavor;
-
-/**
- * This is an image flavor used for transferring images. The
- * representation type is a <code>java.awt.Image</code>.
- */
-public static final DataFlavor imageFlavor;
-
-/**
- * This is the MIME type used for transferring a serialized object.
- * The representation class is the type of object be deserialized.
- */
-public static final String javaSerializedObjectMimeType =
- "application/x-java-serialized-object";
+ /**
+ * This is the data flavor used for tranferring plain text. The MIME
+ * type is "text/plain; charset=unicode". The representation class
+ * is <code>java.io.InputStream</code>.
+ *
+ * @deprecated The charset unicode is platform specific and InputStream
+ * deals with bytes not chars. Use <code>getRederForText()</code>.
+ */
+ public static final DataFlavor plainTextFlavor =
+ new DataFlavor(java.io.InputStream.class,
+ "text/plain; charset=unicode",
+ "plain unicode text");
-/**
- * This is the MIME type used to transfer a Java object reference within
- * the same JVM. The representation class is the class of the object
- * being transferred.
- */
-public static final String javaJVMLocalObjectMimeType =
- "application/x-java-jvm-local-objectref";
+ /**
+ * This is the data flavor used for transferring Java strings. The
+ * MIME type is "application/x-java-serialized-object" and the
+ * representation class is <code>java.lang.String</code>.
+ */
+ public static final DataFlavor stringFlavor =
+ new DataFlavor(java.lang.String.class, "Java Unicode String");
-/**
- * This is the MIME type used to transfer a link to a remote object.
- * The representation class is the type of object being linked to.
- */
-public static final String javaRemoteObjectMimeType =
- "application/x-java-remote-object";
+ /**
+ * This is a data flavor used for transferring lists of files. The
+ * representation type is a <code>java.util.List</code>, with each
+ * element of the list being a <code>java.io.File</code>.
+ */
+ public static final DataFlavor javaFileListFlavor =
+ new DataFlavor(java.util.List.class,
+ "application/x-java-file-list; class=java.util.List",
+ "Java File List");
-static
-{
- plainTextFlavor
- = new DataFlavor(java.io.InputStream.class,
- "text/plain; charset=unicode",
- "plain unicode text");
+ /**
+ * This is an image flavor used for transferring images. The
+ * representation type is a <code>java.awt.Image</code>.
+ */
+ public static final DataFlavor imageFlavor =
+ new DataFlavor(java.awt.Image.class, "Java Image");
- stringFlavor
- = new DataFlavor(java.lang.String.class,
- "Java Unicode String");
+ /**
+ * This is the MIME type used for transferring a serialized object.
+ * The representation class is the type of object be deserialized.
+ */
+ public static final String javaSerializedObjectMimeType =
+ "application/x-java-serialized-object";
- javaFileListFlavor
- = new DataFlavor(java.util.List.class,
- "application/x-java-file-list; class=java.util.List",
- "Java File List");
+ /**
+ * This is the MIME type used to transfer a Java object reference within
+ * the same JVM. The representation class is the class of the object
+ * being transferred.
+ */
+ public static final String javaJVMLocalObjectMimeType =
+ "application/x-java-jvm-local-objectref";
- imageFlavor
- = new DataFlavor(java.awt.Image.class,
- "Java Image");
-}
+ /**
+ * This is the MIME type used to transfer a link to a remote object.
+ * The representation class is the type of object being linked to.
+ */
+ public static final String javaRemoteObjectMimeType =
+ "application/x-java-remote-object";
/*************************************************************************/
@@ -153,856 +141,753 @@ private String humanPresentableName;
/*************************************************************************/
-/*
- * Static Methods
- */
-
-/**
- * This method attempts to load the named class. The following class
- * loaders are searched in order: the bootstrap class loader, the
- * system class loader, the context class loader (if it exists), and
- * the specified fallback class loader.
- *
- * @param className The name of the class to load.
- * @param classLoader The class loader to use if all others fail, which
- * may be <code>null</code>.
- *
- * @exception ClassNotFoundException If the class cannot be loaded.
- */
-protected static final Class<?>
-tryToLoadClass(String className, ClassLoader classLoader)
- throws ClassNotFoundException
-{
- try
- {
- return(Class.forName(className));
- }
- catch(Exception e) { ; }
- // Commented out for Java 1.1
/*
- try
+ * Static Methods
+ */
+
+ /**
+ * This method attempts to load the named class. The following class
+ * loaders are searched in order: the bootstrap class loader, the
+ * system class loader, the context class loader (if it exists), and
+ * the specified fallback class loader.
+ *
+ * @param className The name of the class to load.
+ * @param classLoader The class loader to use if all others fail, which
+ * may be <code>null</code>.
+ *
+ * @exception ClassNotFoundException If the class cannot be loaded.
+ */
+ protected static final Class<?> tryToLoadClass(String className,
+ ClassLoader classLoader)
+ throws ClassNotFoundException
+ {
+ try
+ {
+ return(Class.forName(className));
+ }
+ catch(Exception e) { ; }
+ // Commented out for Java 1.1
+ /*
+ try
+ {
+ return(className.getClass().getClassLoader().findClass(className));
+ }
+ catch(Exception e) { ; }
+
+ try
+ {
+ return(ClassLoader.getSystemClassLoader().findClass(className));
+ }
+ catch(Exception e) { ; }
+ */
+
+ // FIXME: What is the context class loader?
+ /*
+ try
+ {
+ }
+ catch(Exception e) { ; }
+ */
+
+ if (classLoader != null)
+ return(classLoader.loadClass(className));
+ else
+ throw new ClassNotFoundException(className);
+ }
+
+ private static Class getRepresentationClassFromMime(String mimeString,
+ ClassLoader classLoader)
{
- return(className.getClass().getClassLoader().findClass(className));
+ String classname = getParameter("class", mimeString);
+ if (classname != null)
+ {
+ try
+ {
+ return tryToLoadClass(classname, classLoader);
+ }
+ catch(Exception e)
+ {
+ throw new IllegalArgumentException("classname: " + e.getMessage());
+ }
+ }
+ else
+ return java.io.InputStream.class;
}
- catch(Exception e) { ; }
+
+ /**
+ * Returns the value of the named MIME type parameter, or <code>null</code>
+ * if the parameter does not exist. Given the parameter name and the mime
+ * string.
+ *
+ * @param paramName The name of the parameter.
+ * @param mimeString The mime string from where the name should be found.
+ *
+ * @return The value of the parameter or null.
+ */
+ private static String getParameter(String paramName, String mimeString)
+ {
+ int idx = mimeString.indexOf(paramName + "=");
+ if (idx == -1)
+ return(null);
+
+ String value = mimeString.substring(idx + paramName.length() + 1);
+
+ idx = value.indexOf(" ");
+ if (idx == -1)
+ return(value);
+ else
+ return(value.substring(0, idx));
+ }
+
+ /**
+ * XXX - Currently returns <code>plainTextFlavor</code>.
+ */
+ public static final DataFlavor getTextPlainUnicodeFlavor()
+ {
+ return plainTextFlavor;
+ }
+
+ /**
+ * Selects the best supported text flavor on this implementation.
+ * Returns <code>null</code> when none of the given flavors is liked.
+ *
+ * The <code>DataFlavor</code> returned the first data flavor in the
+ * array that has either a representation class which is (a subclass of)
+ * <code>Reader</code> or <code>String</code>, or has a representation
+ * class which is (a subclass of) <code>InputStream</code> and has a
+ * primary MIME type of "text" and has an supported encoding.
+ */
+ public static final DataFlavor
+ selectBestTextFlavor(DataFlavor[] availableFlavors)
+ {
+ for(int i = 0; i < availableFlavors.length; i++)
+ {
+ DataFlavor df = availableFlavors[i];
+ Class c = df.representationClass;
+
+ // A Reader or String is good.
+ if ((Reader.class.isAssignableFrom(c))
+ || (String.class.isAssignableFrom(c)))
+ return df;
+
+ // A InputStream is good if the mime primary type is "text"
+ if ((InputStream.class.isAssignableFrom(c))
+ && ("text".equals(df.getPrimaryType())))
+ {
+ String encoding = availableFlavors[i].getParameter("charset");
+ if (encoding == null)
+ encoding = "us-ascii";
+ Reader r = null;
+ try
+ {
+ // Try to construct a dummy reader with the found encoding
+ r = new InputStreamReader
+ (new ByteArrayInputStream(new byte[0]), encoding);
+ }
+ catch(UnsupportedEncodingException uee) { /* ignore */ }
+
+ if (r != null)
+ return df;
+ }
+ }
+
+ // Nothing found
+ return null;
+ }
- try
- {
- return(ClassLoader.getSystemClassLoader().findClass(className));
- }
- catch(Exception e) { ; }
- */
- // FIXME: What is the context class loader?
/*
- try
- {
- }
- catch(Exception e) { ; }
- */
-
- if (classLoader != null)
- return(classLoader.loadClass(className));
- else
- throw new ClassNotFoundException(className);
-}
-
-/*************************************************************************/
-
-/*
- * Constructors
- */
-
-/**
- * Empty public constructor needed for externalization.
- * Should not be used for normal instantiation.
- */
-public
-DataFlavor()
-{
+ * Constructors
+ */
+
+ /**
+ * Empty public constructor needed for externalization.
+ * Should not be used for normal instantiation.
+ */
+ public DataFlavor()
+ {
mimeType = null;
representationClass = null;
humanPresentableName = null;
-}
+ }
/*************************************************************************/
/**
* Private constructor.
*/
-private
-DataFlavor(Class<?> representationClass,
- String mimeType,
- String humanPresentableName)
-{
- this.representationClass = representationClass;
- this.mimeType = mimeType;
- if (humanPresentableName != null)
+ private
+ DataFlavor(Class<?> representationClass,
+ String mimeType,
+ String humanPresentableName)
+ {
+ this.representationClass = representationClass;
+ this.mimeType = mimeType;
+ if (humanPresentableName != null)
this.humanPresentableName = humanPresentableName;
- else
+ else
this.humanPresentableName = mimeType;
-}
-
-/*************************************************************************/
-
-/**
- * Initializes a new instance of <code>DataFlavor</code>. The class
- * and human readable name are specified, the MIME type will be
- * "application/x-java-serialized-object". If the human readable name
- * is not specified (<code>null</code>) then the human readable name
- * will be the same as the MIME type.
- *
- * @param representationClass The representation class for this object.
- * @param humanPresentableName The display name of the object.
- */
-public
-DataFlavor(Class<?> representationClass, String humanPresentableName)
-{
- this(representationClass,
- "application/x-java-serialized-object"
- + "; class="
- + representationClass.getName(),
- humanPresentableName);
-}
-
-/*************************************************************************/
-
-/**
- * Initializes a new instance of <code>DataFlavor</code> with the
- * specified MIME type and description. If the MIME type has a
- * "class=&lt;rep class&gt;" parameter then the representation class will
- * be the class name specified. Otherwise the class defaults to
- * <code>java.io.InputStream</code>. If the human readable name
- * is not specified (<code>null</code>) then the human readable name
- * will be the same as the MIME type.
- *
- * @param mimeType The MIME type for this flavor.
- * @param humanPresentableName The display name of this flavor.
- * @param classLoader The class loader for finding classes if the default
- * class loaders do not work.
- *
- * @exception IllegalArgumentException If the representation class
- * specified cannot be loaded.
- * @exception ClassNotFoundException If the class is not loaded.
- */
-public
-DataFlavor(String mimeType, String humanPresentableName,
- ClassLoader classLoader) throws ClassNotFoundException
-{
- this(getRepresentationClassFromMime(mimeType, classLoader),
- mimeType, humanPresentableName);
-}
-
-private static Class
-getRepresentationClassFromMime(String mimeString, ClassLoader classLoader)
-{
- String classname = getParameter("class", mimeString);
- if (classname != null)
- {
- try
- {
- return tryToLoadClass(classname, classLoader);
- }
- catch(Exception e)
- {
- throw new IllegalArgumentException("classname: " + e.getMessage());
- }
- }
- else
- {
- return java.io.InputStream.class;
}
-}
-
-/*************************************************************************/
-
-/**
- * Initializes a new instance of <code>DataFlavor</code> with the
- * specified MIME type and description. If the MIME type has a
- * "class=&lt;rep class&gt;" parameter then the representation class will
- * be the class name specified. Otherwise the class defaults to
- * <code>java.io.InputStream</code>. If the human readable name
- * is not specified (<code>null</code>) then the human readable name
- * will be the same as the MIME type. This is the same as calling
- * <code>new DataFlavor(mimeType, humanPresentableName, null)</code>.
- *
- * @param mimeType The MIME type for this flavor.
- * @param humanPresentableName The display name of this flavor.
- *
- * @exception IllegalArgumentException If the representation class
- * specified cannot be loaded.
- */
-public
-DataFlavor(String mimeType, String humanPresentableName)
-{
- this (getRepresentationClassFromMime (mimeType, null),
- mimeType, humanPresentableName);
-}
/*************************************************************************/
-/**
- * Initializes a new instance of <code>DataFlavor</code> with the specified
- * MIME type. This type can have a "class=" parameter to specify the
- * representation class, and then the class must exist or an exception will
- * be thrown. If there is no "class=" parameter then the representation class
- * will be <code>java.io.InputStream</code>. This is the same as calling
- * <code>new DataFlavor(mimeType, null)</code>.
- *
- * @param mimeType The MIME type for this flavor.
- *
- * @exception IllegalArgumentException If a class is not specified in
- * the MIME type.
- * @exception ClassNotFoundException If the class cannot be loaded.
- */
-public
-DataFlavor(String mimeType) throws ClassNotFoundException
-{
- this(mimeType, null);
-}
-
-/*************************************************************************/
-
-/**
- * Returns the MIME type of this flavor.
- *
- * @return The MIME type for this flavor.
- */
-public String
-getMimeType()
-{
- return(mimeType);
-}
-
-/*************************************************************************/
-
-/**
- * Returns the representation class for this flavor.
- *
- * @return The representation class for this flavor.
- */
-public Class<?>
-getRepresentationClass()
-{
- return(representationClass);
-}
-
-/*************************************************************************/
-
-/**
- * Returns the human presentable name for this flavor.
- *
- * @return The human presentable name for this flavor.
- */
-public String
-getHumanPresentableName()
-{
- return(humanPresentableName);
-}
-
-/*************************************************************************/
-
-/**
- * Returns the primary MIME type for this flavor.
- *
- * @return The primary MIME type for this flavor.
- */
-public String
-getPrimaryType()
-{
- int idx = mimeType.indexOf("/");
- if (idx == -1)
- return(mimeType);
-
- return(mimeType.substring(0, idx));
-}
-
-/*************************************************************************/
-
-/**
- * Returns the MIME subtype for this flavor.
- *
- * @return The MIME subtype for this flavor.
- */
-public String
-getSubType()
-{
- int start = mimeType.indexOf("/");
- if (start == -1)
- return "";
-
- int end = mimeType.indexOf(";", start + 1);
- if (end == -1)
- return mimeType.substring(start + 1);
- else
- return mimeType.substring(start + 1, end);
-}
-
-/*************************************************************************/
-
-/**
- * Returns the value of the named MIME type parameter, or <code>null</code>
- * if the parameter does not exist. Given the parameter name and the mime
- * string.
- *
- * @param paramName The name of the parameter.
- * @param mimeString The mime string from where the name should be found.
- *
- * @return The value of the parameter or null.
- */
-private static String
-getParameter(String paramName, String mimeString)
-{
- int idx = mimeString.indexOf(paramName + "=");
- if (idx == -1)
- return(null);
-
- String value = mimeString.substring(idx + paramName.length() + 1);
-
- idx = value.indexOf(" ");
- if (idx == -1)
- return(value);
- else
- return(value.substring(0, idx));
-}
-
-/*************************************************************************/
-
-/**
- * Returns the value of the named MIME type parameter, or <code>null</code>
- * if the parameter does not exist.
- *
- * @param paramName The name of the paramter.
- *
- * @return The value of the parameter.
- */
-public String
-getParameter(String paramName)
-{
- if ("humanPresentableName".equals(paramName))
- return getHumanPresentableName();
-
- return getParameter(paramName, mimeType);
-}
-
-/*************************************************************************/
-
-/**
- * Sets the human presentable name to the specified value.
- *
- * @param humanPresentableName The new display name.
- */
-public void
-setHumanPresentableName(String humanPresentableName)
-{
- this.humanPresentableName = humanPresentableName;
-}
-
-/*************************************************************************/
-
-/**
- * Tests the MIME type of this object for equality against the specified
- * MIME type. Ignores parameters.
- *
- * @param mimeType The MIME type to test against.
- *
- * @return <code>true</code> if the MIME type is equal to this object's
- * MIME type (ignoring parameters), <code>false</code> otherwise.
- *
- * @exception NullPointerException If mimeType is null.
- */
-public boolean
-isMimeTypeEqual(String mimeType)
-{
- String mime = getMimeType();
- int i = mime.indexOf(";");
- if (i != -1)
- mime = mime.substring(0, i);
-
- i = mimeType.indexOf(";");
- if (i != -1)
- mimeType = mimeType.substring(0, i);
-
- return mime.equals(mimeType);
-}
-
-/*************************************************************************/
-
-/**
- * Tests the MIME type of this object for equality against the specified
- * data flavor's MIME type
- *
- * @param flavor The flavor to test against.
- *
- * @return <code>true</code> if the flavor's MIME type is equal to this
- * object's MIME type, <code>false</code> otherwise.
- */
-public final boolean
-isMimeTypeEqual(DataFlavor flavor)
-{
- return(isMimeTypeEqual(flavor.getMimeType()));
-}
-
-/*************************************************************************/
-
-/**
- * Tests whether or not this flavor represents a serialized object.
- *
- * @return <code>true</code> if this flavor represents a serialized
- * object, <code>false</code> otherwise.
- */
-public boolean
-isMimeTypeSerializedObject()
-{
- return(mimeType.startsWith(javaSerializedObjectMimeType));
-}
-
-/*************************************************************************/
-
-/**
- * Tests whether or not this flavor has a representation class of
- * <code>java.io.InputStream</code>.
- *
- * @return <code>true</code> if the representation class of this flavor
- * is <code>java.io.InputStream</code>, <code>false</code> otherwise.
- */
-public boolean
-isRepresentationClassInputStream()
-{
- return(representationClass.getName().equals("java.io.InputStream"));
-}
-
-/*************************************************************************/
-
-/**
- * Tests whether the representation class for this flavor is
- * serializable.
- *
- * @return <code>true</code> if the representation class is serializable,
- * <code>false</code> otherwise.
- */
-public boolean
-isRepresentationClassSerializable()
-{
- Class[] interfaces = representationClass.getInterfaces();
-
- int i = 0;
- while (i < interfaces.length)
+ /**
+ * Initializes a new instance of <code>DataFlavor</code>. The class
+ * and human readable name are specified, the MIME type will be
+ * "application/x-java-serialized-object". If the human readable name
+ * is not specified (<code>null</code>) then the human readable name
+ * will be the same as the MIME type.
+ *
+ * @param representationClass The representation class for this object.
+ * @param humanPresentableName The display name of the object.
+ */
+ public
+ DataFlavor(Class<?> representationClass, String humanPresentableName)
{
- if (interfaces[i].getName().equals("java.io.Serializable"))
- return(true);
- ++i;
+ this(representationClass,
+ "application/x-java-serialized-object"
+ + "; class="
+ + representationClass.getName(),
+ humanPresentableName);
}
- return(false);
-}
-
-/*************************************************************************/
-
-/**
- * Tests whether the representation class for his flavor is remote.
- *
- * @return <code>true</code> if the representation class is remote,
- * <code>false</code> otherwise.
- */
-public boolean
-isRepresentationClassRemote()
-{
- return Remote.class.isAssignableFrom (representationClass);
-}
-
-/*************************************************************************/
-
-/**
- * Tests whether or not this flavor represents a serialized object.
- *
- * @return <code>true</code> if this flavor represents a serialized
- * object, <code>false</code> otherwise.
- */
-public boolean
-isFlavorSerializedObjectType()
-{
- // FIXME: What is the diff between this and isMimeTypeSerializedObject?
- return(mimeType.startsWith(javaSerializedObjectMimeType));
-}
-
-/*************************************************************************/
-
-/**
- * Tests whether or not this flavor represents a remote object.
- *
- * @return <code>true</code> if this flavor represents a remote object,
- * <code>false</code> otherwise.
- */
-public boolean
-isFlavorRemoteObjectType()
-{
- return(mimeType.startsWith(javaRemoteObjectMimeType));
-}
-
-/*************************************************************************/
+ /**
+ * Initializes a new instance of <code>DataFlavor</code> with the
+ * specified MIME type and description. If the MIME type has a
+ * "class=&lt;rep class&gt;" parameter then the representation class will
+ * be the class name specified. Otherwise the class defaults to
+ * <code>java.io.InputStream</code>. If the human readable name
+ * is not specified (<code>null</code>) then the human readable name
+ * will be the same as the MIME type.
+ *
+ * @param mimeType The MIME type for this flavor.
+ * @param humanPresentableName The display name of this flavor.
+ * @param classLoader The class loader for finding classes if the default
+ * class loaders do not work.
+ *
+ * @exception IllegalArgumentException If the representation class
+ * specified cannot be loaded.
+ * @exception ClassNotFoundException If the class is not loaded.
+ */
+ public DataFlavor(String mimeType, String humanPresentableName,
+ ClassLoader classLoader)
+ throws ClassNotFoundException
+ {
+ this(getRepresentationClassFromMime(mimeType, classLoader),
+ mimeType, humanPresentableName);
+ }
-/**
- * Tests whether or not this flavor represents a list of files.
- *
- * @return <code>true</code> if this flavor represents a list of files,
- * <code>false</code> otherwise.
- */
-public boolean
-isFlavorJavaFileListType()
-{
- if (this.mimeType.equals(javaFileListFlavor.mimeType) &&
- this.representationClass.equals(javaFileListFlavor.representationClass))
- return(true);
+ /**
+ * Initializes a new instance of <code>DataFlavor</code> with the
+ * specified MIME type and description. If the MIME type has a
+ * "class=&lt;rep class&gt;" parameter then the representation class will
+ * be the class name specified. Otherwise the class defaults to
+ * <code>java.io.InputStream</code>. If the human readable name
+ * is not specified (<code>null</code>) then the human readable name
+ * will be the same as the MIME type. This is the same as calling
+ * <code>new DataFlavor(mimeType, humanPresentableName, null)</code>.
+ *
+ * @param mimeType The MIME type for this flavor.
+ * @param humanPresentableName The display name of this flavor.
+ *
+ * @exception IllegalArgumentException If the representation class
+ * specified cannot be loaded.
+ */
+ public DataFlavor(String mimeType, String humanPresentableName)
+ {
+ this(getRepresentationClassFromMime (mimeType, null),
+ mimeType, humanPresentableName);
+ }
- return(false);
-}
+ /**
+ * Initializes a new instance of <code>DataFlavor</code> with the specified
+ * MIME type. This type can have a "class=" parameter to specify the
+ * representation class, and then the class must exist or an exception will
+ * be thrown. If there is no "class=" parameter then the representation class
+ * will be <code>java.io.InputStream</code>. This is the same as calling
+ * <code>new DataFlavor(mimeType, null)</code>.
+ *
+ * @param mimeType The MIME type for this flavor.
+ *
+ * @exception IllegalArgumentException If a class is not specified in
+ * the MIME type.
+ * @exception ClassNotFoundException If the class cannot be loaded.
+ */
+ public DataFlavor(String mimeType) throws ClassNotFoundException
+ {
+ this(mimeType, null);
+ }
/*************************************************************************/
-/**
- * Returns a copy of this object.
- *
- * @return A copy of this object.
- *
- * @exception CloneNotSupportedException If the object's class does not support
- * the Cloneable interface. Subclasses that override the clone method can also
- * throw this exception to indicate that an instance cannot be cloned.
- */
-public Object clone () throws CloneNotSupportedException
-{
- try
- {
- return(super.clone());
- }
- catch(Exception e)
- {
- return(null);
- }
-}
-
-/*************************************************************************/
+ /**
+ * Returns the MIME type of this flavor.
+ *
+ * @return The MIME type for this flavor.
+ */
+ public String getMimeType()
+ {
+ return(mimeType);
+ }
-/**
- * This method test the specified <code>DataFlavor</code> for equality
- * against this object. This will be true if the MIME type and
- * representation type are the equal.
- *
- * @param flavor The <code>DataFlavor</code> to test against.
- *
- * @return <code>true</code> if the flavor is equal to this object,
- * <code>false</code> otherwise.
- */
-public boolean
-equals(DataFlavor flavor)
-{
- if (flavor == null)
- return(false);
+ /**
+ * Returns the representation class for this flavor.
+ *
+ * @return The representation class for this flavor.
+ */
+ public Class<?> getRepresentationClass()
+ {
+ return(representationClass);
+ }
- if (!this.mimeType.toLowerCase().equals(flavor.mimeType.toLowerCase()))
- return(false);
+ /**
+ * Returns the human presentable name for this flavor.
+ *
+ * @return The human presentable name for this flavor.
+ */
+ public String getHumanPresentableName()
+ {
+ return(humanPresentableName);
+ }
- if (!this.representationClass.equals(flavor.representationClass))
- return(false);
+ /**
+ * Returns the primary MIME type for this flavor.
+ *
+ * @return The primary MIME type for this flavor.
+ */
+ public String getPrimaryType()
+ {
+ int idx = mimeType.indexOf("/");
+ if (idx == -1)
+ return(mimeType);
+
+ return(mimeType.substring(0, idx));
+ }
- return(true);
-}
+ /**
+ * Returns the MIME subtype for this flavor.
+ *
+ * @return The MIME subtype for this flavor.
+ */
+ public String getSubType()
+ {
+ int start = mimeType.indexOf("/");
+ if (start == -1)
+ return "";
+
+ int end = mimeType.indexOf(";", start + 1);
+ if (end == -1)
+ return mimeType.substring(start + 1);
+ else
+ return mimeType.substring(start + 1, end);
+ }
-/*************************************************************************/
+ /**
+ * Returns the value of the named MIME type parameter, or <code>null</code>
+ * if the parameter does not exist.
+ *
+ * @param paramName The name of the paramter.
+ *
+ * @return The value of the parameter.
+ */
+ public String getParameter(String paramName)
+ {
+ if ("humanPresentableName".equals(paramName))
+ return getHumanPresentableName();
+
+ return getParameter(paramName, mimeType);
+ }
-/**
- * This method test the specified <code>Object</code> for equality
- * against this object. This will be true if the following conditions
- * are met:
- * <p>
- * <ul>
- * <li>The object is not <code>null</code>.</li>
- * <li>The object is an instance of <code>DataFlavor</code>.</li>
- * <li>The object's MIME type and representation class are equal to
- * this object's.</li>
- * </ul>
- *
- * @param obj The <code>Object</code> to test against.
- *
- * @return <code>true</code> if the flavor is equal to this object,
- * <code>false</code> otherwise.
- */
-public boolean
-equals(Object obj)
-{
- if (!(obj instanceof DataFlavor))
- return(false);
+ /**
+ * Sets the human presentable name to the specified value.
+ *
+ * @param humanPresentableName The new display name.
+ */
+ public void setHumanPresentableName(String humanPresentableName)
+ {
+ this.humanPresentableName = humanPresentableName;
+ }
- return(equals((DataFlavor)obj));
-}
+ /**
+ * Tests the MIME type of this object for equality against the specified
+ * MIME type. Ignores parameters.
+ *
+ * @param mimeType The MIME type to test against.
+ *
+ * @return <code>true</code> if the MIME type is equal to this object's
+ * MIME type (ignoring parameters), <code>false</code> otherwise.
+ *
+ * @exception NullPointerException If mimeType is null.
+ */
+ public boolean isMimeTypeEqual(String mimeType)
+ {
+ String mime = getMimeType();
+ int i = mime.indexOf(";");
+ if (i != -1)
+ mime = mime.substring(0, i);
+
+ i = mimeType.indexOf(";");
+ if (i != -1)
+ mimeType = mimeType.substring(0, i);
+
+ return mime.equals(mimeType);
+ }
-/*************************************************************************/
+ /**
+ * Tests the MIME type of this object for equality against the specified
+ * data flavor's MIME type
+ *
+ * @param flavor The flavor to test against.
+ *
+ * @return <code>true</code> if the flavor's MIME type is equal to this
+ * object's MIME type, <code>false</code> otherwise.
+ */
+ public final boolean isMimeTypeEqual(DataFlavor flavor)
+ {
+ return isMimeTypeEqual(flavor.getMimeType());
+ }
-/**
- * Tests whether or not the specified string is equal to the MIME type
- * of this object.
- *
- * @param str The string to test against.
- *
- * @return <code>true</code> if the string is equal to this object's MIME
- * type, <code>false</code> otherwise.
- *
- * @deprecated Not compatible with <code>hashCode()</code>.
- * Use <code>isMimeTypeEqual()</code>
- */
-public boolean
-equals(String str)
-{
- return(isMimeTypeEqual(str));
-}
+ /**
+ * Tests whether or not this flavor represents a serialized object.
+ *
+ * @return <code>true</code> if this flavor represents a serialized
+ * object, <code>false</code> otherwise.
+ */
+ public boolean isMimeTypeSerializedObject()
+ {
+ return mimeType.startsWith(javaSerializedObjectMimeType);
+ }
-/*************************************************************************/
+ /**
+ * Tests whether or not this flavor has a representation class of
+ * <code>java.io.InputStream</code>.
+ *
+ * @return <code>true</code> if the representation class of this flavor
+ * is <code>java.io.InputStream</code>, <code>false</code> otherwise.
+ */
+ public boolean isRepresentationClassInputStream()
+ {
+ return representationClass.getName().equals("java.io.InputStream");
+ }
-/**
- * Returns the hash code for this data flavor.
- * The hash code is based on the (lower case) mime type and the
- * representation class.
- */
-public int
-hashCode()
-{
- return(mimeType.toLowerCase().hashCode()^representationClass.hashCode());
-}
+ /**
+ * Tests whether the representation class for this flavor is
+ * serializable.
+ *
+ * @return <code>true</code> if the representation class is serializable,
+ * <code>false</code> otherwise.
+ */
+ public boolean isRepresentationClassSerializable()
+ {
+ Class[] interfaces = representationClass.getInterfaces();
+
+ int i = 0;
+ while (i < interfaces.length)
+ {
+ if (interfaces[i].getName().equals("java.io.Serializable"))
+ return true;
+ ++i;
+ }
+
+ return false;
+ }
-/*************************************************************************/
+ /**
+ * Tests whether the representation class for his flavor is remote.
+ *
+ * @return <code>true</code> if the representation class is remote,
+ * <code>false</code> otherwise.
+ */
+ public boolean isRepresentationClassRemote()
+ {
+ return Remote.class.isAssignableFrom (representationClass);
+ }
-/**
- * Returns <code>true</code> when the given <code>DataFlavor</code>
- * matches this one.
- */
-public boolean
-match(DataFlavor dataFlavor)
-{
- // XXX - How is this different from equals?
- return(equals(dataFlavor));
-}
+ /**
+ * Tests whether or not this flavor represents a serialized object.
+ *
+ * @return <code>true</code> if this flavor represents a serialized
+ * object, <code>false</code> otherwise.
+ */
+ public boolean isFlavorSerializedObjectType()
+ {
+ // FIXME: What is the diff between this and isMimeTypeSerializedObject?
+ return(mimeType.startsWith(javaSerializedObjectMimeType));
+ }
-/*************************************************************************/
+ /**
+ * Tests whether or not this flavor represents a remote object.
+ *
+ * @return <code>true</code> if this flavor represents a remote object,
+ * <code>false</code> otherwise.
+ */
+ public boolean isFlavorRemoteObjectType()
+ {
+ return(mimeType.startsWith(javaRemoteObjectMimeType));
+ }
-/**
- * This method exists for backward compatibility. It simply returns
- * the same name/value pair passed in.
- *
- * @param name The parameter name.
- * @param value The parameter value.
- *
- * @return The name/value pair.
- *
- * @deprecated
- */
-protected String
-normalizeMimeTypeParameter(String name, String value)
-{
- return(name + "=" + value);
-}
+ /**
+ * Tests whether or not this flavor represents a list of files.
+ *
+ * @return <code>true</code> if this flavor represents a list of files,
+ * <code>false</code> otherwise.
+ */
+ public boolean isFlavorJavaFileListType()
+ {
+ if (mimeType.equals(javaFileListFlavor.mimeType)
+ && representationClass.equals(javaFileListFlavor.representationClass))
+ return true;
+
+ return false ;
+ }
-/*************************************************************************/
+ /**
+ * Returns a copy of this object.
+ *
+ * @return A copy of this object.
+ *
+ * @exception CloneNotSupportedException If the object's class does not support
+ * the Cloneable interface. Subclasses that override the clone method can also
+ * throw this exception to indicate that an instance cannot be cloned.
+ */
+ public Object clone () throws CloneNotSupportedException
+ {
+ // FIXME - This cannot be right.
+ try
+ {
+ return super.clone();
+ }
+ catch(Exception e)
+ {
+ return null;
+ }
+ }
-/**
- * This method exists for backward compatibility. It simply returns
- * the MIME type string unchanged.
- *
- * @param type The MIME type.
- *
- * @return The MIME type.
- *
- * @deprecated
- */
-protected String
-normalizeMimeType(String type)
-{
- return(type);
-}
+ /**
+ * This method test the specified <code>DataFlavor</code> for equality
+ * against this object. This will be true if the MIME type and
+ * representation type are the equal.
+ *
+ * @param flavor The <code>DataFlavor</code> to test against.
+ *
+ * @return <code>true</code> if the flavor is equal to this object,
+ * <code>false</code> otherwise.
+ */
+ public boolean equals(DataFlavor flavor)
+ {
+ if (flavor == null)
+ return false;
+
+ if (! this.mimeType.toLowerCase().equals(flavor.mimeType.toLowerCase()))
+ return false;
+
+ if (! this.representationClass.equals(flavor.representationClass))
+ return false;
+
+ return true;
+ }
-/*************************************************************************/
+ /**
+ * This method test the specified <code>Object</code> for equality
+ * against this object. This will be true if the following conditions
+ * are met:
+ * <p>
+ * <ul>
+ * <li>The object is not <code>null</code>.</li>
+ * <li>The object is an instance of <code>DataFlavor</code>.</li>
+ * <li>The object's MIME type and representation class are equal to
+ * this object's.</li>
+ * </ul>
+ *
+ * @param obj The <code>Object</code> to test against.
+ *
+ * @return <code>true</code> if the flavor is equal to this object,
+ * <code>false</code> otherwise.
+ */
+ public boolean equals(Object obj)
+ {
+ if (! (obj instanceof DataFlavor))
+ return false;
+
+ return equals((DataFlavor) obj);
+ }
-/**
- * Serialize this class.
- *
- * @param stream The <code>ObjectOutput</code> stream to serialize to.
- *
- * @exception IOException If an error occurs.
- */
-public void
-writeExternal(ObjectOutput stream) throws IOException
-{
- // FIXME: Implement me
-}
+ /**
+ * Tests whether or not the specified string is equal to the MIME type
+ * of this object.
+ *
+ * @param str The string to test against.
+ *
+ * @return <code>true</code> if the string is equal to this object's MIME
+ * type, <code>false</code> otherwise.
+ *
+ * @deprecated Not compatible with <code>hashCode()</code>.
+ * Use <code>isMimeTypeEqual()</code>
+ */
+ public boolean equals(String str)
+ {
+ return isMimeTypeEqual(str);
+ }
-/*************************************************************************/
+ /**
+ * Returns the hash code for this data flavor.
+ * The hash code is based on the (lower case) mime type and the
+ * representation class.
+ */
+ public int hashCode()
+ {
+ return mimeType.toLowerCase().hashCode() ^ representationClass.hashCode();
+ }
-/**
- * De-serialize this class.
- *
- * @param stream The <code>ObjectInput</code> stream to deserialize from.
- *
- * @exception IOException If an error ocurs.
- * @exception ClassNotFoundException If the class for an object being restored
- * cannot be found.
- */
-public void
-readExternal(ObjectInput stream) throws IOException, ClassNotFoundException
-{
- // FIXME: Implement me
-}
+ /**
+ * Returns <code>true</code> when the given <code>DataFlavor</code>
+ * matches this one.
+ */
+ public boolean match(DataFlavor dataFlavor)
+ {
+ // XXX - How is this different from equals?
+ return equals(dataFlavor);
+ }
-/*************************************************************************/
+ /**
+ * This method exists for backward compatibility. It simply returns
+ * the same name/value pair passed in.
+ *
+ * @param name The parameter name.
+ * @param value The parameter value.
+ *
+ * @return The name/value pair.
+ *
+ * @deprecated
+ */
+ protected String normalizeMimeTypeParameter(String name, String value)
+ {
+ return name + "=" + value;
+ }
-/**
- * Returns a string representation of this DataFlavor. Including the
- * representation class name, MIME type and human presentable name.
- */
-public String
-toString()
-{
- return(getClass().getName()
- + "[representationClass=" + getRepresentationClass().getName()
- + ",mimeType=" + getMimeType()
- + ",humanPresentableName=" + getHumanPresentableName()
- + "]");
-}
+ /**
+ * This method exists for backward compatibility. It simply returns
+ * the MIME type string unchanged.
+ *
+ * @param type The MIME type.
+ *
+ * @return The MIME type.
+ *
+ * @deprecated
+ */
+ protected String normalizeMimeType(String type)
+ {
+ return type;
+ }
-/*************************************************************************/
+ /**
+ * Serialize this class.
+ *
+ * @param stream The <code>ObjectOutput</code> stream to serialize to.
+ *
+ * @exception IOException If an error occurs.
+ */
+ public void writeExternal(ObjectOutput stream) throws IOException
+ {
+ // FIXME: Implement me
+ }
-/**
- * XXX - Currently returns <code>plainTextFlavor</code>.
- */
-public static final DataFlavor
-getTextPlainUnicodeFlavor()
-{
- return(plainTextFlavor);
-}
-/*************************************************************************/
+ /**
+ * De-serialize this class.
+ *
+ * @param stream The <code>ObjectInput</code> stream to deserialize from.
+ *
+ * @exception IOException If an error ocurs.
+ * @exception ClassNotFoundException If the class for an object being restored
+ * cannot be found.
+ */
+ public void readExternal(ObjectInput stream)
+ throws IOException, ClassNotFoundException
+ {
+ // FIXME: Implement me
+ }
-/**
- * XXX - Currently returns <code>java.io.InputStream</code>.
- *
- * @since 1.3
- */
-public final Class<?>
-getDefaultRepresentationClass()
-{
- return(java.io.InputStream.class);
-}
-/*************************************************************************/
+ /**
+ * Returns a string representation of this DataFlavor. Including the
+ * representation class name, MIME type and human presentable name.
+ */
+ public String toString()
+ {
+ return (getClass().getName()
+ + "[representationClass=" + getRepresentationClass().getName()
+ + ",mimeType=" + getMimeType()
+ + ",humanPresentableName=" + getHumanPresentableName()
+ + "]");
+ }
-/**
- * XXX - Currently returns <code>java.io.InputStream</code>.
- */
-public final String
-getDefaultRepresentationClassAsString()
-{
- return(getDefaultRepresentationClass().getName());
-}
+ /**
+ * XXX - Currently returns <code>java.io.InputStream</code>.
+ *
+ * @since 1.3
+ */
+ public final Class<?> getDefaultRepresentationClass()
+ {
+ return java.io.InputStream.class;
+ }
-/*************************************************************************/
+ /**
+ * XXX - Currently returns <code>java.io.InputStream</code>.
+ */
+ public final String getDefaultRepresentationClassAsString()
+ {
+ return getDefaultRepresentationClass().getName();
+ }
-/**
- * Selects the best supported text flavor on this implementation.
- * Returns <code>null</code> when none of the given flavors is liked.
- *
- * The <code>DataFlavor</code> returned the first data flavor in the
- * array that has either a representation class which is (a subclass of)
- * <code>Reader</code> or <code>String</code>, or has a representation
- * class which is (a subclass of) <code>InputStream</code> and has a
- * primary MIME type of "text" and has an supported encoding.
- */
-public static final DataFlavor
-selectBestTextFlavor(DataFlavor[] availableFlavors)
-{
- for(int i=0; i<availableFlavors.length; i++)
- {
- DataFlavor df = availableFlavors[i];
- Class c = df.representationClass;
-
- // A Reader or String is good.
- if ((Reader.class.isAssignableFrom(c))
- || (String.class.isAssignableFrom(c)))
- {
- return df;
- }
-
- // A InputStream is good if the mime primary type is "text"
- if ((InputStream.class.isAssignableFrom(c))
- && ("text".equals(df.getPrimaryType())))
+ /**
+ * Creates a <code>Reader</code> for a given <code>Transferable</code>.
+ *
+ * If the representation class is a (subclass of) <code>Reader</code>
+ * then an instance of the representation class is returned. If the
+ * representatation class is a <code>String</code> then a
+ * <code>StringReader</code> is returned. And if the representation class
+ * is a (subclass of) <code>InputStream</code> and the primary MIME type
+ * is "text" then a <code>InputStreamReader</code> for the correct charset
+ * encoding is returned.
+ *
+ * @param transferable The <code>Transferable</code> for which a text
+ * <code>Reader</code> is requested.
+ *
+ * @exception IllegalArgumentException If the representation class is not one
+ * of the seven listed above or the Transferable has null data.
+ * @exception NullPointerException If the Transferable is null.
+ * @exception UnsupportedFlavorException when the transferable doesn't
+ * support this <code>DataFlavor</code>. Or if the representable class
+ * isn't a (subclass of) <code>Reader</code>, <code>String</code>,
+ * <code>InputStream</code> and/or the primary MIME type isn't "text".
+ * @exception IOException when any IOException occurs.
+ * @exception UnsupportedEncodingException if the "charset" isn't supported
+ * on this platform.
+ */
+ public Reader getReaderForText(Transferable transferable)
+ throws UnsupportedFlavorException, IOException
+ {
+ if (!transferable.isDataFlavorSupported(this))
+ throw new UnsupportedFlavorException(this);
+
+ if (Reader.class.isAssignableFrom(representationClass))
+ return (Reader)transferable.getTransferData(this);
+
+ if (String.class.isAssignableFrom(representationClass))
+ return new StringReader((String)transferable.getTransferData(this));
+
+ if (InputStream.class.isAssignableFrom(representationClass)
+ && "text".equals(getPrimaryType()))
{
- String encoding = availableFlavors[i].getParameter("charset");
+ InputStream in = (InputStream)transferable.getTransferData(this);
+ String encoding = getParameter("charset");
if (encoding == null)
- encoding = "us-ascii";
- Reader r = null;
- try
- {
- // Try to construct a dummy reader with the found encoding
- r = new InputStreamReader
- (new ByteArrayInputStream(new byte[0]), encoding);
- }
- catch(UnsupportedEncodingException uee) { /* ignore */ }
- if (r != null)
- return df;
+ encoding = "us-ascii";
+ return new InputStreamReader(in, encoding);
}
- }
-
- // Nothing found
- return(null);
-}
-
-/*************************************************************************/
-
-/**
- * Creates a <code>Reader</code> for a given <code>Transferable</code>.
- *
- * If the representation class is a (subclass of) <code>Reader</code>
- * then an instance of the representation class is returned. If the
- * representatation class is a <code>String</code> then a
- * <code>StringReader</code> is returned. And if the representation class
- * is a (subclass of) <code>InputStream</code> and the primary MIME type
- * is "text" then a <code>InputStreamReader</code> for the correct charset
- * encoding is returned.
- *
- * @param transferable The <code>Transferable</code> for which a text
- * <code>Reader</code> is requested.
- *
- * @exception IllegalArgumentException If the representation class is not one
- * of the seven listed above or the Transferable has null data.
- * @exception NullPointerException If the Transferable is null.
- * @exception UnsupportedFlavorException when the transferable doesn't
- * support this <code>DataFlavor</code>. Or if the representable class
- * isn't a (subclass of) <code>Reader</code>, <code>String</code>,
- * <code>InputStream</code> and/or the primary MIME type isn't "text".
- * @exception IOException when any IOException occurs.
- * @exception UnsupportedEncodingException if the "charset" isn't supported
- * on this platform.
- */
-public Reader getReaderForText(Transferable transferable)
- throws UnsupportedFlavorException, IOException
-{
- if (!transferable.isDataFlavorSupported(this))
- throw new UnsupportedFlavorException(this);
-
- if (Reader.class.isAssignableFrom(representationClass))
- return((Reader)transferable.getTransferData(this));
-
- if (String.class.isAssignableFrom(representationClass))
- return(new StringReader((String)transferable.getTransferData(this)));
-
- if (InputStream.class.isAssignableFrom(representationClass)
- && "text".equals(getPrimaryType()))
- {
- InputStream in = (InputStream)transferable.getTransferData(this);
- String encoding = getParameter("charset");
- if (encoding == null)
- encoding = "us-ascii";
- return(new InputStreamReader(in, encoding));
- }
-
- throw new UnsupportedFlavorException(this);
-}
+
+ throw new UnsupportedFlavorException(this);
+ }
/**
* Returns whether the representation class for this DataFlavor is
@@ -1010,9 +895,9 @@ public Reader getReaderForText(Transferable transferable)
*
* @since 1.4
*/
- public boolean isRepresentationClassByteBuffer ()
+ public boolean isRepresentationClassByteBuffer()
{
- return ByteBuffer.class.isAssignableFrom (representationClass);
+ return ByteBuffer.class.isAssignableFrom(representationClass);
}
/**
@@ -1021,9 +906,9 @@ public Reader getReaderForText(Transferable transferable)
*
* @since 1.4
*/
- public boolean isRepresentationClassCharBuffer ()
+ public boolean isRepresentationClassCharBuffer()
{
- return CharBuffer.class.isAssignableFrom (representationClass);
+ return CharBuffer.class.isAssignableFrom(representationClass);
}
/**
@@ -1032,10 +917,67 @@ public Reader getReaderForText(Transferable transferable)
*
* @since 1.4
*/
- public boolean isRepresentationClassReader ()
+ public boolean isRepresentationClassReader()
{
- return Reader.class.isAssignableFrom (representationClass);
+ return Reader.class.isAssignableFrom(representationClass);
+ }
+
+ /**
+ * Returns whether this <code>DataFlavor</code> is a valid text flavor for
+ * this implementation of the Java platform. Only flavors equivalent to
+ * <code>DataFlavor.stringFlavor</code> and <code>DataFlavor</code>s with
+ * a primary MIME type of "text" can be valid text flavors.
+ * <p>
+ * If this flavor supports the charset parameter, it must be equivalent to
+ * <code>DataFlavor.stringFlavor</code>, or its representation must be
+ * <code>java.io.Reader</code>, <code>java.lang.String</code>,
+ * <code>java.nio.CharBuffer</code>, <code>java.io.InputStream</code> or
+ * <code>java.nio.ByteBuffer</code>,
+ * If the representation is <code>java.io.InputStream</code> or
+ * <code>java.nio.ByteBuffer</code>, then this flavor's <code>charset</code>
+ * parameter must be supported by this implementation of the Java platform.
+ * If a charset is not specified, then the platform default charset, which
+ * is always supported, is assumed.
+ * <p>
+ * If this flavor does not support the charset parameter, its
+ * representation must be <code>java.io.InputStream</code>,
+ * <code>java.nio.ByteBuffer</code>.
+ * <p>
+ * See <code>selectBestTextFlavor</code> for a list of text flavors which
+ * support the charset parameter.
+ *
+ * @return <code>true</code> if this <code>DataFlavor</code> is a valid
+ * text flavor as described above; <code>false</code> otherwise
+ * @see #selectBestTextFlavor
+ * @since 1.4
+ */
+ public boolean isFlavorTextType() {
+ // FIXME: I'm not 100% sure if this implementation does the same like sun's does
+ if(equals(DataFlavor.stringFlavor) || getPrimaryType().equals("text"))
+ {
+ String charset = getParameter("charset");
+ Class c = getRepresentationClass();
+ if(charset != null)
+ {
+ if(Reader.class.isAssignableFrom(c)
+ || CharBuffer.class.isAssignableFrom(c)
+ || String.class.isAssignableFrom(c))
+ {
+ return true;
+ }
+ else if(InputStream.class.isAssignableFrom(c)
+ || ByteBuffer.class.isAssignableFrom(c))
+ {
+ return Charset.isSupported(charset);
+ }
+ }
+ else if(InputStream.class.isAssignableFrom(c)
+ || ByteBuffer.class.isAssignableFrom(c))
+ {
+ return true;
+ }
+ }
+ return false;
}
-
} // class DataFlavor
diff --git a/java/awt/datatransfer/SystemFlavorMap.java b/java/awt/datatransfer/SystemFlavorMap.java
index 628d15dd4..702830789 100644
--- a/java/awt/datatransfer/SystemFlavorMap.java
+++ b/java/awt/datatransfer/SystemFlavorMap.java
@@ -41,6 +41,7 @@ package java.awt.datatransfer;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
+import java.util.WeakHashMap;
/**
* This class maps between native platform type names and DataFlavors.
@@ -54,9 +55,10 @@ import java.util.Map;
public final class SystemFlavorMap implements FlavorMap, FlavorTable
{
/**
- * The default (instance) flavor map.
+ * The map which maps the thread's <code>ClassLoaders</code> to
+ * <code>SystemFlavorMaps</code>.
*/
- private static FlavorMap defaultFlavorMap;
+ private static final Map systemFlavorMaps = new WeakHashMap();
/**
* Private constructor.
@@ -98,14 +100,31 @@ public final class SystemFlavorMap implements FlavorMap, FlavorTable
}
/**
- * Returns the default (instance) (System)FlavorMap.
+ * Returns the (System)FlavorMap for the current thread's
+ * ClassLoader.
*/
public static FlavorMap getDefaultFlavorMap ()
{
- if (defaultFlavorMap == null)
- defaultFlavorMap = new SystemFlavorMap ();
-
- return defaultFlavorMap;
+ ClassLoader classLoader = Thread.currentThread()
+ .getContextClassLoader();
+
+ //if ContextClassLoader not set, use system default
+ if(classLoader == null)
+ {
+ classLoader = ClassLoader.getSystemClassLoader();
+ }
+
+ synchronized(systemFlavorMaps)
+ {
+ FlavorMap map = (FlavorMap)
+ systemFlavorMaps.get(classLoader);
+ if(map == null)
+ {
+ map = new SystemFlavorMap();
+ systemFlavorMaps.put(classLoader, map);
+ }
+ return map;
+ }
}
/**
diff --git a/java/awt/event/InvocationEvent.java b/java/awt/event/InvocationEvent.java
index 75feb62bd..6f39d6b91 100644
--- a/java/awt/event/InvocationEvent.java
+++ b/java/awt/event/InvocationEvent.java
@@ -107,6 +107,13 @@ public class InvocationEvent extends AWTEvent implements ActiveEvent
private Exception exception;
/**
+ * This is the caught Throwable thrown in the <code>run()</code> method.
+ * It is null if throwables are ignored, the run method hasn't completed,
+ * or there were no throwables thrown.
+ */
+ private Throwable throwable;
+
+ /**
* The timestamp when this event was created.
*
* @see #getWhen()
@@ -183,9 +190,11 @@ public class InvocationEvent extends AWTEvent implements ActiveEvent
{
runnable.run();
}
- catch (Exception e)
+ catch (Throwable t)
{
- exception = e;
+ throwable = t;
+ if (t instanceof Exception)
+ exception = (Exception)t;
}
else
runnable.run();
@@ -211,6 +220,18 @@ public class InvocationEvent extends AWTEvent implements ActiveEvent
}
/**
+ * Returns a throwable caught while executing the Runnable's run() method.
+ * Null if none was thrown or if this InvocationEvent doesn't catch
+ * throwables.
+ * @return the caught Throwable
+ * @since 1.5
+ */
+ public Throwable getThrowable()
+ {
+ return throwable;
+ }
+
+ /**
* Gets the timestamp of when this event was created.
*
* @return the timestamp of this event
diff --git a/java/awt/image/AreaAveragingScaleFilter.java b/java/awt/image/AreaAveragingScaleFilter.java
index 194d483d9..6333ce9e7 100644
--- a/java/awt/image/AreaAveragingScaleFilter.java
+++ b/java/awt/image/AreaAveragingScaleFilter.java
@@ -45,7 +45,7 @@ package java.awt.image;
* points should give the desired results although Sun does not
* specify what the exact algorithm should be.
* <br>
- * Currently this filter does nothing and needs to be implemented.
+ * FIXME: Currently this filter does nothing and needs to be implemented.
*
* @author C. Brian Jones (cbj@gnu.org)
*/
diff --git a/java/awt/image/BufferedImage.java b/java/awt/image/BufferedImage.java
index c730c6dcb..1e2ebe296 100644
--- a/java/awt/image/BufferedImage.java
+++ b/java/awt/image/BufferedImage.java
@@ -1,5 +1,5 @@
/* BufferedImage.java --
- Copyright (C) 2000, 2002, 2003, 2004 Free Software Foundation
+ Copyright (C) 2000, 2002, 2003, 2004, 2005 Free Software Foundation
This file is part of GNU Classpath.
@@ -62,7 +62,7 @@ import java.util.Vector;
* @author Rolf W. Rasmussen (rolfwr@ii.uib.no)
*/
public class BufferedImage extends Image
- implements WritableRenderedImage
+ implements WritableRenderedImage, Transparency
{
public static final int TYPE_CUSTOM = 0,
TYPE_INT_RGB = 1,
@@ -688,4 +688,16 @@ public class BufferedImage extends Image
observers.remove (to);
}
+
+ /**
+ * Return the transparency type.
+ *
+ * @return One of {@link #OPAQUE}, {@link #BITMASK}, or {@link #TRANSLUCENT}.
+ * @see Transparency#getTransparency()
+ * @since 1.5
+ */
+ public int getTransparency()
+ {
+ return colorModel.getTransparency();
+ }
}
diff --git a/java/awt/image/MemoryImageSource.java b/java/awt/image/MemoryImageSource.java
index 3fe055ae1..cb3526f6e 100644
--- a/java/awt/image/MemoryImageSource.java
+++ b/java/awt/image/MemoryImageSource.java
@@ -187,7 +187,7 @@ public class MemoryImageSource implements ImageProducer
ic = (ImageConsumer) list.elementAt(i);
sendPicture(ic);
if (animated)
- ic.imageComplete(ImageConsumer.SINGLEFRAME);
+ ic.imageComplete(ImageConsumer.SINGLEFRAMEDONE);
else
ic.imageComplete(ImageConsumer.STATICIMAGEDONE);
}
diff --git a/java/beans/IndexedPropertyChangeEvent.java b/java/beans/IndexedPropertyChangeEvent.java
new file mode 100644
index 000000000..1a7306d14
--- /dev/null
+++ b/java/beans/IndexedPropertyChangeEvent.java
@@ -0,0 +1,81 @@
+/* Indexed property change event
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package java.beans;
+
+/**
+ * This is like a PropertyChangeEvent, but also carries with it the
+ * index of the property which changed.
+ * @author Tom Tromey (tromey@redhat.com)
+ * @since 1.5
+ */
+public class IndexedPropertyChangeEvent extends PropertyChangeEvent
+{
+ private static final long serialVersionUID = -320227448495806870L;
+
+ /**
+ * Index of the item that was changed.
+ */
+ private int index;
+
+ /**
+ * Create a new IndexedPropertyChangeEvent.
+ * @param source the Bean containing the property
+ * @param name the property's name
+ * @param oldValue the old value of the property
+ * @param newValue the new value of the property
+ * @param index the index of the element in the property which changed
+ * @throws IllegalArgumentException if source is null
+ */
+ public IndexedPropertyChangeEvent(Object source, String name,
+ Object oldValue, Object newValue,
+ int index)
+ {
+ super(source, name, oldValue, newValue);
+ this.index = index;
+ }
+
+ /**
+ * Return the index of the changed property.
+ * @return the index
+ */
+ public int getIndex()
+ {
+ return index;
+ }
+}
diff --git a/java/beans/PropertyChangeSupport.java b/java/beans/PropertyChangeSupport.java
index a0e64af4d..da30f994d 100644
--- a/java/beans/PropertyChangeSupport.java
+++ b/java/beans/PropertyChangeSupport.java
@@ -397,6 +397,59 @@ public class PropertyChangeSupport implements Serializable
}
/**
+ * Fire an indexed property change event. This will only fire
+ * an event if the old and new values are not equal and not null.
+ * @param name the name of the property which changed
+ * @param index the index of the property which changed
+ * @param oldValue the old value of the property
+ * @param newValue the new value of the property
+ * @since 1.5
+ */
+ public void fireIndexedPropertyChange(String name, int index,
+ Object oldValue, Object newValue)
+ {
+ // FIXME: should we use equals() here?
+ if (oldValue == newValue && oldValue != null)
+ firePropertyChange(new IndexedPropertyChangeEvent(source, name,
+ oldValue, newValue,
+ index));
+ }
+
+ /**
+ * Fire an indexed property change event. This will only fire
+ * an event if the old and new values are not equal.
+ * @param name the name of the property which changed
+ * @param index the index of the property which changed
+ * @param oldValue the old value of the property
+ * @param newValue the new value of the property
+ * @since 1.5
+ */
+ public void fireIndexedPropertyChange(String name, int index,
+ int oldValue, int newValue)
+ {
+ if (oldValue != newValue)
+ fireIndexedPropertyChange(name, index, Integer.valueOf(oldValue),
+ Integer.valueOf(newValue));
+ }
+
+ /**
+ * Fire an indexed property change event. This will only fire
+ * an event if the old and new values are not equal.
+ * @param name the name of the property which changed
+ * @param index the index of the property which changed
+ * @param oldValue the old value of the property
+ * @param newValue the new value of the property
+ * @since 1.5
+ */
+ public void fireIndexedPropertyChange(String name, int index,
+ boolean oldValue, boolean newValue)
+ {
+ if (oldValue != newValue)
+ fireIndexedPropertyChange(name, index, Boolean.valueOf(oldValue),
+ Boolean.valueOf(newValue));
+ }
+
+ /**
* Tell whether the specified property is being listened on or not. This
* will only return <code>true</code> if there are listeners on all
* properties or if there is a listener specifically on this property.
diff --git a/java/io/File.java b/java/io/File.java
index dc06bcf09..6af262943 100644
--- a/java/io/File.java
+++ b/java/io/File.java
@@ -457,6 +457,8 @@ public class File implements Serializable, Comparable<File>
else
return drvDir;
}
+ else if (path.equals(""))
+ return System.getProperty ("user.dir");
else
return System.getProperty ("user.dir") + separatorChar + path;
}
@@ -543,6 +545,9 @@ public class File implements Serializable, Comparable<File>
{
String prefix = null;
int nameSeqIndex = 0;
+
+ if (path.equals(""))
+ return null;
// The "prefix", if present, is the leading "/" on UNIX and
// either the drive specifier (e.g. "C:") or the leading "\\"
@@ -954,8 +959,8 @@ public class File implements Serializable, Comparable<File>
public URI toURI()
{
String abspath = getAbsolutePath();
-
- if (isDirectory())
+
+ if (isDirectory() || path.equals(""))
abspath = abspath + separatorChar;
if (separatorChar == '\\')
diff --git a/java/io/FilePermission.java b/java/io/FilePermission.java
index 356787bfa..31802c631 100644
--- a/java/io/FilePermission.java
+++ b/java/io/FilePermission.java
@@ -278,13 +278,13 @@ public final class FilePermission extends Permission implements Serializable
break;
}
- if (readPerm && ! fp.readPerm)
+ if (fp.readPerm && ! readPerm)
return false;
- if (writePerm && ! fp.writePerm)
+ if (fp.writePerm && ! writePerm)
return false;
- if (executePerm && ! fp.executePerm)
+ if (fp.executePerm && ! executePerm)
return false;
- if (deletePerm && ! fp.deletePerm)
+ if (fp.deletePerm && ! deletePerm)
return false;
return true;
diff --git a/java/io/InputStreamReader.java b/java/io/InputStreamReader.java
index 4f77172af..57cdc53ed 100644
--- a/java/io/InputStreamReader.java
+++ b/java/io/InputStreamReader.java
@@ -249,8 +249,12 @@ public class InputStreamReader extends Reader
this.in = in;
this.decoder = decoder;
+ Charset charset = decoder.charset();
try {
- maxBytesPerChar = decoder.charset().newEncoder().maxBytesPerChar();
+ if (charset == null)
+ maxBytesPerChar = 1f;
+ else
+ maxBytesPerChar = charset.newEncoder().maxBytesPerChar();
} catch(UnsupportedOperationException _){
maxBytesPerChar = 1f;
}
@@ -258,7 +262,10 @@ public class InputStreamReader extends Reader
decoder.onMalformedInput(CodingErrorAction.REPLACE);
decoder.onUnmappableCharacter(CodingErrorAction.REPLACE);
decoder.reset();
- encoding = EncodingHelper.getOldCanonical(decoder.charset().name());
+ if (charset == null)
+ encoding = "US-ASCII";
+ else
+ encoding = EncodingHelper.getOldCanonical(decoder.charset().name());
}
/**
diff --git a/java/io/ObjectInputStream.java b/java/io/ObjectInputStream.java
index b0982dcf7..b8c8b79a8 100644
--- a/java/io/ObjectInputStream.java
+++ b/java/io/ObjectInputStream.java
@@ -119,7 +119,10 @@ public class ObjectInputStream extends InputStream
* <code>private void readObject (ObjectInputStream)</code>.
*
* If an exception is thrown from this method, the stream is left in
- * an undefined state.
+ * an undefined state. This method can also throw Errors and
+ * RuntimeExceptions if caused by existing readResolve() user code.
+ *
+ * @return The object read from the underlying stream.
*
* @exception ClassNotFoundException The class that an object being
* read in belongs to cannot be found.
@@ -1573,8 +1576,15 @@ public class ObjectInputStream extends InputStream
catch (IllegalAccessException ignore)
{
}
- catch (InvocationTargetException ignore)
+ catch (InvocationTargetException exception)
{
+ Throwable cause = exception.getCause();
+ if (cause instanceof ObjectStreamException)
+ throw (ObjectStreamException) cause;
+ else if (cause instanceof RuntimeException)
+ throw (RuntimeException) cause;
+ else if (cause instanceof Error)
+ throw (Error) cause;
}
}
diff --git a/java/io/PrintWriter.java b/java/io/PrintWriter.java
index 36a3ac96e..5b4294cba 100644
--- a/java/io/PrintWriter.java
+++ b/java/io/PrintWriter.java
@@ -382,7 +382,7 @@ public class PrintWriter extends Writer
* This is the system dependent line separator
*/
private static final char[] line_separator
- = System.getProperty("line.separator").toCharArray();
+ = System.getProperty("line.separator", "\n").toCharArray();
/**
* This method prints a line separator sequence to the stream. The value
diff --git a/java/io/StreamTokenizer.java b/java/io/StreamTokenizer.java
index bd7773b19..b4695ab3d 100644
--- a/java/io/StreamTokenizer.java
+++ b/java/io/StreamTokenizer.java
@@ -550,6 +550,12 @@ public class StreamTokenizer
/**
* This method sets the numeric attribute on the characters '0' - '9' and
* the characters '.' and '-'.
+ * When this method is used, the result of giving other attributes
+ * (whitespace, quote, or comment) to the numeric characters may
+ * vary depending on the implementation. For example, if
+ * parseNumbers() and then whitespaceChars('1', '1') are called,
+ * this implementation reads "121" as 2, while some other implementation
+ * will read it as 21.
*/
public void parseNumbers()
{
diff --git a/java/lang/Boolean.java b/java/lang/Boolean.java
index 0af8a9c6e..1041eab39 100644
--- a/java/lang/Boolean.java
+++ b/java/lang/Boolean.java
@@ -223,8 +223,12 @@ public final class Boolean implements Serializable, Comparable<Boolean>
}
/**
- * This implements the comparison contract specified by Comparable.
- * @see Comparable
+ * Compares this Boolean to another.
+ *
+ * @param b the Boolean to compare this Boolean to
+ * @return 0 if both Booleans represent the same value, a positive number
+ * if this Boolean represents true and the other false, and a negative
+ * number otherwise.
* @since 1.5
*/
public int compareTo(Boolean other)
@@ -243,4 +247,5 @@ public final class Boolean implements Serializable, Comparable<Boolean>
{
return "true".equalsIgnoreCase(b) ? true : false;
}
+
}
diff --git a/java/lang/SecurityManager.java b/java/lang/SecurityManager.java
index db2c5447d..ff542bc48 100644
--- a/java/lang/SecurityManager.java
+++ b/java/lang/SecurityManager.java
@@ -424,7 +424,7 @@ public class SecurityManager
public void checkAccess(Thread thread)
{
if (thread.getThreadGroup() != null
- && thread.getThreadGroup().getParent() != null)
+ && thread.getThreadGroup().getParent() == null)
checkPermission(new RuntimePermission("modifyThread"));
}
@@ -457,7 +457,7 @@ public class SecurityManager
*/
public void checkAccess(ThreadGroup g)
{
- if (g.getParent() != null)
+ if (g.getParent() == null)
checkPermission(new RuntimePermission("modifyThreadGroup"));
}
diff --git a/java/lang/StackTraceElement.java b/java/lang/StackTraceElement.java
index 6dd4d8532..cf4d1c76f 100644
--- a/java/lang/StackTraceElement.java
+++ b/java/lang/StackTraceElement.java
@@ -49,7 +49,7 @@ import java.io.Serializable;
* @author Mark Wielaard (mark@klomp.org)
* @author Eric Blake (ebb9@email.byu.edu)
* @since 1.4
- * @status updated to 1.4
+ * @status updated to 1.5
*/
public final class StackTraceElement implements Serializable
{
@@ -112,6 +112,26 @@ public final class StackTraceElement implements Serializable
}
/**
+ * Create a new StackTraceElement representing a given source location.
+ *
+ * @param className the fully qualified name of the class
+ * @param methodName the name of the method
+ * @param fileName the name of the file, null if unknown
+ * @param lineNumber the line in the file, negative if unknown, or -2
+ * if this method is native
+ *
+ * @since 1.5
+ */
+ public StackTraceElement(String className, String methodName, String fileName,
+ int lineNumber)
+ {
+ this(fileName, lineNumber, className, methodName, lineNumber == -2);
+ // The public constructor doesn't allow certain values to be null.
+ if (className == null || methodName == null)
+ throw new NullPointerException("invalid argument to constructor");
+ }
+
+ /**
* Returns the name of the file, or null if unknown. This is usually
* obtained from the <code>SourceFile</code> attribute of the class file
* format, if present.
diff --git a/java/lang/String.java b/java/lang/String.java
index 69464b78a..fdec7f929 100644
--- a/java/lang/String.java
+++ b/java/lang/String.java
@@ -1875,4 +1875,43 @@ public final class String
return value;
}
+
+ /**
+ * Returns true iff this String contains the sequence of Characters
+ * described in s.
+ * @param s the CharSequence
+ * @return true iff this String contains s
+ */
+ public boolean contains (CharSequence s)
+ {
+ return this.indexOf(s.toString()) != -1;
+ }
+
+ /**
+ * Returns a string that is this string with all instances of the sequence
+ * represented by <code>target</code> replaced by the sequence in
+ * <code>replacement</code>.
+ * @param target the sequence to be replaced
+ * @param replacement the sequence used as the replacement
+ * @return the string constructed as above
+ */
+ public String replace (CharSequence target, CharSequence replacement)
+ {
+ String targetString = target.toString();
+ String replaceString = replacement.toString();
+ int targetLength = target.length();
+ int replaceLength = replacement.length();
+
+ int startPos = this.indexOf(targetString);
+ StringBuilder result = new StringBuilder(this);
+ while (startPos != -1)
+ {
+ // Replace the target with the replacement
+ result.replace(startPos, startPos + targetLength, replaceString);
+
+ // Search for a new occurrence of the target
+ startPos = result.indexOf(targetString, startPos + replaceLength);
+ }
+ return result.toString();
+ }
}
diff --git a/java/net/URL.java b/java/net/URL.java
index 627dbc391..1d947a0b4 100644
--- a/java/net/URL.java
+++ b/java/net/URL.java
@@ -408,10 +408,7 @@ public final class URL implements Serializable
// The 1.2 doc specifically says these are copied to the new URL.
host = context.host;
port = context.port;
- file = context.file;
userInfo = context.userInfo;
- if (file == null || file.length() == 0)
- file = "/";
authority = context.authority;
}
}
@@ -423,10 +420,13 @@ public final class URL implements Serializable
protocol = context.protocol;
host = context.host;
port = context.port;
- file = context.file;
userInfo = context.userInfo;
- if (file == null || file.length() == 0)
- file = "/";
+ if (spec.indexOf(":/", 1) < 0)
+ {
+ file = context.file;
+ if (file == null || file.length() == 0)
+ file = "/";
+ }
authority = context.authority;
}
else // Protocol NOT specified in spec. and no context available.
diff --git a/java/net/URLClassLoader.java b/java/net/URLClassLoader.java
index 5aaaedaa3..02a811d93 100644
--- a/java/net/URLClassLoader.java
+++ b/java/net/URLClassLoader.java
@@ -536,15 +536,15 @@ public class URLClassLoader extends SecureClassLoader
Resource getResource(String name)
{
try
- {
- File file = new File(dir, name).getCanonicalFile();
- if (file.exists() && !file.isDirectory())
- return new FileResource(this, file);
- }
+ {
+ File file = new File(dir, name).getCanonicalFile();
+ if (file.exists() && !file.isDirectory())
+ return new FileResource(this, file);
+ }
catch (IOException e)
- {
- // Fall through...
- }
+ {
+ // Fall through...
+ }
return null;
}
}
@@ -873,47 +873,47 @@ public class URLClassLoader extends SecureClassLoader
// construct the class (and watch out for those nasty IOExceptions)
try
{
- byte[] data;
- InputStream in = resource.getInputStream();
- try
- {
- int length = resource.getLength();
- if (length != -1)
- {
- // We know the length of the data.
- // Just try to read it in all at once
- data = new byte[length];
- int pos = 0;
- while (length - pos > 0)
- {
- int len = in.read(data, pos, length - pos);
- if (len == -1)
- throw new EOFException("Not enough data reading from: "
- + in);
- pos += len;
- }
- }
- else
- {
- // We don't know the data length.
- // Have to read it in chunks.
- ByteArrayOutputStream out = new ByteArrayOutputStream(4096);
- byte[] b = new byte[4096];
- int l = 0;
- while (l != -1)
- {
- l = in.read(b);
- if (l != -1)
- out.write(b, 0, l);
- }
- data = out.toByteArray();
- }
- }
- finally
- {
- in.close();
- }
- final byte[] classData = data;
+ byte[] data;
+ InputStream in = resource.getInputStream();
+ try
+ {
+ int length = resource.getLength();
+ if (length != -1)
+ {
+ // We know the length of the data.
+ // Just try to read it in all at once
+ data = new byte[length];
+ int pos = 0;
+ while (length - pos > 0)
+ {
+ int len = in.read(data, pos, length - pos);
+ if (len == -1)
+ throw new EOFException("Not enough data reading from: "
+ + in);
+ pos += len;
+ }
+ }
+ else
+ {
+ // We don't know the data length.
+ // Have to read it in chunks.
+ ByteArrayOutputStream out = new ByteArrayOutputStream(4096);
+ byte[] b = new byte[4096];
+ int l = 0;
+ while (l != -1)
+ {
+ l = in.read(b);
+ if (l != -1)
+ out.write(b, 0, l);
+ }
+ data = out.toByteArray();
+ }
+ }
+ finally
+ {
+ in.close();
+ }
+ final byte[] classData = data;
// Now get the CodeSource
final CodeSource source = resource.getCodeSource();
diff --git a/java/security/ProtectionDomain.java b/java/security/ProtectionDomain.java
index a5851b5ad..a8a093925 100644
--- a/java/security/ProtectionDomain.java
+++ b/java/security/ProtectionDomain.java
@@ -37,6 +37,8 @@ exception statement from your version. */
package java.security;
+import gnu.classpath.SystemProperties;
+
/**
* <p>This <code>ProtectionDomain</code> class encapsulates the characteristics
* of a domain, which encloses a set of classes whose instances are granted a
@@ -222,7 +224,7 @@ public class ProtectionDomain
*/
public String toString()
{
- String linesep = System.getProperty("line.separator");
+ String linesep = SystemProperties.getProperty("line.separator");
StringBuffer sb = new StringBuffer("ProtectionDomain (").append(linesep);
if (code_source == null)
diff --git a/java/util/Arrays.java b/java/util/Arrays.java
index 17064ef6a..23b1895dd 100644
--- a/java/util/Arrays.java
+++ b/java/util/Arrays.java
@@ -2544,7 +2544,13 @@ public class Arrays
return true;
}
- /** @since 1.5 */
+ /**
+ * Returns a String representation of the argument array. Returns "null"
+ * if <code>a</code> is null.
+ * @param a the array to represent
+ * @return a String representing this array
+ * @since 1.5
+ */
public static String toString(boolean[] v)
{
if (v == null)
@@ -2560,7 +2566,13 @@ public class Arrays
return b.toString();
}
- /** @since 1.5 */
+ /**
+ * Returns a String representation of the argument array. Returns "null"
+ * if <code>a</code> is null.
+ * @param a the array to represent
+ * @return a String representing this array
+ * @since 1.5
+ */
public static String toString(byte[] v)
{
if (v == null)
@@ -2576,7 +2588,13 @@ public class Arrays
return b.toString();
}
- /** @since 1.5 */
+ /**
+ * Returns a String representation of the argument array. Returns "null"
+ * if <code>a</code> is null.
+ * @param a the array to represent
+ * @return a String representing this array
+ * @since 1.5
+ */
public static String toString(char[] v)
{
if (v == null)
@@ -2592,7 +2610,13 @@ public class Arrays
return b.toString();
}
- /** @since 1.5 */
+ /**
+ * Returns a String representation of the argument array. Returns "null"
+ * if <code>a</code> is null.
+ * @param a the array to represent
+ * @return a String representing this array
+ * @since 1.5
+ */
public static String toString(short[] v)
{
if (v == null)
@@ -2608,7 +2632,13 @@ public class Arrays
return b.toString();
}
- /** @since 1.5 */
+ /**
+ * Returns a String representation of the argument array. Returns "null"
+ * if <code>a</code> is null.
+ * @param a the array to represent
+ * @return a String representing this array
+ * @since 1.5
+ */
public static String toString(int[] v)
{
if (v == null)
@@ -2624,7 +2654,13 @@ public class Arrays
return b.toString();
}
- /** @since 1.5 */
+ /**
+ * Returns a String representation of the argument array. Returns "null"
+ * if <code>a</code> is null.
+ * @param a the array to represent
+ * @return a String representing this array
+ * @since 1.5
+ */
public static String toString(long[] v)
{
if (v == null)
@@ -2640,7 +2676,13 @@ public class Arrays
return b.toString();
}
- /** @since 1.5 */
+ /**
+ * Returns a String representation of the argument array. Returns "null"
+ * if <code>a</code> is null.
+ * @param a the array to represent
+ * @return a String representing this array
+ * @since 1.5
+ */
public static String toString(float[] v)
{
if (v == null)
@@ -2656,7 +2698,13 @@ public class Arrays
return b.toString();
}
- /** @since 1.5 */
+ /**
+ * Returns a String representation of the argument array. Returns "null"
+ * if <code>a</code> is null.
+ * @param a the array to represent
+ * @return a String representing this array
+ * @since 1.5
+ */
public static String toString(double[] v)
{
if (v == null)
@@ -2672,7 +2720,13 @@ public class Arrays
return b.toString();
}
- /** @since 1.5 */
+ /**
+ * Returns a String representation of the argument array. Returns "null"
+ * if <code>a</code> is null.
+ * @param a the array to represent
+ * @return a String representing this array
+ * @since 1.5
+ */
public static String toString(Object[] v)
{
if (v == null)
diff --git a/java/util/Properties.java b/java/util/Properties.java
index 9f0f5c70c..703869fa4 100644
--- a/java/util/Properties.java
+++ b/java/util/Properties.java
@@ -219,12 +219,15 @@ label = Name:\\u0020</pre>
// The characters up to the next Whitespace, ':', or '='
// describe the key. But look for escape sequences.
- StringBuffer key = new StringBuffer();
+ // Try to short-circuit when there is no escape char.
+ int start = pos;
+ boolean needsEscape = line.indexOf('\\', pos) != -1;
+ StringBuilder key = needsEscape ? new StringBuilder() : null;
while (pos < line.length()
&& ! Character.isWhitespace(c = line.charAt(pos++))
&& c != '=' && c != ':')
{
- if (c == '\\')
+ if (needsEscape && c == '\\')
{
if (pos == line.length())
{
@@ -268,11 +271,20 @@ label = Name:\\u0020</pre>
}
}
}
- else
+ else if (needsEscape)
key.append(c);
}
boolean isDelim = (c == ':' || c == '=');
+
+ String keyString;
+ if (needsEscape)
+ keyString = key.toString();
+ else if (isDelim || Character.isWhitespace(c))
+ keyString = line.substring(start, pos - 1);
+ else
+ keyString = line.substring(start, pos);
+
while (pos < line.length()
&& Character.isWhitespace(c = line.charAt(pos)))
pos++;
@@ -285,7 +297,15 @@ label = Name:\\u0020</pre>
pos++;
}
- StringBuffer element = new StringBuffer(line.length() - pos);
+ // Short-circuit if no escape chars found.
+ if (!needsEscape)
+ {
+ put(keyString, line.substring(pos));
+ continue;
+ }
+
+ // Escape char found so iterate through the rest of the line.
+ StringBuilder element = new StringBuilder(line.length() - pos);
while (pos < line.length())
{
c = line.charAt(pos++);
@@ -341,7 +361,7 @@ label = Name:\\u0020</pre>
else
element.append(c);
}
- put(key.toString(), element.toString());
+ put(keyString, element.toString());
}
}
@@ -406,7 +426,7 @@ label = Name:\\u0020</pre>
Iterator iter = entrySet ().iterator ();
int i = size ();
- StringBuffer s = new StringBuffer (); // Reuse the same buffer.
+ StringBuilder s = new StringBuilder (); // Reuse the same buffer.
while (--i >= 0)
{
Map.Entry entry = (Map.Entry) iter.next ();
@@ -549,7 +569,7 @@ label = Name:\\u0020</pre>
* leading spaces must be escaped for the value
* @see #store(OutputStream, String)
*/
- private void formatForOutput(String str, StringBuffer buffer, boolean key)
+ private void formatForOutput(String str, StringBuilder buffer, boolean key)
{
if (key)
{
diff --git a/java/util/WeakHashMap.java b/java/util/WeakHashMap.java
index af5f74b04..c38d7e3aa 100644
--- a/java/util/WeakHashMap.java
+++ b/java/util/WeakHashMap.java
@@ -243,7 +243,8 @@ public class WeakHashMap<K,V> extends AbstractMap<K,V>
// This method will get inlined.
cleanQueue();
if (knownMod != modCount)
- throw new ConcurrentModificationException();
+ throw new ConcurrentModificationException(knownMod + " != "
+ + modCount);
}
/**
@@ -700,21 +701,20 @@ public class WeakHashMap<K,V> extends AbstractMap<K,V>
// bucket may be enqueued later by the garbage collection, and
// internalRemove will be called a second time.
bucket.slot = -1;
- if (buckets[slot] == bucket)
- buckets[slot] = bucket.next;
- else
+
+ WeakBucket prev = null;
+ WeakBucket next = buckets[slot];
+ while (next != bucket)
{
- WeakBucket prev = buckets[slot];
- /* This may throw a NullPointerException. It shouldn't but if
- * a race condition occurred (two threads removing the same
- * bucket at the same time) it may happen. <br>
- * But with race condition many much worse things may happen
- * anyway.
- */
- while (prev.next != bucket)
- prev = prev.next;
- prev.next = bucket.next;
+ if (next == null) throw new InternalError("WeakHashMap in incosistent state");
+ prev = next;
+ next = prev.next;
}
+ if (prev == null)
+ buckets[slot] = bucket.next;
+ else
+ prev.next = bucket.next;
+
size--;
}
diff --git a/javax/print/attribute/Attribute.java b/javax/print/attribute/Attribute.java
index fcaa7d84c..7ce0247ce 100644
--- a/javax/print/attribute/Attribute.java
+++ b/javax/print/attribute/Attribute.java
@@ -1,5 +1,5 @@
/* Attribute.java --
- Copyright (C) 2002 Free Software Foundation, Inc.
+ Copyright (C) 2002, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -40,11 +40,27 @@ package javax.print.attribute;
import java.io.Serializable;
/**
- * @author Michael Koch
+ * Base interface of every printing attribute of the Java Print Service API.
+ *
+ * @author Michael Koch (konqueror@gmx.de)
*/
public interface Attribute extends Serializable
{
+ /**
+ * Returns the category of the printing attribute which is the specific
+ * attribute class implementing this interface.
+ *
+ * @return The concrete {@link Class} instance of the attribute class.
+ */
Class getCategory ();
+ /**
+ * Returns the descriptive name of the attribute category.
+ *
+ * Implementations of the <code>Attribute</code> interfaces providing equal
+ * category values have to return equal name values.
+ *
+ * @return The name of the attribute category.
+ */
String getName ();
}
diff --git a/javax/print/attribute/AttributeSet.java b/javax/print/attribute/AttributeSet.java
index cdc7a8e48..b4bdecad2 100644
--- a/javax/print/attribute/AttributeSet.java
+++ b/javax/print/attribute/AttributeSet.java
@@ -1,5 +1,5 @@
/* AttributeSet.java --
- Copyright (C) 2002 Free Software Foundation, Inc.
+ Copyright (C) 2002, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -38,40 +38,159 @@ exception statement from your version. */
package javax.print.attribute;
/**
- * @author Michael Koch
+ * <code>AttributeSet</code> is the top-level interface for sets of printing
+ * attributes in the Java Print Service API.
+ * <p>
+ * There are no duplicate values allowed in an attribute set and there is
+ * at most one attribute object contained per category type. Based on the
+ * {@link java.util.Map} interface the values of attribute sets are objects
+ * of type {@link javax.print.attribute.Attribute} and the entries are the
+ * categories as {@link java.lang.Class} instances.
+ * </p>
+ * <p>
+ * The following specialized types of <code>AttributeSet</code> are available:
+ * <ul>
+ * <li>{@link javax.print.attribute.DocAttributeSet}</li>
+ * <li>{@link javax.print.attribute.PrintRequestAttributeSet}</li>
+ * <li>{@link javax.print.attribute.PrintJobAttributeSet}</li>
+ * <li>{@link javax.print.attribute.PrintServiceAttributeSet}</li>
+ * </ul>
+ * </p>
+ * <p>
+ * Attribute sets may be unmodifiable depending on the context of usage. If
+ * used as read-only attribute set modifying operations throw an
+ * {@link javax.print.attribute.UnmodifiableSetException}.
+ * </p>
+ * <p>
+ * The Java Print Service API provides implementation classes for the existing
+ * attribute set interfaces but applications may use their own implementations.
+ * </p>
+ *
+ * @author Michael Koch (konqueror@gmx.de)
*/
public interface AttributeSet
{
/**
- * Adds the specified attribute value to this attribute set
+ * Adds the specified attribute value to this attribute set
* if it is not already present.
+ *
+ * This operation removes any existing attribute of the same category
+ * before adding the given attribute to the set.
+ *
+ * @param attribute the attribute to add.
+ * @return <code>true</code> if the set is changed, false otherwise.
+ * @throws NullPointerException if the attribute is <code>null</code>.
+ * @throws UnmodifiableSetException if the set does not support modification.
*/
boolean add (Attribute attribute);
/**
- * Adds all of the elements in the specified set to this attribute.
+ * Adds all of the elements in the specified set to this attribute set.
+ *
+ * @param attributes the set of attributes to add.
+ * @return <code>true</code> if the set is changed, false otherwise.
+ * @throws UnmodifiableSetException if the set does not support modification.
+ *
+ * @see #add(Attribute)
*/
boolean addAll (AttributeSet attributes);
-
+
+ /**
+ * Removes all attributes from this attribute set.
+ *
+ * @throws UnmodifiableSetException if the set does not support modification.
+ */
void clear ();
-
+
+ /**
+ * Checks if this attributes set contains an attribute with the given
+ * category.
+ *
+ * @param category the category to test for.
+ * @return <code>true</code> if an attribute of the category is contained
+ * in the set, <code>false</code> otherwise.
+ */
boolean containsKey (Class category);
-
+
+ /**
+ * Checks if this attribute set contains the given attribute.
+ *
+ * @param attribute the attribute to test for.
+ * @return <code>true</code> if the attribute is contained in the set,
+ * <code>false</code> otherwise.
+ */
boolean containsValue (Attribute attribute);
+ /**
+ * Tests this set for equality with the given object. <code>true</code> is
+ * returned, if the given object is also of type <code>AttributeSet</code>
+ * and the contained attributes are the same as in this set.
+ *
+ * @param obj the Object to test.
+ * @return <code>true</code> if equal, false otherwise.
+ */
boolean equals (Object obj);
-
- Attribute get (Class Category);
-
+
+ /**
+ * Returns the attribute object contained in this set for the given attribute
+ * category.
+ *
+ * @param category the category of the attribute. A <code>Class</code>
+ * instance of a class implementing the <code>Attribute</code> interface.
+ * @return The attribute for this category or <code>null</code> if no
+ * attribute is contained for the given category.
+ * @throws NullPointerException if category is null.
+ * @throws ClassCastException if category is not implementing
+ * <code>Attribute</code>.
+ */
+ Attribute get (Class category);
+
+ /**
+ * Returns the hashcode value. The hashcode value is the sum of all hashcodes
+ * of the attributes contained in this set.
+ *
+ * @return The hashcode for this attribute set.
+ */
int hashCode ();
-
+
+ /**
+ * Checks if the attribute set is empty.
+ *
+ * @return <code>true</code> if the attribute set is empty, false otherwise.
+ */
boolean isEmpty ();
+ /**
+ * Removes the given attribute from the set. If the given attribute is <code>null</code>
+ * nothing is done and <code>false</code> is returned.
+ *
+ * @param attribute the attribute to remove.
+ * @return <code>true</code> if removed, false in all other cases.
+ * @throws UnmodifiableSetException if the set does not support modification.
+ */
boolean remove (Attribute attribute);
-
+
+ /**
+ * Removes the attribute entry of the given category from the set. If the given
+ * category is <code>null</code> nothing is done and <code>false</code> is returned.
+ *
+ * @param category the category of the entry to be removed.
+ * @return <code>true</code> if an attribute is removed, false in all other cases.
+ * @throws UnmodifiableSetException if the set does not support modification.
+ */
boolean remove (Class category);
-
+
+ /**
+ * Returns the number of elements in this attribute set.
+ *
+ * @return The number of elements.
+ */
int size ();
-
+
+ /**
+ * Returns the content of the attribute set as an array
+ *
+ * @return An array of attributes.
+ */
Attribute[] toArray ();
}
diff --git a/javax/print/attribute/AttributeSetUtilities.java b/javax/print/attribute/AttributeSetUtilities.java
index 6f0ffc10d..5d97c66f2 100644
--- a/javax/print/attribute/AttributeSetUtilities.java
+++ b/javax/print/attribute/AttributeSetUtilities.java
@@ -39,12 +39,41 @@ package javax.print.attribute;
import java.io.Serializable;
+/**
+ * <code>AttributeSetUtilities</code> provides static methods for working
+ * with <code>AttributeSet</code>s.
+ * <p>
+ * For every type of an attribute set available in the Java Print Service API
+ * are methods provided to get an unmodifiable view of an attribute set.
+ * This unmodifiable view provides a read-only version of the attribute
+ * set which throws {@link javax.print.attribute.UnmodifiableSetException}s
+ * if state changing methods are invoked.
+ * </p>
+ * <p>
+ * Methods for getting a synchronized view of an attribute set are also
+ * available. This view provides synchronized (thread safe) access to the
+ * underlying wrapped attribute set.
+ * </P>
+ * <p>
+ * Three static methods for the implementation of own AttributeSets
+ * are provided, which verify that:
+ * <ul>
+ * <li>the given object is an attribute of the given interface.</li>
+ * <li>the category of given attribute is equals to a given category.</li>
+ * <li>the given object is a <code>Class</code> that implements the given
+ * interface name.</li>
+ * </ul>
+ *
+ */
public final class AttributeSetUtilities
{
/**
* This class isn't intended to be instantiated.
*/
- private AttributeSetUtilities() {}
+ private AttributeSetUtilities()
+ {
+ // only static methods
+ }
private static class UnmodifiableAttributeSet
implements AttributeSet, Serializable
@@ -287,7 +316,8 @@ public final class AttributeSetUtilities
/**
* Returns a synchronized view of the given attribute set.
*
- * @return the sychronized attribute set
+ * @param attributeSet the set to synchronize.
+ * @return The sychronized attribute set.
*/
public static AttributeSet synchronizedView(AttributeSet attributeSet)
{
@@ -297,7 +327,8 @@ public final class AttributeSetUtilities
/**
* Returns a synchronized view of the given attribute set.
*
- * @return the sychronized attribute set
+ * @param attributeSet the set to synchronize.
+ * @return The sychronized attribute set.
*/
public static DocAttributeSet synchronizedView(DocAttributeSet attributeSet)
{
@@ -307,7 +338,8 @@ public final class AttributeSetUtilities
/**
* Returns a synchronized view of the given attribute set.
*
- * @return the sychronized attribute set
+ * @param attributeSet the set to synchronize.
+ * @return The sychronized attribute set.
*/
public static PrintJobAttributeSet synchronizedView(PrintJobAttributeSet attributeSet)
{
@@ -317,7 +349,8 @@ public final class AttributeSetUtilities
/**
* Returns a synchronized view of the given attribute set.
*
- * @return the sychronized attribute set
+ * @param attributeSet the set to synchronize.
+ * @return The sychronized attribute set.
*/
public static PrintRequestAttributeSet synchronizedView(PrintRequestAttributeSet attributeSet)
{
@@ -327,7 +360,8 @@ public final class AttributeSetUtilities
/**
* Returns a synchronized view of the given attribute set.
*
- * @return the sychronized attribute set
+ * @param attributeSet the set to synchronize.
+ * @return The sychronized attribute set.
*/
public static PrintServiceAttributeSet synchronizedView(PrintServiceAttributeSet attributeSet)
{
@@ -337,7 +371,8 @@ public final class AttributeSetUtilities
/**
* Returns an unmodifiable view of the given attribute set.
*
- * @return the sychronized attribute set
+ * @param attributeSet the set to make unmodifiable.
+ * @return The unmodifiable attribute set.
*/
public static AttributeSet unmodifiableView(AttributeSet attributeSet)
{
@@ -347,7 +382,8 @@ public final class AttributeSetUtilities
/**
* Returns an unmodifiable view of the given attribute set.
*
- * @return the sychronized attribute set
+ * @param attributeSet the set to make unmodifiable.
+ * @return The unmodifiable attribute set.
*/
public static DocAttributeSet unmodifiableView(DocAttributeSet attributeSet)
{
@@ -357,7 +393,8 @@ public final class AttributeSetUtilities
/**
* Returns an unmodifiable view of the given attribute set.
*
- * @return the sychronized attribute set
+ * @param attributeSet the set to make unmodifiable.
+ * @return The unmodifiable attribute set.
*/
public static PrintJobAttributeSet unmodifiableView(PrintJobAttributeSet attributeSet)
{
@@ -367,7 +404,8 @@ public final class AttributeSetUtilities
/**
* Returns an unmodifiable view of the given attribute set.
*
- * @return the sychronized attribute set
+ * @param attributeSet the set to make unmodifiable.
+ * @return The unmodifiable attribute set.
*/
public static PrintRequestAttributeSet unmodifiableView(PrintRequestAttributeSet attributeSet)
{
@@ -377,7 +415,8 @@ public final class AttributeSetUtilities
/**
* Returns an unmodifiable view of the given attribute set.
*
- * @return the sychronized attribute set
+ * @param attributeSet the set to make unmodifiable.
+ * @return The unmodifiable attribute set.
*/
public static PrintServiceAttributeSet unmodifiableView(PrintServiceAttributeSet attributeSet)
{
@@ -386,8 +425,10 @@ public final class AttributeSetUtilities
/**
* Verifies that the given object is a <code>Class</code> that
- * implements the given interface name.
- *
+ * implements the given interface name and returns it casted.
+ *
+ * @param object the object to test.
+ * @param interfaceName the <code>Class</code> to verify against.
* @return object casted to <code>Class</code>
*
* @exception ClassCastException if object is not a <code>Class</code>
@@ -410,7 +451,10 @@ public final class AttributeSetUtilities
/**
* Verifies that the given object is an attribute of the given interface.
- *
+ * and returns it casted to the interface type.
+ *
+ * @param object the object to test.
+ * @param interfaceName the <code>Class</code> to verify against.
* @return the object casted to <code>Attribute</code>
*
* @exception ClassCastException if object is no instance of interfaceName.
@@ -429,10 +473,11 @@ public final class AttributeSetUtilities
}
/**
- * Verifies that the category of attribute is equals to category.
- *
- * @param category the category the atteribute should be
- * @param attribute the attribute to verify
+ * Verifies that the category of attribute is equals to the given category
+ * class.
+ *
+ * @param category the category to test.
+ * @param attribute the attribute to verify.
*
* @exception IllegalArgumentException if the categories are not equal
* @exception NullPointerException if category is null
@@ -440,10 +485,10 @@ public final class AttributeSetUtilities
public static void verifyCategoryForValue(Class category,
Attribute attribute)
{
- if (category == null)
- throw new NullPointerException("object may not be null");
+ if (category == null || attribute == null)
+ throw new NullPointerException("category or attribute may not be null");
- if (category.equals(attribute.getCategory()))
+ if (!category.equals(attribute.getCategory()))
throw new IllegalArgumentException
("category of attribute not equal to category");
}
diff --git a/javax/print/attribute/DateTimeSyntax.java b/javax/print/attribute/DateTimeSyntax.java
index 0e583e0b9..d59193265 100644
--- a/javax/print/attribute/DateTimeSyntax.java
+++ b/javax/print/attribute/DateTimeSyntax.java
@@ -1,5 +1,5 @@
/* DateTimeSyntax.java --
- Copyright (C) 2003 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -41,7 +41,10 @@ import java.io.Serializable;
import java.util.Date;
/**
- * @author Michael Koch
+ * <code>DateTimeSyntax</code> is the abstract base class of all attribute
+ * classes having a date and a time as value.
+ *
+ * @author Michael Koch (konqueror@gmx.de)
*/
public abstract class DateTimeSyntax implements Cloneable, Serializable
{
@@ -52,7 +55,7 @@ public abstract class DateTimeSyntax implements Cloneable, Serializable
/**
* Creates a <code>DateTimeSyntax</code> with a given value.
*
- * @param value the value for this syntax
+ * @param value the date for this syntax
*
* @exception NullPointerException if value is null
*/
@@ -67,7 +70,7 @@ public abstract class DateTimeSyntax implements Cloneable, Serializable
/**
* Returns the date value of this object.
*
- * @return the date value
+ * @return The date value.
*/
public Date getValue()
{
@@ -79,7 +82,8 @@ public abstract class DateTimeSyntax implements Cloneable, Serializable
*
* @param obj the object to test
*
- * @return True if both objects are equal, false otherwise.
+ * @return <code>true</code> if both objects are equal,
+ * <code>false</code> otherwise.
*/
public boolean equals(Object obj)
{
@@ -92,7 +96,7 @@ public abstract class DateTimeSyntax implements Cloneable, Serializable
/**
* Returns the hashcode for this object.
*
- * @return the hashcode
+ * @return The hashcode.
*/
public int hashCode()
{
diff --git a/javax/print/attribute/DocAttribute.java b/javax/print/attribute/DocAttribute.java
index 669d7d982..9af3a7052 100644
--- a/javax/print/attribute/DocAttribute.java
+++ b/javax/print/attribute/DocAttribute.java
@@ -1,5 +1,5 @@
/* DocAttribute.java --
- Copyright (C) 2003 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -38,8 +38,23 @@ exception statement from your version. */
package javax.print.attribute;
/**
- * @author Michael Koch
+ * Marker interface for all attribute classes describing attributes of
+ * a {@link javax.print.Doc} object.
+ * <p>
+ * Instances of implementing attribute classes may be collected in a
+ * {@link javax.print.attribute.DocAttributeSet}.
+ * </p><p>
+ * Attributes attached to a {@link javax.print.Doc} instance specify how the
+ * data should be printed.
+ * For example {@link javax.print.attribute.standard.Chromaticity} can be
+ * used to specify that a doc should be printed in color or monochrome.
+ * </p>
+ *
+ * @see javax.print.attribute.DocAttributeSet
+ *
+ * @author Michael Koch (konqueror@gmx.de)
*/
public interface DocAttribute extends Attribute
{
+ // Marker interface
}
diff --git a/javax/print/attribute/DocAttributeSet.java b/javax/print/attribute/DocAttributeSet.java
index 72cd6d88a..d8d09eb48 100644
--- a/javax/print/attribute/DocAttributeSet.java
+++ b/javax/print/attribute/DocAttributeSet.java
@@ -1,5 +1,5 @@
/* DocAttributeSet.java --
- Copyright (C) 2003 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -38,18 +38,45 @@ exception statement from your version. */
package javax.print.attribute;
/**
- * @author Michael Koch
+ * <code>DocAttributeSet</code> specifies an attribute set which only
+ * allows printing attributes of type
+ * {@link javax.print.attribute.DocAttribute}.
+ * <p>
+ * The methods {@link #add(Attribute)} and {@link #addAll(AttributeSet)} are
+ * respecified in this interface to indicate that only
+ * <code>DocAttribute</code> instances are allowed in this set.
+ * </p>
+ *
+ * @author Michael Koch (konqueror@gmx.de)
*/
public interface DocAttributeSet extends AttributeSet
{
/**
- * Adds the specified attribute value to this attribute set
+ * Adds the specified attribute value to this attribute set
* if it is not already present.
+ *
+ * This operation removes any existing attribute of the same category
+ * before adding the given attribute.
+ *
+ * @param attribute the attribute to add.
+ * @return <code>true</code> if the set is changed, false otherwise.
+ * @throws ClassCastException if attribute is not of type
+ * <code>DocAttribute</code>.
+ * @throws NullPointerException if the attribute is <code>null</code>.
+ * @throws UnmodifiableSetException if the set does not support modification.
*/
boolean add (Attribute attribute);
/**
- * Adds all of the elements in the specified set to this attribute.
+ * Adds all of the elements in the specified set to this attribute set.
+ *
+ * @param attributes the set of attributes to add.
+ * @return <code>true</code> if the set is changed, false otherwise.
+ * @throws ClassCastException if one of the attributes is not of type
+ * <code>DocAttribute</code>.
+ * @throws UnmodifiableSetException if the set does not support modification.
+ *
+ * @see #add(Attribute)
*/
boolean addAll (AttributeSet attributes);
}
diff --git a/javax/print/attribute/EnumSyntax.java b/javax/print/attribute/EnumSyntax.java
index 3ed79fc5f..9a5e62d45 100644
--- a/javax/print/attribute/EnumSyntax.java
+++ b/javax/print/attribute/EnumSyntax.java
@@ -1,5 +1,5 @@
/* EnumSyntax.java --
- Copyright (C) 2003 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -37,10 +37,69 @@ exception statement from your version. */
package javax.print.attribute;
+import java.io.InvalidObjectException;
+import java.io.ObjectStreamException;
import java.io.Serializable;
/**
- * @author Michael Koch
+ * <code>EnumSyntax</code> is the abstract base class of all enumeration
+ * classes in the Java Print Service API.
+ * <p>
+ * Every enumeration class which extends from EnumSyntax provides several
+ * enumeration objects as singletons of its class.
+ * </p>
+ * <p>
+ * Notes for implementing subclasses:
+ * <ul>
+ * <li>
+ * The values of all enumeration singelton instances have to be in a
+ * sequence which may start at any value. See: {@link #getOffset()}
+ * </li>
+ * <li>
+ * Subclasses have to override {@link #getEnumValueTable()} and should
+ * override {@link #getStringTable()} for correct serialization.
+ * </li>
+ * </ul>
+ * </p>
+ * Example:
+ * <pre>
+ * public class PrinterState extends EnumSyntax
+ * {
+ * public static final PrinterState IDLE = new PrinterState(1);
+ * public static final PrinterState PROCESSING = new PrinterState(2);
+ * public static final PrinterState STOPPED = new PrinterState(3);
+ *
+ * protected PrinterState(int value)
+ * {
+ * super(value);
+ * }
+ *
+ * // Overridden because values start not at zero !
+ * protected int getOffset()
+ * {
+ * return 1;
+ * }
+ *
+ * private static final String[] stringTable = { "idle", "processing",
+ * "stopped" };
+ *
+ * protected String[] getStringTable()
+ * {
+ * return stringTable;
+ * }
+ *
+ * private static final PrinterState[] enumValueTable = { IDLE,
+ * PROCESSING, STOPPED};
+ *
+ * protected EnumSyntax[] getEnumValueTable()
+ * {
+ * return enumValueTable;
+ * }
+ * }
+ * </pre>
+ *
+ * @author Michael Koch (konqueror@gmx.de)
+ * @author Wolfgang Baer (WBaer@gmx.de)
*/
public abstract class EnumSyntax implements Cloneable, Serializable
{
@@ -51,7 +110,7 @@ public abstract class EnumSyntax implements Cloneable, Serializable
/**
* Creates a <code>EnumSyntax</code> object.
*
- * @param value the value to set
+ * @param value the value to set.
*/
protected EnumSyntax(int value)
{
@@ -59,9 +118,9 @@ public abstract class EnumSyntax implements Cloneable, Serializable
}
/**
- * Returns the value of this object.
+ * Returns the value of this enumeration object.
*
- * @return the value
+ * @return The value.
*/
public int getValue()
{
@@ -71,7 +130,7 @@ public abstract class EnumSyntax implements Cloneable, Serializable
/**
* Clones this object.
*
- * @return a clone of this object
+ * @return A clone of this object.
*/
public Object clone()
{
@@ -87,9 +146,10 @@ public abstract class EnumSyntax implements Cloneable, Serializable
}
/**
- * Returns the hashcode for this object.
+ * Returns the hashcode for this object.
+ * The hashcode is the value of this enumeration object.
*
- * @return the hashcode
+ * @return The hashcode.
*/
public int hashCode()
{
@@ -98,8 +158,11 @@ public abstract class EnumSyntax implements Cloneable, Serializable
/**
* Returns the string representation for this object.
+ * The string value from <code>getStringTable()</code> method is returned
+ * if subclasses override this method. Otherwise the value of this object
+ * as a string is returned.
*
- * @return the string representation
+ * @return The string representation.
*/
public String toString()
{
@@ -118,9 +181,10 @@ public abstract class EnumSyntax implements Cloneable, Serializable
* Returns a table with the enumeration values represented as strings
* for this object.
*
- * The default implementation just returns null.
+ * The default implementation just returns null. Subclasses should
+ * override this method.
*
- * @return the enumeration values as strings
+ * @return The enumeration values as strings.
*/
protected String[] getStringTable()
{
@@ -128,17 +192,49 @@ public abstract class EnumSyntax implements Cloneable, Serializable
}
/**
+ * Needed for singelton semantics during deserialisation.
+ *
+ * Subclasses must not override this class. Subclasses have to override
+ * <code>getEnumValueTable()</code> and should override
+ * <code>getStringTable()</code> for correct serialization.
+ *
+ * @return The Object at index <code>value - getOffset()</code>
+ * in getEnumValueTable.
+ * @throws ObjectStreamException if getEnumValueTable() returns null.
+ */
+ protected Object readResolve() throws ObjectStreamException
+ {
+ EnumSyntax[] table = getEnumValueTable();
+ if (table == null)
+ throw new InvalidObjectException("Null enumeration value table "
+ + "for class "
+ + this.getClass().toString());
+
+ return table[value - getOffset()];
+ }
+
+ /**
* Returns a table with the enumeration values for this object.
*
- * The default implementation just returns null.
+ * The default implementation just returns null. Subclasses have to
+ * to override this method for serialization.
*
- * @return the enumeration values
+ * @return The enumeration values.
*/
protected EnumSyntax[] getEnumValueTable()
{
return null;
}
+ /**
+ * Returns the lowest used value by the enumerations of this class.
+ *
+ * The default implementation returns 0. This is enough if enumerations
+ * start with a zero value. Otherwise subclasses need to override this
+ * method for serialization and return the lowest value they use.
+ * .
+ * @return The lowest used value used.
+ */
protected int getOffset()
{
return 0;
diff --git a/javax/print/attribute/HashAttributeSet.java b/javax/print/attribute/HashAttributeSet.java
index c5fbe5ea8..0db81bae5 100644
--- a/javax/print/attribute/HashAttributeSet.java
+++ b/javax/print/attribute/HashAttributeSet.java
@@ -1,5 +1,5 @@
/* HashAttributeSet.java --
- Copyright (C) 2003, 2004 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2004, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -41,6 +41,10 @@ import java.io.Serializable;
import java.util.HashMap;
import java.util.Iterator;
+/**
+ * <code>HashAttributeSet</code> provides an implementation of
+ * {@link javax.print.attribute.AttributeSet}.
+ */
public class HashAttributeSet implements AttributeSet, Serializable
{
private static final long serialVersionUID = 5311560590283707917L;
@@ -73,9 +77,11 @@ public class HashAttributeSet implements AttributeSet, Serializable
* Creates a <code>HashAttributeSet</code> object with the given
* attributes in it.
*
- * @param attributes the attributes to put into the set
+ * @param attributes the array of attributes to put into the set. If
+ * <code>null</code> an empty set is created.
*
- * @exception NullPointerException If attributes is null
+ * @exception NullPointerException if one of the attributes of the given
+ * array is null.
*/
public HashAttributeSet(Attribute[] attributes)
{
@@ -83,12 +89,11 @@ public class HashAttributeSet implements AttributeSet, Serializable
}
/**
- * Creates a <code>HashAttributeSet</code> object with the given
- * attributes in it.
- *
- * @param attributes the attributes to put into the set
+ * Creates a <code>HashAttributeSet</code> object with attributes
+ * of the given attributes set in it.
*
- * @exception NullPointerException If attributes is null
+ * @param attributes the attributes set to put into the set. If
+ * <code>null</code> an empty set is created.
*/
public HashAttributeSet(AttributeSet attributes)
{
@@ -111,7 +116,11 @@ public class HashAttributeSet implements AttributeSet, Serializable
}
/**
- * Creates an empty <code>HashAttributeSet</code> object.
+ * Creates a <code>HashAttributeSet</code> object with the given
+ * attribute in it.
+ *
+ * @param attribute the attribute to put into the set.
+ * @param interfaceName the interface that all members must implement.
*
* @exception ClassCastException if attribute is not an interface of
* interfaceName
@@ -128,7 +137,12 @@ public class HashAttributeSet implements AttributeSet, Serializable
}
/**
- * Creates an empty <code>HashAttributeSet</code> object.
+ * Creates a <code>HashAttributeSet</code> object with the given
+ * attributes in it.
+ *
+ * @param attributes the array of attributes to put into the set. If
+ * <code>null</code> an empty set is created.
+ * @param interfaceName the interface that all members must implement.
*
* @exception ClassCastException if any element of attributes is not an
* interface of interfaceName
@@ -138,15 +152,20 @@ public class HashAttributeSet implements AttributeSet, Serializable
{
this(interfaceName);
- if (attributes == null)
- throw new NullPointerException();
-
- for (int index = 0; index < attributes.length; index++)
- addInternal(attributes[index], interfaceName);
+ if (attributes != null)
+ {
+ for (int index = 0; index < attributes.length; index++)
+ addInternal(attributes[index], interfaceName);
+ }
}
/**
- * Creates an empty <code>HashAttributeSet</code> object.
+ * Creates a <code>HashAttributeSet</code> object with attributes
+ * of the given attributes set in it.
+ *
+ * @param attributes the attributes set to put into the set. If
+ * <code>null</code> an empty set is created.
+ * @param interfaceName the interface that all members must implement.
*
* @exception ClassCastException if any element of attributes is not an
* interface of interfaceName
@@ -160,15 +179,16 @@ public class HashAttributeSet implements AttributeSet, Serializable
}
/**
- * Adds the given attribute to the set.
- *
- * @param attribute the attribute to add
- *
- * @return true if the attribute set has changed, false otherwise
- *
- * @exception NullPointerException if attribute is null
- * @exception UnmodifiableSetException if this attribute set does not
- * support this action.
+ * Adds the specified attribute value to this attribute set
+ * if it is not already present.
+ *
+ * This operation removes any existing attribute of the same category
+ * before adding the given attribute to the set.
+ *
+ * @param attribute the attribute to add.
+ * @return <code>true</code> if the set is changed, false otherwise.
+ * @throws NullPointerException if the attribute is <code>null</code>.
+ * @throws UnmodifiableSetException if the set does not support modification.
*/
public boolean add(Attribute attribute)
{
@@ -190,14 +210,13 @@ public class HashAttributeSet implements AttributeSet, Serializable
}
/**
- * Adds the given attributes to the set.
- *
- * @param attributes the attributes to add
- *
- * @return true if the attribute set has changed, false otherwise
- *
- * @exception UnmodifiableSetException if this attribute set does not
- * support this action.
+ * Adds all of the elements in the specified set to this attribute set.
+ *
+ * @param attributes the set of attributes to add.
+ * @return <code>true</code> if the set is changed, false otherwise.
+ * @throws UnmodifiableSetException if the set does not support modification.
+ *
+ * @see #add(Attribute)
*/
public boolean addAll(AttributeSet attributes)
{
@@ -218,9 +237,8 @@ public class HashAttributeSet implements AttributeSet, Serializable
/**
* Removes all attributes from this attribute set.
- *
- * @exception UnmodifiableSetException if this attribute set does not
- * support this action.
+ *
+ * @throws UnmodifiableSetException if the set does not support modification.
*/
public void clear()
{
@@ -228,11 +246,12 @@ public class HashAttributeSet implements AttributeSet, Serializable
}
/**
- * Checks if this attribute set contains an entry with the given category.
- *
- * @param category the category to test for
- *
- * @return true if the category exists in this attribute set, false otherwise.
+ * Checks if this attributes set contains an attribute with the given
+ * category.
+ *
+ * @param category the category to test for.
+ * @return <code>true</code> if an attribute of the category is contained
+ * in the set, <code>false</code> otherwise.
*/
public boolean containsKey(Class category)
{
@@ -240,12 +259,11 @@ public class HashAttributeSet implements AttributeSet, Serializable
}
/**
- * Checks if this attribute set contains an entry with the given attribute.
- *
- * @param attribute the attribute to test for
- *
- * @return true if the attribute exists in this attribute set,
- * false otherwise.
+ * Checks if this attribute set contains the given attribute.
+ *
+ * @param attribute the attribute to test for.
+ * @return <code>true</code> if the attribute is contained in the set,
+ * <code>false</code> otherwise.
*/
public boolean containsValue(Attribute attribute)
{
@@ -253,11 +271,12 @@ public class HashAttributeSet implements AttributeSet, Serializable
}
/**
- * Tests of obj is equal to this object.
- *
- * @param obj the object to test
- *
- * @return true if both objects are equal, false otherwise.
+ * Tests this set for equality with the given object. <code>true</code> is
+ * returned, if the given object is also of type <code>AttributeSet</code>
+ * and the contained attributes are the same as in this set.
+ *
+ * @param obj the Object to test.
+ * @return <code>true</code> if equal, false otherwise.
*/
public boolean equals(Object obj)
{
@@ -268,33 +287,45 @@ public class HashAttributeSet implements AttributeSet, Serializable
}
/**
- * Returns the attribute value that is connected to the given attribute
- * category. If the attribute set does not contains the given category null
- * will be returned.
- *
- * @param category the attribute category to return the attribute value for
- *
- * @return the attribute associated to category, or null
+ * Returns the attribute object contained in this set for the given attribute
+ * category.
+ *
+ * @param category the category of the attribute. A <code>Class</code>
+ * instance of a class implementing the <code>Attribute</code> interface.
+ * @return The attribute for this category or <code>null</code> if no
+ * attribute is contained for the given category.
+ * @throws NullPointerException if category is null.
+ * @throws ClassCastException if category is not implementing
+ * <code>Attribute</code>.
*/
public Attribute get(Class category)
{
+ if (category == null)
+ throw new NullPointerException("category may not be null");
+
return (Attribute) attributeMap.get(category);
}
/**
- * Returns the hashcode for this object.
- *
- * @return the hashcode
+ * Returns the hashcode value. The hashcode value is the sum of all hashcodes
+ * of the attributes contained in this set.
+ *
+ * @return The hashcode for this attribute set.
*/
public int hashCode()
{
- return attributeMap.hashCode() + interfaceName.hashCode();
+ int hashcode = 0;
+ Iterator it = attributeMap.values().iterator();
+ while (it.hasNext())
+ hashcode = hashcode + it.next().hashCode();
+
+ return hashcode;
}
/**
* Checks if the attribute set is empty.
*
- * @return true if the attribute set is empty, false otherwise
+ * @return <code>true</code> if the attribute set is empty, false otherwise.
*/
public boolean isEmpty()
{
@@ -302,14 +333,12 @@ public class HashAttributeSet implements AttributeSet, Serializable
}
/**
- * Removes the entry with the given attribute in it.
- *
- * @param attribute the attribute value of the entry to be removed
- *
- * @return true if the attribute set has changed, false otherwise.
- *
- * @exception UnmodifiableSetException if this attribute set does not
- * support this action.
+ * Removes the given attribute from the set. If the given attribute is <code>null</code>
+ * nothing is done and <code>false</code> is returned.
+ *
+ * @param attribute the attribute to remove.
+ * @return <code>true</code> if removed, false in all other cases.
+ * @throws UnmodifiableSetException if the set does not support modification.
*/
public boolean remove(Attribute attribute)
{
@@ -320,11 +349,12 @@ public class HashAttributeSet implements AttributeSet, Serializable
}
/**
- * Removes the entry with the given category in it.
- *
- * @param category the category value of the entry to be removed
- *
- * @return true if the attribute set has changed, false otherwise.
+ * Removes the attribute entry of the given category from the set. If the given
+ * category is <code>null</code> nothing is done and <code>false</code> is returned.
+ *
+ * @param category the category of the entry to be removed.
+ * @return <code>true</code> if an attribute is removed, false in all other cases.
+ * @throws UnmodifiableSetException if the set does not support modification.
*/
public boolean remove(Class category)
{
@@ -337,7 +367,7 @@ public class HashAttributeSet implements AttributeSet, Serializable
/**
* Returns the number of elements in this attribute set.
*
- * @return the number of elements.
+ * @return The number of elements.
*/
public int size()
{
@@ -347,12 +377,12 @@ public class HashAttributeSet implements AttributeSet, Serializable
/**
* Returns the content of the attribute set as an array
*
- * @return an array of attributes
+ * @return An array of attributes.
*/
public Attribute[] toArray()
{
int index = 0;
- Iterator it = attributeMap.entrySet().iterator();
+ Iterator it = attributeMap.values().iterator();
Attribute[] array = new Attribute[size()];
while (it.hasNext())
diff --git a/javax/print/attribute/HashDocAttributeSet.java b/javax/print/attribute/HashDocAttributeSet.java
index 1647ae2f9..2317db3bc 100644
--- a/javax/print/attribute/HashDocAttributeSet.java
+++ b/javax/print/attribute/HashDocAttributeSet.java
@@ -1,5 +1,5 @@
/* HashDocAttributeSet.java --
- Copyright (C) 2003 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -39,6 +39,10 @@ package javax.print.attribute;
import java.io.Serializable;
+/**
+ * <code>HashDocAttributeSet</code> provides an implementation of
+ * {@link javax.print.attribute.DocAttributeSet}.
+ */
public class HashDocAttributeSet extends HashAttributeSet
implements DocAttributeSet, Serializable
{
@@ -56,7 +60,7 @@ public class HashDocAttributeSet extends HashAttributeSet
* Creates a <code>HashDocAttributeSet</code> object with the given
* attribute in it.
*
- * @param attribute the attriute tu put into the attribute set
+ * @param attribute the attribute to put into the attribute set
*
* @exception NullPointerException if attribute is null
*/
@@ -69,9 +73,11 @@ public class HashDocAttributeSet extends HashAttributeSet
* Creates a <code>HashDocAttributeSet</code> object with the given
* attributes in it.
*
- * @param attributes the attributes to put into the attribute set
+ * @param attributes the array of attributes to put into the set. If
+ * <code>null</code> an empty set is created.
*
- * @exception NullPointerException if attributes is null
+ * @exception NullPointerException if one of the attributes of the given
+ * array is null.
*/
public HashDocAttributeSet(DocAttribute[] attributes)
{
@@ -79,11 +85,11 @@ public class HashDocAttributeSet extends HashAttributeSet
}
/**
- * Creates a <code>HashDocAttributeSet</code> object with the given
- * attributes in it.
- *
- * @param attributes the attributes to put into the attribute set
+ * Creates a <code>HashDocAttributeSet</code> object with the attributes
+ * of the given attributes set in it.
*
+ * @param attributes the attributes set to put into the set. If
+ * <code>null</code> an empty set is created.
* @exception ClassCastException if any element of attributes is not
* an instance of <code>DocAttribute</code>
*/
diff --git a/javax/print/attribute/HashPrintJobAttributeSet.java b/javax/print/attribute/HashPrintJobAttributeSet.java
index 84fa7ec5d..ac4c902c3 100644
--- a/javax/print/attribute/HashPrintJobAttributeSet.java
+++ b/javax/print/attribute/HashPrintJobAttributeSet.java
@@ -1,5 +1,5 @@
/* HashPrintJobAttributeSet.java --
- Copyright (C) 2003 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -39,6 +39,10 @@ package javax.print.attribute;
import java.io.Serializable;
+/**
+ * <code>HashPrintJobAttributeSet</code> provides an implementation of
+ * {@link javax.print.attribute.PrintJobAttributeSet}.
+ */
public class HashPrintJobAttributeSet extends HashAttributeSet
implements Serializable, PrintJobAttributeSet
{
@@ -56,7 +60,7 @@ public class HashPrintJobAttributeSet extends HashAttributeSet
* Creates a <code>HashPrintJobAttributeSet</code> object with the given
* attribute in it.
*
- * @param attribute the attriute tu put into the attribute set
+ * @param attribute the attribute to put into the attribute set
*
* @exception NullPointerException if attribute is null
*/
@@ -69,9 +73,11 @@ public class HashPrintJobAttributeSet extends HashAttributeSet
* Creates a <code>HashPrintJobAttributeSet</code> object with the given
* attributes in it.
*
- * @param attributes the attributes to put into the attribute set
+ * @param attributes the array of attributes to put into the set. If
+ * <code>null</code> an empty set is created.
*
- * @exception NullPointerException if attributes is null
+ * @exception NullPointerException if one of the attributes of the given
+ * array is null.
*/
public HashPrintJobAttributeSet(PrintJobAttribute[] attributes)
{
@@ -79,11 +85,11 @@ public class HashPrintJobAttributeSet extends HashAttributeSet
}
/**
- * Creates a <code>HashPrintJobAttributeSet</code> object with the given
- * attributes in it.
- *
- * @param attributes the attributes to put into the attribute set
+ * Creates a <code>HashPrintJobAttributeSet</code> object with the attributes
+ * of the given attributes set in it.
*
+ * @param attributes the attributes set to put into the set. If
+ * <code>null</code> an empty set is created.
* @exception ClassCastException if any element of attributes is not
* an instance of <code>PrintJobAttribute</code>
*/
diff --git a/javax/print/attribute/HashPrintRequestAttributeSet.java b/javax/print/attribute/HashPrintRequestAttributeSet.java
index 29a17861f..e74c0e00f 100644
--- a/javax/print/attribute/HashPrintRequestAttributeSet.java
+++ b/javax/print/attribute/HashPrintRequestAttributeSet.java
@@ -1,5 +1,5 @@
/* HashPrintRequestAttributeSet.java --
- Copyright (C) 2003 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -39,6 +39,10 @@ package javax.print.attribute;
import java.io.Serializable;
+/**
+ * <code>HashPrintRequestAttributeSet</code> provides an implementation of
+ * {@link javax.print.attribute.PrintRequestAttributeSet}.
+ */
public class HashPrintRequestAttributeSet extends HashAttributeSet
implements Serializable, PrintRequestAttributeSet
{
@@ -56,7 +60,7 @@ public class HashPrintRequestAttributeSet extends HashAttributeSet
* Creates a <code>HashPrintRequestAttributeSet</code> object with the given
* attribute in it.
*
- * @param attribute the attriute tu put into the attribute set
+ * @param attribute the attribute to put into the attribute set
*
* @exception NullPointerException if attribute is null
*/
@@ -69,9 +73,11 @@ public class HashPrintRequestAttributeSet extends HashAttributeSet
* Creates a <code>HashPrintRequestAttributeSet</code> object with the given
* attributes in it.
*
- * @param attributes the attributes to put into the attribute set
+ * @param attributes the array of attributes to put into the set. If
+ * <code>null</code> an empty set is created.
*
- * @exception NullPointerException if attributes is null
+ * @exception NullPointerException if one of the attributes of the given
+ * array is null.
*/
public HashPrintRequestAttributeSet(PrintRequestAttribute[] attributes)
{
@@ -79,11 +85,11 @@ public class HashPrintRequestAttributeSet extends HashAttributeSet
}
/**
- * Creates a <code>HashPrintRequestAttributeSet</code> object with the given
- * attributes in it.
- *
- * @param attributes the attributes to put into the attribute set
+ * Creates a <code>HashPrintRequestAttributeSet</code> object with the attributes
+ * of the given attributes set in it.
*
+ * @param attributes the attributes set to put into the set. If
+ * <code>null</code> an empty set is created.
* @exception ClassCastException if any element of attributes is not
* an instance of <code>PrintRequestAttribute</code>
*/
diff --git a/javax/print/attribute/HashPrintServiceAttributeSet.java b/javax/print/attribute/HashPrintServiceAttributeSet.java
index 60e12bff0..155514f2b 100644
--- a/javax/print/attribute/HashPrintServiceAttributeSet.java
+++ b/javax/print/attribute/HashPrintServiceAttributeSet.java
@@ -1,5 +1,5 @@
/* HashPrintServiceAttributeSet.java --
- Copyright (C) 2003 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -39,6 +39,10 @@ package javax.print.attribute;
import java.io.Serializable;
+/**
+ * <code>HashPrintServiceAttributeSet</code> provides an implementation of
+ * {@link javax.print.attribute.PrintServiceAttributeSet}.
+ */
public class HashPrintServiceAttributeSet extends HashAttributeSet
implements Serializable, PrintServiceAttributeSet
{
@@ -56,7 +60,7 @@ public class HashPrintServiceAttributeSet extends HashAttributeSet
* Creates a <code>HashPrintServiceAttributeSet</code> object with the given
* attribute in it.
*
- * @param attribute the attriute tu put into the attribute set
+ * @param attribute the attribute to put into the attribute set
*
* @exception NullPointerException if attribute is null
*/
@@ -69,9 +73,11 @@ public class HashPrintServiceAttributeSet extends HashAttributeSet
* Creates a <code>HashPrintServiceAttributeSet</code> object with the given
* attributes in it.
*
- * @param attributes the attributes to put into the attribute set
+ * @param attributes the array of attributes to put into the set. If
+ * <code>null</code> an empty set is created.
*
- * @exception NullPointerException if attributes is null
+ * @exception NullPointerException if one of the attributes of the given
+ * array is null.
*/
public HashPrintServiceAttributeSet(PrintServiceAttribute[] attributes)
{
@@ -79,11 +85,11 @@ public class HashPrintServiceAttributeSet extends HashAttributeSet
}
/**
- * Creates a <code>HashPrintServiceAttributeSet</code> object with the given
- * attributes in it.
- *
- * @param attributes the attributes to put into the attribute set
+ * Creates a <code>HashPrintServiceAttributeSet</code> object with the attributes
+ * of the given attributes set in it.
*
+ * @param attributes the attributes set to put into the set. If
+ * <code>null</code> an empty set is created.
* @exception ClassCastException if any element of attributes is not
* an instance of <code>PrintServiceAttribute</code>
*/
diff --git a/javax/print/attribute/IntegerSyntax.java b/javax/print/attribute/IntegerSyntax.java
index d5500b4ca..c2f9224a2 100644
--- a/javax/print/attribute/IntegerSyntax.java
+++ b/javax/print/attribute/IntegerSyntax.java
@@ -1,5 +1,5 @@
/* IntegerSyntax.java --
- Copyright (C) 2003, 2004 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2004, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -40,7 +40,10 @@ package javax.print.attribute;
import java.io.Serializable;
/**
- * @author Michael Koch
+ * <code>IntegerSyntax</code> is the abstract base class of all attribute
+ * classes having an integer as value.
+ *
+ * @author Michael Koch (konqueror@gmx.de)
*/
public abstract class IntegerSyntax implements Cloneable, Serializable
{
@@ -49,7 +52,7 @@ public abstract class IntegerSyntax implements Cloneable, Serializable
/**
* Creates a <code>IntegerSyntax</code> with the given value.
*
- * @param value the value to set
+ * @param value the integer to set
*/
protected IntegerSyntax(int value)
{
@@ -57,9 +60,10 @@ public abstract class IntegerSyntax implements Cloneable, Serializable
}
/**
- * Creates a <code>IntegerSyntax</code> with the given arguments.
+ * Creates a <code>IntegerSyntax</code> with the given integer value
+ * and checks if the value lies inside the given bounds..
*
- * @param value the value to set
+ * @param value the integer to set
* @param lowerBound the lower bound for the value
* @param upperBound the upper bound for the value
*
@@ -78,7 +82,7 @@ public abstract class IntegerSyntax implements Cloneable, Serializable
/**
* Returns the value of this object.
*
- * @return the value
+ * @return The integer value.
*/
public int getValue()
{
@@ -86,11 +90,12 @@ public abstract class IntegerSyntax implements Cloneable, Serializable
}
/**
- * Tests of obj is equal to this object.
+ * Tests if the given object is equal to this object.
*
* @param obj the object to test
*
- * @return true if both objects are equal, false otherwise.
+ * @return <code>true</code> if both objects are equal,
+ * <code>false</code> otherwise.
*/
public boolean equals(Object obj)
{
@@ -103,7 +108,7 @@ public abstract class IntegerSyntax implements Cloneable, Serializable
/**
* Returns the hashcode for this object.
*
- * @return the hashcode
+ * @return The hashcode.
*/
public int hashCode()
{
@@ -113,7 +118,7 @@ public abstract class IntegerSyntax implements Cloneable, Serializable
/**
* Returns the string representation for this object.
*
- * @return the string representation
+ * @return The string representation.
*/
public String toString()
{
diff --git a/javax/print/attribute/PrintJobAttribute.java b/javax/print/attribute/PrintJobAttribute.java
index ba3a737b5..fd3663496 100644
--- a/javax/print/attribute/PrintJobAttribute.java
+++ b/javax/print/attribute/PrintJobAttribute.java
@@ -1,5 +1,5 @@
/* PrintJobAttribute.java --
- Copyright (C) 2003 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -38,8 +38,23 @@ exception statement from your version. */
package javax.print.attribute;
/**
- * @author Michael Koch
+ * Marker interface for all attribute classes describing attributes or the
+ * status of a ({@link javax.print.DocPrintJob} object.
+ * <p>
+ * Instances of implementing attribute classes may be collected in a
+ * {@link javax.print.attribute.PrintJobAttributeSet}.
+ * </p><p>
+ * A print service uses attributes of this type to inform about the status
+ * of a print job.
+ * For example {@link javax.print.attribute.standard.DateTimeAtProcessing}
+ * is used to report at which date and time a job has started processing.
+ * </p>
+ *
+ * @see javax.print.attribute.PrintJobAttributeSet
+ *
+ * @author Michael Koch (konqueror@gmx.de)
*/
public interface PrintJobAttribute extends Attribute
{
+ // Marker interface
}
diff --git a/javax/print/attribute/PrintJobAttributeSet.java b/javax/print/attribute/PrintJobAttributeSet.java
index 905d53c2d..6283ae142 100644
--- a/javax/print/attribute/PrintJobAttributeSet.java
+++ b/javax/print/attribute/PrintJobAttributeSet.java
@@ -1,5 +1,5 @@
/* PrintJobAttributeSet.java --
- Copyright (C) 2003 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -38,18 +38,45 @@ exception statement from your version. */
package javax.print.attribute;
/**
- * @author Michael Koch
+ * <code>PrintJobAttributeSet</code> specifies an attribute set which only
+ * allows printing attributes of type
+ * {@link javax.print.attribute.PrintJobAttribute}.
+ * <p>
+ * The methods {@link #add(Attribute)} and {@link #addAll(AttributeSet)} are
+ * respecified in this interface to indicate that only
+ * <code>PrintJobAttribute</code> instances are allowed in this set.
+ * </p>
+ *
+ * @author Michael Koch (konqueror@gmx.de)
*/
public interface PrintJobAttributeSet extends AttributeSet
{
/**
- * Adds the specified attribute value to this attribute set
+ * Adds the specified attribute value to this attribute set
* if it is not already present.
+ *
+ * This operation removes any existing attribute of the same category
+ * before adding the given attribute.
+ *
+ * @param attribute the attribute to add.
+ * @return <code>true</code> if the set is changed, false otherwise.
+ * @throws ClassCastException if attribute is not of type
+ * <code>PrintJobAttribute</code>.
+ * @throws NullPointerException if the attribute is <code>null</code>.
+ * @throws UnmodifiableSetException if the set does not support modification.
*/
boolean add (Attribute attribute);
/**
- * Adds all of the elements in the specified set to this attribute.
+ * Adds all of the elements in the specified set to this attribute set.
+ *
+ * @param attributes the set of attributes to add.
+ * @return <code>true</code> if the set is changed, false otherwise.
+ * @throws ClassCastException if one of the attributes is not of type
+ * <code>PrintJobAttribute</code>.
+ * @throws UnmodifiableSetException if the set does not support modification.
+ *
+ * @see #add(Attribute)
*/
boolean addAll (AttributeSet attributes);
}
diff --git a/javax/print/attribute/PrintRequestAttribute.java b/javax/print/attribute/PrintRequestAttribute.java
index 756350020..8a05b75d3 100644
--- a/javax/print/attribute/PrintRequestAttribute.java
+++ b/javax/print/attribute/PrintRequestAttribute.java
@@ -1,5 +1,5 @@
/* PrintRequestAttribute.java --
- Copyright (C) 2003 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -38,8 +38,18 @@ exception statement from your version. */
package javax.print.attribute;
/**
- * @author Michael Koch
+ * Marker interface for all attribute classes which specify a requested
+ * attribute of {@link javax.print.DocPrintJob} object.
+ * <p>
+ * Instances of implementing attribute classes may be collected in a
+ * {@link javax.print.attribute.PrintRequestAttributeSet}.
+ * </p>
+ *
+ * @see javax.print.attribute.PrintRequestAttributeSet
+ *
+ * @author Michael Koch (konqueror@gmx.de)
*/
public interface PrintRequestAttribute extends Attribute
{
+ // Marker interface
}
diff --git a/javax/print/attribute/PrintRequestAttributeSet.java b/javax/print/attribute/PrintRequestAttributeSet.java
index d72d2d71c..350d9a644 100644
--- a/javax/print/attribute/PrintRequestAttributeSet.java
+++ b/javax/print/attribute/PrintRequestAttributeSet.java
@@ -1,5 +1,5 @@
/* PrintRequestAttributeSet.java --
- Copyright (C) 2002 Free Software Foundation, Inc.
+ Copyright (C) 2002, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -38,18 +38,45 @@ exception statement from your version. */
package javax.print.attribute;
/**
- * @author Michael Koch
+ * <code>PrintRequestAttributeSet</code> specifies an attribute set which only
+ * allows printing attributes of type
+ * {@link javax.print.attribute.PrintRequestAttribute}.
+ * <p>
+ * The methods {@link #add(Attribute)} and {@link #addAll(AttributeSet)} are
+ * respecified in this interface to indicate that only
+ * <code>PrintRequestAttribute</code> instances are allowed in this set.
+ * </p>
+ *
+ * @author Michael Koch (konqueror@gmx.de)
*/
public interface PrintRequestAttributeSet extends AttributeSet
{
/**
- * Adds the specified attribute value to this attribute set
+ * Adds the specified attribute value to this attribute set
* if it is not already present.
+ *
+ * This operation removes any existing attribute of the same category
+ * before adding the given attribute.
+ *
+ * @param attribute the attribute to add.
+ * @return <code>true</code> if the set is changed, false otherwise.
+ * @throws ClassCastException if attribute is not of type
+ * <code>PrintRequestAttribute</code>.
+ * @throws NullPointerException if the attribute is <code>null</code>.
+ * @throws UnmodifiableSetException if the set does not support modification.
*/
boolean add (Attribute attribute);
/**
- * Adds all of the elements in the specified set to this attribute.
+ * Adds all of the elements in the specified set to this attribute set.
+ *
+ * @param attributes the set of attributes to add.
+ * @return <code>true</code> if the set is changed, false otherwise.
+ * @throws ClassCastException if one of the attributes is not of type
+ * <code>PrintRequestAttribute</code>.
+ * @throws UnmodifiableSetException if the set does not support modification.
+ *
+ * @see #add(Attribute)
*/
boolean addAll (AttributeSet attributes);
}
diff --git a/javax/print/attribute/PrintServiceAttribute.java b/javax/print/attribute/PrintServiceAttribute.java
index 3cf8825f5..213f43796 100644
--- a/javax/print/attribute/PrintServiceAttribute.java
+++ b/javax/print/attribute/PrintServiceAttribute.java
@@ -1,5 +1,5 @@
/* PrintServiceAttribute.java --
- Copyright (C) 2003 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -38,8 +38,23 @@ exception statement from your version. */
package javax.print.attribute;
/**
- * @author Michael Koch
+ * Marker interface for all attribute classes describing parameters
+ * or the status of a {@link javax.print.PrintService}.
+ * <p>
+ * Instances of implementing attribute classes may be collected in a
+ * {@link javax.print.attribute.PrintServiceAttributeSet}.
+ * </p><p>
+ * A print service uses attributes of this type to inform about the status
+ * or the specific capabilities of itself.
+ * For example {@link javax.print.attribute.standard.PagesPerMinute} is used
+ * to specify the average printable pages per minute of the print service.
+ * </p>
+ *
+ * @see javax.print.attribute.PrintServiceAttributeSet
+ *
+ * @author Michael Koch (konqueror@gmx.de)
*/
public interface PrintServiceAttribute extends Attribute
{
+ // Marker interface
}
diff --git a/javax/print/attribute/PrintServiceAttributeSet.java b/javax/print/attribute/PrintServiceAttributeSet.java
index d67c9af55..fa22ee0d9 100644
--- a/javax/print/attribute/PrintServiceAttributeSet.java
+++ b/javax/print/attribute/PrintServiceAttributeSet.java
@@ -1,5 +1,5 @@
/* PrintServiceAttributeSet.java --
- Copyright (C) 2003 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -38,18 +38,45 @@ exception statement from your version. */
package javax.print.attribute;
/**
- * @author Michael Koch
+ * <code>PrintServiceAttributeSet</code> specifies an attribute set which only
+ * allows printing attributes of type
+ * {@link javax.print.attribute.PrintServiceAttribute}.
+ * <p>
+ * The methods {@link #add(Attribute)} and {@link #addAll(AttributeSet)} are
+ * respecified in this interface to indicate that only
+ * <code>PrintServiceAttribute</code> instances are allowed in this set.
+ * </p>
+ *
+ * @author Michael Koch (konqueror@gmx.de)
*/
public interface PrintServiceAttributeSet extends AttributeSet
{
/**
- * Adds the specified attribute value to this attribute set
+ * Adds the specified attribute value to this attribute set
* if it is not already present.
+ *
+ * This operation removes any existing attribute of the same category
+ * before adding the given attribute.
+ *
+ * @param attribute the attribute to add.
+ * @return <code>true</code> if the set is changed, false otherwise.
+ * @throws ClassCastException if attribute is not of type
+ * <code>PrintServiceAttribute</code>.
+ * @throws NullPointerException if the attribute is <code>null</code>.
+ * @throws UnmodifiableSetException if the set does not support modification.
*/
boolean add (Attribute attribute);
/**
- * Adds all of the elements in the specified set to this attribute.
+ * Adds all of the elements in the specified set to this attribute set.
+ *
+ * @param attributes the set of attributes to add.
+ * @return <code>true</code> if the set is changed, false otherwise.
+ * @throws ClassCastException if one of the attributes is not of type
+ * <code>PrintServiceAttribute</code>.
+ * @throws UnmodifiableSetException if the set does not support modification.
+ *
+ * @see #add(Attribute)
*/
boolean addAll (AttributeSet attributes);
}
diff --git a/javax/print/attribute/ResolutionSyntax.java b/javax/print/attribute/ResolutionSyntax.java
index a7878c50b..aca4c0188 100644
--- a/javax/print/attribute/ResolutionSyntax.java
+++ b/javax/print/attribute/ResolutionSyntax.java
@@ -1,5 +1,5 @@
/* ResolutionSyntax.java --
- Copyright (C) 2003, 2004 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2004, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -40,7 +40,42 @@ package javax.print.attribute;
import java.io.Serializable;
/**
- * @author Michael Koch
+ * <code>ResolutionSyntax</code> is the abstract base class of all attribute
+ * classes which provide a resolution as value (e.g. printer resolution).
+ * <p>
+ * A <code>ResolutionSyntax</code> instance consists of two integer values
+ * describing the resolution in feed and cross feed direction. The units of
+ * the given values is determined by two defined constants:
+ * <ul>
+ * <li>DPCM - dots per centimeter</li>
+ * <li>DPI - dots per inch</li>
+ * </ul>
+ * </p>
+ * <p>
+ * A resolutions attribute is constructed by two values for the resolution and
+ * one of the two constants defining the actual units of the given values.
+ * </p>
+ * <p>
+ * There are different methods provided to return the resolution values in
+ * either of the both units and to compare if a resolution is less than or
+ * equal to a given other resolution attribute.
+ * </p>
+ * <p>
+ * <b>Internal storage:</b><br>
+ * The resolutions are stored internally as dots per 100 inches (dphi). The
+ * values of the provided constants for dots per inch (value 100) and dots
+ * per centimeter (value 254) are used as conversion factors to the internal
+ * storage units. To get the internal dphi values a multiplication of a given
+ * resolution value with its units constant value is needed. Retrieving the
+ * resolution for specific units is done by dividing the internal stored
+ * value through the units constant value. Clients are therefore able to
+ * provide their own resolution units by supplying other conversion factors.
+ * Subclasses of <code>ResolutionSyntax</code> have access to the internal
+ * resolution values through the protected methods
+ * {@link #getCrossFeedResolutionDphi()} and {@link #getFeedResolutionDphi()}.
+ * </p>
+ *
+ * @author Michael Koch (konqueror@gmx.de)
*/
public abstract class ResolutionSyntax
implements Cloneable, Serializable
@@ -65,7 +100,7 @@ public abstract class ResolutionSyntax
*
* @param crossFeedResolution the cross feed resolution
* @param feedResolution the feed resolution
- * @param units the unit to use
+ * @param units the unit to use (e.g. {@link #DPCM} or {@link #DPI})
*
* @exception IllegalArgumentException if preconditions fail
*/
@@ -82,11 +117,12 @@ public abstract class ResolutionSyntax
}
/**
- * Tests of obj is equal to this object.
+ * Tests if the given object is equal to this object.
*
* @param obj the object to test
*
- * @return true if both objects are equal, false otherwise.
+ * @return <code>true</code> if both objects are equal,
+ * <code>false</code> otherwise.
*/
public boolean equals(Object obj)
{
@@ -100,24 +136,25 @@ public abstract class ResolutionSyntax
}
/**
- * Returns the cross feed resolution in units.
+ * Returns the cross feed resolution for the given units.
*
- * @return the resolution
+ * @param units the unit to use (e.g. {@link #DPCM} or {@link #DPI})
+ * @return The resolution for the given units.
*
- * @exception IllegalArgumentException if units < 1
+ * @exception IllegalArgumentException if units &lt; 1
*/
public int getCrossFeedResolution(int units)
{
if (units < 1)
throw new IllegalArgumentException("units may not be less then 1");
- return (crossFeedResolution + units) / units;
+ return crossFeedResolution / units;
}
/**
- * Returns the raw cross feed resolution in units.
+ * Returns the raw cross feed resolution in dots per 100 inches.
*
- * @return the raw resolution
+ * @return The raw resolution.
*/
protected int getCrossFeedResolutionDphi()
{
@@ -125,24 +162,25 @@ public abstract class ResolutionSyntax
}
/**
- * Returns the feed resolution in units.
+ * Returns the feed resolution for the given units.
*
- * @return the resolution
+ * @param units the unit to use (e.g. {@link #DPCM} or {@link #DPI})
+ * @return The resolution for the given units.
*
- * @exception IllegalArgumentException if units < 1
+ * @exception IllegalArgumentException if units &lt; 1
*/
public int getFeedResolution(int units)
{
if (units < 1)
throw new IllegalArgumentException("units may not be less then 1");
- return (crossFeedResolution + units) / units;
+ return feedResolution / units;
}
/**
- * Returns the raw feed resolution in units.
+ * Returns the raw feed resolution in dots per 100 inches.
*
- * @return the raw resolution
+ * @return The raw resolution.
*/
protected int getFeedResolutionDphi()
{
@@ -155,7 +193,7 @@ public abstract class ResolutionSyntax
*
* @param units the units to use
*
- * @return the array with the resolutions
+ * @return The array with the resolutions.
*/
public int[] getResolution(int units)
{
@@ -168,7 +206,7 @@ public abstract class ResolutionSyntax
/**
* Returns the hashcode for this object.
*
- * @return the hashcode
+ * @return The hashcode.
*/
public int hashCode()
{
@@ -176,11 +214,13 @@ public abstract class ResolutionSyntax
}
/**
- * Checks of other is a lower or equal resolution.
+ * Checks if the given resolution attribute is a lower or equal
+ * to this resolution object.
*
* @param other the resolution to check against
*
- * @return true if other describes a lower or equal resolution
+ * @return <code>true</code> if other resolution attribute describes
+ * a lower or equal resolution, <code>false</code> otherwise.
*/
public boolean lessThanOrEquals(ResolutionSyntax other)
{
@@ -193,8 +233,12 @@ public abstract class ResolutionSyntax
/**
* Returns the string representation for this object.
- *
- * @return the string representation
+ * <p>
+ * The returned string is in the form "CxF dphi" with C standing
+ * for the cross feed and F for the feed direction resolution.
+ * Units used are dots per 100 inches (dphi).
+ * </p>
+ * @return The string representation.
*/
public String toString()
{
@@ -203,14 +247,23 @@ public abstract class ResolutionSyntax
/**
* Returns the string representation for this object.
- *
+ * <p>
+ * The returned string is in the form "CxF U" with C standing
+ * for the cross feed and F for the feed direction resolution.
+ * U denotes the units name if one is supplied.
+ * </p>
+ *
* @param units the units to use
- * @param unitsName the name of the units
+ * @param unitsName the name of the units. If <code>null</code>
+ * it is ommitted from the string representation.
*
- * @return the string representation
+ * @return The string representation.
*/
public String toString(int units, String unitsName)
{
+ if (unitsName == null)
+ return getCrossFeedResolution(units) + "x" + getFeedResolution(units);
+
return ("" + getCrossFeedResolution(units)
+ "x" + getFeedResolution(units)
+ " " + unitsName);
diff --git a/javax/print/attribute/SetOfIntegerSyntax.java b/javax/print/attribute/SetOfIntegerSyntax.java
index 3990b66c5..4c0dd2f19 100644
--- a/javax/print/attribute/SetOfIntegerSyntax.java
+++ b/javax/print/attribute/SetOfIntegerSyntax.java
@@ -1,5 +1,5 @@
/* SetOfIntegerSyntax.java --
- Copyright (C) 2003, 2004 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2004, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -45,7 +45,55 @@ import java.util.Arrays;
import java.util.Comparator;
/**
- * @author Michael Koch
+ * <code>SetOfIntegerSyntax</code> is the abstract base class of all attribute
+ * classes which provide a set of non-negative integers as value (e.g. the
+ * page ranges to print) represented as single values or ranges of values.
+ * <p>
+ * A <code>SetOfIntegerSyntax</code> instance consists of an integer array of
+ * ranges. Ranges may have the same lower and upper bound representing a single
+ * integer value. Ranges with a lower bound greater than the upper bound are
+ * null ranges and discarded. Ranges may overlap in their values. In no case
+ * negative integers are allowed.
+ * </p>
+ * <p>
+ * There are several constructors available:
+ * <ul>
+ * <li><code>SetOfIntegerSyntax(int member)</code><br>
+ * Constructor for an instance with only one integer value.
+ * </li><br>
+ * <li><code>SetOfIntegerSyntax(int lowerBound, int upperBound)</code><br>
+ * Constructor for an instance with one range of integer values.
+ * </li><br>
+ * <li><code>SetOfIntegerSyntax(int[][] members)</code><br>
+ * Flexible constructor for an instance with several single integer values
+ * and/or several ranges of integer values. The allowed array form is an
+ * array of integer arrays of length one or two. Examples are:
+ * <code>int[0][]</code> for empty set of integers, <code>int[][] {{1}}</code>
+ * , <code>int[][] {{1,5}}</code>, <code>int[][] {{1,5},{7,9}}</code>,
+ * <code>int[][] {{3,7},{19}}</code>.
+ * </li><br>
+ * <li><code>SetOfIntegerSyntax(String s)</code><br>
+ * Flexible constructor for an instance with several single integer values
+ * and/or several ranges of integer values. The allowed String instance have
+ * to be a String with comma separated ranges of integer values or single
+ * values. Ranges are represented by two integer with a hypen (-) or colon (:)
+ * between the lower and upper bound value. Whitespace characters are ignored.
+ * Examples are: <code>""</code> for an empty set of integers,
+ * <code>"1"</code>, <code>"1-5"</code>, <code>"1-5,7-9"</code>,
+ * <code>"3-7,19"</code> and <code>"1:2,4"</code>.
+ * </li>
+ * </ul>
+ * </p>
+ * <p>
+ * <b>Internal storage:</b><br>
+ * The set of integers are stored internally in a normalized array form.
+ * In the normalized array form the set of integer ranges are represented
+ * in as few ranges as possible and overlapping ranges are merged. The ranges
+ * are always represented as an integer array of length two with ranges
+ * stored in {lower bound, upper bound} form. The ranges are stored in
+ * ascending order, without any null ranges.
+ * </p>
+ * @author Michael Koch (konqueror@gmx.de)
*/
public abstract class SetOfIntegerSyntax
implements Cloneable, Serializable
@@ -96,7 +144,7 @@ public abstract class SetOfIntegerSyntax
*
* @param member the member value
*
- * @exception IllegalArgumentException if member is < 0
+ * @exception IllegalArgumentException if member is &lt; 0
*/
protected SetOfIntegerSyntax(int member)
{
@@ -109,7 +157,8 @@ public abstract class SetOfIntegerSyntax
/**
* Creates a <code>SetOfIntegerSyntax</code> object.
*
- * @param members the members to use in this set
+ * @param members the members to use in this set. If
+ * <code>null</code> an empty set is created.
*
* @exception IllegalArgumentException if any element is invalid
* @exception NullPointerException if any element of members is null
@@ -176,55 +225,68 @@ public abstract class SetOfIntegerSyntax
return readAny;
}
+ /**
+ * Creates a <code>SetOfIntegerSyntax</code> object.
+ *
+ * @param s the members to use in this set in string form. If
+ * <code>null</code> an empty set is created.
+ *
+ * @exception IllegalArgumentException if any element is invalid
+ */
protected SetOfIntegerSyntax(String s)
{
- ArrayList vals = new ArrayList();
-
- StringCharacterIterator it = new StringCharacterIterator(s);
-
- while (true)
- {
- // Skip whitespace.
- if (skipWhitespace(it))
- break;
-
- // Parse integer.
- int index = it.getIndex();
- if (! skipNumber(it))
- throw new IllegalArgumentException();
- int[] item = new int[2];
- item[0] = Integer.parseInt(s.substring(index, it.getIndex()));
-
- if (! skipWhitespace(it))
+ if (s == null)
+ this.members = normalize(new int[0][], 0);
+ else
+ {
+ ArrayList vals = new ArrayList();
+
+ StringCharacterIterator it = new StringCharacterIterator(s);
+
+ while (true)
{
- char c = it.current();
- if (c == ':' || c == '-')
+ // Skip whitespace.
+ if (skipWhitespace(it))
+ break;
+
+ // Parse integer.
+ int index = it.getIndex();
+ if (! skipNumber(it))
+ throw new IllegalArgumentException();
+ int[] item = new int[2];
+ item[0] = Integer.parseInt(s.substring(index, it.getIndex()));
+
+ if (! skipWhitespace(it))
{
- it.next();
- if (skipWhitespace(it))
- throw new IllegalArgumentException();
- index = it.getIndex();
- if (! skipNumber(it))
- throw new IllegalArgumentException();
- item[1] = Integer.parseInt(s.substring(index, it.getIndex()));
+ char c = it.current();
+ if (c == ':' || c == '-')
+ {
+ it.next();
+ if (skipWhitespace(it))
+ throw new IllegalArgumentException();
+ index = it.getIndex();
+ if (! skipNumber(it))
+ throw new IllegalArgumentException();
+ item[1] = Integer.parseInt(s.substring(index, it.getIndex()));
+ }
+ else
+ item[1] = item[0];
}
else
item[1] = item[0];
+
+ if (item[0] <= item[1])
+ vals.add(item);
+
+ if (skipWhitespace(it))
+ break;
+ if (it.current() != ',')
+ throw new IllegalArgumentException();
+ it.next();
}
- else
- item[1] = item[0];
-
- if (item[0] <= item[1])
- vals.add(item);
- if (skipWhitespace(it))
- break;
- if (it.current() != ',')
- throw new IllegalArgumentException();
- it.next();
+ members = normalize((int[][]) vals.toArray(new int[0][]), vals.size());
}
-
- members = normalize((int[][]) vals.toArray(new int[0][]), vals.size());
}
/**
@@ -248,7 +310,7 @@ public abstract class SetOfIntegerSyntax
}
/**
- * Checks if this set contains value.
+ * Checks if this set contains the given value.
*
* @param value the value to test for
*
@@ -269,7 +331,7 @@ public abstract class SetOfIntegerSyntax
}
/**
- * Checks if this set contains value.
+ * Checks if this set contains the given value.
*
* @param value the value to test for
*
@@ -281,7 +343,7 @@ public abstract class SetOfIntegerSyntax
}
/**
- * Tests of obj is equal to this object.
+ * Tests if the given object is equal to this object.
*
* @param obj the object to test
*
@@ -306,7 +368,7 @@ public abstract class SetOfIntegerSyntax
/**
* Returns an array describing the members included in this set.
*
- * @return the array with the members
+ * @return The members in normalized array form.
*/
public int[][] getMembers()
{
@@ -316,7 +378,7 @@ public abstract class SetOfIntegerSyntax
/**
* Returns the hashcode for this object.
*
- * @return the hashcode
+ * @return The hashcode.
*/
public int hashCode()
{
@@ -331,7 +393,8 @@ public abstract class SetOfIntegerSyntax
*
* @param x an integer value
*
- * @return the next value
+ * @return The next smallest integer value, or <code>-1</code> if there
+ * is no greater integer in the set.
*/
public int next(int x)
{
@@ -349,8 +412,10 @@ public abstract class SetOfIntegerSyntax
/**
* Returns the string representation for this object.
+ * The value is a zero length string for an empty set, or a comma seperated
+ * list of ranges and single values in the form <code>"1-2,5-7,10"</code>.
*
- * @return the string representation
+ * @return The string representation.
*/
public String toString()
{
diff --git a/javax/print/attribute/Size2DSyntax.java b/javax/print/attribute/Size2DSyntax.java
index c8d6ec781..0b5c10070 100644
--- a/javax/print/attribute/Size2DSyntax.java
+++ b/javax/print/attribute/Size2DSyntax.java
@@ -1,5 +1,5 @@
/* Size2DSyntax.java --
- Copyright (C) 2003 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -40,21 +40,62 @@ package javax.print.attribute;
import java.io.Serializable;
/**
- * @author Michael Koch
+ * <code>Size2DSyntax</code> is the abstract base class of all attribute
+ * classes which provide a two dimensional size as value (e.g. the size of
+ * a media like Letter or A4).
+ * <p>
+ * A <code>Size2DSyntax</code> instance consists of two integer values
+ * describing the size in the x and y dimension. The units of
+ * the given values is determined by two defined constants:
+ * <ul>
+ * <li>INCH - defines an inch</li>
+ * <li>MM - defines a millimeter</li>
+ * </ul>
+ * </p>
+ * <p>
+ * A size 2D attribute is constructed by two values for the size of the x and
+ * y dimension and the actual units of the given values as defined by the
+ * constants.
+ * </p>
+ * <p>
+ * There are different methods provided to return the size values for the
+ * dimensions in either of the two predefined units or with a given client
+ * supplied units conversion factor.
+ * </p>
+ * <p>
+ * <b>Internal storage:</b><br>
+ * The size of the x,y dimensions are stored internally in micrometers. The
+ * values of the provided constants for inch (value 25400) and millimeters
+ * (value 1000) are used as conversion factors to the internal storage units.
+ * To get the internal micrometers values a multiplication of a given
+ * size value with its units constant value is done. Retrieving the size value
+ * for specific units is done by dividing the internal stored value by the
+ * units constant value. Clients are therefore able to provide their own
+ * size units by supplying other conversion factors.
+ * Subclasses of <code>Size2DSyntax</code> have access to the internal
+ * size values through the protected methods
+ * {@link #getXMicrometers()} and {@link #getYMicrometers()}.
+ * </p>
+ *
+ * @author Michael Koch (konqueror@gmx.de)
*/
public abstract class Size2DSyntax implements Cloneable, Serializable
{
/**
- * Constant for units of dots per mircometer to describe an inch.
+ * Constant for the units of inches.
+ * The actual value is the conversion factor to micrometers.
*/
public static final int INCH = 25400;
/**
- * Constant for units of dots per mircometer to describe a centimeter.
+ * Constant for the units of millimeters.
+ * The actual value is the conversion factor to micrometers.
*/
public static final int MM = 1000;
+ /** x size in micrometers. */
private int x;
+ /** y size in micrometers. */
private int y;
/**
@@ -64,7 +105,7 @@ public abstract class Size2DSyntax implements Cloneable, Serializable
* @param y the size in y direction
* @param units the units to use for the sizes
*
- * @exception IllegalArgumentException if preconditions fail
+ * @exception IllegalArgumentException if x or y &lt; 0 or units &lt; 1
*/
protected Size2DSyntax(float x, float y, int units)
{
@@ -85,7 +126,7 @@ public abstract class Size2DSyntax implements Cloneable, Serializable
* @param y the size in y direction
* @param units the units to use for the sizes
*
- * @exception IllegalArgumentException if preconditions fail
+ * @exception IllegalArgumentException if x or y &lt; 0 or units &lt; 1
*/
protected Size2DSyntax(int x, int y, int units)
{
@@ -100,11 +141,11 @@ public abstract class Size2DSyntax implements Cloneable, Serializable
}
/**
- * Tests of obj is equal to this object.
+ * Tests if the given object is equal to this object.
*
* @param obj the object to test
*
- * @returns true if both objects are equal, false otherwise.
+ * @return <code>true</code> if both objects are equal, <code>false</code> otherwise.
*/
public boolean equals(Object obj)
{
@@ -118,15 +159,15 @@ public abstract class Size2DSyntax implements Cloneable, Serializable
}
/**
- * Return the size described in this object as a two field array.
+ * Returns the size described in this object as a two field array.
* Index 0 contains the size in x direction, index 1 the size in
* y direction.
*
* @param units the units to use
*
- * @return the array that describes the size
+ * @return The array with the size dimensions.
*
- * @exception IllegalArgumentException if units < 1
+ * @exception IllegalArgumentException if units &lt; 1
*/
public float[] getSize(int units)
{
@@ -137,13 +178,13 @@ public abstract class Size2DSyntax implements Cloneable, Serializable
}
/**
- * Return the size in x direction.
+ * Returns the size in x direction.
*
* @param units the units to use
*
- * @return the size value
+ * @return The size in x direction.
*
- * @exception IllegalArgumentException if units < 1
+ * @exception IllegalArgumentException if units &lt; 1
*/
public float getX(int units)
{
@@ -155,8 +196,9 @@ public abstract class Size2DSyntax implements Cloneable, Serializable
/**
* Returns the size in x direction in mircometers.
+ * To be used by sublcasses that need access to the internal storage value.
*
- * @return the size value
+ * @return The size in x direction in micrometers.
*/
protected int getXMicrometers()
{
@@ -168,9 +210,9 @@ public abstract class Size2DSyntax implements Cloneable, Serializable
*
* @param units the units to use
*
- * @return the size value
+ * @return The size in y direction.
*
- * @exception IllegalArgumentException if units < 1
+ * @exception IllegalArgumentException if units &lt; 1
*/
public float getY(int units)
{
@@ -182,8 +224,9 @@ public abstract class Size2DSyntax implements Cloneable, Serializable
/**
* Returns the size in y direction in mircometers.
+ * To be used by sublcasses that need access to the internal storage value.
*
- * @return the size value
+ * @return The size in y direction in micrometers.
*/
protected int getYMicrometers()
{
@@ -193,7 +236,7 @@ public abstract class Size2DSyntax implements Cloneable, Serializable
/**
* Returns the hashcode for this object.
*
- * @return the hashcode
+ * @return The hashcode.
*/
public int hashCode()
{
@@ -202,24 +245,39 @@ public abstract class Size2DSyntax implements Cloneable, Serializable
/**
* Returns the string representation for this object.
- *
- * @return the string representation
+ * <p>
+ * The returned string is in the form "XxY um" with X standing
+ * for size in x and Y for the size in y direction. The used
+ * micrometers units is indicated by the appended "um" notation.
+ * </p>
+ *
+ * @return The string representation in micrometers.
*/
public String toString()
{
- return toString(1, "um");
+ return getXMicrometers() + "x" + getYMicrometers() + " um";
}
/**
* Returns the string representation for this object.
- *
+ * <p>
+ * The returned string is in the form "XxY U" with X standing
+ * for size in x and Y for the size in y direction. U denotes
+ * the units name if one is supplied. The values are given as
+ * floating point values.
+ * </p>
+ *
* @param units the units to use
- * @param unitsName the name of the units
+ * @param unitsName the name of the units. If <code>null</code>
+ * it is ommitted from the string representation.
*
- * @return the string representation
+ * @return The string representation.
*/
public String toString(int units, String unitsName)
{
- return "" + getX(units) + "x" + getY(units) + " " + unitsName;
+ if (unitsName == null)
+ return getX(units) + "x" + getY(units);
+
+ return getX(units) + "x" + getY(units) + " " + unitsName;
}
}
diff --git a/javax/print/attribute/SupportedValuesAttribute.java b/javax/print/attribute/SupportedValuesAttribute.java
index d0f4b65c6..a001e7e91 100644
--- a/javax/print/attribute/SupportedValuesAttribute.java
+++ b/javax/print/attribute/SupportedValuesAttribute.java
@@ -1,5 +1,5 @@
-/* Attribute.java --
- Copyright (C) 2003 Free Software Foundation, Inc.
+/* SupportedValuesAttribute.java --
+ Copyright (C) 2003, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -38,8 +38,22 @@ exception statement from your version. */
package javax.print.attribute;
/**
- * @author Michael Koch
+ * Marker interface for all attribute classes specifying the
+ * supported/allowed values for another printing attribute class.
+ * <p>
+ * A {@link javax.print.PrintService} instance for example provides
+ * printing attribute classes implementing this interface to indicate
+ * that a specific attribute type is supported and if the supported values.
+ * </p><p>
+ * E.g. a {@link javax.print.attribute.standard.JobPrioritySupported}
+ * instance indicates that the attribute class
+ * {@link javax.print.attribute.standard.JobPriority} is supported and
+ * provides the number of the possible priority levels.
+ * </p>
+ *
+ * @author Michael Koch (konqueror@gmx.de)
*/
public interface SupportedValuesAttribute extends Attribute
{
+ // Marker interface
}
diff --git a/javax/print/attribute/TextSyntax.java b/javax/print/attribute/TextSyntax.java
index 98fabdc67..2daab6ec3 100644
--- a/javax/print/attribute/TextSyntax.java
+++ b/javax/print/attribute/TextSyntax.java
@@ -1,5 +1,5 @@
/* TextSyntax.java --
- Copyright (C) 2003, 2004 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2004, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -41,7 +41,14 @@ import java.io.Serializable;
import java.util.Locale;
/**
- * @author Michael Koch
+ * <code>TextSyntax</code> is the abstract base class of all attribute
+ * classes which provide a string as value (e.g. the location of the printer).
+ * <p>
+ * A <code>TextSyntax</code> instance consists of a string value and a
+ * locale which indicates the language of the locale of the string.
+ * </p>
+ *
+ * @author Michael Koch (konqueror@gmx.de)
*/
public abstract class TextSyntax implements Cloneable, Serializable
{
@@ -55,23 +62,24 @@ public abstract class TextSyntax implements Cloneable, Serializable
* and locale.
*
* @param value the value for this syntax
- * @param locale the locale to use
+ * @param locale the locale to use, if <code>null</code> the default
+ * locale is used.
*
- * @exception NullPointerException if value and/or locale is null
+ * @exception NullPointerException if value is null
*/
protected TextSyntax(String value, Locale locale)
{
- if (value == null || locale == null)
- throw new NullPointerException("value and/or locale may not be null");
-
+ if (value == null)
+ throw new NullPointerException("value may not be null");
+
this.value = value;
- this.locale = locale;
+ this.locale = (locale == null ? Locale.getDefault() : locale);
}
/**
* Returns the value of this syntax object.
*
- * @return the value
+ * @return The value.
*/
public String getValue()
{
@@ -81,7 +89,7 @@ public abstract class TextSyntax implements Cloneable, Serializable
/**
* Returns the locale of this syntax object.
*
- * @return the locale
+ * @return The locale.
*/
public Locale getLocale()
{
@@ -91,7 +99,7 @@ public abstract class TextSyntax implements Cloneable, Serializable
/**
* Returns the hashcode for this object.
*
- * @return the hashcode
+ * @return The hashcode.
*/
public int hashCode()
{
@@ -99,7 +107,7 @@ public abstract class TextSyntax implements Cloneable, Serializable
}
/**
- * Tests of obj is equal to this object.
+ * Tests if the given object is equal to this object.
*
* @param obj the object to test
*
@@ -117,7 +125,10 @@ public abstract class TextSyntax implements Cloneable, Serializable
}
/**
- * Returns a string representing the object.
+ * Returns a string representing the object. The returned
+ * string is the underlying text value of this object.
+ *
+ * @return The string representation.
*/
public String toString()
{
diff --git a/javax/print/attribute/URISyntax.java b/javax/print/attribute/URISyntax.java
index f0583f7e5..07deb4b57 100644
--- a/javax/print/attribute/URISyntax.java
+++ b/javax/print/attribute/URISyntax.java
@@ -1,5 +1,5 @@
/* URISyntax.java --
- Copyright (C) 2003 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -41,7 +41,10 @@ import java.io.Serializable;
import java.net.URI;
/**
- * @author Michael Koch
+ * <code>URISyntax</code> is the abstract base class of all attribute
+ * classes having an Uniform Resource Identifier URI as value.
+ *
+ * @author Michael Koch (konqueror@gmx.de)
*/
public abstract class URISyntax
implements Cloneable, Serializable
@@ -66,11 +69,12 @@ public abstract class URISyntax
}
/**
- * Tests of obj is equal to this object.
+ * Tests if the given object is equal to this object.
*
* @param obj the object to test
*
- * @returns true if both objects are equal, false otherwise.
+ * @return <code>true</code> if both objects are equal,
+ * <code>false</code> otherwise.
*/
public boolean equals(Object obj)
{
@@ -83,7 +87,7 @@ public abstract class URISyntax
/**
* Returns the URI value of this syntax object.
*
- * @return the URI
+ * @return The URI.
*/
public URI getURI()
{
@@ -93,7 +97,7 @@ public abstract class URISyntax
/**
* Returns the hashcode for this object.
*
- * @return the hashcode
+ * @return The hashcode.
*/
public int hashCode()
{
@@ -103,7 +107,7 @@ public abstract class URISyntax
/**
* Returns the string representation for this object.
*
- * @return the string representation
+ * @return The string representation.
*/
public String toString()
{
diff --git a/javax/print/attribute/UnmodifiableSetException.java b/javax/print/attribute/UnmodifiableSetException.java
index 678531769..ed1687c4c 100644
--- a/javax/print/attribute/UnmodifiableSetException.java
+++ b/javax/print/attribute/UnmodifiableSetException.java
@@ -1,5 +1,5 @@
-/* Attribute.java --
- Copyright (C) 2003 Free Software Foundation, Inc.
+/* UnmodifiableSetException.java --
+ Copyright (C) 2003, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -35,10 +35,14 @@ this exception to your version of the library, but you are not
obligated to do so. If you do not wish to do so, delete this
exception statement from your version. */
+
package javax.print.attribute;
/**
- * @author Michael Koch
+ * Exception which is thrown if an operation on an unmodifiable set
+ * is invoked.
+ *
+ * @author Michael Koch (konqueror@gmx.de)
*
* @since 1.4
*/
@@ -56,7 +60,7 @@ public class UnmodifiableSetException extends RuntimeException
* Creates a <code>UnmodifiableSetException</code>
* with the given message.
*
- * @param message the message for the exception
+ * @param message the message of the exception
*/
public UnmodifiableSetException(String message)
{
diff --git a/javax/print/attribute/package.html b/javax/print/attribute/package.html
index ba67d1a79..37f24d56b 100644
--- a/javax/print/attribute/package.html
+++ b/javax/print/attribute/package.html
@@ -1,6 +1,6 @@
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 3.2 Final//EN">
<!-- package.html - describes classes in javax.print.attribute package.
- Copyright (C) 2003 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -40,7 +40,10 @@ exception statement from your version. -->
<head><title>GNU Classpath - javax.print.attribute</title></head>
<body>
-<p></p>
-
+<p>Provides classes and interfaces describing the roles and
+syntax of attribute objects in the Java Print Service API.</p>
+<p>
+<b>Since:</b> 1.4
+</p>
</body>
</html>
diff --git a/javax/print/attribute/standard/MediaName.java b/javax/print/attribute/standard/MediaName.java
new file mode 100644
index 000000000..a6dc3e63e
--- /dev/null
+++ b/javax/print/attribute/standard/MediaName.java
@@ -0,0 +1,86 @@
+/* MediaName.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+package javax.print.attribute.standard;
+
+import javax.print.attribute.EnumSyntax;
+
+/**
+ * An enumeration of media types, which may be used in alternative to MediaSize/MediaTray.
+ *
+ * @author Sven de Marothy
+ */
+public class MediaName extends Media
+{
+ /**
+ * Transparent A4
+ */
+ public static final MediaName ISO_A4_TRANSPARENT = new MediaName(0);
+
+ /**
+ * White A4
+ */
+ public static final MediaName ISO_A4_WHITE = new MediaName(1);
+
+ /**
+ * Transparent Letter
+ */
+ public static final MediaName NA_LETTER_TRANSPARENT = new MediaName(2);
+
+ /**
+ * White Letter
+ */
+ public static final MediaName NA_LETTER_WHITE = new MediaName(3);
+
+ protected MediaName(int i)
+ {
+ super( i );
+ }
+
+ protected EnumSyntax[] getEnumValueTable()
+ {
+ // FIXME
+ return (EnumSyntax[])null;
+ }
+
+ protected String[] getStringTable()
+ {
+ // FIXME
+ return (String[])null;
+ }
+}
+
diff --git a/javax/print/attribute/standard/MediaSize.java b/javax/print/attribute/standard/MediaSize.java
index 6abf97974..d1b35727a 100644
--- a/javax/print/attribute/standard/MediaSize.java
+++ b/javax/print/attribute/standard/MediaSize.java
@@ -111,4 +111,558 @@ public class MediaSize extends Size2DSyntax
{
return "media-size";
}
+
+ /**
+ * Container class for predefined ISO media sizes.
+ */
+ public static final class ISO
+ {
+
+ /**
+ * ISO A0 paper, 841 mm x 1189 mm.
+ */
+ public static final MediaSize A0 = new MediaSize(841, 1189,
+ MediaSize.MM,
+ MediaSizeName.ISO_A0);
+
+ /**
+ * ISO A1 paper, 594 mm x 841 mm
+ */
+ public static final MediaSize A1 = new MediaSize(594, 841, MediaSize.MM,
+ MediaSizeName.ISO_A1);
+
+ /**
+ * ISO A2 paper, 420 mm x 594 mm
+ */
+ public static final MediaSize A2 = new MediaSize(420, 594, MediaSize.MM, MediaSizeName.ISO_A2);
+
+ /**
+ * ISO A3 paper, 297 mm x 420 mm
+ */
+ public static final MediaSize A3 = new MediaSize(297, 420, MediaSize.MM, MediaSizeName.ISO_A3);
+
+ /**
+ * ISO A4 paper, 210 mm x 297 mm
+ */
+ public static final MediaSize A4 = new MediaSize(210, 297, MediaSize.MM, MediaSizeName.ISO_A4);
+
+ /**
+ * ISO A5 paper, 148 mm x 210 mm
+ */
+ public static final MediaSize A5 = new MediaSize(148, 210, MediaSize.MM, MediaSizeName.ISO_A5);
+
+ /**
+ * ISO A6 paper, 105 mm x 148 mm
+ */
+ public static final MediaSize A6 = new MediaSize(105, 148, MediaSize.MM, MediaSizeName.ISO_A6);
+
+ /**
+ * ISO A7 paper, 74 mm x 105 mm
+ */
+ public static final MediaSize A7 = new MediaSize(74, 105, MediaSize.MM, MediaSizeName.ISO_A7);
+
+ /**
+ * ISO A8 paper, 52 mm x 74 mm
+ */
+ public static final MediaSize A8 = new MediaSize(52, 74, MediaSize.MM, MediaSizeName.ISO_A8);
+
+ /**
+ * ISO A9 paper, 37 mm x 52 mm
+ */
+ public static final MediaSize A9 = new MediaSize(37, 52, MediaSize.MM, MediaSizeName.ISO_A9);
+
+ /**
+ * ISO A10 paper, 26 mm x 37 mm
+ */
+ public static final MediaSize A10 = new MediaSize(26, 37, MediaSize.MM, MediaSizeName.ISO_A10);
+
+
+ /**
+ * ISO B0 paper, 1000 mm x 1414 mm
+ */
+ public static final MediaSize B0 = new MediaSize(1000, 1414, MediaSize.MM, MediaSizeName.ISO_B0);
+
+ /**
+ * ISO B1 paper, 707 mm x 1000 mm
+ */
+ public static final MediaSize B1 = new MediaSize(707, 1000, MediaSize.MM, MediaSizeName.ISO_B1);
+
+ /**
+ * ISO B2 paper, 500 mm x 707 mm
+ */
+ public static final MediaSize B2 = new MediaSize(500, 707, MediaSize.MM, MediaSizeName.ISO_B2);
+
+ /**
+ * ISO B3 paper, 353 mm x 500 mm
+ */
+ public static final MediaSize B3 = new MediaSize(353, 500, MediaSize.MM, MediaSizeName.ISO_B3);
+
+ /**
+ * ISO B4 paper, 250 mm x 353 mm
+ */
+ public static final MediaSize B4 = new MediaSize(250, 353, MediaSize.MM, MediaSizeName.ISO_B4);
+
+ /**
+ * ISO B5 paper, 176 mm x 250 mm
+ */
+ public static final MediaSize B5 = new MediaSize(176, 250, MediaSize.MM, MediaSizeName.ISO_B5);
+
+ /**
+ * ISO B6 paper, 125 mm x 176 mm
+ */
+ public static final MediaSize B6 = new MediaSize(125, 176, MediaSize.MM, MediaSizeName.ISO_B6);
+
+ /**
+ * ISO B7 paper, 88 mm x 125 mm
+ */
+ public static final MediaSize B7 = new MediaSize(88, 125, MediaSize.MM, MediaSizeName.ISO_B7);
+
+ /**
+ * ISO B8 paper, 62 mm x 88 mm
+ */
+ public static final MediaSize B8 = new MediaSize(62, 88, MediaSize.MM, MediaSizeName.ISO_B8);
+
+ /**
+ * ISO B9 paper, 44 mm x 62 mm
+ */
+ public static final MediaSize B9 = new MediaSize(44, 62, MediaSize.MM, MediaSizeName.ISO_B9);
+
+ /**
+ * ISO B10 paper, 31 mm x 44 mm
+ */
+ public static final MediaSize B10 = new MediaSize(31, 44, MediaSize.MM, MediaSizeName.ISO_B10);
+
+ /**
+ * ISO C3 envelope, 324 mm x 458 mm
+ */
+ public static final MediaSize C3 = new MediaSize(324, 458, MediaSize.MM, MediaSizeName.ISO_C3);
+
+ /**
+ * ISO C4 envelope, 229 mm x 324 mm
+ */
+ public static final MediaSize C4 = new MediaSize(229, 324, MediaSize.MM, MediaSizeName.ISO_C4);
+
+ /**
+ * ISO C5 envelope, 162 mm x 229 mm
+ */
+ public static final MediaSize C5 = new MediaSize(162, 229, MediaSize.MM, MediaSizeName.ISO_C5);
+
+ /**
+ * ISO C6 envelope, 114 mm x 162 mm
+ */
+ public static final MediaSize C6 = new MediaSize(114, 162, MediaSize.MM, MediaSizeName.ISO_C6);
+
+ /**
+ * ISO ISO Designated Long paper, 324 mm x 458 mm
+ */
+ public static final MediaSize DESIGNATED_LONG =
+ new MediaSize(324, 458, MediaSize.MM, MediaSizeName.ISO_DESIGNATED_LONG);
+ }
+
+ /**
+ * Container class for predefined North American media sizes.
+ */
+ public static final class NA
+ {
+ /**
+ * US Legal paper size, 8.5 inch x 14 inch
+ */
+ public static final MediaSize LEGAL = new MediaSize(8.5f, 14f, MediaSize.INCH,
+ MediaSizeName.NA_LEGAL);
+
+ /**
+ * US Letter paper size, 8.5 inch x 11 inch
+ */
+ public static final MediaSize LETTER = new MediaSize(8.5f, 11f, MediaSize.INCH,
+ MediaSizeName.NA_LETTER);
+
+ /**
+ * 5 inch x 7 inch paper size.
+ */
+ public static final MediaSize NA_5X7 = new MediaSize(5, 7, MediaSize.INCH,
+ MediaSizeName.NA_5X7);
+
+ /**
+ * 8 inch x 10 inch paper size.
+ */
+ public static final MediaSize NA_8X10 = new MediaSize(8, 10, MediaSize.INCH,
+ MediaSizeName.NA_8X10);
+
+ /**
+ * 6 inch x 9 inch envelope size.
+ */
+ public static final MediaSize NA_6X9_ENVELOPE = new MediaSize(6f, 9f,
+ MediaSize.INCH,
+ MediaSizeName.NA_6X9_ENVELOPE);
+
+ /**
+ * 7 inch x 9 inch envelope size.
+ */
+ public static final MediaSize NA_7X9_ENVELOPE = new MediaSize(7f, 9f,
+ MediaSize.INCH,
+ MediaSizeName.NA_7X9_ENVELOPE);
+
+ /**
+ * 9 inch x 11 inch envelope size.
+ */
+ public static final MediaSize NA_9x11_ENVELOPE = new MediaSize(9f, 11f,
+ MediaSize.INCH,
+ MediaSizeName.NA_9X11_ENVELOPE);
+
+ /**
+ * 9 inch x 12 inch envelope size.
+ */
+ public static final MediaSize NA_9x12_ENVELOPE = new MediaSize(9f, 12f,
+ MediaSize.INCH,
+ MediaSizeName.NA_9X12_ENVELOPE);
+
+
+ /**
+ * 10 inch x 13 inch envelope size.
+ */
+ public static final MediaSize NA_10x13_ENVELOPE = new MediaSize(10f, 13f,
+ MediaSize.INCH,
+ MediaSizeName.NA_10X13_ENVELOPE);
+
+ /**
+ * 10 inch x 14 inch envelope size.
+ */
+ public static final MediaSize NA_10x14_ENVELOPE = new MediaSize(10f, 14f,
+ MediaSize.INCH,
+ MediaSizeName.NA_10X14_ENVELOPE);
+
+ /**
+ * 10 inch x 15 inch envelope size.
+ */
+ public static final MediaSize NA_10X15_ENVELOPE = new MediaSize(10f, 15f,
+ MediaSize.INCH,
+ MediaSizeName.NA_10X15_ENVELOPE);
+
+ /**
+ * Number 9 envelope size. 4.5 inch x 10.375 inch
+ */
+ public static final MediaSize NA_NUMBER_9_ENVELOPE = new MediaSize(3.875f, 8.875f,
+ MediaSize.INCH,
+ MediaSizeName.NA_NUMBER_9_ENVELOPE);
+
+ /**
+ * Number 10 envelope size. 4.125 inch x 9.5 inch
+ */
+ public static final MediaSize NA_NUMBER_10_ENVELOPE =
+ new MediaSize(4.125f, 9.5f, MediaSize.INCH, MediaSizeName.NA_NUMBER_10_ENVELOPE);
+
+ /**
+ * Number 11 envelope size. 4.5 inch x 10.375 inch
+ */
+ public static final MediaSize NA_NUMBER_11_ENVELOPE = new MediaSize(4.5f, 10.375f, MediaSize.INCH,
+ MediaSizeName.NA_NUMBER_11_ENVELOPE);
+
+ /**
+ * Number 12 envelope size. 4.75 inch x 11 inch
+ */
+ public static final MediaSize NA_NUMBER_12_ENVELOPE = new MediaSize(4.75f, 11f,
+ MediaSize.INCH,
+ MediaSizeName.NA_NUMBER_12_ENVELOPE);
+
+ /**
+ * Number 14 envelope size. 5 inch x 11.5 inch
+ */
+ public static final MediaSize NA_NUMBER_14_ENVELOPE = new MediaSize(5f, 11.5f,
+ MediaSize.INCH,
+ MediaSizeName.NA_NUMBER_14_ENVELOPE);
+ }
+
+ /**
+ * Container class for predefined US Engineering media sizes.
+ */
+ public static final class Engineering
+ {
+ /**
+ * ANSI A paper size. 8.5 inch x 11 inch
+ */
+ public static final MediaSize A = new MediaSize(8.5f, 11f,
+ MediaSize.INCH, MediaSizeName.A);
+
+ /**
+ * ANSI B paper size. 11 inch x 17 inch
+ */
+ public static final MediaSize B = new MediaSize(11f, 17f,
+ MediaSize.INCH, MediaSizeName.B);
+
+ /**
+ * ANSI C paper size. 17 inch x 22 inch
+ */
+ public static final MediaSize C = new MediaSize(17f, 22f,
+ MediaSize.INCH, MediaSizeName.C);
+
+ /**
+ * ANSI D paper size. 22 inch x 34 inch
+ */
+ public static final MediaSize D = new MediaSize(22f, 34f,
+ MediaSize.INCH, MediaSizeName.D);
+
+ /**
+ * ANSI E paper size. 33 inch x 44 inch
+ */
+ public static final MediaSize E = new MediaSize(34f, 44f,
+ MediaSize.INCH, MediaSizeName.E);
+ }
+
+ /**
+ * Container class for predefined Japanese JIS media sizes.
+ */
+ public static final class JIS
+ {
+ /**
+ * JIS B0 paper. 1030 mm x 1456 mm
+ * Note: The JIS B-series is not identical to the ISO B-series.
+ */
+ public static final MediaSize B0 = new MediaSize(1030, 1456, MediaSize.MM, MediaSizeName.JIS_B0);
+
+ /**
+ * JIS B1 paper. 1030 mm x 1456 mm
+ * Note: The JIS B-series is not identical to the ISO B-series.
+ */
+ public static final MediaSize B1 = new MediaSize(728, 1030, MediaSize.MM, MediaSizeName.JIS_B1);
+
+ /**
+ * JIS B2 paper. 515 mm x 728 mm
+ * Note: The JIS B-series is not identical to the ISO B-series.
+ */
+ public static final MediaSize B2 = new MediaSize(515, 728, MediaSize.MM, MediaSizeName.JIS_B2);
+
+ /**
+ * JIS B3 paper. 364 mm x 515 mm
+ * Note: The JIS B-series is not identical to the ISO B-series.
+ */
+ public static final MediaSize B3 = new MediaSize(364, 515, MediaSize.MM, MediaSizeName.JIS_B3);
+
+ /**
+ * JIS B4 paper. 257 mm x 364 mm
+ * Note: The JIS B-series is not identical to the ISO B-series.
+ */
+ public static final MediaSize B4 = new MediaSize(257, 364, MediaSize.MM, MediaSizeName.JIS_B4);
+
+ /**
+ * JIS B5 paper. 1030 mm x 1456 mm
+ * Note: The JIS B-series is not identical to the ISO B-series.
+ */
+ public static final MediaSize B5 = new MediaSize(182, 257, MediaSize.MM, MediaSizeName.JIS_B5);
+
+ /**
+ * JIS B6 paper. 128 mm x 182 mm
+ * Note: The JIS B-series is not identical to the ISO B-series.
+ */
+ public static final MediaSize B6 = new MediaSize(128, 182, MediaSize.MM, MediaSizeName.JIS_B6);
+
+ /**
+ * JIS B7 paper. 91 mm x 128 mm
+ * Note: The JIS B-series is not identical to the ISO B-series.
+ */
+ public static final MediaSize B7 = new MediaSize(91, 128, MediaSize.MM, MediaSizeName.JIS_B7);
+
+ /**
+ * JIS B8 paper. 64 mm x 91 mm
+ * Note: The JIS B-series is not identical to the ISO B-series.
+ */
+ public static final MediaSize B8 = new MediaSize(64, 91, MediaSize.MM, MediaSizeName.JIS_B8);
+
+ /**
+ * JIS B9 paper. 45 mm x 64 mm
+ * Note: The JIS B-series is not identical to the ISO B-series.
+ */
+ public static final MediaSize B9 = new MediaSize(45, 64, MediaSize.MM, MediaSizeName.JIS_B9);
+
+ /**
+ * JIS B10 paper. 32 mm x 45 mm
+ * Note: The JIS B-series is not identical to the ISO B-series.
+ */
+ public static final MediaSize B10 = new MediaSize(32, 45, MediaSize.MM, MediaSizeName.JIS_B10);
+
+ /**
+ * JIS chou #1 envelope size, 142 mm x 332 mm
+ */
+ public static final MediaSize CHOU_1 = new MediaSize(142, 332, MediaSize.MM);
+
+ /**
+ * JIS chou #2 envelope size, 119 mm x 227 mm
+ */
+ public static final MediaSize CHOU_2 = new MediaSize(119, 227, MediaSize.MM);
+
+ /**
+ * JIS chou #3 envelope size, 120 mm x 235 mm
+ */
+ public static final MediaSize CHOU_3 = new MediaSize(120, 235, MediaSize.MM);
+
+ /**
+ * JIS chou #4 envelope size, 90 mm x 205 mm
+ */
+ public static final MediaSize CHOU_4 = new MediaSize(90, 205, MediaSize.MM);
+
+ /**
+ * JIS chou #30 envelope size, 92 mm x 235 mm
+ */
+ public static final MediaSize CHOU_30 = new MediaSize(92, 235, MediaSize.MM);
+
+ /**
+ * JIS chou #40 envelope size, 90 mm x 225 mm
+ */
+ public static final MediaSize CHOU_40 = new MediaSize(90, 225, MediaSize.MM);
+
+ /**
+ * JIS kaku #0 envelope size, 287 mm x 382 mm
+ */
+ public static final MediaSize KAKU_0 = new MediaSize(287, 382, MediaSize.MM);
+
+ /**
+ * JIS kaku #1 envelope size, 270 mm x 382 mm
+ */
+ public static final MediaSize KAKU_1 = new MediaSize(270, 382, MediaSize.MM);
+
+ /**
+ * JIS kaku #2 envelope size, 240 mm x 332 mm
+ */
+ public static final MediaSize KAKU_2 = new MediaSize(240, 332, MediaSize.MM);
+
+ /**
+ * JIS kaku #20 envelope size, 229 mm x 324 mm
+ */
+ public static final MediaSize KAKU_20 = new MediaSize(229, 324, MediaSize.MM);
+
+ /**
+ * JIS kaku #3 envelope size, 216 mm x 227 mm
+ */
+ public static final MediaSize KAKU_3 = new MediaSize(216, 227, MediaSize.MM);
+
+ /**
+ * JIS kaku #4 envelope size, 197 mm x 267 mm
+ */
+ public static final MediaSize KAKU_4 = new MediaSize(197, 267, MediaSize.MM);
+
+ /**
+ * JIS kaku #5 envelope size, 190 mm x 240 mm
+ */
+ public static final MediaSize KAKU_5 = new MediaSize(190, 240, MediaSize.MM);
+
+ /**
+ * JIS kaku #6 envelope size, 162 mm x 229 mm
+ */
+ public static final MediaSize KAKU_6 = new MediaSize(162, 229, MediaSize.MM);
+
+ /**
+ * JIS kaku #7 envelope size, 142 mm x 205 mm
+ */
+ public static final MediaSize KAKU_7 = new MediaSize(142, 205, MediaSize.MM);
+
+ /**
+ * JIS kaku #8 envelope size, 119 mm x 197 mm
+ */
+ public static final MediaSize KAKU_8 = new MediaSize(119, 197, MediaSize.MM);
+
+ /**
+ * JIS kaku A4 envelope size, 228 mm x 312 mm
+ */
+ public static final MediaSize KAKU_A4 = new MediaSize(228, 312, MediaSize.MM);
+
+ /**
+ * JIS you #1 envelope size, 120 mm x 176 mm
+ */
+ public static final MediaSize YOU_1 = new MediaSize(120, 176, MediaSize.MM);
+
+ /**
+ * JIS you #2 envelope size, 114 mm x 162 mm
+ */
+ public static final MediaSize YOU_2 = new MediaSize(114, 162, MediaSize.MM);
+
+ /**
+ * JIS you #3 envelope size, 98 mm x 148 mm
+ */
+ public static final MediaSize YOU_3 = new MediaSize(98, 148, MediaSize.MM);
+
+ /**
+ * JIS you #4 envelope size, 105 mm x 235 mm
+ */
+ public static final MediaSize YOU_4 = new MediaSize(105, 235, MediaSize.MM);
+
+ /**
+ * JIS you #5 envelope size, 95 mm x 217 mm
+ */
+ public static final MediaSize YOU_5 = new MediaSize(95, 217, MediaSize.MM);
+
+ /**
+ * JIS you #6 envelope size, 98 mm x 190 mm
+ */
+ public static final MediaSize YOU_6 = new MediaSize(98, 190, MediaSize.MM);
+
+ /**
+ * JIS you #7 envelope size, 92 mm x 165 mm
+ */
+ public static final MediaSize YOU_7 = new MediaSize(92, 165, MediaSize.MM);
+ }
+
+ /**
+ * Container class for miscellaneous media sizes.
+ */
+ public static final class Other
+ {
+ /**
+ * US Executive paper size, 7.25 inch x 10.5 inch
+ */
+ public static final MediaSize EXECUTIVE = new MediaSize(7.25f, 10.5f,
+ MediaSize.INCH, MediaSizeName.EXECUTIVE);
+
+ /**
+ * US Folio paper size, 8.5 inch x 13 inch
+ */
+ public static final MediaSize FOLIO = new MediaSize(8.5f, 13f, MediaSize.INCH, MediaSizeName.FOLIO);
+
+ /**
+ * US Quarto paper size, 8.5 inches by 10.83 inches.
+ */
+ public static final MediaSize QUARTO = new MediaSize(8.5f, 10.83f, MediaSize.INCH,
+ MediaSizeName.QUARTO);
+
+ /**
+ * US Invoice size, 5.5 inch x 8.5 inch
+ */
+ public static final MediaSize INVOICE = new MediaSize(5.5f, 8.5f,
+ MediaSize.INCH, MediaSizeName.INVOICE);
+
+ /**
+ * US Ledger size, 11 inch x 17 inch
+ */
+ public static final MediaSize LEDGER = new MediaSize(11, 17, MediaSize.INCH,
+ MediaSizeName.LEDGER);
+
+ /**
+ * Monarch (7 3/4) envelope size, 3.87 inch x 7.5 inch
+ */
+ public static final MediaSize MONARCH_ENVELOPE = new MediaSize(3.87f, 7.5f,
+ MediaSize.INCH,
+ MediaSizeName.MONARCH_ENVELOPE);
+
+ /**
+ * Personal envelope size, 3.625 inch x 6.5 inch.
+ */
+ public static final MediaSize PERSONAL_ENVELOPE = new MediaSize(3.625f, 6.5f, MediaSize.INCH,
+ MediaSizeName.PERSONAL_ENVELOPE);
+
+ /**
+ * Italian envelope size, 110 mm x 230 mm
+ */
+ public static final MediaSize ITALY_ENVELOPE = new MediaSize(110, 230,
+ MediaSize.MM,
+ MediaSizeName.ITALY_ENVELOPE);
+
+ /**
+ * Japanese postcard, 100 mm x 148 mm
+ */
+ public static final MediaSize JAPANESE_POSTCARD = new MediaSize(100, 148, MediaSize.MM, MediaSizeName.JAPANESE_POSTCARD);
+
+ /**
+ * Japanese double postcard, 148 mm x 200 mm
+ */
+ public static final MediaSize JAPANESE_DOUBLE_POSTCARD = new MediaSize(148, 200, MediaSize.MM, MediaSizeName.JAPANESE_DOUBLE_POSTCARD);
+ }
}
+
diff --git a/javax/print/attribute/standard/MediaSizeName.java b/javax/print/attribute/standard/MediaSizeName.java
index 9990a2def..ed345163d 100644
--- a/javax/print/attribute/standard/MediaSizeName.java
+++ b/javax/print/attribute/standard/MediaSizeName.java
@@ -37,7 +37,11 @@ exception statement from your version. */
package javax.print.attribute.standard;
+import javax.print.attribute.EnumSyntax;
+
/**
+ * An enumeration of media size names, conforming to RFC 2911.
+ *
* @author Michael Koch (konqueror@gmx.de)
*/
public class MediaSizeName extends Media
@@ -132,4 +136,16 @@ public class MediaSizeName extends Media
{
super(value);
}
+
+ protected EnumSyntax[] getEnumValueTable()
+ {
+ // FIXME
+ return null;
+ }
+
+ protected String[] getStringTable()
+ {
+ // FIXME
+ return null;
+ }
}
diff --git a/javax/print/attribute/standard/MediaTray.java b/javax/print/attribute/standard/MediaTray.java
new file mode 100644
index 000000000..36e11b259
--- /dev/null
+++ b/javax/print/attribute/standard/MediaTray.java
@@ -0,0 +1,106 @@
+/* MediaTray.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+package javax.print.attribute.standard;
+
+import javax.print.attribute.EnumSyntax;
+
+/**
+ * An enumeration of input tray parameters.
+ *
+ * @author Sven de Marothy
+ */
+public class MediaTray extends Media
+{
+ /**
+ * Bottom tray
+ */
+ public static final MediaTray BOTTOM = new MediaTray(0);
+
+ /**
+ * Envelope tray
+ */
+ public static final MediaTray ENVELOPE = new MediaTray(1);
+
+ /**
+ * Large capacity tray
+ */
+ public static final MediaTray LARGE_CAPACITY = new MediaTray(2);
+
+ /**
+ * Main tray
+ */
+ public static final MediaTray MAIN = new MediaTray(3);
+
+ /**
+ * Manual-feed tray
+ */
+ public static final MediaTray MANUAL = new MediaTray(4);
+
+ /**
+ * Middle tray
+ */
+ public static final MediaTray MIDDLE = new MediaTray(5);
+
+ /**
+ * Side tray
+ */
+ public static final MediaTray SIDE = new MediaTray(6);
+
+ /**
+ * Top tray
+ */
+ public static final MediaTray TOP = new MediaTray(7);
+
+ protected MediaTray(int i)
+ {
+ super( i );
+ }
+
+ protected EnumSyntax[] getEnumValueTable()
+ {
+ // FIXME
+ return (EnumSyntax[])null;
+ }
+
+ protected String[] getStringTable()
+ {
+ // FIXME
+ return (String[])null;
+ }
+}
+
diff --git a/javax/print/event/PrintEvent.java b/javax/print/event/PrintEvent.java
index cbf93852c..d44c20668 100644
--- a/javax/print/event/PrintEvent.java
+++ b/javax/print/event/PrintEvent.java
@@ -1,5 +1,5 @@
/* PrintEvent.java --
- Copyright (C) 2004 Free Software Foundation, Inc.
+ Copyright (C) 2004, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -41,6 +41,8 @@ import java.util.EventObject;
/**
+ * Superclass of all events in the Java Print Service API.
+ *
* @author Michael Koch (konqueror@gmx.de)
*/
public class PrintEvent extends EventObject
@@ -58,7 +60,7 @@ public class PrintEvent extends EventObject
/**
* Returns a string representation of this object.
*
- * @return the string representation
+ * @return The string representation
*/
public String toString()
{
diff --git a/javax/print/event/PrintJobAdapter.java b/javax/print/event/PrintJobAdapter.java
index 3615108f9..9229d195f 100644
--- a/javax/print/event/PrintJobAdapter.java
+++ b/javax/print/event/PrintJobAdapter.java
@@ -1,5 +1,5 @@
/* PrintJobAdapter.java --
- Copyright (C) 2004 Free Software Foundation, Inc.
+ Copyright (C) 2004, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -39,6 +39,11 @@ package javax.print.event;
/**
+ * Adapter class for implementing {@link javax.print.event.PrintJobListener}
+ * classes. The methods in this class do nothing by default. Subclasses may
+ * only implement the methods for the {@link javax.print.event.PrintJobEvent}s
+ * they are interested in.
+ *
* @author Michael Koch (konqueror@gmx.de)
*/
public abstract class PrintJobAdapter
@@ -53,10 +58,11 @@ public abstract class PrintJobAdapter
}
/**
- * Called to notify the client that all data has bin successfully transferred
+ * Called to notify the client that all data has been successfully transferred
* to the print service.
+ * <p>The default implementation does nothing.</p>
*
- * <p>The default implementation does nothing</p>
+ * @param event the event.
*/
public void printDataTransferCompleted(PrintJobEvent event)
{
@@ -64,9 +70,10 @@ public abstract class PrintJobAdapter
}
/**
- * Called to notify the client that a print job was canceled.
+ * Called to notify the client that a print job was canceled.
+ * <p>The default implementation does nothing.</p>
*
- * <p>The default implementation does nothing</p>
+ * @param event the event.
*/
public void printJobCanceled(PrintJobEvent event)
{
@@ -75,8 +82,9 @@ public abstract class PrintJobAdapter
/**
* Called to notify the client that a print job was successfully completed.
+ * <p>The default implementation does nothing.</p>
*
- * <p>The default implementation does nothing</p>
+ * @param event the event.
*/
public void printJobCompleted(PrintJobEvent event)
{
@@ -86,8 +94,9 @@ public abstract class PrintJobAdapter
/**
* Called to notify the client that a print job failed to complete
* successfully.
+ * <p>The default implementation does nothing.</p>
*
- * <p>The default implementation does nothing</p>
+ * @param event the event.
*/
public void printJobFailed(PrintJobEvent event)
{
@@ -96,8 +105,9 @@ public abstract class PrintJobAdapter
/**
* Called to notify the client that no more job events will be send.
+ * <p>The default implementation does nothing.</p>
*
- * <p>The default implementation does nothing</p>
+ * @param event the event.
*/
public void printJobNoMoreEvents(PrintJobEvent event)
{
@@ -105,10 +115,12 @@ public abstract class PrintJobAdapter
}
/**
- * Called to notify the client that a problem occured during printing
- * but the user may be able to fix it.
+ * Called to notify the client that a problem occured during printing.
+ * This event signals problems a user might be able to fix
+ * (e.g. out of paper or paper jam).
+ * <p>The default implementation does nothing.</p>
*
- * <p>The default implementation does nothing</p>
+ * @param event the event.
*/
public void printJobRequiresAttention(PrintJobEvent event)
{
diff --git a/javax/print/event/PrintJobAttributeEvent.java b/javax/print/event/PrintJobAttributeEvent.java
index 0914aea9f..d401ab151 100644
--- a/javax/print/event/PrintJobAttributeEvent.java
+++ b/javax/print/event/PrintJobAttributeEvent.java
@@ -1,5 +1,5 @@
/* PrintJobAttributeEvent.java --
- Copyright (C) 2004 Free Software Foundation, Inc.
+ Copyright (C) 2004, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -42,6 +42,10 @@ import javax.print.attribute.PrintJobAttributeSet;
/**
+ * <code>PrintJobAttributeEvent</code>s are generated by a
+ * <code>PrintService</code> to inform registered listeners that attributes
+ * associated with a {@link javax.print.DocPrintJob} instance have changed.
+ *
* @author Michael Koch (konqueror@gmx.de)
*/
public class PrintJobAttributeEvent extends PrintEvent
@@ -66,7 +70,7 @@ public class PrintJobAttributeEvent extends PrintEvent
/**
* Returns the print job generating this event.
*
- * @return the print job
+ * @return The print job.
*/
public DocPrintJob getPrintJob()
{
@@ -76,7 +80,7 @@ public class PrintJobAttributeEvent extends PrintEvent
/**
* Returns the attributes that changed and their new values.
*
- * @return the changes attributes
+ * @return The changed attributes.
*/
public PrintJobAttributeSet getAttributes()
{
diff --git a/javax/print/event/PrintJobAttributeListener.java b/javax/print/event/PrintJobAttributeListener.java
index ee816d22a..9f96d267e 100644
--- a/javax/print/event/PrintJobAttributeListener.java
+++ b/javax/print/event/PrintJobAttributeListener.java
@@ -1,5 +1,5 @@
/* PrintJobAttributeListener.java --
- Copyright (C) 2004 Free Software Foundation, Inc.
+ Copyright (C) 2004, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -39,6 +39,10 @@ package javax.print.event;
/**
+ * Listener interface to receive attribute changes from a print job.
+ * Implementations of this interface can be registered with a
+ * {@link javax.print.DocPrintJob} instance.
+ *
* @author Michael Koch (konqueror@gmx.de)
*/
public interface PrintJobAttributeListener
diff --git a/javax/print/event/PrintJobEvent.java b/javax/print/event/PrintJobEvent.java
index c4b7cd6f9..cc15f9753 100644
--- a/javax/print/event/PrintJobEvent.java
+++ b/javax/print/event/PrintJobEvent.java
@@ -1,5 +1,5 @@
/* PrintEvent.java --
- Copyright (C) 2004 Free Software Foundation, Inc.
+ Copyright (C) 2004, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -41,19 +41,38 @@ import javax.print.DocPrintJob;
/**
+ * <code>PrintJobEvent</code>s are generated by a print job during
+ * print job processing to inform registered listeners about the state
+ * of processing.
+ *
* @author Michael Koch (konqueror@gmx.de)
*/
public class PrintJobEvent extends PrintEvent
{
private static final long serialVersionUID = -1711656903622072997L;
-
+
+ /** Indicates that the data transfer to the print service has completed. */
public static final int DATA_TRANSFER_COMPLETE = 106;
+
+ /** Indicates that the print job was canceled. */
public static final int JOB_CANCELED = 101;
+
+ /** Indicates that the print job was completed (=printed). */
public static final int JOB_COMPLETE = 102;
+
+ /** Indicates that the print job failed to complete. */
public static final int JOB_FAILED = 103;
+
+ /** Indicates that no more job events will be send.*/
public static final int NO_MORE_EVENTS = 105;
+
+ /**
+ * Indicates a situation where human intervention might be needed.
+ * E.g. the printer run out of paper or a paper jam occured.
+ */
public static final int REQUIRES_ATTENTION = 104;
+ /** The reason (one of the defined constants). */
private int reason;
/**
@@ -71,7 +90,7 @@ public class PrintJobEvent extends PrintEvent
/**
* Returns the reason for this event.
*
- * @return the reason
+ * @return The reason.
*/
public int getPrintEventType()
{
@@ -81,7 +100,7 @@ public class PrintJobEvent extends PrintEvent
/**
* Returns the print job that generated this event.
*
- * @return the print job
+ * @return The print job.
*/
public DocPrintJob getPrintJob()
{
diff --git a/javax/print/event/PrintJobListener.java b/javax/print/event/PrintJobListener.java
index d1dcf42be..96c6d411d 100644
--- a/javax/print/event/PrintJobListener.java
+++ b/javax/print/event/PrintJobListener.java
@@ -1,5 +1,5 @@
/* PrintJobListener.java --
- Copyright (C) 2004 Free Software Foundation, Inc.
+ Copyright (C) 2004, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -39,7 +39,14 @@ package javax.print.event;
/**
- * @author Michael Koch (konqueror@gmx.de) */
+ * Listener interface to receive processing events from a print job.
+ * Implementations of this interface can be registered with a
+ * {@link javax.print.DocPrintJob} instance.
+ *
+ * @see javax.print.event.PrintJobAdapter
+ *
+ * @author Michael Koch (konqueror@gmx.de)
+ */
public interface PrintJobListener
{
/**
@@ -79,7 +86,9 @@ public interface PrintJobListener
void printJobNoMoreEvents(PrintJobEvent event);
/**
- * Notifies the listener that an error occured and the user might be able to fix it.
+ * Notifies the listener that a problem occured during printing.
+ * This event signals problems a user might be able to fix
+ * (e.g. out of paper or paper jam).
*
* @param event the event
*/
diff --git a/javax/print/event/PrintServiceAttributeEvent.java b/javax/print/event/PrintServiceAttributeEvent.java
index d3981747f..a41e213ff 100644
--- a/javax/print/event/PrintServiceAttributeEvent.java
+++ b/javax/print/event/PrintServiceAttributeEvent.java
@@ -1,5 +1,5 @@
/* PrintServiceAttributeEvent.java --
- Copyright (C) 2004 Free Software Foundation, Inc.
+ Copyright (C) 2004, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -42,6 +42,10 @@ import javax.print.attribute.PrintServiceAttributeSet;
/**
+ * <code>PrintServiceAttributeEvent</code>s are generated by a
+ * <code>PrintService</code> to inform registered listeners that
+ * its associated attributes have changed.
+ *
* @author Michael Koch (konqueror@gmx.de)
*/
public class PrintServiceAttributeEvent extends PrintEvent
@@ -64,7 +68,7 @@ public class PrintServiceAttributeEvent extends PrintEvent
/**
* Returns the print service that generated this event.
*
- * @return the print service
+ * @return The print service.
*/
public PrintService getPrintService()
{
@@ -74,7 +78,7 @@ public class PrintServiceAttributeEvent extends PrintEvent
/**
* Returns the changed attributes this event reports.
*
- * @return the changed attributes
+ * @return The changed attributes.
*/
public PrintServiceAttributeSet getAttributes()
{
diff --git a/javax/print/event/PrintServiceAttributeListener.java b/javax/print/event/PrintServiceAttributeListener.java
index e43d9ad65..b46bf3b69 100644
--- a/javax/print/event/PrintServiceAttributeListener.java
+++ b/javax/print/event/PrintServiceAttributeListener.java
@@ -1,5 +1,5 @@
/* PrintServiceAttributeListener.java --
- Copyright (C) 2004 Free Software Foundation, Inc.
+ Copyright (C) 2004, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -39,6 +39,10 @@ package javax.print.event;
/**
+ * Listener interface to receive attribute changes from a print service.
+ * Implementations of this interface can be registered with a
+ * {@link javax.print.PrintService} instance.
+ *
* @author Michael Koch (konqueror@gmx.de)
*/
public interface PrintServiceAttributeListener
diff --git a/javax/print/event/package.html b/javax/print/event/package.html
index 52a298a68..f811013d1 100644
--- a/javax/print/event/package.html
+++ b/javax/print/event/package.html
@@ -1,6 +1,6 @@
<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 3.2 Final//EN">
<!-- package.html - describes classes in javax.print.event package.
- Copyright (C) 2003 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -40,7 +40,9 @@ exception statement from your version. -->
<head><title>GNU Classpath - javax.print.event</title></head>
<body>
-<p></p>
-
+<p>Provides events and listeners to be used with the Java Print Service API.</p>
+<p>
+<b>Since:</b> 1.4
+</p>
</body>
</html>
diff --git a/javax/sound/sampled/AudioFileFormat.java b/javax/sound/sampled/AudioFileFormat.java
new file mode 100644
index 000000000..81bbe4ecf
--- /dev/null
+++ b/javax/sound/sampled/AudioFileFormat.java
@@ -0,0 +1,242 @@
+/* Audio file format
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled;
+
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * This describes an audio file, including information about its length,
+ * the format of the audio data, and other things.
+ * @since 1.3
+ */
+public class AudioFileFormat
+{
+ /**
+ * An instance of this type describes a standard audio file format.
+ * @since 1.3
+ */
+ public static class Type
+ {
+ // This is kind of goofy since there are multiple extensions for
+ // some of these.
+
+ /** The AIFC format. */
+ public static final Type AIFC = new Type("AIFC", "aifc");
+
+ /** The AIFF format. */
+ public static final Type AIFF = new Type("AIFF", "aiff");
+
+ /** The AU format. */
+ public static final Type AU = new Type("AU", "au");
+
+ /** The SND format. */
+ public static final Type SND = new Type("SND", "snd");
+
+ /** The WAVE format. */
+ public static final Type WAVE = new Type ("WAVE", "wav");
+
+ private String name;
+ private String extension;
+
+ /**
+ * Create a new Type given its name and file extension.
+ * The file extension does not include the ".".
+ * @param name the type's name
+ * @param extension the file extension
+ */
+ public Type(String name, String extension)
+ {
+ this.name = name;
+ this.extension = extension;
+ }
+
+ public final boolean equals(Object o)
+ {
+ if (! (o instanceof Type))
+ return false;
+ Type other = (Type) o;
+ return name.equals(other.name) && extension.equals(other.extension);
+ }
+
+ public final int hashCode()
+ {
+ return name.hashCode() + extension.hashCode();
+ }
+
+ /**
+ * Return the extension associated with this Type.
+ */
+ public String getExtension()
+ {
+ return extension;
+ }
+
+ /**
+ * Return the name of this Type.
+ */
+ public final String toString()
+ {
+ return name;
+ }
+ }
+
+ private int byteLength;
+ private AudioFormat format;
+ private Type type;
+ private int frameLength;
+ private Map properties;
+
+ /**
+ * Create a new AudioFileFormat given the type, the format, and the
+ * frame length. The new object will have an unspecified byte length,
+ * and an empty properties map.
+ * @param type the type
+ * @param fmt the format
+ * @param frameLen the frame length
+ */
+ public AudioFileFormat(Type type, AudioFormat fmt, int frameLen)
+ {
+ this.byteLength = AudioSystem.NOT_SPECIFIED;
+ this.format = fmt;
+ this.type = type;
+ this.frameLength = frameLen;
+ this.properties = Collections.EMPTY_MAP;
+ }
+
+ /**
+ * Create a new AudioFileFormat given the type, the format, the
+ * frame length, and some properties. The new object will have an
+ * unspecified byte length. A copy of the properties argument will
+ * be made, so changes to the map passed in will not affect the
+ * new AudioFileFormat.
+ * @param type the type
+ * @param fmt the format
+ * @param frameLen the frame length
+ * @param properties the properties
+ */
+ public AudioFileFormat(Type type, AudioFormat fmt, int frameLen,
+ Map properties)
+ {
+ this.byteLength = AudioSystem.NOT_SPECIFIED;
+ this.format = fmt;
+ this.type = type;
+ this.frameLength = frameLen;
+ this.properties = Collections.unmodifiableMap(new HashMap(properties));
+ }
+
+ /**
+ * Create a new AudioFileFormat given the type, the byte length, the format,
+ * and the frame length. The new object will have an empty properties map.
+ * @param type the type
+ * @param byteLen the byte length
+ * @param fmt the format
+ * @param frameLen the frame length
+ */
+ protected AudioFileFormat(Type type, int byteLen, AudioFormat fmt,
+ int frameLen)
+ {
+ this.byteLength = byteLen;
+ this.format = fmt;
+ this.type = type;
+ this.frameLength = frameLen;
+ this.properties = Collections.EMPTY_MAP;
+ }
+
+ /**
+ * Return the byte length of this file format.
+ */
+ public int getByteLength()
+ {
+ return byteLength;
+ }
+
+ /**
+ * Return the AudioFormat associated with this file format.
+ */
+ public AudioFormat getFormat()
+ {
+ return format;
+ }
+
+ /**
+ * Return the frame length of this file format.
+ */
+ public int getFrameLength()
+ {
+ return frameLength;
+ }
+
+ /**
+ * Return the value of a property defined in this format.
+ * @param key the property name
+ * @return the value of the property, or null if the property is not defined
+ */
+ public Object getProperty(String key)
+ {
+ return properties.get(key);
+ }
+
+ /**
+ * Return the Type associated with this file format.
+ */
+ public Type getType()
+ {
+ return type;
+ }
+
+ /**
+ * Return the properties associated with this format, as a Map.
+ * The returned Map is unmodifiable.
+ */
+ public Map properties()
+ {
+ return properties;
+ }
+
+ /**
+ * Return a description of this AudioFileFormat.
+ */
+ public String toString()
+ {
+ return ("byteLength=" + byteLength + "; format=" + format
+ + "; type=" + type + "; frameLength=" + frameLength);
+ }
+}
diff --git a/javax/sound/sampled/AudioFormat.java b/javax/sound/sampled/AudioFormat.java
new file mode 100644
index 000000000..5199d71c3
--- /dev/null
+++ b/javax/sound/sampled/AudioFormat.java
@@ -0,0 +1,345 @@
+/* An audio format
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled;
+
+import java.util.Collections;
+import java.util.HashMap;
+import java.util.Map;
+
+/**
+ * This class describes an audio format, including its encoding,
+ * the number of channels, its frame rate, etc.
+ * @since 1.3
+ */
+public class AudioFormat
+{
+ /**
+ * This describes a given audio format encoding.
+ * @since 1.3
+ */
+ public static class Encoding
+ {
+ /** The ALAW encoding. */
+ public static final Encoding ALAW = new Encoding("alaw");
+
+ /** The signed PCM encoding. */
+ public static final Encoding PCM_SIGNED = new Encoding("pcm_signed");
+
+ /** The unsigned PCM encoding. */
+ public static final Encoding PCM_UNSIGNED = new Encoding("pcm_unsigned");
+
+ /** The ULAW encoding. */
+ public static final Encoding ULAW = new Encoding("ulaw");
+
+ private String name;
+
+ /**
+ * Create a new encoding descriptor, given its name.
+ * @param name the name
+ */
+ public Encoding(String name)
+ {
+ this.name = name;
+ }
+
+ public final boolean equals(Object o)
+ {
+ return super.equals(o);
+ }
+
+ public final int hashCode()
+ {
+ return super.hashCode();
+ }
+
+ /**
+ * Return the name of this encoding.
+ */
+ public final String toString()
+ {
+ return name;
+ }
+ }
+
+ /**
+ * True if the audio data is stored big-endian.
+ */
+ protected boolean bigEndian;
+
+ /**
+ * The number of channels of data in this format.
+ */
+ protected int channels;
+
+ /**
+ * The encoding of this format.
+ */
+ protected Encoding encoding;
+
+ /**
+ * The frame rate of this format. This is the number of frames
+ * per second.
+ */
+ protected float frameRate;
+
+ /**
+ * The number of bytes per frame in this format.
+ */
+ protected int frameSize;
+
+ /**
+ * The number of samples per second.
+ */
+ protected float sampleRate;
+
+ /**
+ * The number of bits in each sample.
+ */
+ protected int sampleSizeInBits;
+
+ private Map properties;
+
+ /**
+ * Create a new audio format, given various attributes of it.
+ * The properties map for this format will be empty.
+ *
+ * @param encoding the encoding for this format
+ * @param sampleRate the sample rate
+ * @param sampleSizeInBits the sample size, in bits
+ * @param channels the number of channels
+ * @param frameSize the frame size, in bytes
+ * @param frameRate the frame rate, in frames per second
+ * @param bigEndian true if the data is stored big-endian
+ */
+ public AudioFormat(Encoding encoding, float sampleRate, int sampleSizeInBits,
+ int channels, int frameSize, float frameRate,
+ boolean bigEndian)
+ {
+ this.encoding = encoding;
+ this.sampleRate = sampleRate;
+ this.sampleSizeInBits = sampleSizeInBits;
+ this.channels = channels;
+ this.frameSize = frameSize;
+ this.frameRate = frameRate;
+ this.bigEndian = bigEndian;
+ this.properties = Collections.EMPTY_MAP;
+ }
+
+ /**
+ * Create a new audio format, given various attributes of it.
+ * The properties map is copied by this constructor, so changes
+ * to the argument Map will not affect the new object.
+ *
+ * @param encoding the encoding for this format
+ * @param sampleRate the sample rate
+ * @param sampleSizeInBits the sample size, in bits
+ * @param channels the number of channels
+ * @param frameSize the frame size, in bytes
+ * @param frameRate the frame rate, in frames per second
+ * @param bigEndian true if the data is stored big-endian
+ * @param properties a map describing properties of this format
+ */
+ public AudioFormat(Encoding encoding, float sampleRate, int sampleSizeInBits,
+ int channels, int frameSize, float frameRate,
+ boolean bigEndian, Map properties)
+ {
+ this.encoding = encoding;
+ this.sampleRate = sampleRate;
+ this.sampleSizeInBits = sampleSizeInBits;
+ this.channels = channels;
+ this.frameSize = frameSize;
+ this.frameRate = frameRate;
+ this.bigEndian = bigEndian;
+ this.properties = Collections.unmodifiableMap(new HashMap(properties));
+ }
+
+ /**
+ * Create a new PCM-based audio format, given various attributes of it.
+ * The encoding will either be Encoding#PCM_SIGNED or Encoding#PCM_UNSIGNED.
+ * The frame size for this format will be derived from the sample size in
+ * bits and the number of channels, unless one of those is
+ * AudioSystem#NOT_SPECIFIED. The frame rate will be the same as the sample
+ * rate, and the properties map will be empty.
+ *
+ * @param sampleRate the sample rate
+ * @param sampleSizeInBits the sample size, in bits
+ * @param channels the number of channels
+ * @param signed true if this is a signed encoding
+ * @param bigEndian true if the data is stored big-endian
+ */
+ public AudioFormat(float sampleRate, int sampleSizeInBits,
+ int channels, boolean signed, boolean bigEndian)
+ {
+ this.encoding = signed ? Encoding.PCM_SIGNED : Encoding.PCM_UNSIGNED;
+ this.sampleRate = sampleRate;
+ this.sampleSizeInBits = sampleSizeInBits;
+ this.channels = channels;
+ // It isn't clear whether channels can be NOT_SPECIFIED.
+ if (sampleSizeInBits == AudioSystem.NOT_SPECIFIED
+ || channels == AudioSystem.NOT_SPECIFIED)
+ this.frameSize = AudioSystem.NOT_SPECIFIED;
+ else
+ this.frameSize = (sampleSizeInBits + 7) / 8 * channels;
+ this.frameRate = sampleRate;
+ this.bigEndian = bigEndian;
+ this.properties = Collections.EMPTY_MAP;
+ }
+
+ /**
+ * Return the number of channels in this format.
+ */
+ public int getChannels()
+ {
+ return channels;
+ }
+
+ /**
+ * Return the encoding of this format.
+ */
+ public Encoding getEncoding()
+ {
+ return encoding;
+ }
+
+ /**
+ * Return the frame rate of this format.
+ */
+ public float getFrameRate()
+ {
+ return frameRate;
+ }
+
+ /**
+ * Return the frame size of this format.
+ */
+ public int getFrameSize()
+ {
+ return frameSize;
+ }
+
+ /**
+ * Given a key, return a property associated with this format;
+ * or null if this property is not set.
+ * @param key the name of the property
+ * @return the value of the property, or null if the property is not set
+ */
+ public Object getProperty(String key)
+ {
+ return properties.get(key);
+ }
+
+ /**
+ * Return the sample rate of this format.
+ */
+ public float getSampleRate()
+ {
+ return sampleRate;
+ }
+
+ /**
+ * Return the sample size of this format, in bits.
+ */
+ public int getSampleSizeInBits()
+ {
+ return sampleSizeInBits;
+ }
+
+ /**
+ * Return true if this format is big endian, false otherwise.
+ * This only matters for formats whose sample size is greater than
+ * one byte.
+ */
+ public boolean isBigEndian()
+ {
+ return bigEndian;
+ }
+
+ /**
+ * Return true if this audio format matches another.
+ * @param fmt the format to match against
+ * @return true if they match, false otherwise
+ */
+ public boolean matches(AudioFormat fmt)
+ {
+ if (! encoding.equals(fmt.encoding)
+ || channels != fmt.channels
+ || sampleSizeInBits != fmt.sampleSizeInBits
+ || frameSize != fmt.frameSize)
+ return false;
+ if (sampleRate != AudioSystem.NOT_SPECIFIED
+ && fmt.sampleRate != AudioSystem.NOT_SPECIFIED
+ && sampleRate != fmt.sampleRate)
+ return false;
+ if (frameRate != AudioSystem.NOT_SPECIFIED
+ && fmt.frameRate != AudioSystem.NOT_SPECIFIED
+ && frameRate != fmt.frameRate)
+ return false;
+ if (sampleSizeInBits > 8)
+ return bigEndian == fmt.bigEndian;
+ return true;
+ }
+
+ /**
+ * Return a read-only Map holding the properties associated with
+ * this format.
+ */
+ public Map properties()
+ {
+ return properties;
+ }
+
+ /**
+ * Return a description of this format.
+ */
+ public String toString()
+ {
+ StringBuffer result = new StringBuffer();
+ result.append(encoding);
+ result.append(" ");
+ result.append(sampleRate);
+ result.append(" Hz ");
+ result.append(sampleSizeInBits);
+ result.append(" bits ");
+ result.append(channels);
+ result.append(" channels");
+ if (sampleSizeInBits > 8)
+ result.append(bigEndian ? " big endian" : " little endian");
+ return result.toString();
+ }
+}
diff --git a/javax/sound/sampled/AudioInputStream.java b/javax/sound/sampled/AudioInputStream.java
new file mode 100644
index 000000000..863578b0b
--- /dev/null
+++ b/javax/sound/sampled/AudioInputStream.java
@@ -0,0 +1,258 @@
+/*
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled;
+
+import java.io.IOException;
+import java.io.InputStream;
+
+/**
+ * This is an InputStream which is specialized for reading audio files.
+ * In particular it only allows operations to act on a multiple of
+ * the audio stream's frame size.
+ * @since 1.3
+ */
+public class AudioInputStream extends InputStream
+{
+ /** The format of the audio stream. */
+ protected AudioFormat format;
+
+ /** The length of the audio stream in frames. */
+ protected long frameLength;
+
+ /** The current frame position, starting from frame zero. */
+ protected long framePos;
+
+ /** The size of a frame in bytes. */
+ protected int frameSize;
+
+ // I wonder why this class doesn't inherit from FilterInputStream.
+ private InputStream input;
+
+ // The saved frame position, used for mark/reset.
+ private long markedFramePos;
+
+ /**
+ * Create a new AudioInputStream given an underlying InputStream,
+ * the audio format, and the length of the data in frames. The
+ * frame size is taken from the format.
+ * @param is the underlying input stream
+ * @param fmt the format of the data
+ * @param length the length of the data in frames
+ */
+ public AudioInputStream(InputStream is, AudioFormat fmt, long length)
+ {
+ this.format = fmt;
+ this.frameLength = length;
+ this.framePos = 0;
+ this.frameSize = fmt.getFrameSize();
+ this.input = is;
+ }
+
+ /**
+ * Create a new AudioInputStream given a TargetDataLine. The audio
+ * format and the frame size are taken from the line.
+ * @param line the TargetDataLine
+ */
+ public AudioInputStream(TargetDataLine line)
+ {
+ this(new TargetInputStream(line), line.getFormat(),
+ AudioSystem.NOT_SPECIFIED);
+ }
+
+ /**
+ * Return the number of bytes available to be read from the
+ * underlying stream. This wrapper method ensures that the result
+ * is always a multiple of the frame size.
+ */
+ public int available() throws IOException
+ {
+ int result = input.available();
+ // Ensure result is a multiple of the frame size.
+ if (frameSize != AudioSystem.NOT_SPECIFIED)
+ result -= result % frameSize;
+ return result;
+ }
+
+ /**
+ * Close the stream.
+ */
+ public void close() throws IOException
+ {
+ input.close();
+ }
+
+ /**
+ * Get the format associated with this stream.
+ * @return the AudioFormat
+ */
+ public AudioFormat getFormat()
+ {
+ return format;
+ }
+
+ /**
+ * Get the length of this stream in frames. Note that this
+ * may be AudioSystem#NOT_SPECIFIED.
+ * @return the length of the stream in frames
+ */
+ public long getFrameLength()
+ {
+ return frameLength;
+ }
+
+ public void mark(int limit)
+ {
+ input.mark(limit);
+ markedFramePos = framePos;
+ }
+
+ /**
+ * Return true if the underlying stream supports mark and reset,
+ * false otherwise.
+ */
+ public boolean markSupported()
+ {
+ return input.markSupported();
+ }
+
+ /**
+ * Read a single byte from the underlying stream. If the frame
+ * size is set, and is not one byte, an IOException will be thrown.
+ */
+ public int read() throws IOException
+ {
+ if (frameSize != 1)
+ throw new IOException("frame size must be 1 for read()");
+ int result;
+ if (framePos == frameLength)
+ result = -1;
+ else
+ result = input.read();
+ if (result != -1)
+ ++framePos;
+ return result;
+ }
+
+ public int read(byte[] buf) throws IOException
+ {
+ return read(buf, 0, buf.length);
+ }
+
+ public int read(byte[] buf, int offset, int length) throws IOException
+ {
+ int result;
+ if (framePos == frameLength)
+ result = -1;
+ else
+ {
+ int myFrameSize = (frameSize == AudioSystem.NOT_SPECIFIED
+ ? 1 : frameSize);
+ // Ensure length is a multiple of frame size.
+ length -= length % myFrameSize;
+
+ result = 0;
+ while (result == 0 || result % myFrameSize != 0)
+ {
+ int val = input.read(buf, offset, length);
+ if (val < 0)
+ {
+ // This is a weird situation as we might have read a
+ // frame already. It isn't clear at all what to do if
+ // we only found a partial frame. For now we just
+ // return whatever we did find.
+ if (result == 0)
+ return -1;
+ result -= result % myFrameSize;
+ break;
+ }
+ result += val;
+ }
+ // assert result % myFrameSize == 0;
+ framePos += result / myFrameSize;
+ }
+ return result;
+ }
+
+ public void reset() throws IOException
+ {
+ input.reset();
+ framePos = markedFramePos;
+ }
+
+ public long skip(long n) throws IOException
+ {
+ if (frameSize != AudioSystem.NOT_SPECIFIED)
+ n -= n % frameSize;
+ long actual = input.skip(n);
+ if (frameSize != AudioSystem.NOT_SPECIFIED)
+ framePos += actual / frameSize;
+ return actual;
+ }
+
+ private static class TargetInputStream extends InputStream
+ {
+ private TargetDataLine line;
+ private byte[] buf;
+
+ /**
+ * Create a new TargetInputStream.
+ * @param line the line to wrap
+ */
+ public TargetInputStream(TargetDataLine line)
+ {
+ this.line = line;
+ // FIXME: do we have to call line.open()?
+ }
+
+ public synchronized int read() throws IOException
+ {
+ if (buf == null)
+ buf = new byte[1];
+ int count = read(buf, 0, 1);
+ if (count < 0)
+ return -1;
+ return buf[0];
+ }
+
+ public int read(byte[] buf, int offset, int length) throws IOException
+ {
+ return line.read(buf, offset, length);
+ }
+ }
+}
diff --git a/javax/sound/sampled/AudioPermission.java b/javax/sound/sampled/AudioPermission.java
new file mode 100644
index 000000000..6698e35ce
--- /dev/null
+++ b/javax/sound/sampled/AudioPermission.java
@@ -0,0 +1,70 @@
+/*
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled;
+
+import java.security.BasicPermission;
+
+/**
+ * This represents the permission to use an audio device.
+ * The only predefined permission names are "play" and "record".
+ * @since 1.3
+ */
+public class AudioPermission extends BasicPermission
+{
+ private static final long serialVersionUID = -5518053473477801126L;
+
+ /**
+ * Construct an AudioPermission with the given name.
+ * @param name the name of the permission, like "play" or "record"
+ */
+ public AudioPermission(String name)
+ {
+ super(name);
+ }
+
+ /**
+ * Construct an AudioPermission with the given name.
+ * @param name the name of the permission, like "play" or "record"
+ * @param actions the actions; should be null
+ */
+ public AudioPermission(String name, String actions)
+ {
+ super(name, actions);
+ }
+}
diff --git a/javax/sound/sampled/AudioSystem.java b/javax/sound/sampled/AudioSystem.java
new file mode 100644
index 000000000..0b0b754b5
--- /dev/null
+++ b/javax/sound/sampled/AudioSystem.java
@@ -0,0 +1,744 @@
+/* Main interface to audio system
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled;
+
+import gnu.classpath.ServiceFactory;
+
+import java.io.File;
+import java.io.IOException;
+import java.io.InputStream;
+import java.io.OutputStream;
+import java.net.URL;
+import java.util.HashSet;
+import java.util.Iterator;
+
+import javax.sound.sampled.spi.AudioFileReader;
+import javax.sound.sampled.spi.AudioFileWriter;
+import javax.sound.sampled.spi.FormatConversionProvider;
+import javax.sound.sampled.spi.MixerProvider;
+
+/**
+ * This clas is the primary interface to the audio system. It contains
+ * a number of static methods which can be used to access this package's
+ * functionality.
+ *
+ * @since 1.3
+ */
+public class AudioSystem
+{
+ /**
+ * A constant which can be passed to a number of methods in this package,
+ * to indicate an unspecified value.
+ */
+ public static final int NOT_SPECIFIED = -1;
+
+ /**
+ * Return the file format of a given File.
+ * @param f the file to check
+ * @return the format of the file
+ * @throws UnsupportedAudioFileException if the file's format is not
+ * recognized
+ * @throws IOException if there is an I/O error reading the file
+ */
+ public static AudioFileFormat getAudioFileFormat(File f)
+ throws UnsupportedAudioFileException, IOException
+ {
+ Iterator i = ServiceFactory.lookupProviders(AudioFileReader.class);
+ while (i.hasNext())
+ {
+ AudioFileReader reader = (AudioFileReader) i.next();
+ try
+ {
+ return reader.getAudioFileFormat(f);
+ }
+ catch (UnsupportedAudioFileException _)
+ {
+ // Try the next provider.
+ }
+ }
+ throw new UnsupportedAudioFileException("file type not recognized");
+ }
+
+ /**
+ * Return the file format of a given input stream.
+ * @param is the input stream to check
+ * @return the format of the stream
+ * @throws UnsupportedAudioFileException if the stream's format is not
+ * recognized
+ * @throws IOException if there is an I/O error reading the stream
+ */
+ public static AudioFileFormat getAudioFileFormat(InputStream is)
+ throws UnsupportedAudioFileException, IOException
+ {
+ Iterator i = ServiceFactory.lookupProviders(AudioFileReader.class);
+ while (i.hasNext())
+ {
+ AudioFileReader reader = (AudioFileReader) i.next();
+ try
+ {
+ return reader.getAudioFileFormat(is);
+ }
+ catch (UnsupportedAudioFileException _)
+ {
+ // Try the next provider.
+ }
+ }
+ throw new UnsupportedAudioFileException("input stream type not recognized");
+ }
+
+ /**
+ * Return the file format of a given URL.
+ * @param url the URL to check
+ * @return the format of the URL
+ * @throws UnsupportedAudioFileException if the URL's format is not
+ * recognized
+ * @throws IOException if there is an I/O error reading the URL
+ */
+ public static AudioFileFormat getAudioFileFormat(URL url)
+ throws UnsupportedAudioFileException, IOException
+ {
+ Iterator i = ServiceFactory.lookupProviders(AudioFileReader.class);
+ while (i.hasNext())
+ {
+ AudioFileReader reader = (AudioFileReader) i.next();
+ try
+ {
+ return reader.getAudioFileFormat(url);
+ }
+ catch (UnsupportedAudioFileException _)
+ {
+ // Try the next provider.
+ }
+ }
+ throw new UnsupportedAudioFileException("URL type not recognized");
+ }
+
+ /**
+ * Return an array of all the supported AudioFileFormat types.
+ * @return an array of unique types
+ */
+ public static AudioFileFormat.Type[] getAudioFileTypes()
+ {
+ HashSet result = new HashSet();
+ Iterator i = ServiceFactory.lookupProviders(AudioFileWriter.class);
+ while (i.hasNext())
+ {
+ AudioFileWriter writer = (AudioFileWriter) i.next();
+ AudioFileFormat.Type[] types = writer.getAudioFileTypes();
+ for (int j = 0; j < types.length; ++j)
+ result.add(types[j]);
+ }
+ return (AudioFileFormat.Type[]) result.toArray(new AudioFileFormat.Type[result.size()]);
+ }
+
+ /**
+ * Return an array of all the supported AudioFileFormat types which match the
+ * given audio input stream
+ * @param ais the audio input stream
+ * @return an array of unique types
+ */
+ public static AudioFileFormat.Type[] getAudioFileTypes(AudioInputStream ais)
+ {
+ HashSet result = new HashSet();
+ Iterator i = ServiceFactory.lookupProviders(AudioFileWriter.class);
+ while (i.hasNext())
+ {
+ AudioFileWriter writer = (AudioFileWriter) i.next();
+ AudioFileFormat.Type[] types = writer.getAudioFileTypes(ais);
+ for (int j = 0; j < types.length; ++j)
+ result.add(types[j]);
+ }
+ return (AudioFileFormat.Type[]) result.toArray(new AudioFileFormat.Type[result.size()]);
+ }
+
+ /**
+ * Given an audio input stream, this will try to create a new audio input
+ * stream whose encoding matches the given target encoding. If no provider
+ * offers this conversion, an exception is thrown.
+ * @param targ the target encoding
+ * @param ais the original audio stream
+ * @return a new audio stream
+ * @throws IllegalArgumentException if the conversion cannot be made
+ */
+ public static AudioInputStream getAudioInputStream(AudioFormat.Encoding targ,
+ AudioInputStream ais)
+ {
+ HashSet result = new HashSet();
+ Iterator i = ServiceFactory.lookupProviders(FormatConversionProvider.class);
+ while (i.hasNext())
+ {
+ FormatConversionProvider prov = (FormatConversionProvider) i.next();
+ if (! prov.isConversionSupported(targ, ais.getFormat()))
+ continue;
+ return prov.getAudioInputStream(targ, ais);
+ }
+ throw new IllegalArgumentException("encoding not supported for stream");
+ }
+
+ /**
+ * Given an audio input stream, this will try to create a new audio input
+ * stream whose format matches the given target format. If no provider
+ * offers this conversion, an exception is thrown.
+ * @param targ the target format
+ * @param ais the original audio stream
+ * @return a new audio stream
+ * @throws IllegalArgumentException if the conversion cannot be made
+ */
+ public static AudioInputStream getAudioInputStream(AudioFormat targ,
+ AudioInputStream ais)
+ {
+ HashSet result = new HashSet();
+ Iterator i = ServiceFactory.lookupProviders(FormatConversionProvider.class);
+ while (i.hasNext())
+ {
+ FormatConversionProvider prov = (FormatConversionProvider) i.next();
+ if (! prov.isConversionSupported(targ, ais.getFormat()))
+ continue;
+ return prov.getAudioInputStream(targ, ais);
+ }
+ throw new IllegalArgumentException("format not supported for stream");
+ }
+
+ /**
+ * Return an audio input stream for the file.
+ * @param f the file to read
+ * @return an audio input stream for the file
+ * @throws UnsupportedAudioFileException if the file's audio format is not
+ * recognized
+ * @throws IOException if there is an error while reading the file
+ */
+ public static AudioInputStream getAudioInputStream(File f)
+ throws UnsupportedAudioFileException, IOException
+ {
+ Iterator i = ServiceFactory.lookupProviders(AudioFileReader.class);
+ while (i.hasNext())
+ {
+ AudioFileReader reader = (AudioFileReader) i.next();
+ try
+ {
+ return reader.getAudioInputStream(f);
+ }
+ catch (UnsupportedAudioFileException _)
+ {
+ // Try the next provider.
+ }
+ }
+ throw new UnsupportedAudioFileException("file type not recognized");
+ }
+
+ /**
+ * Return an audio input stream given an input stream.
+ * @param is the input stream
+ * @return an audio input stream
+ * @throws UnsupportedAudioFileException if the input stream's audio format
+ * is not supported by any of the installed providers
+ * @throws IOException if there is an error while reading the input stream
+ */
+ public static AudioInputStream getAudioInputStream(InputStream is)
+ throws UnsupportedAudioFileException, IOException
+ {
+ Iterator i = ServiceFactory.lookupProviders(AudioFileReader.class);
+ while (i.hasNext())
+ {
+ AudioFileReader reader = (AudioFileReader) i.next();
+ try
+ {
+ return reader.getAudioInputStream(is);
+ }
+ catch (UnsupportedAudioFileException _)
+ {
+ // Try the next provider.
+ }
+ }
+ throw new UnsupportedAudioFileException("input stream type not recognized");
+ }
+
+ /**
+ * Return an audio input stream for the given URL.
+ * @param url the URL
+ * @return an audio input stream
+ * @throws UnsupportedAudioFileException if the URL's audio format is not
+ * supported by any of the installed providers
+ * @throws IOException if there is an error while reading the URL
+ */
+ public static AudioInputStream getAudioInputStream(URL url)
+ throws UnsupportedAudioFileException, IOException
+ {
+ Iterator i = ServiceFactory.lookupProviders(AudioFileReader.class);
+ while (i.hasNext())
+ {
+ AudioFileReader reader = (AudioFileReader) i.next();
+ try
+ {
+ return reader.getAudioInputStream(url);
+ }
+ catch (UnsupportedAudioFileException _)
+ {
+ // Try the next provider.
+ }
+ }
+ throw new UnsupportedAudioFileException("URL type not recognized");
+ }
+
+ /**
+ * Return a new clip which can be used for playing back an audio stream.
+ * @throws LineUnavailableException if a clip is not available for some
+ * reason
+ * @throws SecurityException if a clip cannot be made for security reasons
+ * @since 1.5
+ */
+ public static Clip getClip()
+ throws LineUnavailableException
+ {
+ Mixer.Info[] infos = getMixerInfo();
+ for (int i = 0; i < infos.length; ++i)
+ {
+ Mixer mix = getMixer(infos[i]);
+ Line[] lines = mix.getSourceLines();
+ for (int j = 0; j < lines.length; ++j)
+ {
+ if (lines[j] instanceof Clip)
+ return (Clip) lines[j];
+ }
+ }
+ throw new LineUnavailableException("no Clip available");
+ }
+
+ /**
+ * Return a new clip which can be used for playing back an audio stream.
+ * The clip is obtained from the indicated mixer.
+ * @param info the mixer to use
+ * @throws LineUnavailableException if a clip is not available for some
+ * reason
+ * @throws SecurityException if a clip cannot be made for security reasons
+ * @since 1.5
+ */
+ public static Clip getClip(Mixer.Info info)
+ throws LineUnavailableException
+ {
+ Mixer mix = getMixer(info);
+ Line[] lines = mix.getSourceLines();
+ for (int j = 0; j < lines.length; ++j)
+ {
+ if (lines[j] instanceof Clip)
+ return (Clip) lines[j];
+ }
+ throw new LineUnavailableException("no Clip available");
+ }
+
+ /**
+ * Return a line matching the provided description. All the providers
+ * on the system are searched for a matching line.
+ * @param info description of the line
+ * @return the matching line
+ * @throws LineUnavailableException if no provider supplies a matching line
+ */
+ public static Line getLine(Line.Info info) throws LineUnavailableException
+ {
+ Mixer.Info[] infos = getMixerInfo();
+ for (int i = 0; i < infos.length; ++i)
+ {
+ Mixer mix = getMixer(infos[i]);
+ try
+ {
+ return mix.getLine(info);
+ }
+ catch (LineUnavailableException _)
+ {
+ // Try the next provider.
+ }
+ }
+ throw new LineUnavailableException("no Clip available");
+ }
+
+ /**
+ * Return a mixer matching the provided description. All the providers
+ * on the system are searched for a matching mixer.
+ * @param info description of the mixer
+ * @return the matching mixer
+ * @throws IllegalArgumentException if no provider supplies a matching mixer
+ */
+ public static Mixer getMixer(Mixer.Info info)
+ {
+ Iterator i = ServiceFactory.lookupProviders(MixerProvider.class);
+ while (i.hasNext())
+ {
+ MixerProvider prov = (MixerProvider) i.next();
+ if (prov.isMixerSupported(info))
+ return prov.getMixer(info);
+ }
+ throw new IllegalArgumentException("mixer not found");
+ }
+
+ /**
+ * Return an array of descriptions of all the mixers provided on the system.
+ */
+ public static Mixer.Info[] getMixerInfo()
+ {
+ HashSet result = new HashSet();
+ Iterator i = ServiceFactory.lookupProviders(MixerProvider.class);
+ while (i.hasNext())
+ {
+ MixerProvider prov = (MixerProvider) i.next();
+ Mixer.Info[] is = prov.getMixerInfo();
+ for (int j = 0; j < is.length; ++j)
+ result.add(is[j]);
+ }
+ return (Mixer.Info[]) result.toArray(new Mixer.Info[result.size()]);
+ }
+
+ /**
+ * Return a source data line matching the given audio format.
+ * @param fmt the audio format
+ * @throws LineUnavailableException if no source data line matching
+ * this format is available
+ * @since 1.5
+ */
+ public static SourceDataLine getSourceDataLine(AudioFormat fmt)
+ throws LineUnavailableException
+ {
+ DataLine.Info info = new DataLine.Info(SourceDataLine.class, fmt);
+ Mixer.Info[] mixers = getMixerInfo();
+ for (int i = 0; i < mixers.length; ++i)
+ {
+ Mixer mix = getMixer(mixers[i]);
+ if (mix.isLineSupported(info))
+ return (SourceDataLine) mix.getLine(info);
+ }
+ throw new LineUnavailableException("source data line not found");
+ }
+
+ /**
+ * Return a target data line matching the given audio format.
+ * @param fmt the audio format
+ * @throws LineUnavailableException if no target data line matching
+ * this format is available
+ * @since 1.5
+ */
+ public static SourceDataLine getSourceDataLine(AudioFormat fmt,
+ Mixer.Info mixer)
+ throws LineUnavailableException
+ {
+ DataLine.Info info = new DataLine.Info(SourceDataLine.class, fmt);
+ Mixer mix = getMixer(mixer);
+ if (mix.isLineSupported(info))
+ return (SourceDataLine) mix.getLine(info);
+ throw new LineUnavailableException("source data line not found");
+ }
+
+ /**
+ * Return an array of descriptions of all the source lines matching
+ * the given line description.
+ * @param info description of the lines to match
+ */
+ public static Line.Info[] getSourceLineInfo(Line.Info info)
+ {
+ HashSet result = new HashSet();
+ Mixer.Info[] infos = getMixerInfo();
+ for (int i = 0; i < infos.length; ++i)
+ {
+ Mixer mix = getMixer(infos[i]);
+ Line.Info[] srcs = mix.getSourceLineInfo(info);
+ for (int j = 0; j < srcs.length; ++j)
+ result.add(srcs[j]);
+ }
+ return (Line.Info[]) result.toArray(new Line.Info[result.size()]);
+ }
+
+ /**
+ * Find and return a target data line matching the given audio format.
+ * @param fmt the format to match
+ * @throws LineUnavailableException if no matching line was found
+ * @since 1.5
+ */
+ public static TargetDataLine getTargetDataLine(AudioFormat fmt)
+ throws LineUnavailableException
+ {
+ DataLine.Info info = new DataLine.Info(TargetDataLine.class, fmt);
+ Mixer.Info[] mixers = getMixerInfo();
+ for (int i = 0; i < mixers.length; ++i)
+ {
+ Mixer mix = getMixer(mixers[i]);
+ if (mix.isLineSupported(info))
+ return (TargetDataLine) mix.getLine(info);
+ }
+ throw new LineUnavailableException("target data line not found");
+ }
+
+ /**
+ * Return a target data line matching the given audio format and
+ * mixer.
+ * @param fmt the audio format
+ * @param mixer the mixer description
+ * @return a target data line
+ * @throws LineUnavailableException if no matching target data line was
+ * found
+ * @since 1.5
+ */
+ public static TargetDataLine getTargetDataLine(AudioFormat fmt,
+ Mixer.Info mixer)
+ throws LineUnavailableException
+ {
+ DataLine.Info info = new DataLine.Info(TargetDataLine.class, fmt);
+ Mixer mix = getMixer(mixer);
+ if (mix.isLineSupported(info))
+ return (TargetDataLine) mix.getLine(info);
+ throw new LineUnavailableException("target data line not found");
+ }
+
+ /**
+ * Given a source encoding, return an array of all target encodings to which
+ * data in this form can be converted.
+ * @param source the source encoding
+ */
+ public static AudioFormat.Encoding[] getTargetEncodings(AudioFormat.Encoding source)
+ {
+ HashSet result = new HashSet();
+ Iterator i = ServiceFactory.lookupProviders(FormatConversionProvider.class);
+ while (i.hasNext())
+ {
+ FormatConversionProvider prov = (FormatConversionProvider) i.next();
+ if (! prov.isSourceEncodingSupported(source))
+ continue;
+ AudioFormat.Encoding[] es = prov.getTargetEncodings();
+ for (int j = 0; j < es.length; ++j)
+ result.add(es[j]);
+ }
+ return (AudioFormat.Encoding[]) result.toArray(new AudioFormat.Encoding[result.size()]);
+ }
+
+ /**
+ * Given a source format, return an array of all the target encodings to
+ * which data in this format can be converted.
+ * @param source the source format
+ */
+ public static AudioFormat.Encoding[] getTargetEncodings(AudioFormat source)
+ {
+ HashSet result = new HashSet();
+ Iterator i = ServiceFactory.lookupProviders(FormatConversionProvider.class);
+ while (i.hasNext())
+ {
+ FormatConversionProvider prov = (FormatConversionProvider) i.next();
+ AudioFormat.Encoding[] es = prov.getTargetEncodings(source);
+ for (int j = 0; j < es.length; ++j)
+ result.add(es[j]);
+ }
+ return (AudioFormat.Encoding[]) result.toArray(new AudioFormat.Encoding[result.size()]);
+ }
+
+ /**
+ * Given a target encoding and a source audio format, return an array of all
+ * matching audio formats to which data in this source format can be converted.
+ * @param encoding the target encoding
+ * @param sourceFmt the source format
+ */
+ public static AudioFormat[] getTargetFormats(AudioFormat.Encoding encoding,
+ AudioFormat sourceFmt)
+ {
+ HashSet result = new HashSet();
+ Iterator i = ServiceFactory.lookupProviders(FormatConversionProvider.class);
+ while (i.hasNext())
+ {
+ FormatConversionProvider prov = (FormatConversionProvider) i.next();
+ AudioFormat[] es = prov.getTargetFormats(encoding, sourceFmt);
+ for (int j = 0; j < es.length; ++j)
+ result.add(es[j]);
+ }
+ return (AudioFormat[]) result.toArray(new AudioFormat[result.size()]);
+ }
+
+ /**
+ * Given a line description, return an array of descriptions of all
+ * the matching target lines.
+ * @param info the line description
+ */
+ public static Line.Info[] getTargetLineInfo(Line.Info info)
+ {
+ HashSet result = new HashSet();
+ Mixer.Info[] infos = getMixerInfo();
+ for (int i = 0; i < infos.length; ++i)
+ {
+ Mixer mix = getMixer(infos[i]);
+ Line.Info[] targs = mix.getTargetLineInfo(info);
+ for (int j = 0; j < targs.length; ++j)
+ result.add(targs[j]);
+ }
+ return (Line.Info[]) result.toArray(new Line.Info[result.size()]);
+ }
+
+ /**
+ * Return true if the currently installed providers are able to
+ * convert data from the given source format to the given target encoding.
+ * @param targ the target encoding
+ * @param source the source format
+ */
+ public static boolean isConversionSupported(AudioFormat.Encoding targ,
+ AudioFormat source)
+ {
+ Iterator i
+ = ServiceFactory.lookupProviders(FormatConversionProvider.class);
+ while (i.hasNext())
+ {
+ FormatConversionProvider prov = (FormatConversionProvider) i.next();
+ if (prov.isConversionSupported(targ, source))
+ return true;
+ }
+ return false;
+ }
+
+ /**
+ * Return true if the currently installed providers are able to convert
+ * the given source format to the given target format.
+ * @param targ the target format
+ * @param source the source format
+ */
+ public static boolean isConversionSupported(AudioFormat targ,
+ AudioFormat source)
+ {
+ Iterator i
+ = ServiceFactory.lookupProviders(FormatConversionProvider.class);
+ while (i.hasNext())
+ {
+ FormatConversionProvider prov = (FormatConversionProvider) i.next();
+ if (prov.isConversionSupported(targ, source))
+ return true;
+ }
+ return false;
+ }
+
+ private static boolean isFileTypeSupported(AudioFileFormat.Type[] types,
+ AudioFileFormat.Type type)
+ {
+ for (int i = 0; i < types.length; ++i)
+ {
+ if (types[i].equals(type))
+ return true;
+ }
+ return false;
+ }
+
+ /**
+ * Return true if the given audio file format is supported by one of
+ * the providers installed on the system.
+ * @param type the audio file format type
+ */
+ public static boolean isFileTypeSupported(AudioFileFormat.Type type)
+ {
+ return isFileTypeSupported(getAudioFileTypes(), type);
+ }
+
+ /**
+ * Return true if the given audio file format is supported for the
+ * given audio input stream by one of the providers installed on the
+ * system.
+ * @param type the audio file format type
+ * @param ais the audio input stream
+ */
+ public static boolean isFileTypeSupported(AudioFileFormat.Type type,
+ AudioInputStream ais)
+ {
+ return isFileTypeSupported(getAudioFileTypes(ais), type);
+ }
+
+ /**
+ * Return true if some provider on the system supplies a line
+ * matching the argument.
+ * @param info the line to match
+ */
+ public static boolean isLineSupported(Line.Info info)
+ {
+ Mixer.Info[] infos = getMixerInfo();
+ for (int i = 0; i < infos.length; ++i)
+ {
+ if (getMixer(infos[i]).isLineSupported(info))
+ return true;
+ }
+ return false;
+ }
+
+ /**
+ * Write an audio input stream to the given file, using the specified
+ * audio file format. All the providers installed on the system will
+ * be searched to find one that supports this operation.
+ * @param ais the audio input stream to write
+ * @param type the desired audio file format type
+ * @param out the file to write to
+ * @return the number of bytes written
+ * @throws IOException if an I/O error occurs while writing
+ * @throws IllegalArgumentException if the file type is not supported
+ */
+ public static int write(AudioInputStream ais, AudioFileFormat.Type type,
+ File out)
+ throws IOException
+ {
+ Iterator i = ServiceFactory.lookupProviders(AudioFileWriter.class);
+ while (i.hasNext())
+ {
+ AudioFileWriter w = (AudioFileWriter) i.next();
+ if (w.isFileTypeSupported(type, ais))
+ return w.write(ais, type, out);
+ }
+ throw new IllegalArgumentException("file type not supported by system");
+ }
+
+ /**
+ * Write an audio input stream to the given output stream, using the
+ * specified audio file format. All the providers installed on the
+ * system will be searched to find one that supports this operation.
+ * @param ais the audio input stream to write
+ * @param type the desired audio file format type
+ * @param os the output stream to write to
+ * @return the number of bytes written
+ * @throws IOException if an I/O error occurs while writing
+ * @throws IllegalArgumentException if the file type is not supported
+ */
+ public static int write(AudioInputStream ais, AudioFileFormat.Type type,
+ OutputStream os)
+ throws IOException
+ {
+ Iterator i = ServiceFactory.lookupProviders(AudioFileWriter.class);
+ while (i.hasNext())
+ {
+ AudioFileWriter w = (AudioFileWriter) i.next();
+ if (w.isFileTypeSupported(type, ais))
+ return w.write(ais, type, os);
+ }
+ throw new IllegalArgumentException("file type not supported by system");
+ }
+}
diff --git a/javax/sound/sampled/BooleanControl.java b/javax/sound/sampled/BooleanControl.java
new file mode 100644
index 000000000..aae1e23a2
--- /dev/null
+++ b/javax/sound/sampled/BooleanControl.java
@@ -0,0 +1,145 @@
+/*
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled;
+
+/**
+ * A BooleanControl is a Control which has two states.
+ * @since 1.3
+ */
+public class BooleanControl extends Control
+{
+ /**
+ * A Type specialized to represent a boolean control.
+ * @since 1.3
+ */
+ public static class Type extends Control.Type
+ {
+ // FIXME: correct constructions?
+
+ /**
+ * A control for applying reverb.
+ */
+ public final static Type APPLY_REVERB = new Type("Apply reverb");
+
+ /**
+ * A control for muting.
+ */
+ public final static Type MUTE = new Type("Mute");
+
+ /**
+ * Create a new Type given its name.
+ * @param name the name of the type
+ */
+ protected Type(String name)
+ {
+ super(name);
+ }
+ }
+
+ private Type type;
+ private boolean value;
+ private String trueLabel;
+ private String falseLabel;
+
+ /**
+ * Create a new boolean control, with the indicated Type and initial
+ * value. The description strings will default to "true" and "false".
+ * @param type the type
+ * @param init the initial value
+ */
+ protected BooleanControl(Type type, boolean init)
+ {
+ super(type);
+ this.value = init;
+ this.trueLabel = "true";
+ this.falseLabel = "false";
+ }
+
+ /**
+ * Create a new boolean control, with the indicated Type, initial
+ * value, and labels.
+ * @param type the type
+ * @param init the initial value
+ * @param trueLabel the label for the true state
+ * @param falseLabel the label for the false state
+ */
+ protected BooleanControl(Type type, boolean init, String trueLabel,
+ String falseLabel)
+ {
+ super(type);
+ this.value = init;
+ this.trueLabel = trueLabel;
+ this.falseLabel = falseLabel;
+ }
+
+ /**
+ * Return the label corresponding to the indicated state.
+ * @param state the state
+ * @return the true label or the false label, as appropriate
+ */
+ public String getStateLabel(boolean state)
+ {
+ return state ? trueLabel : falseLabel;
+ }
+
+ /**
+ * Return the current value of thhe control.
+ */
+ public boolean getValue()
+ {
+ return value;
+ }
+
+ /**
+ * Set the value of the control as indicated.
+ * @param value the new value
+ */
+ public void setValue(boolean value)
+ {
+ this.value = value;
+ }
+
+ /**
+ * Return a string describing this control.
+ */
+ public String toString()
+ {
+ return super.toString() + ": " + getStateLabel(value);
+ }
+}
diff --git a/javax/sound/sampled/Clip.java b/javax/sound/sampled/Clip.java
new file mode 100644
index 000000000..1fa769470
--- /dev/null
+++ b/javax/sound/sampled/Clip.java
@@ -0,0 +1,115 @@
+/*
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled;
+
+import java.io.IOException;
+
+/**
+ * A Clip represents some pre-loaded audio data.
+ * @since 1.3
+ */
+public interface Clip extends DataLine
+{
+ /**
+ * This can be passed to {@link #loop(int)} to indicate that looping
+ * should be done continuously.
+ */
+ int LOOP_CONTINUOUSLY = -1;
+
+ /**
+ * Return the frame length of this clip.
+ */
+ int getFrameLength();
+
+ /**
+ * Return the length of the clip in microseconds.
+ */
+ long getMicrosecondLength();
+
+ /**
+ * Start looping the clip. Looping will occur count times, or, if count
+ * is LOOP_CONTINUOUSLY, will be done continuously. A count of 0 indicates
+ * that any current looping should stop.
+ * @param count the number of times to loop
+ */
+ void loop(int count);
+
+ /**
+ * Open a clip, given an audio format and some data.
+ * @param fmt the format of the data
+ * @param data a byte array containing the audio data
+ * @param offset the offset of the first byte of data in the array
+ * @param len the length of the audio data in the array, in bytes
+ * @throws LineUnavailableException if the line cannot be opened
+ * @throws SecurityException if the line cannot be opened for security
+ * reasons
+ */
+ void open(AudioFormat fmt, byte[] data, int offset, int len)
+ throws LineUnavailableException;
+
+ /**
+ * Open a clip, given an audio input stream.
+ * @param ais the input stream
+ * @throws LineUnavailableException if the line cannot be opened
+ * @throws SecurityException if the line cannot be opened for security
+ * reasons
+ * @throws IOException if there is an I/O error while reading the stream
+ */
+ void open(AudioInputStream ais)
+ throws LineUnavailableException, IOException;
+
+ /**
+ * Set the position to the indicated frame.
+ * @param where new frame position
+ */
+ void setFramePosition(int where);
+
+ /**
+ * Set the loop begin and end points. These are used by loop(int).
+ * @param begin the starting point
+ * @param end the ending point
+ */
+ void setLoopPoints(int begin, int end);
+
+ /**
+ * Set the position to the indicated microsecond.
+ * @param ms the new position in microseconds
+ */
+ void setMicrosecondPosition(long ms);
+}
diff --git a/javax/sound/sampled/CompoundControl.java b/javax/sound/sampled/CompoundControl.java
new file mode 100644
index 000000000..8664abca8
--- /dev/null
+++ b/javax/sound/sampled/CompoundControl.java
@@ -0,0 +1,102 @@
+/* Control consisting of several other controls
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled;
+
+/**
+ * A compound control provides control over several other controls.
+ * @since 1.3
+ */
+public class CompoundControl extends Control
+{
+ /**
+ * This describes a single compound control.
+ * @since 1.3
+ */
+ public static class Type extends Control.Type
+ {
+ /**
+ * Create a new Type given its name.
+ * @param name the name of the type
+ */
+ protected Type(String name)
+ {
+ super(name);
+ }
+ }
+
+ private Control[] memberControls;
+
+ /**
+ * Create a new compound control given its type and members.
+ * @param type the type of the compound control
+ * @param members the members of the compound control
+ */
+ protected CompoundControl(Type type, Control[] members)
+ {
+ super(type);
+ // FIXME: clone?
+ this.memberControls = members;
+ }
+
+ /**
+ * Return the members of this compound control.
+ */
+ public Control[] getMemberControls()
+ {
+ // FIXME: clone?
+ return memberControls;
+ }
+
+ /**
+ * Return a string description of this compound control.
+ */
+ public String toString()
+ {
+ StringBuffer result = new StringBuffer();
+ result.append(super.toString());
+ result.append(": ");
+ for (int i = 0; i < memberControls.length; ++i)
+ {
+ if (i > 0)
+ result.append(", ");
+ result.append(memberControls[i].toString());
+ }
+ return result.toString();
+ }
+}
diff --git a/javax/sound/sampled/Control.java b/javax/sound/sampled/Control.java
new file mode 100644
index 000000000..810c2edd5
--- /dev/null
+++ b/javax/sound/sampled/Control.java
@@ -0,0 +1,111 @@
+/* Control over an attribute of a line
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled;
+
+/**
+ * A control provides the ability to affect some attribute of a line,
+ * for instance its volume.
+ * @since 1.3
+ */
+public class Control
+{
+ /**
+ * This describes a single control.
+ * @since 1.3
+ */
+ public static class Type
+ {
+ private String name;
+
+ /**
+ * Create a new Type given its name.
+ * @param name the name of the type
+ */
+ protected Type(String name)
+ {
+ this.name = name;
+ }
+
+ public final boolean equals(Object o)
+ {
+ return super.equals(o);
+ }
+
+ public final int hashCode()
+ {
+ return super.hashCode();
+ }
+
+ /**
+ * Return the name of this Type.
+ */
+ public String toString()
+ {
+ return name;
+ }
+ }
+
+ private Type type;
+
+ /**
+ * Create a new Control given its Type.
+ * @param type the type
+ */
+ protected Control(Type type)
+ {
+ this.type = type;
+ }
+
+ /**
+ * Return the Type of this Control.
+ */
+ public Type getType()
+ {
+ return type;
+ }
+
+ /**
+ * Return a String descrsibing this control. In particular the
+ * value will include the name of the associated Type.
+ */
+ public String toString()
+ {
+ return type.toString();
+ }
+}
diff --git a/javax/sound/sampled/DataLine.java b/javax/sound/sampled/DataLine.java
new file mode 100644
index 000000000..f755958fe
--- /dev/null
+++ b/javax/sound/sampled/DataLine.java
@@ -0,0 +1,265 @@
+/*
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled;
+
+/**
+ * The DataLine interface adds data-related functionality to the Line
+ * interface. For example, it adds methods to start and stop the data
+ * on the line.
+ * @since 1.3
+ */
+public interface DataLine extends Line
+{
+ /**
+ * This class extends Line.Info with information specific to DataLine.
+ * In particular it adds information about buffer sizes, and about supported
+ * audio formats.
+ * @since 1.3
+ */
+ class Info extends Line.Info
+ {
+ private int minBufferSize;
+ private int maxBufferSize;
+ private AudioFormat[] formats;
+
+ /**
+ * Create a new Info given the line's class and a supported
+ * audio format. The buffer sizes default to AudioSystem.NOT_SPECIFIED.
+ * @param klass the class of the line
+ * @param fmt the supported format
+ */
+ public Info(Class klass, AudioFormat fmt)
+ {
+ super(klass);
+ this.minBufferSize = AudioSystem.NOT_SPECIFIED;
+ this.maxBufferSize = AudioSystem.NOT_SPECIFIED;
+ this.formats = new AudioFormat[] { fmt };
+ }
+
+ /**
+ * Create a new Info given the line's class, the supported audio formats,
+ * the minimum buffer size, and the maximum buffer size.
+ * @param klass the class of the linee
+ * @param fmts the supported audio formats
+ * @param minSize the minimum buffer size
+ * @param maxSize the maximum buffer size
+ */
+ public Info(Class klass, AudioFormat[] fmts, int minSize, int maxSize)
+ {
+ super(klass);
+ this.minBufferSize = minSize;
+ this.maxBufferSize = maxSize;
+ this.formats = fmts;
+ }
+
+ /**
+ * Create a new Info given the line's class, a supported
+ * audio format, and a buffer size. Both the minimum and maximum
+ * sizes are set from this size.
+ * @param klass the class of the line
+ * @param fmt the supported format
+ * @param size the buffer size
+ */
+ public Info(Class klass, AudioFormat fmt, int size)
+ {
+ super(klass);
+ this.minBufferSize = size;
+ this.maxBufferSize = size;
+ this.formats = new AudioFormat[] { fmt };
+ }
+
+ /**
+ * Return the supported audio formats.
+ */
+ public AudioFormat[] getFormats()
+ {
+ // FIXME: clone?
+ return formats;
+ }
+
+ /**
+ * Return the maximum buffer size.
+ */
+ public int getMaxBufferSize()
+ {
+ return maxBufferSize;
+ }
+
+ /**
+ * Return the minimum buffer size.
+ */
+ public int getMinBufferSize()
+ {
+ return minBufferSize;
+ }
+
+ /**
+ * Return true if the indicated audio format is supported by this
+ * Info, false otherwise.
+ * @param fmt the audio format
+ * @return true if the format is supported
+ */
+ public boolean isFormatSupported(AudioFormat fmt)
+ {
+ for (int i = 0; i < formats.length; ++i)
+ {
+ if (fmt.matches(formats[i]))
+ return true;
+ }
+ return false;
+ }
+
+ /**
+ * Return true if this Info matches another Info object.
+ */
+ public boolean matches(Line.Info o)
+ {
+ if (! super.matches(o) || ! (o instanceof Info))
+ return false;
+ Info other = (Info) o;
+ if (minBufferSize < other.minBufferSize
+ || maxBufferSize > other.maxBufferSize)
+ return false;
+ for (int i = 0; i < formats.length; ++i)
+ {
+ boolean ok = false;
+ for (int j = 0; j < other.formats.length; ++j)
+ {
+ if (formats[i].matches(other.formats[j]))
+ {
+ ok = true;
+ break;
+ }
+ }
+ if (! ok)
+ return false;
+ }
+ return true;
+ }
+
+ /**
+ * Return a description of this Info object.
+ */
+ public String toString()
+ {
+ StringBuffer result = new StringBuffer();
+ result.append("formats: [");
+ for (int i = 0; i < formats.length; ++i)
+ {
+ if (i > 0)
+ result.append(", ");
+ result.append(formats[i].toString());
+ }
+ result.append("]; minBufferSize: ");
+ result.append(minBufferSize);
+ result.append("; maxBufferSize: ");
+ result.append(maxBufferSize);
+ return result.toString();
+ }
+ }
+
+ /**
+ * Return the number of bytes currently available on this DataLine.
+ */
+ int available();
+
+ /**
+ * This method blocks until whatever data is buffered in the
+ * DataLine's internal buffer has been drained.
+ */
+ void drain();
+
+ /**
+ * This flushes the DataLine by discarding any buffered data.
+ */
+ void flush();
+
+ /**
+ * Returns the size of the DataLine's internal buffer, in bytes.
+ */
+ int getBufferSize();
+
+ /**
+ * Return the current format of the data associated with this DataLine.
+ */
+ AudioFormat getFormat();
+
+ /**
+ * Return the current frame position.
+ */
+ int getFramePosition();
+
+ /**
+ * Return the volume level for this DataLine.
+ */
+ float getLevel();
+
+ /**
+ * Return the current frame position.
+ * @since 1.5
+ */
+ long getLongFramePosition();
+
+ /**
+ * Return the number of microseconds this DataLine has been playing.
+ */
+ long getMicrosecondPosition();
+
+ /**
+ * Return true if this line is active, meaning that it is actively
+ * performing audio I/O.
+ */
+ boolean isActive();
+
+ /**
+ * Return true if this line is running, meaning that it has been
+ * started. When the line is stopped, this method will return false.
+ */
+ boolean isRunning();
+
+ /**
+ * Start processing data. This will emit a START event.
+ */
+ void start();
+
+ /**
+ * Stop processing data. This will emit a STOP event.
+ */
+ void stop();
+}
diff --git a/javax/sound/sampled/EnumControl.java b/javax/sound/sampled/EnumControl.java
new file mode 100644
index 000000000..798f3a91c
--- /dev/null
+++ b/javax/sound/sampled/EnumControl.java
@@ -0,0 +1,126 @@
+/*
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled;
+
+/**
+ * An EnumControl is a Control which can take one of a specified set of
+ * values.
+ * @since 1.3
+ */
+public class EnumControl extends Control
+{
+ /**
+ * This Type describes an EnumControl.
+ * @since 1.3
+ */
+ public static class Type extends Control.Type
+ {
+ /** This describes an enum control used for reverb. */
+ public static final Type REVERB = new Type("Reverb");
+
+ /**
+ * Create a new Type given its name.
+ * @param name the name of the type
+ */
+ protected Type(String name)
+ {
+ super(name);
+ }
+ }
+
+ private Object[] values;
+ private Object value;
+
+ /**
+ * Create a new enumerated control given its Type, the range of valid
+ * values, and its initial value.
+ * @param type the type
+ * @param values the valid values
+ * @param val the initial value
+ */
+ protected EnumControl(Type type, Object[] values, Object val)
+ {
+ super(type);
+ // FIXME: error checking: values.length>0, val in values... ?
+ // FIXME: clone here?
+ this.values = values;
+ this.value = val;
+ }
+
+ /**
+ * Return the current value of this control.
+ */
+ public Object getValue()
+ {
+ return value;
+ }
+
+ /**
+ * Return the valid values for this control.
+ */
+ public Object[] getValues()
+ {
+ // FIXME: clone here?
+ return values;
+ }
+
+ /**
+ * Set the value of this control. If the indicated value is not among
+ * the valid values, this method will throw an IllegalArgumentException.
+ * @param value the new value
+ * @throws IllegalArgumentException if the new value is invalid
+ */
+ public void setValue(Object value)
+ {
+ for (int i = 0; i < values.length; ++i)
+ {
+ if (! values[i].equals(value))
+ throw new IllegalArgumentException("value not supported");
+ }
+ this.value = value;
+ }
+
+ /**
+ * Return a string describing this control.
+ */
+ public String toString()
+ {
+ return super.toString() + ": " + value;
+ }
+}
diff --git a/javax/sound/sampled/FloatControl.java b/javax/sound/sampled/FloatControl.java
new file mode 100644
index 000000000..409c90de2
--- /dev/null
+++ b/javax/sound/sampled/FloatControl.java
@@ -0,0 +1,267 @@
+/* Floating point control
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled;
+
+/** @since 1.3 */
+public class FloatControl extends Control
+{
+ /**
+ * An instance of this class describes a particular floating point control.
+ * @since 1.3
+ */
+ public static class Type extends Control.Type
+ {
+ /** Auxiliary return gain. */
+ public static final Type AUX_RETURN = new Type("AUX return");
+
+ /** Auxiliary send gain. */
+ public static final Type AUX_SEND = new Type("AUX send");
+
+ /** Balance. */
+ public static final Type BALANCE = new Type("Balance");
+
+ /** Master gain control. */
+ public static final Type MASTER_GAIN = new Type("Master gain");
+
+ /** Control for panning. */
+ public static final Type PAN = new Type("Pan");
+
+ /** Post-reverb gain. */
+ public static final Type REVERB_RETURN = new Type("Reverb return");
+
+ /** Pre-reverb gain. */
+ public static final Type REVERB_SEND = new Type("Reverb send");
+
+ /** Control the sample rate. */
+ public static final Type SAMPLE_RATE = new Type("Sample rate");
+
+ /** Volume control. */
+ public static final Type VOLUME = new Type("Volume");
+
+ /**
+ * Create a new type given its name.
+ * @param name the name of the type
+ */
+ protected Type(String name)
+ {
+ super(name);
+ }
+ }
+
+ private float minimum;
+ private float maximum;
+ private float precision;
+ private int updatePeriod;
+ private float value;
+ private String units;
+ private String minLabel;
+ private String maxLabel;
+ private String midLabel;
+
+ /**
+ * Create a new FloatControl given its type and various parameters.
+ * The minimum, maximum, and midpoint labels will all be the empty string.
+ *
+ * @param type the type
+ * @param min the minimum valuee
+ * @param max the maximum value
+ * @param prec the precision
+ * @param update the update period
+ * @param init the initial value
+ * @param units the description of the units
+ */
+ protected FloatControl(Type type, float min, float max, float prec,
+ int update, float init, String units)
+ {
+ super(type);
+ this.minimum = min;
+ this.maximum = max;
+ this.precision = prec;
+ this.updatePeriod = update;
+ this.value = init;
+ this.units = units;
+ this.minLabel = "";
+ this.maxLabel = "";
+ this.midLabel = "";
+ }
+
+ /**
+ * Create a new FloatControl given its type and various parameters.
+ *
+ * @param type the type
+ * @param min the minimum valuee
+ * @param max the maximum value
+ * @param prec the precision
+ * @param update the update period
+ * @param init the initial value
+ * @param units the description of the units
+ * @param minLabel the label for the minimum value
+ * @param midLabel the label for the midpoint
+ * @param maxLabel the label for the maximum value
+ */
+ protected FloatControl(Type type, float min, float max, float prec,
+ int update, float init, String units,
+ String minLabel, String midLabel, String maxLabel)
+ {
+ super(type);
+ this.minimum = min;
+ this.maximum = max;
+ this.precision = prec;
+ this.updatePeriod = update;
+ this.value = init;
+ this.units = units;
+ this.minLabel = minLabel;
+ this.maxLabel = maxLabel;
+ this.midLabel = midLabel;
+ }
+
+ /**
+ * Return the maximum value of this control.
+ */
+ public float getMaximum()
+ {
+ return maximum;
+ }
+
+ /**
+ * Return the label for the minimum value of this control.
+ */
+ public String getMaxLabel()
+ {
+ return maxLabel;
+ }
+
+ /**
+ * Return the label for the midpoint of this control.
+ */
+ public String getMidLabel()
+ {
+ return midLabel;
+ }
+
+ /**
+ * Return the minimum value of this control.
+ */
+ public float getMinimum()
+ {
+ return minimum;
+ }
+
+ /**
+ * Return the label for the minimum value of this control.
+ */
+ public String getMinLabel()
+ {
+ return minLabel;
+ }
+
+ /**
+ * Return the precision of this control.
+ */
+ public float getPrecision()
+ {
+ return precision;
+ }
+
+ /**
+ * Return the name of the units for this control.
+ */
+ public String getUnits()
+ {
+ return units;
+ }
+
+ /**
+ * Return the update period of this control.
+ */
+ public int getUpdatePeriod()
+ {
+ return updatePeriod;
+ }
+
+ /**
+ * Return the current value of this control.
+ */
+ public float getValue()
+ {
+ return value;
+ }
+
+ /**
+ * Set the new value of this control.
+ * @param value the new value
+ * @throws IllegalArgumentException if the new value is greater than the
+ * maximum or less than the minimum.
+ */
+ public void setValue(float value)
+ {
+ if (value < minimum || value > maximum)
+ throw new IllegalArgumentException("value out of range");
+ this.value = value;
+ }
+
+ /**
+ * This tells the control to start at the starting value
+ * and to shift its value incrementally to the final value
+ * over the given time interval, specified in microseconds.
+ * The default implementation does not do this, but instead
+ * simply sets the value to the final value immediately.
+ *
+ * @param from the starting value
+ * @param to the final value
+ * @param ms the number of microseconds
+ */
+ public void shift(float from, float to, int ms)
+ {
+ if (from < minimum || from > maximum
+ || to < minimum || to > maximum
+ || ms < 0)
+ throw new IllegalArgumentException("argument out of range");
+ // The default just sets the value to TO.
+ this.value = to;
+ }
+
+ /**
+ * Return a string describing this control.
+ */
+ public String toString()
+ {
+ return super.toString() + ": " + value;
+ }
+}
diff --git a/javax/sound/sampled/Line.java b/javax/sound/sampled/Line.java
new file mode 100644
index 000000000..69bb9084f
--- /dev/null
+++ b/javax/sound/sampled/Line.java
@@ -0,0 +1,150 @@
+/* An input or output line
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled;
+
+/**
+ * A Line represents a single input or output audio line.
+ * @since 1.3
+ */
+public interface Line
+{
+ /**
+ * An object of this type holds information about a Line.
+ * @since 1.3
+ */
+ class Info
+ {
+ private Class klass;
+
+ /**
+ * Create a new Info object. The argument is the class of the line,
+ * for instance TargetDataLine.class.
+ * @param klass the class of the line
+ */
+ public Info(Class klass)
+ {
+ this.klass = klass;
+ }
+
+ /**
+ * Return the line's class.
+ */
+ public Class getLineClass()
+ {
+ return klass;
+ }
+
+ /**
+ * Return true if this Info object matches the given object.
+ * @param other the object to match
+ * @return true if they match, false otherwise
+ */
+ public boolean matches(Info other)
+ {
+ return klass.equals(other.klass);
+ }
+
+ /**
+ * Return a description of this Info object.
+ */
+ public String toString()
+ {
+ return klass.toString();
+ }
+ }
+
+ /**
+ * Add a listener which will be notified whenever this Line changes state.
+ * @param listener the listener to notify
+ */
+ void addLineListener(LineListener listener);
+
+ /**
+ * Close this line.
+ */
+ void close();
+
+ /**
+ * Return the control associated with this Line that matches the
+ * argument.
+ * @param what the type of the control to match
+ * @return the associated control
+ * @throws IllegalArgumentException if a control of this type is not
+ * available for this line
+ */
+ Control getControl(Control.Type what);
+
+ /**
+ * Return an array of controls associated with this Line. Note that
+ * this method will not return null -- if there are no controls, it
+ * will return a zero-length array.
+ */
+ Control[] getControls();
+
+ /**
+ * Return the Info object associated with this Line.
+ */
+ Info getLineInfo();
+
+ /**
+ * Return true if a Control matching the argument is available for this
+ * Line, false otherwise.
+ * @param what the type of the control to match
+ */
+ boolean isControlSupported(Control.Type what);
+
+ /**
+ * Return true if this line is open, false otherwise.
+ */
+ boolean isOpen();
+
+ /**
+ * Open this line.
+ * @throws LineUnavailableException if the line is unavailable for some
+ * reason
+ */
+ void open() throws LineUnavailableException;
+
+ /**
+ * Remove the listener from this Line; after this call the listener will
+ * no longer be notified when this Line changes state.
+ * @param listener the listener to remove
+ */
+ void removeLineListener(LineListener listener);
+}
diff --git a/javax/sound/sampled/LineEvent.java b/javax/sound/sampled/LineEvent.java
new file mode 100644
index 000000000..7bba2cd1d
--- /dev/null
+++ b/javax/sound/sampled/LineEvent.java
@@ -0,0 +1,150 @@
+/*
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled;
+
+import java.util.EventObject;
+
+// FIXME: attempts to serialize this should fail
+
+/**
+ * This class holds information about a state change of a Line.
+ * @since 1.3
+ */
+public class LineEvent extends EventObject
+{
+ /**
+ * This class represents the kinds of state changes that can occur
+ * to a Line. The standard states are availabe as static instances.
+ * @since 1.3
+ */
+ public static class Type
+ {
+ /** An event of this type is posted when a Line closes. */
+ public static final Type CLOSE = new Type("close");
+
+ /** An event of this type is posted when a Line opens. */
+ public static final Type OPEN = new Type("open");
+
+ /** An event of this type is posted when a Line starts. */
+ public static final Type START = new Type("start");
+
+ /** An event of this type is posted when a Line stops. */
+ public static final Type STOP = new Type("stop");
+
+ private String name;
+
+ /**
+ * Create a new type with the indicated name.
+ * @param name the name
+ */
+ protected Type(String name)
+ {
+ this.name = name;
+ }
+
+ public final boolean equals(Object o)
+ {
+ return super.equals(o);
+ }
+
+ public final int hashCode()
+ {
+ return super.hashCode();
+ }
+
+ /**
+ * Return the name of this Type.
+ */
+ public String toString()
+ {
+ return name;
+ }
+ }
+
+ private Type type;
+ private long framePosition;
+ private Line line;
+
+ /**
+ * Create a new LineEvent with the indicated line, type, and frame position.
+ * @param line the line
+ * @param type the type of the event
+ * @param pos the frame position
+ */
+ public LineEvent(Line line, Type type, long pos)
+ {
+ super(line);
+ this.line = line;
+ this.type = type;
+ this.framePosition = pos;
+ }
+
+ /**
+ * Return the frame position associated with this event.
+ */
+ public long getFramePosition()
+ {
+ return framePosition;
+ }
+
+ /**
+ * Return the Line associated with this event.
+ */
+ public Line getLine()
+ {
+ return line;
+ }
+
+ /**
+ * Return the Type associated with this event.
+ */
+ public Type getType()
+ {
+ return type;
+ }
+
+ /**
+ * Return a description of this event.
+ */
+ public String toString()
+ {
+ return ("type=" + type + "; framePosition=" + framePosition
+ + "line=" + line);
+ }
+}
diff --git a/javax/sound/sampled/LineListener.java b/javax/sound/sampled/LineListener.java
new file mode 100644
index 000000000..1b87c0279
--- /dev/null
+++ b/javax/sound/sampled/LineListener.java
@@ -0,0 +1,55 @@
+/* Listener for Lines
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled;
+
+import java.util.EventListener;
+
+/**
+ * This interface is used by classes which wish to be notified
+ * when the state of a Line changes.
+ * @since 1.3
+ */
+public interface LineListener extends EventListener
+{
+ /**
+ * This is called when the line's status changes.
+ * @param ev the event describing the change
+ */
+ void update(LineEvent ev);
+}
diff --git a/javax/sound/sampled/LineUnavailableException.java b/javax/sound/sampled/LineUnavailableException.java
new file mode 100644
index 000000000..b203d7be2
--- /dev/null
+++ b/javax/sound/sampled/LineUnavailableException.java
@@ -0,0 +1,61 @@
+/*
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled;
+
+/** @since 1.3 */
+public class LineUnavailableException extends Exception
+{
+ private static final long serialVersionUID = -2046718279487432130L;
+
+ /**
+ * Create a new LineUnavailableException.
+ */
+ public LineUnavailableException()
+ {
+ }
+
+ /**
+ * Create a new LineUnavailableException with the given message.
+ * @param msg the message
+ */
+ public LineUnavailableException(String msg)
+ {
+ super(msg);
+ }
+}
diff --git a/javax/sound/sampled/Mixer.java b/javax/sound/sampled/Mixer.java
new file mode 100644
index 000000000..b9afba3fe
--- /dev/null
+++ b/javax/sound/sampled/Mixer.java
@@ -0,0 +1,206 @@
+/* Mixers
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled;
+
+/**
+ * A Mixer is a Line which itself holds multiple lines.
+ * @since 1.3
+ */
+public interface Mixer extends Line
+{
+ /**
+ * An Info object describes a mixer.
+ * @since 1.3
+ */
+ class Info
+ {
+ private String name;
+ private String description;
+ private String vendor;
+ private String version;
+
+ /**
+ * Create a new mixer description.
+ * @param name the name of the mixer
+ * @param vendor the vendor
+ * @param desc a descriptive string
+ * @param vers the mixer's version
+ */
+ public Info(String name, String vendor, String desc, String vers)
+ {
+ this.name = name;
+ this.description = desc;
+ this.vendor = vendor;
+ this.version = vers;
+ }
+
+ public final boolean equals(Object o)
+ {
+ return super.equals(o);
+ }
+
+ public final int hashCode()
+ {
+ return super.hashCode();
+ }
+
+ /**
+ * Return the name of the mixer.
+ */
+ public String getName()
+ {
+ return name;
+ }
+
+ /**
+ * Return the mixer's description.
+ */
+ public String getDescription()
+ {
+ return description;
+ }
+
+ /**
+ * Return the mixer's vendor.
+ */
+ public String getVendor()
+ {
+ return vendor;
+ }
+
+ /**
+ * Return the mixer's version.
+ */
+ public String getVersion()
+ {
+ return version;
+ }
+
+ public String toString()
+ {
+ return ("name=" + name + "; description=" + description
+ + "; vendor=" + vendor + "; version=" + version);
+ }
+ }
+
+ /**
+ * Return a Line associated with this Mixer, given its description.
+ * @param info the description of the line to find
+ * @return the corresponding Line
+ * @throws LineUnavailableException if no Line matching the description
+ * exists in this Mixer
+ */
+ Line getLine(Line.Info info) throws LineUnavailableException;
+
+ /**
+ * Return the number of lines matching this description.
+ * @param info the description of the lines to find.
+ */
+ int getMaxLines(Line.Info info);
+
+ /**
+ * Return an Info object describing this Mixer.
+ */
+ Info getMixerInfo();
+
+ /**
+ * Return an array of Info objects describing all the source lines
+ * available in this Mixer.
+ */
+ Line.Info[] getSourceLineInfo();
+
+ /**
+ * Return an array of Info objects describing all the source lines
+ * available in this Mixer, which match the provided decsription.
+ * @param info the description of the source lines to find
+ */
+ Line.Info[] getSourceLineInfo(Line.Info info);
+
+ /**
+ * Return an array of all the source lines available in this Mixer.
+ */
+ Line[] getSourceLines();
+
+ /**
+ * Return an array of Info objects describing all the target lines
+ * available in this Mixer.
+ */
+ Line.Info[] getTargetLineInfo();
+
+ /**
+ * Return an array of Info objects describing all the target lines
+ * available in this Mixer, which match the provided decsription.
+ * @param info the description of the target lines to find
+ */
+ Line.Info[] getTargetLineInfo(Line.Info info);
+
+ /**
+ * Return an array of all the target lines available in this Mixer.
+ */
+ Line[] getTargetLines();
+
+ /**
+ * Return true if a Line matching the given description is supported
+ * by this Mixer, false otherwise.
+ * @param info the description of the line to find
+ */
+ boolean isLineSupported(Line.Info info);
+
+ /**
+ * Return true if this Mixer supports synchronization of the given set
+ * of lines.
+ * @param lines the lines to check
+ * @param sync true if the synchronization must be accurate at all times
+ */
+ boolean isSynchronizationSupported(Line[] lines, boolean sync);
+
+ /**
+ * Start synchronization on the given set of lines.
+ * @param lines the lines to synchronize, or null for all the lines
+ * @param sync true if the synchronization must be accurate at all times
+ * @throws IllegalArgumentException if the lines cannot be synchronized
+ */
+ void synchronize(Line[] lines, boolean sync);
+
+ /**
+ * Stop synchronization for the given set of lines.
+ * @param lines the lines to unsynchronize, or null for all the lines
+ */
+ void unsynchronize(Line[] lines);
+}
diff --git a/javax/sound/sampled/Port.java b/javax/sound/sampled/Port.java
new file mode 100644
index 000000000..7b3daafd3
--- /dev/null
+++ b/javax/sound/sampled/Port.java
@@ -0,0 +1,135 @@
+/*
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled;
+
+/**
+ * A Port is a Line which represents an audio device, for instance
+ * a microphone.
+ *
+ * @since 1.3
+ */
+public interface Port extends Line
+{
+ /**
+ * This describes a single port.
+ * @since 1.3
+ */
+ class Info extends Line.Info
+ {
+ // FIXME names?
+
+ /** A CD player. */
+ public static final Info COMPACT_DISC = new Info(Port.class,
+ "Compact Disc",
+ true);
+
+ /** Headphones. */
+ public static final Info HEADPHONE = new Info(Port.class, "Headphone",
+ false);
+
+ /** Generic input line. */
+ public static final Info LINE_IN = new Info(Port.class, "Line in",
+ true);
+
+ /** Generic output line. */
+ public static final Info LINE_OUT = new Info(Port.class, "Line out",
+ false);
+
+ /** A microphone. */
+ public static final Info MICROPHONE = new Info(Port.class, "Microphone",
+ true);
+
+ /** A speaker. */
+ public static final Info SPEAKER = new Info(Port.class, "Speaker",
+ false);
+
+ private String name;
+ private boolean isSource;
+
+ /**
+ * Create a new Info object, given the line's class, the name,
+ * and an argument indicating whether this is an input or an output.
+ * @param klass the class of the line
+ * @param name the name of the line
+ * @param isSource true if this is an input source
+ */
+ public Info(Class klass, String name, boolean isSource)
+ {
+ super(klass);
+ this.name = name;
+ this.isSource = isSource;
+ }
+
+ public final boolean equals(Object o)
+ {
+ return super.equals(o);
+ }
+
+ public final int hashCode()
+ {
+ return super.hashCode();
+ }
+
+ /**
+ * Return the name of this object.
+ */
+ public String getName()
+ {
+ return name;
+ }
+
+ /**
+ * Return true if this describes an input line.
+ */
+ public boolean isSource()
+ {
+ return isSource;
+ }
+
+ public boolean matches(Line.Info other)
+ {
+ return super.matches(other) && equals(other);
+ }
+
+ public String toString()
+ {
+ return super.toString() + "; name=" + name + "; isSource=" + isSource;
+ }
+ }
+}
diff --git a/javax/sound/sampled/ReverbType.java b/javax/sound/sampled/ReverbType.java
new file mode 100644
index 000000000..a08959377
--- /dev/null
+++ b/javax/sound/sampled/ReverbType.java
@@ -0,0 +1,144 @@
+/* Reverb attributes
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled;
+
+/**
+ * This represents a reverb effect which can be applied to an audio signal.
+ * @since 1.3
+ */
+public class ReverbType
+{
+ private String name;
+ private int earlyReflectionDelay;
+ private float earlyReflectionIntensity;
+ private int lateReflectionDelay;
+ private float lateReflectionIntensity;
+ private int decayTime;
+
+ /**
+ * Create a new ReverbType given its attributes.
+ * @param name the name of this type
+ * @param earlyDelay the early delay time in microseconds
+ * @param earlyInten the early intensity in decibels
+ * @param lateDelay the late delay time in microseconds
+ * @param lateInten the late intensity in decibels
+ * @param decay the decay time in microseconds
+ */
+ protected ReverbType(String name, int earlyDelay, float earlyInten,
+ int lateDelay, float lateInten, int decay)
+ {
+ this.name = name;
+ this.earlyReflectionDelay = earlyDelay;
+ this.earlyReflectionIntensity = earlyInten;
+ this.lateReflectionDelay = lateDelay;
+ this.lateReflectionIntensity = lateInten;
+ this.decayTime = decay;
+ }
+
+ public final boolean equals(Object o)
+ {
+ return super.equals(o);
+ }
+
+ public final int hashCode()
+ {
+ return super.hashCode();
+ }
+
+ /**
+ * Return the decay time.
+ */
+ public int getDecayTime()
+ {
+ return decayTime;
+ }
+
+ /**
+ * Return the early reflection delay.
+ */
+ public int getEarlyReflectionDelay()
+ {
+ return earlyReflectionDelay;
+ }
+
+ /**
+ * Return the early reflection intensity.
+ */
+ public float getEarlyReflectionIntensity()
+ {
+ return earlyReflectionIntensity;
+ }
+
+ /**
+ * Return the late reflection delay.
+ */
+ public int getLateReflectionDelay()
+ {
+ return lateReflectionDelay;
+ }
+
+ /**
+ * Return the late reflection intensity.
+ */
+ public float getLateReflectionIntensity()
+ {
+ return lateReflectionIntensity;
+ }
+
+ /**
+ * Return the name of this ReverbType.
+ * @since 1.5
+ */
+ public String getName()
+ {
+ return name;
+ }
+
+ /**
+ * Return a description of this ReverbType.
+ */
+ public String toString()
+ {
+ return ("name=" + name + "; earlyReflectionDelay=" + earlyReflectionDelay
+ + "; earlyReflectionIntensity=" + earlyReflectionIntensity
+ + "; lateReflectionDelay=" + lateReflectionDelay
+ + "; lateReflectionIntensity=" + lateReflectionIntensity
+ + "; decayTime=" + decayTime);
+ }
+}
diff --git a/javax/sound/sampled/SourceDataLine.java b/javax/sound/sampled/SourceDataLine.java
new file mode 100644
index 000000000..6e73d6d9c
--- /dev/null
+++ b/javax/sound/sampled/SourceDataLine.java
@@ -0,0 +1,77 @@
+/* Output data line.
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled;
+
+/**
+ * This is a DataLine to which data may be written.
+ * @since 1.3
+ */
+public interface SourceDataLine extends DataLine
+{
+ /**
+ * Open the line, given the desired audio format.
+ * @param fmt the format to use
+ * @throws LineUnavailableException if the line is not available for
+ * some reason
+ * @throws SecurityException if this is prevented by the security manager
+ */
+ void open(AudioFormat fmt)
+ throws LineUnavailableException;
+
+ /**
+ * Open the line, given the desired audio format and the buffer size.
+ * @param fmt the format to use
+ * @param size the buffer size
+ * @throws LineUnavailableException if the line is not available for
+ * some reason
+ * @throws SecurityException if this is prevented by the security manager
+ */
+ void open(AudioFormat fmt, int size)
+ throws LineUnavailableException;
+
+ /**
+ * Write audio data to this line. The data must be an integral number
+ * of frames, as determined by the audio format.
+ * @param buf a byte array of audio data
+ * @param offset index of the first byte in the array to use
+ * @param length the number of bytes to write
+ * @return the number of bytes written
+ */
+ int write(byte[] buf, int offset, int length);
+}
diff --git a/javax/sound/sampled/TargetDataLine.java b/javax/sound/sampled/TargetDataLine.java
new file mode 100644
index 000000000..61ad344ef
--- /dev/null
+++ b/javax/sound/sampled/TargetDataLine.java
@@ -0,0 +1,79 @@
+/* Input data line.
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled;
+
+/**
+ * This is a DataLine from which data may be read.
+ * @since 1.3
+ */
+public interface TargetDataLine extends DataLine
+{
+ /**
+ * Open the line using the indicated audio format.
+ * @param fmt the format to use
+ * @throws LineUnavailableException if the line is not available for
+ * some reason
+ * @throws SecurityException if this operation is prevented by the
+ * security manager
+ */
+ void open(AudioFormat fmt)
+ throws LineUnavailableException;
+
+ /**
+ * Open the line using the indicated audio format and buffer size.
+ * @param fmt the format to use
+ * @throws LineUnavailableException if the line is not available for
+ * some reason
+ * @throws SecurityException if this operation is prevented by the
+ * security manager
+ */
+ void open(AudioFormat fmt, int size)
+ throws LineUnavailableException;
+
+ /**
+ * Read data from the line into the given buffer. The requested data
+ * should be an integral number of framaes, as determined by the audio
+ * format.
+ * @param buf the buffer into which the data is put
+ * @param offset the initial offset at which to write
+ * @param length the maximum number of bytes to read
+ * @return the actual number of bytes read
+ */
+ int read(byte[] buf, int offset, int length);
+}
diff --git a/native/jni/java-io/javaio.h b/javax/sound/sampled/UnsupportedAudioFileException.java
index 2e4a8d103..bced9c18f 100644
--- a/native/jni/java-io/javaio.h
+++ b/javax/sound/sampled/UnsupportedAudioFileException.java
@@ -1,5 +1,5 @@
-/* javaio.h - Declaration for common java.io native functions
- Copyright (C) 1998, 2004 Free Software Foundation, Inc.
+/*
+ Copyright (C) 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -7,7 +7,7 @@ GNU Classpath is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 2, or (at your option)
any later version.
-
+
GNU Classpath is distributed in the hope that it will be useful, but
WITHOUT ANY WARRANTY; without even the implied warranty of
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
@@ -36,23 +36,30 @@ obligated to do so. If you do not wish to do so, delete this
exception statement from your version. */
-#ifndef JAVAIO_H_INCLUDED
-#define JAVAIO_H_INCLUDED
-
-#include <stddef.h>
+package javax.sound.sampled;
-/*
- * Function Prototypes
+/**
+ * An exception of this type is thrown when an operation is attempted
+ * on a file whose format is unrecognized.
+ * @since 1.3
*/
+public class UnsupportedAudioFileException extends Exception
+{
+ private static final long serialVersionUID = -139127412623160368L;
-extern jlong _javaio_get_file_length(JNIEnv *, jint);
-extern jlong _javaio_skip_bytes(JNIEnv *, jint, jlong);
-extern jint _javaio_open(JNIEnv *, jstring, int);
-extern jint _javaio_open_read(JNIEnv *, jstring);
-extern jint _javaio_open_readwrite(JNIEnv *, jstring);
-extern void _javaio_close(JNIEnv *, jint fd);
-extern jint _javaio_read(JNIEnv *, jint, jarray, jint, jint);
-extern jint _javaio_write(JNIEnv *, jint, jarray, jint, jint);
-
-#endif /* JAVAIO_H_INCLUDED */
+ /**
+ * Create a new UnsupportedAudioFileException.
+ */
+ public UnsupportedAudioFileException()
+ {
+ }
+ /**
+ * Create a new UnsupportedAudioFileException with the indicated message.
+ * @param msg the message
+ */
+ public UnsupportedAudioFileException(String msg)
+ {
+ super(msg);
+ }
+}
diff --git a/javax/sound/sampled/spi/AudioFileReader.java b/javax/sound/sampled/spi/AudioFileReader.java
new file mode 100644
index 000000000..6df4cc22d
--- /dev/null
+++ b/javax/sound/sampled/spi/AudioFileReader.java
@@ -0,0 +1,146 @@
+/* Audio file reader API
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled.spi;
+
+import java.io.File;
+import java.io.IOException;
+import java.io.InputStream;
+import java.net.URL;
+
+import javax.sound.sampled.AudioFileFormat;
+import javax.sound.sampled.AudioInputStream;
+import javax.sound.sampled.UnsupportedAudioFileException;
+
+/**
+ * This abstract class defines the interface to audio file readers.
+ * A concrete provider subclass will implement the methods declared
+ * here. These methods can be used to determine the format of
+ * files, and to retrieve an AudioInputStream for a file.
+ * @since 1.3
+ */
+public abstract class AudioFileReader
+{
+ /**
+ * The default constructor. Note that this class is abstract and
+ * thus not directly instantiable.
+ */
+ public AudioFileReader()
+ {
+ }
+
+ /**
+ * Return the format of the given file as deduced by this provider.
+ * If the format of the file is not recognized, throws an exception.
+ * This will also throw an exception if there is an I/O error when
+ * reading the file.
+ * @param file the file to examine
+ * @return the audio file format
+ * @throws UnsupportedAudioFileException if the file's format is not
+ * recognized
+ * @throws IOException if there is an I/O error while reading the file
+ */
+ public abstract AudioFileFormat getAudioFileFormat(File file)
+ throws UnsupportedAudioFileException, IOException;
+
+ /**
+ * Return the format of the given input stream as deduced by this provider.
+ * If the format of the stream is not recognized, throws an exception.
+ * This will also throw an exception if there is an I/O error when
+ * reading the stream. Note that providers typically use mark and reset
+ * on the stream when examining the data, and as a result an IOException
+ * may be thrown if the stream does not support these.
+ * @param is the stream to examine
+ * @return the audio file format
+ * @throws UnsupportedAudioFileException if the stream's format is not
+ * recognized
+ * @throws IOException if there is an I/O error while reading the stream
+ */
+ public abstract AudioFileFormat getAudioFileFormat(InputStream is)
+ throws UnsupportedAudioFileException, IOException;
+
+ /**
+ * Return the format of the given URL as deduced by this provider.
+ * If the format of the URL is not recognized, throws an exception.
+ * This will also throw an exception if there is an I/O error when
+ * reading the URL.
+ * @param url the URL to examine
+ * @return the audio file format
+ * @throws UnsupportedAudioFileException if the URL's format is not
+ * recognized
+ * @throws IOException if there is an I/O error while reading the URL
+ */
+ public abstract AudioFileFormat getAudioFileFormat(URL url)
+ throws UnsupportedAudioFileException, IOException;
+
+ /**
+ * Return an AudioInputStream for the given file. The file is assumed
+ * to hold valid audio data.
+ * @param file the file to read
+ * @return an AudioInputStream for the file
+ * @throws UnsupportedAudioFileException if the file's type is not
+ * recognized
+ * @throws IOException if there is an error while reading the file
+ */
+ public abstract AudioInputStream getAudioInputStream(File file)
+ throws UnsupportedAudioFileException, IOException;
+
+ /**
+ * Return an AudioInputStream wrapping the given input stream. The stream
+ * is assumed to hold valid audio data.
+ * @param is the input stream to wrap
+ * @return an AudioInputStream for the stream
+ * @throws UnsupportedAudioFileException if the stream's type is not
+ * recognized
+ * @throws IOException if there is an error while reading the stream
+ */
+ public abstract AudioInputStream getAudioInputStream(InputStream is)
+ throws UnsupportedAudioFileException, IOException;
+
+ /**
+ * Return an AudioInputStream for the given URL. The URL is assumed
+ * to hold valid audio data.
+ * @param url the URL to read
+ * @return an AudioInputStream for the URL
+ * @throws UnsupportedAudioFileException if the URL's type is not
+ * recognized
+ * @throws IOException if there is an error while reading the URL
+ */
+ public abstract AudioInputStream getAudioInputStream(URL url)
+ throws UnsupportedAudioFileException, IOException;
+}
diff --git a/javax/sound/sampled/spi/AudioFileWriter.java b/javax/sound/sampled/spi/AudioFileWriter.java
new file mode 100644
index 000000000..955bb0517
--- /dev/null
+++ b/javax/sound/sampled/spi/AudioFileWriter.java
@@ -0,0 +1,131 @@
+/* Audio file writer API
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled.spi;
+
+import java.io.File;
+import java.io.IOException;
+import java.io.OutputStream;
+
+import javax.sound.sampled.AudioFileFormat;
+import javax.sound.sampled.AudioInputStream;
+
+/**
+ * This abstract class provides an API for writing audio files. Concrete
+ * subclasses implement the methods declared here.
+ * @since 1.3
+ */
+public abstract class AudioFileWriter
+{
+ /**
+ * Creat a new audio file writer.
+ */
+ public AudioFileWriter()
+ {
+ }
+
+ /**
+ * Return an array of all audio file format types supported by this
+ * provider.
+ */
+ public abstract AudioFileFormat.Type[] getAudioFileTypes();
+
+ /**
+ * Return an array of all the audio file format types supported by this
+ * provider, which can be written given the input stream.
+ * @param ais the audio input stream
+ */
+ public abstract AudioFileFormat.Type[] getAudioFileTypes(AudioInputStream ais);
+
+ /**
+ * Return true if the indicated type is supported by this provider.
+ * @param type the audio file format type
+ */
+ public boolean isFileTypeSupported(AudioFileFormat.Type type)
+ {
+ AudioFileFormat.Type[] types = getAudioFileTypes();
+ for (int i = 0; i < types.length; ++i)
+ {
+ if (type.equals(types[i]))
+ return true;
+ }
+ return false;
+ }
+
+ /**
+ * Return true if the indicated type is supported by this provider,
+ * and can be written from the given audio input stream.
+ * @param type the audio file format type
+ * @param ais the audio input stream to write
+ */
+ public boolean isFileTypeSupported(AudioFileFormat.Type type,
+ AudioInputStream ais)
+ {
+ AudioFileFormat.Type[] types = getAudioFileTypes(ais);
+ for (int i = 0; i < types.length; ++i)
+ {
+ if (type.equals(types[i]))
+ return true;
+ }
+ return false;
+ }
+
+ /**
+ * Write audio data to a file.
+ * @param ais the audio input stream to write
+ * @param type the desired audio file format type
+ * @param out the file to write to
+ * @return the number of bytes written
+ * @throws IOException if an I/O error occurs when writing
+ */
+ public abstract int write(AudioInputStream ais, AudioFileFormat.Type type,
+ File out)
+ throws IOException;
+
+ /**
+ * Write audio data to an output stream.
+ * @param ais the audio input stream to write
+ * @param type the desired audio file format type
+ * @param os the output stream
+ * @return the number of bytes written
+ * @throws IOException if an I/O error occurs when writing
+ */
+ public abstract int write(AudioInputStream ais, AudioFileFormat.Type type,
+ OutputStream os)
+ throws IOException;
+}
diff --git a/javax/sound/sampled/spi/FormatConversionProvider.java b/javax/sound/sampled/spi/FormatConversionProvider.java
new file mode 100644
index 000000000..e96cc0454
--- /dev/null
+++ b/javax/sound/sampled/spi/FormatConversionProvider.java
@@ -0,0 +1,179 @@
+/* Format conversion API
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled.spi;
+
+import javax.sound.sampled.AudioFormat;
+import javax.sound.sampled.AudioInputStream;
+
+/**
+ * A format conversion provider supplies methods for converting between
+ * different audio formats. This abstract class defines the interface
+ * to this functionality; concrete subclasses will implement the methods
+ * declared here.
+ * @since 1.3
+ */
+public abstract class FormatConversionProvider
+{
+ /**
+ * Create a new format conversion provider.
+ */
+ public FormatConversionProvider()
+ {
+ }
+
+ /**
+ * Return an audio input stream given the desired target encoding and
+ * another audio input stream. The data in the given stream will be
+ * converted to the desired encoding.
+ * @param encoding the encoding
+ * @param source the source audio input stream
+ * @return a new audio input stream
+ * @throws IllegalArgumentException if the conversion is not supported
+ */
+ public abstract AudioInputStream getAudioInputStream(AudioFormat.Encoding encoding,
+ AudioInputStream source);
+
+ /**
+ * Return an audio input stream given the desired target format and
+ * another audio input stream. The data in the given stream will be
+ * converted to the desired format.
+ * @param format the format
+ * @param source the source audio input stream
+ * @return a new audio input stream
+ * @throws IllegalArgumentException if the conversion is not supported
+ */
+ public abstract AudioInputStream getAudioInputStream(AudioFormat format,
+ AudioInputStream source);
+
+ /**
+ * Return an array of all the source encodings supported by this conversion
+ * provider.
+ */
+ public abstract AudioFormat.Encoding[] getSourceEncodings();
+
+ /**
+ * Return an array of all the target encodings supported by this conversion
+ * provider.
+ */
+ public abstract AudioFormat.Encoding[] getTargetEncodings();
+
+ /**
+ * Return an array of all the target encodings that are available for a given
+ * source format.
+ * @param fmt the source format
+ * @return an array of supported target encodings
+ */
+ public abstract AudioFormat.Encoding[] getTargetEncodings(AudioFormat fmt);
+
+ /**
+ * Return a array of all the target formats that match given target encoding,
+ * and to which this provider can convert the source format.
+ * @param targ the target encoding to match
+ * @param src the source format
+ * @return an array of supported target formats
+ */
+ public abstract AudioFormat[] getTargetFormats(AudioFormat.Encoding targ,
+ AudioFormat src);
+
+ /**
+ * Return true if this provider supports conversion from the given
+ * source format to the given target encoding.
+ * @param targ the target encoding
+ * @param src the source format
+ * @return true if the conversion is supported
+ */
+ public boolean isConversionSupported(AudioFormat.Encoding targ,
+ AudioFormat src)
+ {
+ AudioFormat.Encoding[] encodings = getTargetEncodings(src);
+ for (int i = 0; i < encodings.length; ++i)
+ {
+ if (targ.equals(encodings[i]))
+ return true;
+ }
+ return false;
+ }
+
+ /**
+ * Return true if this provider supports conversions from the given
+ * source format to the given target format.
+ * @param targ the source format
+ * @param src the target format
+ * @return true if the conversion is supported
+ */
+ public boolean isConversionSupported(AudioFormat targ, AudioFormat src)
+ {
+ AudioFormat[] encodings = getTargetFormats(targ.getEncoding(), src);
+ return encodings.length > 0;
+ }
+
+ /**
+ * Return true if an encoding matching the argument is supported as a
+ * source encoding by this provider.
+ * @param src the source encoding
+ * @return true if it is supported
+ */
+ public boolean isSourceEncodingSupported(AudioFormat.Encoding src)
+ {
+ AudioFormat.Encoding[] srcs = getSourceEncodings();
+ for (int i = 0; i < srcs.length; ++i)
+ {
+ if (src.equals(srcs[i]))
+ return true;
+ }
+ return false;
+ }
+
+ /**
+ * Return true if an encoding matching the argument is supported as a
+ * target encoding by this provider.
+ * @param targ the target encoding
+ * @return true if it is supported
+ */
+ public boolean isTargetEncodingSupported(AudioFormat.Encoding targ)
+ {
+ AudioFormat.Encoding[] encodings = getTargetEncodings();
+ for (int i = 0; i < encodings.length; ++i)
+ {
+ if (targ.equals(encodings[i]))
+ return true;
+ }
+ return false;
+ }
+}
diff --git a/javax/sound/sampled/spi/MixerProvider.java b/javax/sound/sampled/spi/MixerProvider.java
new file mode 100644
index 000000000..1ae7b3bb7
--- /dev/null
+++ b/javax/sound/sampled/spi/MixerProvider.java
@@ -0,0 +1,86 @@
+/* Mixer API
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.sound.sampled.spi;
+
+import javax.sound.sampled.Mixer;
+
+/**
+ * This abstract class defines an interface to mixer providers.
+ * Concrete subclasses will implement the methods in this class.
+ * @since 1.3
+ */
+public abstract class MixerProvider
+{
+ /**
+ * Create a new mixer provider.
+ */
+ public MixerProvider()
+ {
+ }
+
+ /**
+ * Return a mixer that matches the given info object.
+ * @param info description of the mixer to match
+ * @return the mixer
+ * @throws IllegalArgumentException if no mixer matches the description
+ */
+ public abstract Mixer getMixer(Mixer.Info info);
+
+ /**
+ * Return an array of info objects describing all the mixers provided by
+ * this provider.
+ */
+ public abstract Mixer.Info[] getMixerInfo();
+
+ /**
+ * Return true if a mixer matching the provided description is supported.
+ * @param info description of the mixer to match
+ * @return true if it is supported by this provider
+ */
+ public boolean isMixerSupported(Mixer.Info info)
+ {
+ Mixer.Info[] infos = getMixerInfo();
+ for (int i = 0; i < infos.length; ++i)
+ {
+ if (info.equals(infos[i]))
+ return true;
+ }
+ return false;
+ }
+}
diff --git a/javax/swing/AbstractButton.java b/javax/swing/AbstractButton.java
index 9d9597639..376b3a056 100644
--- a/javax/swing/AbstractButton.java
+++ b/javax/swing/AbstractButton.java
@@ -956,6 +956,7 @@ public abstract class AbstractButton extends JComponent
if (b == isEnabled())
return;
super.setEnabled(b);
+ setFocusable(b);
ButtonModel mod = getModel();
if (mod != null)
mod.setEnabled(b);
diff --git a/javax/swing/ActionMap.java b/javax/swing/ActionMap.java
index 56bc41de6..65e193d2e 100644
--- a/javax/swing/ActionMap.java
+++ b/javax/swing/ActionMap.java
@@ -171,7 +171,9 @@ public class ActionMap
*/
public Object[] keys()
{
- return actionMap.keySet().toArray();
+ if (size() != 0)
+ return actionMap.keySet().toArray();
+ return null;
}
/**
@@ -188,7 +190,9 @@ public class ActionMap
set.addAll(Arrays.asList(parent.allKeys()));
set.addAll(actionMap.keySet());
- return set.toArray();
+ if (set.size() != 0)
+ return set.toArray();
+ return null;
}
/**
diff --git a/javax/swing/ComponentInputMap.java b/javax/swing/ComponentInputMap.java
index f95c31045..28aa8e22c 100644
--- a/javax/swing/ComponentInputMap.java
+++ b/javax/swing/ComponentInputMap.java
@@ -78,7 +78,8 @@ public class ComponentInputMap extends InputMap
public void put(KeyStroke keystroke, Object value)
{
super.put(keystroke, value);
- // FIXME: Notify component.
+ if (component != null)
+ component.updateComponentInputMap(this);
}
/**
@@ -87,7 +88,8 @@ public class ComponentInputMap extends InputMap
public void clear()
{
super.clear();
- // FIXME: Notify component.
+ if (component != null)
+ component.updateComponentInputMap(this);
}
/**
@@ -98,7 +100,8 @@ public class ComponentInputMap extends InputMap
public void remove(KeyStroke keystroke)
{
super.remove(keystroke);
- // FIXME: Notify component.
+ if (component != null)
+ component.updateComponentInputMap(this);
}
/**
@@ -111,14 +114,19 @@ public class ComponentInputMap extends InputMap
*/
public void setParent(InputMap parentMap)
{
- if (! (parentMap instanceof ComponentInputMap))
- throw new IllegalArgumentException();
-
- if (((ComponentInputMap) parentMap).getComponent() != component)
- throw new IllegalArgumentException();
+ if (parentMap != null && !(parentMap instanceof ComponentInputMap))
+ throw new IllegalArgumentException("ComponentInputMaps can only have " +
+ "ComponentInputMaps for parents");
+
+ if (parentMap != null &&
+ ((ComponentInputMap) parentMap).getComponent() != component)
+ throw new
+ IllegalArgumentException("ComponentInputMaps' parents must " +
+ "be associated with the same JComponents");
super.setParent(parentMap);
- // FIXME: Notify component.
+ if (component != null)
+ component.updateComponentInputMap(this);
}
/**
diff --git a/javax/swing/InputMap.java b/javax/swing/InputMap.java
index a7ec38c41..cc65dfeed 100644
--- a/javax/swing/InputMap.java
+++ b/javax/swing/InputMap.java
@@ -171,8 +171,12 @@ public class InputMap
*/
public KeyStroke[] keys()
{
- KeyStroke[] array = new KeyStroke[size()];
- return (KeyStroke[]) inputMap.keySet().toArray(array);
+ if (size() != 0)
+ {
+ KeyStroke[] array = new KeyStroke[size()];
+ return (KeyStroke[]) inputMap.keySet().toArray(array);
+ }
+ return null;
}
/**
@@ -189,7 +193,9 @@ public class InputMap
set.addAll(Arrays.asList(parent.allKeys()));
set.addAll(inputMap.keySet());
- KeyStroke[] array = new KeyStroke[size()];
+ if (set.size() == 0)
+ return null;
+ KeyStroke[] array = new KeyStroke[set.size()];
return (KeyStroke[]) set.toArray(array);
}
diff --git a/javax/swing/JApplet.java b/javax/swing/JApplet.java
index 22bbe92bf..e90c45189 100644
--- a/javax/swing/JApplet.java
+++ b/javax/swing/JApplet.java
@@ -85,20 +85,13 @@ public class JApplet extends Applet
/**
* @specnote rootPaneCheckingEnabled is false to comply with J2SE 5.0
*/
- protected boolean rootPaneCheckingEnabled=false;
-
- /**
- * Tells us if we're in the initialization stage.
- * If so, adds go to top-level Container, otherwise they go
- * to the content pane for this container
- */
- private boolean initStageDone = false;
+ protected boolean rootPaneCheckingEnabled = false;
public JApplet()
{
super.setLayout(new BorderLayout(1, 1));
getRootPane(); // Will do set/create.
- initStageDone = true; // Init stage is now over.
+ setRootPaneCheckingEnabled(true); // Init stage is now over.
}
public Dimension getPreferredSize()
@@ -110,13 +103,8 @@ public class JApplet extends Applet
{
// Check if we're in initialization stage. If so, call super.setLayout
// otherwise, valid calls go to the content pane
- if (initStageDone)
- {
- if (isRootPaneCheckingEnabled())
- throw new Error("Cannot set layout. Use getContentPane().setLayout()"
- + "instead.");
- getContentPane().setLayout(manager);
- }
+ if (isRootPaneCheckingEnabled())
+ getContentPane().setLayout(manager);
else
super.setLayout(manager);
}
@@ -176,15 +164,10 @@ public class JApplet extends Applet
{
// If we're adding in the initialization stage use super.add.
// Otherwise pass the add onto the content pane.
- if (!initStageDone)
- super.addImpl(comp, constraints, index);
+ if (isRootPaneCheckingEnabled())
+ getContentPane().add(comp, constraints, index);
else
- {
- if (isRootPaneCheckingEnabled())
- throw new Error("Do not use add() on JApplet directly. Use "
- + "getContentPane().add() instead");
- getContentPane().add(comp, constraints, index);
- }
+ super.addImpl(comp, constraints, index);
}
public AccessibleContext getAccessibleContext()
@@ -206,7 +189,7 @@ public class JApplet extends Applet
protected String paramString()
{
- return "JFrame";
+ return super.paramString();
}
protected void processKeyEvent(KeyEvent e)
diff --git a/javax/swing/JComponent.java b/javax/swing/JComponent.java
index a800501d7..6f9c9dcf8 100644
--- a/javax/swing/JComponent.java
+++ b/javax/swing/JComponent.java
@@ -390,7 +390,7 @@ public abstract class JComponent extends Container implements Serializable
* @see javax.swing.OverlayLayout
* @see javax.swing.BoxLayout
*/
- float alignmentX = 0.5f;
+ float alignmentX = -1.0F;
/**
* A value between 0.0 and 1.0 indicating the preferred vertical
@@ -405,7 +405,7 @@ public abstract class JComponent extends Container implements Serializable
* @see javax.swing.OverlayLayout
* @see javax.swing.BoxLayout
*/
- float alignmentY = 0.5f;
+ float alignmentY = -1.0F;
/**
* The border painted around this component.
@@ -546,7 +546,7 @@ public abstract class JComponent extends Container implements Serializable
private InputMap inputMap_whenFocused;
private InputMap inputMap_whenAncestorOfFocused;
- private InputMap inputMap_whenInFocusedWindow;
+ private ComponentInputMap inputMap_whenInFocusedWindow;
private ActionMap actionMap;
/** @since 1.3 */
private boolean verifyInputWhenFocusTarget;
@@ -555,6 +555,11 @@ public abstract class JComponent extends Container implements Serializable
private TransferHandler transferHandler;
/**
+ * Indicates if this component is currently painting a tile or not.
+ */
+ private boolean paintingTile;
+
+ /**
* A cached Rectangle object to be reused. Be careful when you use that,
* so that it doesn't get modified in another context within the same
* method call chain.
@@ -796,14 +801,23 @@ public abstract class JComponent extends Container implements Serializable
}
/**
- * Return all registered listeners of a particular type.
- *
- * @param listenerType The type of listener to return
- *
- * @return All listeners in the {@link #listenerList} which
- * are of the specified type
+ * Returns all registered {@link EventListener}s of the given
+ * <code>listenerType</code>.
*
+ * @param listenerType the class of listeners to filter (<code>null</code>
+ * not permitted).
+ *
+ * @return An array of registered listeners.
+ *
+ * @throws ClassCastException if <code>listenerType</code> does not implement
+ * the {@link EventListener} interface.
+ * @throws NullPointerException if <code>listenerType</code> is
+ * <code>null</code>.
+ *
+ * @see #getAncestorListeners()
* @see #listenerList
+ *
+ * @since 1.3
*/
public <T extends EventListener> T[] getListeners(Class<T> listenerType)
{
@@ -983,7 +997,8 @@ public abstract class JComponent extends Container implements Serializable
{
VetoableChangeListener[] listeners = getVetoableChangeListeners();
- PropertyChangeEvent evt = new PropertyChangeEvent(this, propertyName, oldValue, newValue);
+ PropertyChangeEvent evt =
+ new PropertyChangeEvent(this, propertyName, oldValue, newValue);
for (int i = 0; i < listeners.length; i++)
listeners[i].vetoableChange(evt);
@@ -1009,7 +1024,12 @@ public abstract class JComponent extends Container implements Serializable
*/
public float getAlignmentX()
{
- return alignmentX;
+ float ret = alignmentX;
+ if (alignmentX < 0)
+ // alignment has not been set explicitly.
+ ret = super.getAlignmentX();
+
+ return ret;
}
/**
@@ -1022,7 +1042,12 @@ public abstract class JComponent extends Container implements Serializable
*/
public float getAlignmentY()
{
- return alignmentY;
+ float ret = alignmentY;
+ if (alignmentY < 0)
+ // alignment has not been set explicitly.
+ ret = super.getAlignmentY();
+
+ return ret;
}
/**
@@ -1604,13 +1629,16 @@ public abstract class JComponent extends Container implements Serializable
}
/**
- * Return <code>true</code> if this component is currently painting a tile.
+ * Return <code>true</code> if this component is currently painting a tile,
+ * this means that paint() is called again on another child component. This
+ * method returns <code>false</code> if this component does not paint a tile
+ * or if the last tile is currently painted.
*
- * @return Whether the component is painting a tile
+ * @return whether the component is painting a tile
*/
public boolean isPaintingTile()
{
- return false;
+ return paintingTile;
}
/**
@@ -1675,10 +1703,11 @@ public abstract class JComponent extends Container implements Serializable
{
if (g.getClip() == null)
g.setClip(0, 0, getWidth(), getHeight());
- paintComponent(g);
- paintBorder(g);
- paintChildren(g);
- Rectangle clip = g.getClipBounds();
+ Graphics g2 = getComponentGraphics(g);
+ paintComponent(g2);
+ paintBorder(g2);
+ paintChildren(g2);
+ Rectangle clip = g2.getClipBounds();
if (clip.x == 0 && clip.y == 0 && clip.width == getWidth()
&& clip.height == getHeight())
RepaintManager.currentManager(this).markCompletelyClean(this);
@@ -1724,8 +1753,38 @@ public abstract class JComponent extends Container implements Serializable
Rectangle inner = SwingUtilities.calculateInnerArea(this, rectCache);
g.clipRect(inner.x, inner.y, inner.width, inner.height);
Component[] children = getComponents();
- for (int i = children.length - 1; i >= 0; --i)
+
+ // Find the bottommost component that needs to be painted. This is a
+ // component that completely covers the current clip and is opaque. In
+ // this case we don't need to paint the components below it.
+ int startIndex = children.length - 1;
+ // No need to check for overlapping components when this component is
+ // optimizedDrawingEnabled (== it tiles its children).
+ if (! isOptimizedDrawingEnabled())
+ {
+ Rectangle clip = g.getClipBounds();
+ for (int i = 0; i < children.length; i++)
+ {
+ Rectangle childBounds = children[i].getBounds();
+ if (children[i].isOpaque()
+ && SwingUtilities.isRectangleContainingRectangle(childBounds,
+ g.getClipBounds()))
+ {
+ startIndex = i;
+ break;
+ }
+ }
+ }
+ // paintingTile becomes true just before we start painting the component's
+ // children.
+ paintingTile = true;
+ for (int i = startIndex; i >= 0; --i)
{
+ // paintingTile must be set to false before we begin to start painting
+ // the last tile.
+ if (i == 0)
+ paintingTile = false;
+
if (!children[i].isVisible())
continue;
@@ -1775,7 +1834,7 @@ public abstract class JComponent extends Container implements Serializable
Graphics g2 = g;
if (!(g instanceof Graphics2D))
g2 = g.create();
- ui.update(getComponentGraphics(g2), this);
+ ui.update(g2, this);
if (!(g instanceof Graphics2D))
g2.dispose();
}
@@ -1868,9 +1927,15 @@ public abstract class JComponent extends Container implements Serializable
g2 = getComponentGraphics(g2);
g2.setClip(r.x, r.y, r.width, r.height);
isPaintingDoubleBuffered = true;
- paint(g2);
- isPaintingDoubleBuffered = false;
- g2.dispose();
+ try
+ {
+ paint(g2);
+ }
+ finally
+ {
+ isPaintingDoubleBuffered = false;
+ g2.dispose();
+ }
// Paint the buffer contents on screen.
g.drawImage(buffer, 0, 0, this);
@@ -2011,7 +2076,11 @@ public abstract class JComponent extends Container implements Serializable
break;
case WHEN_IN_FOCUSED_WINDOW:
- inputMap_whenInFocusedWindow = map;
+ if (map != null && !(map instanceof ComponentInputMap))
+ throw new
+ IllegalArgumentException("WHEN_IN_FOCUSED_WINDOW " +
+ "InputMap must be a ComponentInputMap");
+ inputMap_whenInFocusedWindow = (ComponentInputMap)map;
break;
case UNDEFINED_CONDITION:
@@ -2037,7 +2106,7 @@ public abstract class JComponent extends Container implements Serializable
case WHEN_IN_FOCUSED_WINDOW:
if (inputMap_whenInFocusedWindow == null)
- inputMap_whenInFocusedWindow = new InputMap();
+ inputMap_whenInFocusedWindow = new ComponentInputMap(this);
return inputMap_whenInFocusedWindow;
case UNDEFINED_CONDITION:
@@ -2152,40 +2221,56 @@ public abstract class JComponent extends Container implements Serializable
// 4. The WHEN_IN_FOCUSED_WINDOW maps of all the enabled components in
// the focused window are searched.
- if (processKeyBinding(KeyStroke.getKeyStrokeForEvent(e),
- e, WHEN_FOCUSED, e.getID() == KeyEvent.KEY_PRESSED))
- // This is step 1 from above comment.
- e.consume();
- else if (processKeyBinding(KeyStroke.getKeyStrokeForEvent(e),
- e, WHEN_ANCESTOR_OF_FOCUSED_COMPONENT,
- e.getID() == KeyEvent.KEY_PRESSED))
- // This is step 2 from above comment.
- e.consume();
- else
+ KeyStroke keyStroke = KeyStroke.getKeyStrokeForEvent(e);
+ boolean pressed = e.getID() == KeyEvent.KEY_PRESSED;
+
+ if (processKeyBinding(keyStroke, e, WHEN_FOCUSED, pressed))
{
- // This is step 3 from above comment.
- Container current = this;
- while ((current = current.getParent()) instanceof JComponent)
+ // This is step 1 from above comment.
+ e.consume();
+ return;
+ }
+ else if (processKeyBinding
+ (keyStroke, e, WHEN_ANCESTOR_OF_FOCUSED_COMPONENT, pressed))
+ {
+ // This is step 2 from above comment.
+ e.consume();
+ return;
+ }
+
+ // This is step 3 from above comment.
+ Container current = getParent();
+ while (current != null)
+ {
+ // If current is a JComponent, see if it handles the event in its
+ // WHEN_ANCESTOR_OF_FOCUSED_COMPONENT maps.
+ if ((current instanceof JComponent) &&
+ ((JComponent)current).processKeyBinding
+ (keyStroke, e,WHEN_ANCESTOR_OF_FOCUSED_COMPONENT, pressed))
{
- if (((JComponent)current).processKeyBinding
- (KeyStroke.getKeyStrokeForEvent(e), e,
- WHEN_ANCESTOR_OF_FOCUSED_COMPONENT,
- e.getID() == KeyEvent.KEY_PRESSED))
- {
- e.consume();
- break;
- }
- if (current instanceof Window || current instanceof Applet
- || current instanceof JInternalFrame)
- break;
- }
- if (e.isConsumed())
- return;
+ e.consume();
+ return;
+ }
+
+ // Stop when we've tried a top-level container and it didn't handle it
+ if (current instanceof Window || current instanceof Applet)
+ break;
- // This is step 4 from above comment.
- // FIXME: Implement. Note, should use ComponentInputMaps rather
- // than walking the entire containment hierarchy.
+ // Move up the hierarchy
+ current = current.getParent();
}
+
+ // Current being null means the JComponent does not currently have a
+ // top-level ancestor, in which case we don't need to check
+ // WHEN_IN_FOCUSED_WINDOW bindings.
+ if (current == null || e.isConsumed())
+ return;
+
+ // This is step 4 from above comment. KeyboardManager maintains mappings
+ // related to WHEN_IN_FOCUSED_WINDOW bindings so that we don't have to
+ // traverse the containment hierarchy each time.
+ if (KeyboardManager.getManager().processKeyStroke(current, keyStroke, e))
+ e.consume();
}
protected boolean processKeyBinding(KeyStroke ks,
@@ -2337,7 +2422,12 @@ public abstract class JComponent extends Container implements Serializable
*/
public void setAlignmentX(float a)
{
- alignmentX = a;
+ if (a < 0.0F)
+ alignmentX = 0.0F;
+ else if (a > 1.0)
+ alignmentX = 1.0F;
+ else
+ alignmentX = a;
}
/**
@@ -2347,7 +2437,12 @@ public abstract class JComponent extends Container implements Serializable
*/
public void setAlignmentY(float a)
{
- alignmentY = a;
+ if (a < 0.0F)
+ alignmentY = 0.0F;
+ else if (a > 1.0)
+ alignmentY = 1.0F;
+ else
+ alignmentY = a;
}
/**
@@ -2435,38 +2530,53 @@ public abstract class JComponent extends Container implements Serializable
}
/**
- * Set the value of the {@link #maximumSize} property.
+ * Set the value of the {@link #maximumSize} property. The passed value is
+ * copied, the later direct changes on the argument have no effect on the
+ * property value.
*
* @param max The new value of the property
*/
public void setMaximumSize(Dimension max)
{
Dimension oldMaximumSize = maximumSize;
- maximumSize = max;
+ if (max != null)
+ maximumSize = new Dimension(max);
+ else
+ maximumSize = null;
firePropertyChange("maximumSize", oldMaximumSize, maximumSize);
}
/**
- * Set the value of the {@link #minimumSize} property.
+ * Set the value of the {@link #minimumSize} property. The passed value is
+ * copied, the later direct changes on the argument have no effect on the
+ * property value.
*
* @param min The new value of the property
*/
public void setMinimumSize(Dimension min)
{
Dimension oldMinimumSize = minimumSize;
- minimumSize = min;
+ if (min != null)
+ minimumSize = new Dimension(min);
+ else
+ minimumSize = null;
firePropertyChange("minimumSize", oldMinimumSize, minimumSize);
}
/**
- * Set the value of the {@link #preferredSize} property.
+ * Set the value of the {@link #preferredSize} property. The passed value is
+ * copied, the later direct changes on the argument have no effect on the
+ * property value.
*
* @param pref The new value of the property
*/
public void setPreferredSize(Dimension pref)
{
Dimension oldPreferredSize = preferredSize;
- preferredSize = pref;
+ if (pref != null)
+ preferredSize = new Dimension(pref);
+ else
+ preferredSize = null;
firePropertyChange("preferredSize", oldPreferredSize, preferredSize);
}
@@ -2797,41 +2907,22 @@ public abstract class JComponent extends Container implements Serializable
*/
public void addNotify()
{
+ // Register the WHEN_IN_FOCUSED_WINDOW keyboard bindings
+ // Note that here we unregister all bindings associated with
+ // this component and then re-register them. This may be more than
+ // necessary if the top-level ancestor hasn't changed. Should
+ // maybe improve this.
+ KeyboardManager km = KeyboardManager.getManager();
+ km.clearBindingsForComp(this);
+ km.registerEntireMap((ComponentInputMap)
+ this.getInputMap(WHEN_IN_FOCUSED_WINDOW));
super.addNotify();
- // let parents inherit the keybord mapping
- InputMap input = getInputMap();
- ActionMap actions = getActionMap();
-
- Container parent = getParent();
- while ((parent != null) && (parent instanceof JComponent))
- {
- JComponent jParent = (JComponent) parent;
- InputMap parentInput = jParent.getInputMap();
- ActionMap parentAction = jParent.getActionMap();
-
- KeyStroke[] ikeys = input.keys();
- for (int i = 0; i < ikeys.length; i++)
- {
- Object o = input.get(ikeys[i]);
- parentInput.put(ikeys[i], o);
- }
-
- Object[] akeys = actions.keys();
- for (int i = 0; i < akeys.length; i++)
- {
- Action a = actions.get(akeys[i]);
- parentAction.put(akeys[i], a);
- }
-
- parent = jParent.getParent();
- }
-
// Notify AncestorListeners.
fireAncestorEvent(this, AncestorEvent.ANCESTOR_ADDED);
// fire property change event for 'ancestor'
- firePropertyChange("ancestor", null, parent);
+ firePropertyChange("ancestor", null, getParent());
}
/**
@@ -2854,37 +2945,13 @@ public abstract class JComponent extends Container implements Serializable
{
super.removeNotify();
- // let parents inherit the keybord mapping
- InputMap input = getInputMap();
- ActionMap actions = getActionMap();
-
- Container parent = getParent();
- while ((parent != null) && (parent instanceof JComponent))
- {
- JComponent jParent = (JComponent) parent;
- InputMap parentInput = jParent.getInputMap();
- ActionMap parentAction = jParent.getActionMap();
-
- KeyStroke[] ikeys = input.allKeys();
- for (int i = 0; i < ikeys.length; i++)
- {
- parentInput.remove(ikeys[i]);
- }
-
- Object[] akeys = actions.allKeys();
- for (int i = 0; i < akeys.length; i++)
- {
- parentAction.remove(akeys[i]);
- }
-
- parent = jParent.getParent();
- }
-
+ KeyboardManager.getManager().clearBindingsForComp(this);
+
// Notify ancestor listeners.
fireAncestorEvent(this, AncestorEvent.ANCESTOR_REMOVED);
// fire property change event for 'ancestor'
- firePropertyChange("ancestor", parent, null);
+ firePropertyChange("ancestor", getParent(), null);
}
/**
@@ -3271,4 +3338,35 @@ public abstract class JComponent extends Container implements Serializable
}
return found;
}
+
+ /**
+ * This is the method that gets called when the WHEN_IN_FOCUSED_WINDOW map
+ * is changed.
+ *
+ * @param changed the JComponent associated with the WHEN_IN_FOCUSED_WINDOW
+ * map
+ */
+ void updateComponentInputMap(ComponentInputMap changed)
+ {
+ // Since you can change a component's input map via
+ // setInputMap, we have to check if <code>changed</code>
+ // is still in our WHEN_IN_FOCUSED_WINDOW map hierarchy
+ InputMap curr = getInputMap(WHEN_IN_FOCUSED_WINDOW);
+ while (curr != null && curr != changed)
+ curr = curr.getParent();
+
+ // If curr is null then changed is not in the hierarchy
+ if (curr == null)
+ return;
+
+ // Now we have to update the keyboard manager's hashtable
+ KeyboardManager km = KeyboardManager.getManager();
+
+ // This is a poor strategy, should be improved. We currently
+ // delete all the old bindings for the component and then register
+ // the current bindings.
+ km.clearBindingsForComp(changed.getComponent());
+ km.registerEntireMap((ComponentInputMap)
+ getInputMap(WHEN_IN_FOCUSED_WINDOW));
+ }
}
diff --git a/javax/swing/JDialog.java b/javax/swing/JDialog.java
index 10b4e0d86..b3f7c011f 100644
--- a/javax/swing/JDialog.java
+++ b/javax/swing/JDialog.java
@@ -102,13 +102,6 @@ public class JDialog extends Dialog implements Accessible, WindowConstants,
/** Whether JDialogs are decorated by the Look and Feel. */
private static boolean decorated;
- /**
- * Whether we're in the init stage or not.
- * If so, adds and layouts are for top-level, otherwise they're for the
- * content pane
- */
- private boolean initStageDone = false;
-
/* Creates a new non-modal JDialog with no title
* using a shared Frame as the owner.
*/
@@ -259,7 +252,7 @@ public class JDialog extends Dialog implements Accessible, WindowConstants,
invalidate();
// Now that initStageDone is true, adds and layouts apply to contentPane,
// not top-level.
- initStageDone = true;
+ setRootPaneCheckingEnabled(true);
}
/**
@@ -330,13 +323,8 @@ public class JDialog extends Dialog implements Accessible, WindowConstants,
{
// Check if we're in initialization stage. If so, call super.setLayout
// otherwise, valid calls go to the content pane.
- if (initStageDone)
- {
- if (isRootPaneCheckingEnabled())
- throw new Error("Cannot set top-level layout. Use"
- + " getConentPane().setLayout instead.");
- getContentPane().setLayout(manager);
- }
+ if (isRootPaneCheckingEnabled())
+ getContentPane().setLayout(manager);
else
super.setLayout(manager);
}
@@ -460,15 +448,10 @@ public class JDialog extends Dialog implements Accessible, WindowConstants,
{
// If we're adding in the initialization stage use super.add.
// Otherwise pass the add onto the content pane.
- if (!initStageDone)
- super.addImpl(comp, constraints, index);
+ if (isRootPaneCheckingEnabled())
+ getContentPane().add(comp, constraints, index);
else
- {
- if (isRootPaneCheckingEnabled())
- throw new Error("Do not add directly to JDialog."
- + " Use getContentPane().add instead.");
- getContentPane().add(comp, constraints, index);
- }
+ super.addImpl(comp, constraints, index);
}
/**
diff --git a/javax/swing/JEditorPane.java b/javax/swing/JEditorPane.java
index 9ddf970de..6e99a9595 100644
--- a/javax/swing/JEditorPane.java
+++ b/javax/swing/JEditorPane.java
@@ -59,6 +59,9 @@ import javax.swing.text.Document;
import javax.swing.text.EditorKit;
import javax.swing.text.Element;
import javax.swing.text.JTextComponent;
+import javax.swing.text.View;
+import javax.swing.text.ViewFactory;
+import javax.swing.text.WrappedPlainView;
import javax.swing.text.html.HTML;
import javax.swing.text.html.HTMLDocument;
import javax.swing.text.html.HTMLEditorKit;
@@ -165,6 +168,14 @@ public class JEditorPane extends JTextComponent
{
/**
+ * Creates a new JEditorPaneAccessibleHypertextSupport object.
+ */
+ public JEditorPaneAccessibleHypertextSupport()
+ {
+ super();
+ }
+
+ /**
* The accessible representation of a HTML link.
*
* @author Roman Kennke (kennke@aicas.com)
@@ -466,6 +477,30 @@ public class JEditorPane extends JTextComponent
}
}
+ /**
+ * An EditorKit used for plain text. This is the default editor kit for
+ * JEditorPanes.
+ *
+ * @author Roman Kennke (kennke@aicas.com)
+ */
+ private static class PlainEditorKit extends DefaultEditorKit
+ {
+
+ /**
+ * Returns a ViewFactory that supplies WrappedPlainViews.
+ */
+ public ViewFactory getViewFactory()
+ {
+ return new ViewFactory()
+ {
+ public View create(Element el)
+ {
+ return new WrappedPlainView(el);
+ }
+ };
+ }
+ }
+
private static final long serialVersionUID = 3140472492599046285L;
private URL page;
@@ -497,12 +532,12 @@ public class JEditorPane extends JTextComponent
protected EditorKit createDefaultEditorKit()
{
- return new DefaultEditorKit();
+ return new PlainEditorKit();
}
public static EditorKit createEditorKitForContentType(String type)
{
- return new DefaultEditorKit();
+ return new PlainEditorKit();
}
/**
diff --git a/javax/swing/JFileChooser.java b/javax/swing/JFileChooser.java
index 1598641f1..fcd0aff65 100644
--- a/javax/swing/JFileChooser.java
+++ b/javax/swing/JFileChooser.java
@@ -407,8 +407,7 @@ public class JFileChooser extends JComponent implements Accessible
*/
public JFileChooser(String currentDirectoryPath)
{
- setup(null);
- setCurrentDirectory(fsv.createFileObject(currentDirectoryPath));
+ this(currentDirectoryPath, null);
}
/**
@@ -424,7 +423,10 @@ public class JFileChooser extends JComponent implements Accessible
public JFileChooser(String currentDirectoryPath, FileSystemView fsv)
{
setup(fsv);
- setCurrentDirectory(fsv.createFileObject(currentDirectoryPath));
+ File dir = null;
+ if (currentDirectoryPath != null)
+ dir = getFileSystemView().createFileObject(currentDirectoryPath);
+ setCurrentDirectory(dir);
}
/**
@@ -525,7 +527,7 @@ public class JFileChooser extends JComponent implements Accessible
*/
public void setSelectedFile(File file)
{
- if (selectedFile != file)
+ if (selectedFile == null || !selectedFile.equals(file))
{
File old = selectedFile;
selectedFile = file;
@@ -534,10 +536,10 @@ public class JFileChooser extends JComponent implements Accessible
}
/**
- * Returns the selected file or files.
+ * Returns the selected file or files in an array. If no files are selected,
+ * an empty array is returned.
*
- * @return An array of the selected files, or <code>null</code> if there are
- * no selected files.
+ * @return An array of the selected files (possibly empty).
*/
public File[] getSelectedFiles()
{
@@ -545,7 +547,7 @@ public class JFileChooser extends JComponent implements Accessible
return selectedFiles;
if (selectedFile != null)
return new File[] { selectedFile };
- return null;
+ return new File[0];
}
/**
@@ -557,6 +559,12 @@ public class JFileChooser extends JComponent implements Accessible
*/
public void setSelectedFiles(File[] selectedFiles)
{
+ if (selectedFiles == null)
+ selectedFiles = new File[0];
+ if (selectedFiles.length > 0)
+ setSelectedFile(selectedFiles[0]);
+ else
+ setSelectedFile(null);
if (this.selectedFiles != selectedFiles)
{
File[] old = this.selectedFiles;
@@ -564,8 +572,6 @@ public class JFileChooser extends JComponent implements Accessible
firePropertyChange(SELECTED_FILES_CHANGED_PROPERTY, old, selectedFiles);
}
- if (selectedFiles != null)
- setSelectedFile(selectedFiles[0]);
}
/**
@@ -607,8 +613,7 @@ public class JFileChooser extends JComponent implements Accessible
*/
public void changeToParentDirectory()
{
- if (fsv.getParentDirectory(currentDir) != null)
- setCurrentDirectory(fsv.getParentDirectory(currentDir));
+ setCurrentDirectory(fsv.getParentDirectory(currentDir));
}
/**
@@ -958,14 +963,19 @@ public class JFileChooser extends JComponent implements Accessible
* {@link #CHOOSABLE_FILE_FILTER_CHANGED_PROPERTY}) to all registered
* listeners.
*
- * @param filter the filter.
+ * @param filter the filter (<code>null</code> permitted).
*/
public void addChoosableFileFilter(FileFilter filter)
{
- FileFilter[] old = getChoosableFileFilters();
- choosableFilters.add(filter);
- FileFilter[] newFilters = getChoosableFileFilters();
- firePropertyChange(CHOOSABLE_FILE_FILTER_CHANGED_PROPERTY, old, newFilters);
+ if (filter != null)
+ {
+ FileFilter[] old = getChoosableFileFilters();
+ choosableFilters.add(filter);
+ FileFilter[] newFilters = getChoosableFileFilters();
+ firePropertyChange(CHOOSABLE_FILE_FILTER_CHANGED_PROPERTY, old,
+ newFilters);
+ }
+ setFileFilter(filter);
}
/**
@@ -981,6 +991,8 @@ public class JFileChooser extends JComponent implements Accessible
*/
public boolean removeChoosableFileFilter(FileFilter f)
{
+ if (f == currentFilter)
+ setFileFilter(null);
FileFilter[] old = getChoosableFileFilters();
if (! choosableFilters.remove(f))
return false;
@@ -1037,6 +1049,10 @@ public class JFileChooser extends JComponent implements Accessible
if (isAcceptAll != b)
{
isAcceptAll = b;
+ if (b)
+ addChoosableFileFilter(getAcceptAllFileFilter());
+ else
+ removeChoosableFileFilter(getAcceptAllFileFilter());
firePropertyChange(ACCEPT_ALL_FILE_FILTER_USED_CHANGED_PROPERTY,
! isAcceptAll, isAcceptAll);
}
@@ -1208,15 +1224,17 @@ public class JFileChooser extends JComponent implements Accessible
* property name {@link #FILE_FILTER_CHANGED_PROPERTY}) to all registered
* listeners.
*
- * @param filter the filter.
+ * @param filter the filter (<code>null</code> permitted).
*/
public void setFileFilter(FileFilter filter)
{
if (currentFilter != filter)
{
- FileFilter old = currentFilter;
- currentFilter = filter;
- firePropertyChange(FILE_FILTER_CHANGED_PROPERTY, old, currentFilter);
+ if (filter != null && !choosableFilters.contains(filter))
+ addChoosableFileFilter(filter);
+ FileFilter old = currentFilter;
+ currentFilter = filter;
+ firePropertyChange(FILE_FILTER_CHANGED_PROPERTY, old, currentFilter);
}
}
@@ -1356,8 +1374,12 @@ public class JFileChooser extends JComponent implements Accessible
public boolean accept(File f)
{
if (f == null)
- return false;
- return getFileFilter().accept(f);
+ return true;
+ FileFilter ff = getFileFilter();
+ if (ff != null)
+ return ff.accept(f);
+ else
+ return true;
}
/**
diff --git a/javax/swing/JFrame.java b/javax/swing/JFrame.java
index d8c3d9654..8d4dcb53b 100644
--- a/javax/swing/JFrame.java
+++ b/javax/swing/JFrame.java
@@ -102,13 +102,6 @@ public class JFrame extends Frame
*/
protected boolean rootPaneCheckingEnabled = false;
- /**
- * Tells us if we're in the initialization stage.
- * If so, adds go to top-level Container, otherwise they go
- * to the content pane for this container.
- */
- private boolean initStageDone = false;
-
public JFrame()
{
super("JFrame");
@@ -158,7 +151,7 @@ public class JFrame extends Frame
enableEvents(AWTEvent.WINDOW_EVENT_MASK);
getRootPane(); // will do set/create
// We're now done the init stage.
- initStageDone = true;
+ setRootPaneCheckingEnabled(true);
}
public Dimension getPreferredSize()
@@ -180,13 +173,8 @@ public class JFrame extends Frame
{
// Check if we're in initialization stage. If so, call super.setLayout
// otherwise, valid calls go to the content pane.
- if (initStageDone)
- {
- if (isRootPaneCheckingEnabled())
- throw new Error("Cannot set layout. Use getContentPane().setLayout()"
- + " instead.");
- getContentPane().setLayout(manager);
- }
+ if (isRootPaneCheckingEnabled())
+ getContentPane().setLayout(manager);
else
super.setLayout(manager);
}
@@ -246,15 +234,10 @@ public class JFrame extends Frame
{
// If we're adding in the initialization stage use super.add.
// Otherwise pass the add onto the content pane.
- if (!initStageDone)
- super.addImpl(comp, constraints, index);
+ if (isRootPaneCheckingEnabled())
+ getContentPane().add(comp,constraints,index);
else
- {
- if (isRootPaneCheckingEnabled())
- throw new Error("rootPaneChecking is enabled - adding components "
- + "disallowed.");
- getContentPane().add(comp,constraints,index);
- }
+ super.addImpl(comp, constraints, index);
}
public void remove(Component comp)
diff --git a/javax/swing/JInternalFrame.java b/javax/swing/JInternalFrame.java
index b504aaaa5..479294b13 100644
--- a/javax/swing/JInternalFrame.java
+++ b/javax/swing/JInternalFrame.java
@@ -437,13 +437,6 @@ public class JInternalFrame extends JComponent implements Accessible,
*/
protected boolean rootPaneCheckingEnabled = false;
- /**
- * Tells us if we're in the initialization stage.
- * If so, adds go to top-level Container, otherwise they go
- * to the content pane for this container.
- */
- private boolean initStageDone = false;
-
/** Whether the JInternalFrame is resizable. */
protected boolean resizable;
@@ -567,7 +560,7 @@ public class JInternalFrame extends JComponent implements Accessible,
storedBounds = new Rectangle();
setRootPane(createRootPane());
updateUI();
- initStageDone = true; // Done the init stage, now adds go to content pane.
+ setRootPaneCheckingEnabled(true); // Done the init stage, now adds go to content pane.
}
/**
@@ -587,15 +580,10 @@ public class JInternalFrame extends JComponent implements Accessible,
// If we're in the initialization stage use super.add. Here we add the
// rootPane as well as the title bar and other stuff.
// Otherwise pass the add onto the content pane.
- if (!initStageDone)
- super.addImpl(comp,constraints, index);
+ if (isRootPaneCheckingEnabled())
+ getContentPane().add(comp, constraints, index);
else
- {
- if (isRootPaneCheckingEnabled())
- throw new Error("Do not use add() on JInternalFrame directly. Use "
- + "getContentPane().add() instead");
- getContentPane().add(comp, constraints, index);
- }
+ super.addImpl(comp,constraints, index);
}
/**
@@ -1187,7 +1175,7 @@ public class JInternalFrame extends JComponent implements Accessible,
*/
protected String paramString()
{
- return "JInternalFrame";
+ return super.paramString();
}
/**
@@ -1227,8 +1215,7 @@ public class JInternalFrame extends JComponent implements Accessible,
public void reshape(int x, int y, int width, int height)
{
super.reshape(x, y, width, height);
- invalidate();
- doLayout();
+ revalidate();
}
/**
@@ -1489,13 +1476,8 @@ public class JInternalFrame extends JComponent implements Accessible,
{
// Check if we're in initialization stage. If so, call super.setLayout
// otherwise, valid calls go to the content pane.
- if (initStageDone)
- {
- if (isRootPaneCheckingEnabled())
- throw new Error("Cannot set layout. Use getContentPane().setLayout()"
- + " instead.");
- getContentPane().setLayout(manager);
- }
+ if (isRootPaneCheckingEnabled())
+ getContentPane().setLayout(manager);
else
super.setLayout(manager);
}
@@ -1678,7 +1660,12 @@ public class JInternalFrame extends JComponent implements Accessible,
*/
public void setUI(InternalFrameUI ui)
{
+ // We must temporarily go into init mode so that the UI can directly
+ // manipulate the JInternalFrame.
+ boolean old = isRootPaneCheckingEnabled();
+ setRootPaneCheckingEnabled(false);
super.setUI(ui);
+ setRootPaneCheckingEnabled(old);
}
/**
@@ -1704,7 +1691,13 @@ public class JInternalFrame extends JComponent implements Accessible,
*/
public void updateUI()
{
+ // We must go into the init stage when updating the UI, so the UI can
+ // set layout and components directly on the internal frame, not its
+ // content pane.
+ boolean old = isRootPaneCheckingEnabled();
+ setRootPaneCheckingEnabled(false);
setUI((InternalFrameUI) UIManager.getUI(this));
+ setRootPaneCheckingEnabled(old);
}
/**
diff --git a/javax/swing/JLayeredPane.java b/javax/swing/JLayeredPane.java
index c4b5c61da..31222778a 100644
--- a/javax/swing/JLayeredPane.java
+++ b/javax/swing/JLayeredPane.java
@@ -38,9 +38,12 @@ exception statement from your version. */
package javax.swing;
+import java.awt.Color;
import java.awt.Component;
import java.awt.Container;
import java.awt.Graphics;
+import java.awt.Rectangle;
+import java.awt.Shape;
import java.util.Hashtable;
import java.util.Iterator;
import java.util.Map;
@@ -158,6 +161,8 @@ public class JLayeredPane extends JComponent implements Accessible
TreeMap layers; // Layer Number (Integer) -> Layer Size (Integer)
Hashtable componentToLayer; // Component -> Layer Number (Integer)
+ private transient Rectangle rectCache;
+
public JLayeredPane()
{
layers = new TreeMap ();
@@ -250,22 +255,30 @@ public class JLayeredPane extends JComponent implements Accessible
ret[1] = getComponents ().length;
Iterator i = layers.entrySet ().iterator ();
while (i.hasNext())
- {
+ {
Map.Entry pair = (Map.Entry) i.next();
Integer layerNum = (Integer) pair.getKey ();
Integer layerSz = (Integer) pair.getValue ();
- if (layerNum.intValue() == layer.intValue())
+ int layerInt = layerNum.intValue();
+ if (layerInt == layer.intValue())
{
ret[0] = ret[1] - layerSz.intValue ();
- return ret;
+ break;
+ }
+ // In the following case there exists no layer with the specified
+ // number, so we return an empty interval here with the index at which
+ // such a layer would be inserted
+ else if (layerInt > layer.intValue())
+ {
+ ret[1] = ret[0];
+ break;
}
else
{
ret[1] -= layerSz.intValue ();
}
- }
- // should have found the layer during iteration
- throw new IllegalArgumentException ();
+ }
+ return ret;
}
/**
@@ -629,7 +642,7 @@ public class JLayeredPane extends JComponent implements Accessible
* @param index an ignored parameter, for compatibility.
*/
protected void addImpl(Component comp, Object layerConstraint, int index)
- {
+ {
Integer layer;
if (layerConstraint != null && layerConstraint instanceof Integer)
layer = (Integer) layerConstraint;
@@ -643,8 +656,8 @@ public class JLayeredPane extends JComponent implements Accessible
componentToLayer.put (comp, layer);
incrLayer (layer);
- super.addImpl(comp, null, newIdx);
- }
+ super.addImpl(comp, null, newIdx);
+ }
/**
* Sets the layer property for a JComponent.
@@ -681,8 +694,14 @@ public class JLayeredPane extends JComponent implements Accessible
*/
public void paint(Graphics g)
{
- g.setColor(getBackground());
- g.fillRect(0, 0, getWidth(), getHeight());
+ if (isOpaque())
+ {
+ Color oldColor = g.getColor();
+ Rectangle clip = g.getClipBounds();
+ g.setColor(getBackground());
+ g.fillRect(clip.x, clip.y, clip.width, clip.height);
+ g.setColor(oldColor);
+ }
super.paint(g);
}
diff --git a/javax/swing/JList.java b/javax/swing/JList.java
index 1390ec773..c089aae10 100644
--- a/javax/swing/JList.java
+++ b/javax/swing/JList.java
@@ -1077,6 +1077,7 @@ public class JList extends JComponent implements Accessible, Scrollable
setModel(new DefaultListModel());
setSelectionModel(createSelectionModel());
+ setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
updateUI();
}
@@ -1322,7 +1323,11 @@ public class JList extends JComponent implements Accessible, Scrollable
/**
- * Returns index of the cell to which specified location is closest to
+ * Returns index of the cell to which specified location is closest to. If
+ * the location is outside the bounds of the list, then the greatest index
+ * in the list model is returned. If the list model is empty, then
+ * <code>-1</code> is returned.
+ *
* @param location for which to look for in the list
*
* @return index of the cell to which specified location is closest to.
@@ -1620,10 +1625,15 @@ public class JList extends JComponent implements Accessible, Scrollable
* #listListener} is unsubscribed from the existing model, if it exists,
* and re-subscribed to the new model.
*
- * @param model The new property value
+ * @param model the new model (<code>null</code> not permitted).
+ *
+ * @throws IllegalArgumentException if <code>model</code> is
+ * <code>null</code>.
*/
public void setModel(ListModel model)
{
+ if (model == null)
+ throw new IllegalArgumentException("Null 'model' argument.");
if (this.model == model)
return;
diff --git a/javax/swing/JMenu.java b/javax/swing/JMenu.java
index 9734eb873..369c44d40 100644
--- a/javax/swing/JMenu.java
+++ b/javax/swing/JMenu.java
@@ -96,6 +96,7 @@ public class JMenu extends JMenuItem implements Accessible, MenuElement
public JMenu()
{
super();
+ setOpaque(false);
}
/**
@@ -107,6 +108,7 @@ public class JMenu extends JMenuItem implements Accessible, MenuElement
{
super(text);
popupMenu.setInvoker(this);
+ setOpaque(false);
}
/**
@@ -120,6 +122,7 @@ public class JMenu extends JMenuItem implements Accessible, MenuElement
super(action);
createActionChangeListener(this);
popupMenu.setInvoker(this);
+ setOpaque(false);
}
/**
diff --git a/javax/swing/JMenuBar.java b/javax/swing/JMenuBar.java
index 829d671ec..f018daabf 100644
--- a/javax/swing/JMenuBar.java
+++ b/javax/swing/JMenuBar.java
@@ -234,8 +234,8 @@ public class JMenuBar extends JComponent implements Accessible, MenuElement
*/
public void addNotify()
{
- // FIXME: Should register this menu bar with the keyboard manager
super.addNotify();
+ KeyboardManager.getManager().registerJMenuBar(this);
}
public AccessibleContext getAccessibleContext()
@@ -474,6 +474,63 @@ public class JMenuBar extends JComponent implements Accessible, MenuElement
}
/**
+ * This method overrides JComponent.processKeyBinding to allow the
+ * JMenuBar to check all the child components (recursiveley) to see
+ * if they'll consume the event.
+ *
+ * @param ks the KeyStroke for the event
+ * @param e the KeyEvent for the event
+ * @param condition the focus condition for the binding
+ * @param pressed true if the key is pressed
+ */
+ protected boolean processKeyBinding(KeyStroke ks, KeyEvent e, int condition,
+ boolean pressed)
+ {
+ // See if the regular JComponent behavior consumes the event
+ if (super.processKeyBinding(ks, e, condition, pressed))
+ return true;
+
+ // If not, have to recursively check all the child menu elements to see
+ // if they want it
+ MenuElement[] children = getSubElements();
+ for (int i = 0; i < children.length; i++)
+ if (processKeyBindingHelper(children[i], ks, e, condition, pressed))
+ return true;
+ return false;
+ }
+
+ /**
+ * This is a helper method to recursively check the children of this
+ * JMenuBar to see if they will consume a key event via key bindings.
+ * This is used for menu accelerators.
+ * @param menuElement the menuElement to check (and check all its children)
+ * @param ks the KeyStroke for the event
+ * @param e the KeyEvent that may be consumed
+ * @param condition the focus condition for the binding
+ * @param pressed true if the key was pressed
+ * @return true <code>menuElement</code> or one of its children consume
+ * the event (processKeyBinding returns true for menuElement or one of
+ * its children).
+ */
+ static boolean processKeyBindingHelper(MenuElement menuElement, KeyStroke ks,
+ KeyEvent e, int condition,
+ boolean pressed)
+ {
+ // First check the menuElement itself, if it's a JComponent
+ if (menuElement instanceof JComponent
+ && ((JComponent) menuElement).processKeyBinding(ks, e, condition,
+ pressed))
+ return true;
+
+ // If that didn't consume it, check all the children recursively
+ MenuElement[] children = menuElement.getSubElements();
+ for (int i = 0; i < children.length; i++)
+ if (processKeyBindingHelper(children[i], ks, e, condition, pressed))
+ return true;
+ return false;
+ }
+
+ /**
* Process mouse events forwarded from MenuSelectionManager. This method
* doesn't do anything. It is here to conform to the MenuElement interface.
*
@@ -494,7 +551,7 @@ public class JMenuBar extends JComponent implements Accessible, MenuElement
*/
public void removeNotify()
{
- // Must unregister this menu bar with the current keyboard manager.
+ KeyboardManager.getManager().unregisterJMenuBar(this);
super.removeNotify();
}
diff --git a/javax/swing/JMenuItem.java b/javax/swing/JMenuItem.java
index 9799017f6..c87a4dc2b 100644
--- a/javax/swing/JMenuItem.java
+++ b/javax/swing/JMenuItem.java
@@ -254,7 +254,9 @@ public class JMenuItem extends AbstractButton implements Accessible,
*/
public void setAccelerator(KeyStroke keystroke)
{
+ KeyStroke old = this.accelerator;
this.accelerator = keystroke;
+ firePropertyChange ("accelerator", old, keystroke);
}
/**
diff --git a/javax/swing/JOptionPane.java b/javax/swing/JOptionPane.java
index 2f28ccc91..057326cd2 100644
--- a/javax/swing/JOptionPane.java
+++ b/javax/swing/JOptionPane.java
@@ -369,15 +369,12 @@ public class JOptionPane extends JComponent implements Accessible
inputValue = UNINITIALIZED_VALUE;
value = UNINITIALIZED_VALUE;
- // FIXME: This dialog should be centered on the parent
- // or at the center of the screen (if the parent is null)
- // Need getGraphicsConfiguration to return non-null in
- // order for that to work so we know how large the
- // screen is.
dialog.getContentPane().add(this);
dialog.setModal(true);
dialog.setResizable(false);
-
+ dialog.pack();
+ dialog.setLocationRelativeTo(parentComponent);
+
return dialog;
}
@@ -860,8 +857,6 @@ public class JOptionPane extends JComponent implements Accessible
{
JOptionPane pane = new JOptionPane(message, QUESTION_MESSAGE);
JDialog dialog = pane.createDialog(parentComponent, "Select an Option");
-
- dialog.pack();
dialog.show();
if (pane.getValue() instanceof Integer)
@@ -888,7 +883,6 @@ public class JOptionPane extends JComponent implements Accessible
{
JOptionPane pane = new JOptionPane(message, PLAIN_MESSAGE, optionType);
JDialog dialog = pane.createDialog(parentComponent, title);
- dialog.pack();
dialog.show();
if (pane.getValue() instanceof Integer)
@@ -916,7 +910,6 @@ public class JOptionPane extends JComponent implements Accessible
{
JOptionPane pane = new JOptionPane(message, messageType, optionType);
JDialog dialog = pane.createDialog(parentComponent, title);
- dialog.pack();
dialog.show();
if (pane.getValue() instanceof Integer)
@@ -946,7 +939,6 @@ public class JOptionPane extends JComponent implements Accessible
{
JOptionPane pane = new JOptionPane(message, messageType, optionType, icon);
JDialog dialog = pane.createDialog(parentComponent, title);
- dialog.pack();
dialog.show();
if (pane.getValue() instanceof Integer)
@@ -972,7 +964,6 @@ public class JOptionPane extends JComponent implements Accessible
JOptionPane pane = new JOptionPane(message, QUESTION_MESSAGE);
pane.setWantsInput(true);
JDialog dialog = pane.createDialog(parentComponent, null);
- dialog.pack();
dialog.show();
return (String) pane.getInputValue();
@@ -999,7 +990,6 @@ public class JOptionPane extends JComponent implements Accessible
pane.setInitialSelectionValue(initialSelectionValue);
pane.setWantsInput(true);
JDialog dialog = pane.createDialog(parentComponent, null);
- dialog.pack();
dialog.show();
return (String) pane.getInputValue();
@@ -1025,7 +1015,6 @@ public class JOptionPane extends JComponent implements Accessible
JOptionPane pane = new JOptionPane(message, messageType);
pane.setWantsInput(true);
JDialog dialog = pane.createDialog(parentComponent, title);
- dialog.pack();
dialog.show();
return (String) pane.getInputValue();
@@ -1058,7 +1047,6 @@ public class JOptionPane extends JComponent implements Accessible
pane.setSelectionValues(selectionValues);
pane.setInitialSelectionValue(initialSelectionValue);
JDialog dialog = pane.createDialog(parentComponent, title);
- dialog.pack();
dialog.show();
return pane.getInputValue();
@@ -1079,7 +1067,6 @@ public class JOptionPane extends JComponent implements Accessible
JOptionPane pane = new JOptionPane(message, QUESTION_MESSAGE);
pane.setWantsInput(true);
JDialog dialog = pane.createDialog(null, null);
- dialog.pack();
dialog.show();
return (String) pane.getInputValue();
@@ -1104,7 +1091,6 @@ public class JOptionPane extends JComponent implements Accessible
pane.setWantsInput(true);
pane.setInitialSelectionValue(initialSelectionValue);
JDialog dialog = pane.createDialog(null, null);
- dialog.pack();
dialog.show();
return (String) pane.getInputValue();
@@ -1409,7 +1395,6 @@ public class JOptionPane extends JComponent implements Accessible
{
JOptionPane pane = new JOptionPane(message, INFORMATION_MESSAGE);
JDialog dialog = pane.createDialog(parentComponent, null);
- dialog.pack();
dialog.show();
}
@@ -1428,7 +1413,6 @@ public class JOptionPane extends JComponent implements Accessible
{
JOptionPane pane = new JOptionPane(message, messageType);
JDialog dialog = pane.createDialog(parentComponent, title);
- dialog.pack();
dialog.show();
}
@@ -1449,7 +1433,6 @@ public class JOptionPane extends JComponent implements Accessible
JOptionPane pane = new JOptionPane(message, messageType);
pane.setIcon(icon);
JDialog dialog = pane.createDialog(parentComponent, title);
- dialog.pack();
dialog.show();
}
@@ -1479,7 +1462,6 @@ public class JOptionPane extends JComponent implements Accessible
options, initialValue);
JDialog dialog = pane.createDialog(parentComponent, title);
- dialog.pack();
dialog.show();
if (pane.getValue() instanceof Integer)
diff --git a/javax/swing/JPanel.java b/javax/swing/JPanel.java
index 7805e92b6..c02a9cfad 100644
--- a/javax/swing/JPanel.java
+++ b/javax/swing/JPanel.java
@@ -137,6 +137,6 @@ public class JPanel extends JComponent implements Accessible
protected String paramString()
{
- return "JPanel";
+ return super.paramString();
}
}
diff --git a/javax/swing/JRootPane.java b/javax/swing/JRootPane.java
index b5d436d7e..dea4ee4b1 100644
--- a/javax/swing/JRootPane.java
+++ b/javax/swing/JRootPane.java
@@ -43,8 +43,10 @@ import java.awt.Component;
import java.awt.Container;
import java.awt.Dimension;
import java.awt.IllegalComponentStateException;
+import java.awt.Insets;
import java.awt.LayoutManager;
import java.awt.LayoutManager2;
+import java.awt.Rectangle;
import java.io.Serializable;
import javax.accessibility.Accessible;
@@ -98,11 +100,36 @@ public class JRootPane extends JComponent implements Accessible
private static final long serialVersionUID = -4100116998559815027L;
/**
+ * The cached layout info for the glass pane.
+ */
+ private Rectangle glassPaneBounds;
+
+ /**
+ * The cached layout info for the layered pane.
+ */
+ private Rectangle layeredPaneBounds;
+
+ /**
+ * The cached layout info for the content pane.
+ */
+ private Rectangle contentPaneBounds;
+
+ /**
+ * The cached layout info for the menu bar.
+ */
+ private Rectangle menuBarBounds;
+
+ /**
+ * The cached preferred size.
+ */
+ private Dimension prefSize;
+
+ /**
* Creates a new <code>RootLayout</code> object.
*/
protected RootLayout()
{
- // Nothing to do here.
+ // Nothing to do here.
}
/**
@@ -136,7 +163,7 @@ public class JRootPane extends JComponent implements Accessible
*/
public float getLayoutAlignmentX(Container target)
{
- return target.getAlignmentX();
+ return 0.0F;
}
/**
@@ -148,7 +175,7 @@ public class JRootPane extends JComponent implements Accessible
*/
public float getLayoutAlignmentY(Container target)
{
- return target.getAlignmentY();
+ return 0.0F;
}
/**
@@ -158,7 +185,14 @@ public class JRootPane extends JComponent implements Accessible
*/
public void invalidateLayout(Container target)
{
- // Nothing to do here.
+ synchronized (this)
+ {
+ glassPaneBounds = null;
+ layeredPaneBounds = null;
+ contentPaneBounds = null;
+ menuBarBounds = null;
+ prefSize = null;
+ }
}
/**
@@ -168,84 +202,56 @@ public class JRootPane extends JComponent implements Accessible
*/
public void layoutContainer(Container c)
{
- Dimension menuBarSize;
- int containerWidth = c.getBounds().width - getInsets().left
- - getInsets().right;
- int containerHeight = c.getBounds().height - getInsets().top
- - getInsets().bottom;
- Dimension contentPaneSize = contentPane.getPreferredSize();
-
- // 1. the glassPane fills entire viewable region (bounds - insets).
- // 2. the layeredPane filles entire viewable region.
- // 3. the menuBar is positioned at the upper edge of layeredPane.
- // 4. the contentPane fills viewable region minus menuBar, if present.
-
- /*
- if size of top-level window wasn't set then just set
- contentPane and menuBar to its preferred sizes.
- Otherwise, if the size of top-level window was specified then
- set menuBar to its preferred size and make content pane
- to fit into the remaining space
-
-
- +-------------------------------+
- | JLayeredPane |
- | +--------------------------+ |
- | | menuBar | |
- | +--------------------------+ |
- | +--------------------------+ |
- | |contentPane | |
- | | | |
- | | | |
- | | | |
- | +--------------------------+ |
- +-------------------------------+
-
- */
- if (containerWidth == 0 && containerHeight == 0)
- {
- if (menuBar != null)
- {
- int maxWidth;
- menuBarSize = menuBar.getPreferredSize();
- maxWidth = Math.max(menuBarSize.width, contentPaneSize.width);
- menuBar.setBounds(0, 0, maxWidth, menuBarSize.height);
- glassPane.setBounds(0, 0, maxWidth, menuBarSize.height
- + contentPaneSize.height);
- contentPane.setBounds(0, menuBarSize.height, maxWidth,
- contentPaneSize.height);
- layeredPane.setBounds(0, 0, maxWidth, menuBarSize.height
- + contentPaneSize.height);
- }
- else
- {
- glassPane.setBounds(0, 0, contentPaneSize.width,
- contentPaneSize.height);
- contentPane.setBounds(0, 0, contentPaneSize.width,
- contentPaneSize.height);
- layeredPane.setBounds(0, 0, contentPaneSize.width,
- contentPaneSize.height);
- }
- }
- else
+ if (glassPaneBounds == null || layeredPaneBounds == null
+ || contentPaneBounds == null || menuBarBounds == null)
{
+ Insets i = getInsets();
+ int containerWidth = c.getBounds().width - i.left - i.right;
+ int containerHeight = c.getBounds().height - i.top - i.bottom;
+
+ // 1. the glassPane fills entire viewable region (bounds - insets).
+ // 2. the layeredPane filles entire viewable region.
+ // 3. the menuBar is positioned at the upper edge of layeredPane.
+ // 4. the contentPane fills viewable region minus menuBar, if present.
+
+
+ // +-------------------------------+
+ // | JLayeredPane |
+ // | +--------------------------+ |
+ // | | menuBar | |
+ // | +--------------------------+ |
+ // | +--------------------------+ |
+ // | |contentPane | |
+ // | | | |
+ // | | | |
+ // | | | |
+ // | +--------------------------+ |
+ // +-------------------------------+
+
if (menuBar != null)
{
- menuBarSize = menuBar.getPreferredSize();
+ Dimension menuBarSize = menuBar.getPreferredSize();
if (menuBarSize.height > containerHeight)
menuBarSize.height = containerHeight;
- menuBar.setBounds(0, 0, containerWidth, menuBarSize.height);
- glassPane.setBounds(0, 0, containerWidth, containerHeight);
- contentPane.setBounds(0, menuBarSize.height, containerWidth,
- (containerHeight - menuBarSize.height));
+ menuBarBounds = new Rectangle(0, 0, containerWidth,
+ menuBarSize.height);
+ contentPaneBounds = new Rectangle(0, menuBarSize.height,
+ containerWidth,
+ containerHeight - menuBarSize.height);
}
else
- {
- glassPane.setBounds(0, 0, containerWidth, containerHeight);
- contentPane.setBounds(0, 0, containerWidth, containerHeight);
- }
- layeredPane.setBounds(0, 0, containerWidth, containerHeight);
+ contentPaneBounds = new Rectangle(0, 0, containerWidth,
+ containerHeight);
+
+ glassPaneBounds = new Rectangle(i.left, i.top, containerWidth, containerHeight);
+ layeredPaneBounds = new Rectangle(i.left, i.top, containerWidth, containerHeight);
}
+
+ glassPane.setBounds(glassPaneBounds);
+ layeredPane.setBounds(layeredPaneBounds);
+ if (menuBar != null)
+ menuBar.setBounds(menuBarBounds);
+ contentPane.setBounds(contentPaneBounds);
}
/**
@@ -281,30 +287,29 @@ public class JRootPane extends JComponent implements Accessible
*/
public Dimension preferredLayoutSize(Container c)
{
- Dimension menuBarSize;
- Dimension prefSize;
-
- Dimension containerSize = c.getSize();
- Dimension contentPaneSize = contentPane.getPreferredSize();
-
- if (containerSize.width == 0 && containerSize.height == 0)
+ // We must synchronize here, otherwise we cannot guarantee that the
+ // prefSize is still non-null when returning.
+ synchronized (this)
{
- if (menuBar != null)
+ if (prefSize == null)
{
- int maxWidth;
- menuBarSize = menuBar.getPreferredSize();
- maxWidth = Math.max(menuBarSize.width, contentPaneSize.width);
- prefSize = new Dimension(maxWidth,
- contentPaneSize.height
- + menuBarSize.height);
+ Insets i = getInsets();
+ prefSize = new Dimension(i.left + i.right, i.top + i.bottom);
+ Dimension contentPrefSize = contentPane.getPreferredSize();
+ prefSize.width += contentPrefSize.width;
+ prefSize.height += contentPrefSize.height;
+ if (menuBar != null)
+ {
+ Dimension menuBarSize = menuBar.getPreferredSize();
+ if (menuBarSize.width > contentPrefSize.width)
+ prefSize.width += menuBarSize.width - contentPrefSize.width;
+ prefSize.height += menuBarSize.height;
+ }
}
- else
- prefSize = contentPaneSize;
- }
- else
- prefSize = c.getSize();
-
- return prefSize;
+ // Return a copy here so the cached value won't get trashed by some
+ // other component.
+ return new Dimension(prefSize);
+ }
}
/**
diff --git a/javax/swing/JSplitPane.java b/javax/swing/JSplitPane.java
index cdab7bb6c..70feefab2 100644
--- a/javax/swing/JSplitPane.java
+++ b/javax/swing/JSplitPane.java
@@ -170,13 +170,15 @@ public class JSplitPane extends JComponent implements Accessible
public static final int HORIZONTAL_SPLIT = 1;
/** The property fired when the last divider location property changes. */
- public static final String LAST_DIVIDER_LOCATION_PROPERTY = "lastDividerLocation";
+ public static final String LAST_DIVIDER_LOCATION_PROPERTY =
+ "lastDividerLocation";
/** The constraints string used to add components to the left. */
public static final String LEFT = "left";
/** The property fired when the one touch expandable property changes. */
- public static final String ONE_TOUCH_EXPANDABLE_PROPERTY = "oneTouchExpandable";
+ public static final String ONE_TOUCH_EXPANDABLE_PROPERTY =
+ "oneTouchExpandable";
/** The property fired when the orientation property changes. */
public static final String ORIENTATION_PROPERTY = "orientation";
@@ -199,7 +201,8 @@ public class JSplitPane extends JComponent implements Accessible
/** Whether the JSplitPane uses one touch expandable buttons. */
protected boolean oneTouchExpandable = false;
- // This is the master dividerSize variable and sets the BasicSplitPaneDivider one accordingly
+ // This is the master dividerSize variable and sets the
+ // BasicSplitPaneDivider one accordingly
/** The size of the divider. */
protected int dividerSize = 10;
@@ -286,7 +289,8 @@ public class JSplitPane extends JComponent implements Accessible
*/
public JSplitPane()
{
- this(HORIZONTAL_SPLIT, false, null, null);
+ this(HORIZONTAL_SPLIT, false, new JButton("left button"),
+ new JButton("right button"));
}
/**
@@ -300,7 +304,8 @@ public class JSplitPane extends JComponent implements Accessible
* @param constraints The constraints string to use.
* @param index Where to place to component in the list of components.
*
- * @throws IllegalArgumentException When the constraints is not a known identifier.
+ * @throws IllegalArgumentException When the constraints is not a known
+ * identifier.
*/
protected void addImpl(Component comp, Object constraints, int index)
{
@@ -310,34 +315,35 @@ public class JSplitPane extends JComponent implements Accessible
int place;
if (constraints == null)
{
- if (leftComponent == null)
- constraints = LEFT;
- else if (rightComponent == null)
- constraints = RIGHT;
+ if (leftComponent == null)
+ constraints = LEFT;
+ else if (rightComponent == null)
+ constraints = RIGHT;
}
if (constraints instanceof String)
{
- String placement = (String) constraints;
-
- if (placement.equals(BOTTOM) || placement.equals(RIGHT))
- {
- if (rightComponent != null)
- remove(rightComponent);
- rightComponent = comp;
- }
- else if (placement.equals(LEFT) || placement.equals(TOP))
- {
- if (leftComponent != null)
- remove(leftComponent);
- leftComponent = comp;
- }
- else if (placement.equals(DIVIDER))
- constraints = null;
- else
- throw new IllegalArgumentException("Constraints is not a known identifier.");
-
- super.addImpl(comp, constraints, index);
+ String placement = (String) constraints;
+
+ if (placement.equals(BOTTOM) || placement.equals(RIGHT))
+ {
+ if (rightComponent != null)
+ remove(rightComponent);
+ rightComponent = comp;
+ }
+ else if (placement.equals(LEFT) || placement.equals(TOP))
+ {
+ if (leftComponent != null)
+ remove(leftComponent);
+ leftComponent = comp;
+ }
+ else if (placement.equals(DIVIDER))
+ constraints = null;
+ else
+ throw new
+ IllegalArgumentException("Constraints is not a known identifier.");
+
+ super.addImpl(comp, constraints, index);
}
invalidate();
layout();
@@ -614,10 +620,10 @@ public class JSplitPane extends JComponent implements Accessible
{
if (newContinuousLayout != continuousLayout)
{
- boolean oldValue = continuousLayout;
- continuousLayout = newContinuousLayout;
- firePropertyChange(CONTINUOUS_LAYOUT_PROPERTY, oldValue,
- continuousLayout);
+ boolean oldValue = continuousLayout;
+ continuousLayout = newContinuousLayout;
+ firePropertyChange(CONTINUOUS_LAYOUT_PROPERTY, oldValue,
+ continuousLayout);
}
}
@@ -634,7 +640,8 @@ public class JSplitPane extends JComponent implements Accessible
public void setDividerLocation(double proportionalLocation)
{
if (proportionalLocation > 1 || proportionalLocation < 0)
- throw new IllegalArgumentException("proportion has to be between 0 and 1.");
+ throw new IllegalArgumentException
+ ("proportion has to be between 0 and 1.");
int max = (orientation == HORIZONTAL_SPLIT) ? getWidth() : getHeight();
setDividerLocation((int) (proportionalLocation * max));
@@ -649,9 +656,9 @@ public class JSplitPane extends JComponent implements Accessible
{
if (ui != null && location != getDividerLocation())
{
- int oldLocation = getDividerLocation();
- ((SplitPaneUI) ui).setDividerLocation(this, location);
- firePropertyChange(DIVIDER_LOCATION_PROPERTY, oldLocation, location);
+ int oldLocation = getDividerLocation();
+ ((SplitPaneUI) ui).setDividerLocation(this, location);
+ firePropertyChange(DIVIDER_LOCATION_PROPERTY, oldLocation, location);
}
}
@@ -664,9 +671,9 @@ public class JSplitPane extends JComponent implements Accessible
{
if (newSize != dividerSize)
{
- int oldSize = dividerSize;
- dividerSize = newSize;
- firePropertyChange(DIVIDER_SIZE_PROPERTY, oldSize, dividerSize);
+ int oldSize = dividerSize;
+ dividerSize = newSize;
+ firePropertyChange(DIVIDER_SIZE_PROPERTY, oldSize, dividerSize);
}
}
@@ -683,10 +690,10 @@ public class JSplitPane extends JComponent implements Accessible
{
if (newLastLocation != lastDividerLocation)
{
- int oldValue = lastDividerLocation;
- lastDividerLocation = newLastLocation;
- firePropertyChange(LAST_DIVIDER_LOCATION_PROPERTY, oldValue,
- lastDividerLocation);
+ int oldValue = lastDividerLocation;
+ lastDividerLocation = newLastLocation;
+ firePropertyChange(LAST_DIVIDER_LOCATION_PROPERTY, oldValue,
+ lastDividerLocation);
}
}
@@ -696,11 +703,11 @@ public class JSplitPane extends JComponent implements Accessible
* @param comp The left component.
*/
public void setLeftComponent(Component comp)
- {
+ {
if (comp != null)
add(comp, LEFT);
else
- add(new JButton("left button"), LEFT);
+ remove (leftComponent);
}
/**
@@ -715,10 +722,10 @@ public class JSplitPane extends JComponent implements Accessible
{
if (newValue != oneTouchExpandable)
{
- boolean oldValue = oneTouchExpandable;
- oneTouchExpandable = newValue;
- firePropertyChange(ONE_TOUCH_EXPANDABLE_PROPERTY, oldValue,
- oneTouchExpandable);
+ boolean oldValue = oneTouchExpandable;
+ oneTouchExpandable = newValue;
+ firePropertyChange(ONE_TOUCH_EXPANDABLE_PROPERTY, oldValue,
+ oneTouchExpandable);
}
}
@@ -732,13 +739,14 @@ public class JSplitPane extends JComponent implements Accessible
public void setOrientation(int orientation)
{
if (orientation != HORIZONTAL_SPLIT && orientation != VERTICAL_SPLIT)
- throw new IllegalArgumentException("orientation must be one of VERTICAL_SPLIT, HORIZONTAL_SPLIT");
+ throw new IllegalArgumentException
+ ("orientation must be one of VERTICAL_SPLIT, HORIZONTAL_SPLIT");
if (orientation != this.orientation)
{
- int oldOrientation = this.orientation;
- this.orientation = orientation;
- firePropertyChange(ORIENTATION_PROPERTY, oldOrientation,
- this.orientation);
+ int oldOrientation = this.orientation;
+ this.orientation = orientation;
+ firePropertyChange(ORIENTATION_PROPERTY, oldOrientation,
+ this.orientation);
}
}
@@ -766,7 +774,7 @@ public class JSplitPane extends JComponent implements Accessible
if (comp != null)
add(comp, RIGHT);
else
- add(new JButton("right button"), RIGHT);
+ remove (rightComponent);
}
/**
diff --git a/javax/swing/JTabbedPane.java b/javax/swing/JTabbedPane.java
index 8ef1d8f11..8e32ebdf8 100644
--- a/javax/swing/JTabbedPane.java
+++ b/javax/swing/JTabbedPane.java
@@ -337,9 +337,10 @@ public class JTabbedPane extends JComponent implements Serializable,
*/
public void setComponent(Component c)
{
- remove(component);
- this.component = c;
- add(c);
+ int i = indexOfComponent(component);
+ insertTab(title, icon, c, tip, i);
+ component = c;
+ removeTabAt(i);
}
/**
@@ -620,7 +621,7 @@ public class JTabbedPane extends JComponent implements Serializable,
throw new IllegalArgumentException("tabLayoutPolicy is not valid.");
this.tabPlacement = tabPlacement;
layoutPolicy = tabLayoutPolicy;
-
+
changeEvent = new ChangeEvent(this);
changeListener = createChangeListener();
@@ -912,7 +913,7 @@ public class JTabbedPane extends JComponent implements Serializable,
if (getSelectedIndex() == -1)
setSelectedIndex(0);
- layout();
+ revalidate();
repaint();
}
@@ -968,6 +969,7 @@ public class JTabbedPane extends JComponent implements Serializable,
super.add(component);
else
insertTab(component.getName(), null, component, null, tabs.size());
+
return component;
}
@@ -1051,45 +1053,37 @@ public class JTabbedPane extends JComponent implements Serializable,
}
/**
- * The tab and it's associated component are removed. After the component
- * has been removed from the JTabbedPane, it's set visible to ensure that
- * it can be seen.
+ * Removes the tab at index. After the component associated with
+ * index is removed, its visibility is reset to true to ensure it
+ * will be visible if added to other containers.
*
* @param index The index of the tab to remove.
*/
public void removeTabAt(int index)
{
checkIndex(index, 0, tabs.size());
- Component c = getComponentAt(index);
- super.remove(index);
- c.show();
tabs.remove(index);
+ getComponentAt(index).show();
}
/**
- * This method removes the component from the JTabbedPane. After the
- * component has been removed from the JTabbedPane, it's set visible to
- * ensure that it can be seen.
+ * Removes the specified Component from the JTabbedPane.
*
* @param component The Component to remove.
*/
public void remove(Component component)
{
- // This simply removes the component.
- int index = indexOfComponent(component);
super.remove(component);
- component.show();
- setComponentAt(index, null);
}
/**
- * This method removes the tab and component from the JTabbedPane. It simply
- * calls removeTabAt(int index).
+ * Removes the tab and component which corresponds to the specified index.
*
* @param index The index of the tab to remove.
*/
public void remove(int index)
{
+ remove(getComponentAt(index));
removeTabAt(index);
}
diff --git a/javax/swing/JTable.java b/javax/swing/JTable.java
index 3342d8248..14f00e654 100644
--- a/javax/swing/JTable.java
+++ b/javax/swing/JTable.java
@@ -949,10 +949,13 @@ public class JTable
if (ev.getPropertyName().equals("preferredWidth"))
{
JTableHeader header = getTableHeader();
- TableColumn col = (TableColumn) ev.getSource();
- header.setResizingColumn(col);
- doLayout();
- header.setResizingColumn(null);
+ if (header != null)
+ {
+ TableColumn col = (TableColumn) ev.getSource();
+ header.setResizingColumn(col);
+ doLayout();
+ header.setResizingColumn(null);
+ }
}
}
}
@@ -1763,14 +1766,19 @@ public class JTable
if ((event.getFirstRow() ==TableModelEvent.HEADER_ROW)
&& autoCreateColumnsFromModel)
- createDefaultColumnsFromModel();
+ createDefaultColumnsFromModel();
// If the structure changes, we need to revalidate, since that might
// affect the size parameters of the JTable. Otherwise we only need
// to perform a repaint to update the view.
- if (event.getType() == TableModelEvent.INSERT
- || event.getType() == TableModelEvent.DELETE)
+ if (event.getType() == TableModelEvent.INSERT)
revalidate();
+ else if (event.getType() == TableModelEvent.DELETE)
+ {
+ if (dataModel.getRowCount() == 0)
+ clearSelection();
+ revalidate();
+ }
repaint();
}
@@ -1791,7 +1799,6 @@ public class JTable
{
if (point != null)
{
- int x0 = getLocation().x;
int ncols = getColumnCount();
Dimension gap = getIntercellSpacing();
TableColumnModel cols = getColumnModel();
@@ -1821,7 +1828,6 @@ public class JTable
{
if (point != null)
{
- int y0 = getLocation().y;
int nrows = getRowCount();
int height = getRowHeight();
int y = point.y;
@@ -1890,7 +1896,7 @@ public class JTable
* @return The current value of the selectedRow property
*/
public int getSelectedRow ()
- {
+ {
return selectionModel.getMinSelectionIndex();
}
@@ -1979,16 +1985,13 @@ public class JTable
}
}
-
-
public TableCellRenderer getCellRenderer(int row, int column)
{
TableCellRenderer renderer =
columnModel.getColumn(column).getCellRenderer();
-
if (renderer == null)
- renderer = getDefaultRenderer(dataModel.getColumnClass(column));
-
+ renderer = getDefaultRenderer(getColumnClass(column));
+
return renderer;
}
@@ -2034,19 +2037,29 @@ public class JTable
int row,
int column)
{
- boolean rsa = getRowSelectionAllowed();
- boolean csa = getColumnSelectionAllowed();
- boolean rs = rsa ? getSelectionModel().isSelectedIndex(row) : false;
- boolean cs = csa ? columnModel.getSelectionModel().isSelectedIndex(column) : false;
- boolean isSelected = ((rsa && csa && rs && cs)
- || (rsa && !csa && rs)
- || (!rsa && csa && cs));
-
+
+ boolean rowSelAllowed = getRowSelectionAllowed();
+ boolean colSelAllowed = getColumnSelectionAllowed();
+ boolean isSel = false;
+ if (rowSelAllowed && colSelAllowed || !rowSelAllowed && !colSelAllowed)
+ isSel = isCellSelected(row, column);
+ else
+ isSel = isRowSelected(row) && getRowSelectionAllowed()
+ || isColumnSelected(column) && getColumnSelectionAllowed();
+
+ // Determine the focused cell. The focused cell is the cell at the
+ // leadSelectionIndices of the row and column selection model.
+ ListSelectionModel rowSel = getSelectionModel();
+ ListSelectionModel colSel = getColumnModel().getSelectionModel();
+ boolean hasFocus = hasFocus() && isEnabled()
+ && rowSel.getLeadSelectionIndex() == row
+ && colSel.getLeadSelectionIndex() == column;
+
return renderer.getTableCellRendererComponent(this,
dataModel.getValueAt(row,
convertColumnIndexToModel(column)),
- isSelected,
- false, // hasFocus
+ isSel,
+ hasFocus,
row, column);
}
@@ -2212,7 +2225,6 @@ public class JTable
int lo = lsm.getMinSelectionIndex();
int hi = lsm.getMaxSelectionIndex();
int j = 0;
- java.util.ArrayList ls = new java.util.ArrayList();
if (lo != -1 && hi != -1)
{
switch (lsm.getSelectionMode())
@@ -2968,7 +2980,7 @@ public class JTable
public Class<?> getColumnClass(int column)
{
- return dataModel.getColumnClass(column);
+ return getModel().getColumnClass(column);
}
public String getColumnName(int column)
diff --git a/javax/swing/JTextField.java b/javax/swing/JTextField.java
index 845edc001..8dc2f2569 100644
--- a/javax/swing/JTextField.java
+++ b/javax/swing/JTextField.java
@@ -203,7 +203,9 @@ public class JTextField extends JTextComponent
*/
protected Document createDefaultModel()
{
- return new PlainDocument();
+ PlainDocument doc = new PlainDocument();
+ doc.putProperty("filterNewlines", Boolean.TRUE);
+ return doc;
}
/**
diff --git a/javax/swing/JTextPane.java b/javax/swing/JTextPane.java
index 1f5b99e43..a2aebd4ca 100644
--- a/javax/swing/JTextPane.java
+++ b/javax/swing/JTextPane.java
@@ -47,7 +47,9 @@ import javax.swing.text.Document;
import javax.swing.text.EditorKit;
import javax.swing.text.Element;
import javax.swing.text.MutableAttributeSet;
+import javax.swing.text.SimpleAttributeSet;
import javax.swing.text.Style;
+import javax.swing.text.StyleConstants;
import javax.swing.text.StyledDocument;
import javax.swing.text.StyledEditorKit;
@@ -192,9 +194,20 @@ public class JTextPane
*/
public void insertComponent(Component component)
{
- // TODO: One space must be inserted here with attributes set to indicate
- // that the component must be displayed here. Have to figure out the
- // attributes.
+ SimpleAttributeSet atts = new SimpleAttributeSet();
+ atts.addAttribute(StyleConstants.ComponentAttribute, component);
+ atts.addAttribute(StyleConstants.NameAttribute,
+ StyleConstants.ComponentElementName);
+ try
+ {
+ getDocument().insertString(getCaret().getDot(), " ", atts);
+ }
+ catch (BadLocationException ex)
+ {
+ AssertionError err = new AssertionError("Unexpected bad location");
+ err.initCause(ex);
+ throw err;
+ }
}
/**
@@ -204,9 +217,20 @@ public class JTextPane
*/
public void insertIcon(Icon icon)
{
- // TODO: One space must be inserted here with attributes set to indicate
- // that the icon must be displayed here. Have to figure out the
- // attributes.
+ SimpleAttributeSet atts = new SimpleAttributeSet();
+ atts.addAttribute(StyleConstants.IconAttribute, icon);
+ atts.addAttribute(StyleConstants.NameAttribute,
+ StyleConstants.IconElementName);
+ try
+ {
+ getDocument().insertString(getCaret().getDot(), " ", atts);
+ }
+ catch (BadLocationException ex)
+ {
+ AssertionError err = new AssertionError("Unexpected bad location");
+ err.initCause(ex);
+ throw err;
+ }
}
/**
diff --git a/javax/swing/JTree.java b/javax/swing/JTree.java
index dffa81739..bd71035dd 100644
--- a/javax/swing/JTree.java
+++ b/javax/swing/JTree.java
@@ -1480,7 +1480,7 @@ public class JTree extends JComponent implements Scrollable, Accessible
updateUI();
setRootVisible(true);
setModel(model);
- setSelectionModel(EmptySelectionModel.sharedInstance());
+ setSelectionModel(new EmptySelectionModel());
}
/**
@@ -2065,7 +2065,8 @@ public class JTree extends JComponent implements Scrollable, Accessible
}
Rectangle rect = getPathBounds(path);
scrollRectToVisible(rect);
- setSelectionPath(temp);
+ revalidate();
+ repaint();
}
public void scrollRowToVisible(int row)
@@ -2363,8 +2364,8 @@ public class JTree extends JComponent implements Scrollable, Accessible
public void expandPath(TreePath path)
{
- // Don't expand if last path component is a leaf node.
- if ((path == null) || (treeModel.isLeaf(path.getLastPathComponent())))
+ // Don't expand if path is null
+ if (path == null)
return;
try
@@ -2588,7 +2589,7 @@ public class JTree extends JComponent implements Scrollable, Accessible
if (!isExpanded(parent) && parent != null)
doExpandParents(parent, false);
-
+
nodeStates.put(path, state ? EXPANDED : COLLAPSED);
}
@@ -2596,7 +2597,6 @@ public class JTree extends JComponent implements Scrollable, Accessible
{
if (path == null)
return;
- TreePath parent = path.getParentPath();
doExpandParents(path, state);
}
@@ -2650,7 +2650,7 @@ public class JTree extends JComponent implements Scrollable, Accessible
{
if (path == null)
return;
-
+
expandPath(path.getParentPath());
}
diff --git a/javax/swing/JViewport.java b/javax/swing/JViewport.java
index ba44461cb..285a7bf59 100644
--- a/javax/swing/JViewport.java
+++ b/javax/swing/JViewport.java
@@ -38,6 +38,8 @@ exception statement from your version. */
package javax.swing;
+import gnu.classpath.SystemProperties;
+
import java.awt.Component;
import java.awt.Dimension;
import java.awt.Graphics;
@@ -163,7 +165,13 @@ public class JViewport extends JComponent implements Accessible
public static final int BACKINGSTORE_SCROLL_MODE = 2;
private static final long serialVersionUID = -6925142919680527970L;
-
+
+ /**
+ * The default scrollmode to be used by all JViewports as determined by
+ * the system property gnu.javax.swing.JViewport.scrollMode.
+ */
+ private static final int defaultScrollMode;
+
protected boolean scrollUnderway;
protected boolean isViewSizeSet;
@@ -243,10 +251,27 @@ public class JViewport extends JComponent implements Accessible
*/
boolean sizeChanged = true;
+ /**
+ * Initializes the default setting for the scrollMode property.
+ */
+ static
+ {
+ String scrollModeProp =
+ SystemProperties.getProperty("gnu.javax.swing.JViewport.scrollMode",
+ "BLIT");
+ int myScrollMode;
+ if (scrollModeProp.equalsIgnoreCase("simple"))
+ defaultScrollMode = SIMPLE_SCROLL_MODE;
+ else if (scrollModeProp.equalsIgnoreCase("backingstore"))
+ defaultScrollMode = BACKINGSTORE_SCROLL_MODE;
+ else
+ defaultScrollMode = BLIT_SCROLL_MODE;
+ }
+
public JViewport()
{
setOpaque(true);
- setScrollMode(BLIT_SCROLL_MODE);
+ setScrollMode(defaultScrollMode);
updateUI();
setLayout(createLayoutManager());
lastPaintPosition = new Point();
diff --git a/javax/swing/JWindow.java b/javax/swing/JWindow.java
index 1a7cad488..cc0ac7fd9 100644
--- a/javax/swing/JWindow.java
+++ b/javax/swing/JWindow.java
@@ -86,13 +86,6 @@ public class JWindow extends Window implements Accessible, RootPaneContainer
protected AccessibleContext accessibleContext;
- /**
- * Tells us if we're in the initialization stage.
- * If so, adds go to top-level Container, otherwise they go
- * to the content pane for this container.
- */
- private boolean initStageDone = false;
-
public JWindow()
{
super(SwingUtilities.getOwnerFrame());
@@ -128,7 +121,7 @@ public class JWindow extends Window implements Accessible, RootPaneContainer
super.setLayout(new BorderLayout(1, 1));
getRootPane(); // will do set/create
// Now we're done init stage, adds and layouts go to content pane.
- initStageDone = true;
+ setRootPaneCheckingEnabled(true);
}
public Dimension getPreferredSize()
@@ -140,13 +133,8 @@ public class JWindow extends Window implements Accessible, RootPaneContainer
{
// Check if we're in initialization stage. If so, call super.setLayout
// otherwise, valid calls go to the content pane.
- if (initStageDone)
- {
- if (isRootPaneCheckingEnabled())
- throw new Error("Cannot set layout. Use getContentPane().setLayout()"
- + " instead.");
- getContentPane().setLayout(manager);
- }
+ if (isRootPaneCheckingEnabled())
+ getContentPane().setLayout(manager);
else
super.setLayout(manager);
}
@@ -207,15 +195,10 @@ public class JWindow extends Window implements Accessible, RootPaneContainer
{
// If we're adding in the initialization stage use super.add.
// otherwise pass the add onto the content pane.
- if (!initStageDone)
- super.addImpl(comp, constraints, index);
+ if (isRootPaneCheckingEnabled())
+ getContentPane().add(comp, constraints, index);
else
- {
- if (isRootPaneCheckingEnabled())
- throw new Error("Do not use add() on JWindow directly. Use "
- + "getContentPane().add() instead");
- getContentPane().add(comp, constraints, index);
- }
+ super.addImpl(comp, constraints, index);
}
public void remove(Component comp)
diff --git a/javax/swing/KeyboardManager.java b/javax/swing/KeyboardManager.java
new file mode 100644
index 000000000..aa9524cfe
--- /dev/null
+++ b/javax/swing/KeyboardManager.java
@@ -0,0 +1,280 @@
+/* KeyboardManager.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.swing;
+
+import java.applet.Applet;
+import java.awt.Component;
+import java.awt.Container;
+import java.awt.Window;
+import java.awt.event.KeyEvent;
+import java.util.Enumeration;
+import java.util.Hashtable;
+import java.util.Vector;
+
+/**
+ * This class maintains a mapping from top-level containers to a
+ * Hashtable. The Hashtable maps KeyStrokes to Components to be used when
+ * Components register keyboard actions with the condition
+ * JComponent.WHEN_IN_FOCUSED_WINDOW.
+ *
+ * @author Anthony Balkissoon abalkiss at redhat dot com
+ *
+ */
+class KeyboardManager
+{
+ /** Shared instance of KeyboardManager **/
+ static KeyboardManager manager = new KeyboardManager();
+
+ /**
+ * A mapping between top level containers and Hashtables that
+ * map KeyStrokes to Components.
+ */
+ Hashtable topLevelLookup = new Hashtable();
+
+ /**
+ * A mapping between top level containers and Vectors of JMenuBars
+ * used to allow all the JMenuBars within a top level container
+ * a chance to consume key events.
+ */
+ Hashtable menuBarLookup = new Hashtable();
+ /**
+ * Returns the shared instance of KeyboardManager.
+ * @return the shared instance of KeybaordManager.
+ */
+ public static KeyboardManager getManager()
+ {
+ return manager;
+ }
+ /**
+ * Returns the top-level ancestor for the given JComponent.
+ * @param c the JComponent whose top-level ancestor we want
+ * @return the top-level ancestor for the given JComponent.
+ */
+ static Container findTopLevel (Component c)
+ {
+ Container topLevel = (c instanceof Container) ? (Container) c
+ : c.getParent();
+ while (topLevel != null &&
+ !(topLevel instanceof Window) &&
+ !(topLevel instanceof Applet) &&
+ !(topLevel instanceof JInternalFrame))
+ topLevel = topLevel.getParent();
+ return topLevel;
+ }
+
+ /**
+ * Returns the Hashtable that maps KeyStrokes to Components, for
+ * the specified top-level container c. If no Hashtable exists
+ * we create and register it here and return the newly created
+ * Hashtable.
+ *
+ * @param c the top-level container whose Hashtable we want
+ * @return the Hashtable mapping KeyStrokes to Components for the
+ * specified top-level container
+ */
+ Hashtable getHashtableForTopLevel (Container c)
+ {
+ Hashtable keyToComponent = (Hashtable)topLevelLookup.get(c);
+ if (keyToComponent == null)
+ {
+ keyToComponent = new Hashtable();
+ topLevelLookup.put(c, keyToComponent);
+ }
+ return keyToComponent;
+ }
+
+ /**
+ * Registers a KeyStroke with a Component. This does not register
+ * the KeyStroke to a specific Action. When searching for a
+ * WHEN_IN_FOCUSED_WINDOW binding we will first go up to the focused
+ * top-level Container, then get the Hashtable that maps KeyStrokes
+ * to components for that particular top-level Container, then
+ * call processKeyBindings on that component with the condition
+ * JComponent.WHEN_IN_FOCUSED_WINDOW.
+ * @param comp the JComponent associated with the KeyStroke
+ * @param key the KeyStroke
+ */
+ public void registerBinding(JComponent comp, KeyStroke key)
+ {
+ // This method associates a KeyStroke with a particular JComponent
+ // When the KeyStroke occurs, if this component's top-level ancestor
+ // has focus (one of its children is the focused Component) then
+ // comp.processKeyBindings will be called with condition
+ // JComponent.WHEN_IN_FOCUSED_WINDOW.
+
+ // Look for the JComponent's top-level parent and return if it is null
+ Container topLevel = findTopLevel(comp);
+ if (topLevel == null)
+ return;
+
+ // Now get the Hashtable for this top-level container
+ Hashtable keyToComponent = getHashtableForTopLevel(topLevel);
+
+ // And add the new binding to this Hashtable
+ // FIXME: should allow more than one JComponent to be associated
+ // with a KeyStroke, in case one of them is disabled
+ keyToComponent.put(key, comp);
+ }
+
+ public void clearBindingsForComp(JComponent comp)
+ {
+ // This method clears all the WHEN_IN_FOCUSED_WINDOW bindings associated
+ // with <code>comp</code>. This is used for a terribly ineffcient
+ // strategy in which JComponent.updateComponentInputMap simply clears
+ // all bindings associated with its component and then reloads all the
+ // bindings from the updated ComponentInputMap. This is only a preliminary
+ // strategy and should be improved upon once the WHEN_IN_FOCUSED_WINDOW
+ // bindings work.
+
+ // Find the top-level ancestor
+
+ Container topLevel = findTopLevel(comp);
+ if (topLevel == null)
+ return;
+ // And now get its Hashtable
+ Hashtable keyToComponent = getHashtableForTopLevel(topLevel);
+
+ Enumeration keys = keyToComponent.keys();
+ Object temp;
+
+ // Iterate through the keys and remove any key whose value is comp
+ while (keys.hasMoreElements())
+ {
+ temp = keys.nextElement();
+ if (comp == (JComponent)keyToComponent.get(temp))
+ keyToComponent.remove(temp);
+ }
+ }
+
+ /**
+ * This method registers all the bindings in the given ComponentInputMap.
+ * Rather than call registerBinding on all the keys, we do the work here
+ * so that we don't duplicate finding the top-level container and
+ * getting its Hashtable.
+ *
+ * @param map the ComponentInputMap whose bindings we want to register
+ */
+ public void registerEntireMap (ComponentInputMap map)
+ {
+ if (map == null)
+ return;
+ JComponent comp = map.getComponent();
+ KeyStroke[] keys = map.keys();
+ if (keys == null)
+ return;
+ // Find the top-level container associated with this ComponentInputMap
+ Container topLevel = findTopLevel(comp);
+ if (topLevel == null)
+ return;
+
+ // Register the KeyStrokes in the top-level container's Hashtable
+ Hashtable keyToComponent = getHashtableForTopLevel(topLevel);
+ for (int i = 0; i < keys.length; i++)
+ keyToComponent.put(keys[i], comp);
+ }
+
+ public boolean processKeyStroke (Component comp, KeyStroke key, KeyEvent e)
+ {
+ boolean pressed = e.getID() == KeyEvent.KEY_PRESSED;
+
+ // Look for the top-level ancestor
+ Container topLevel = findTopLevel(comp);
+ if (topLevel == null)
+ return false;
+ // Now get the Hashtable for that top-level container
+ Hashtable keyToComponent = getHashtableForTopLevel(topLevel);
+ Enumeration keys = keyToComponent.keys();
+ JComponent target = (JComponent)keyToComponent.get(key);
+ if (target != null && target.processKeyBinding
+ (key, e, JComponent.WHEN_IN_FOCUSED_WINDOW, pressed))
+ return true;
+
+ // Have to give all the JMenuBars a chance to consume the event
+ Vector menuBars = getVectorForTopLevel(topLevel);
+ for (int i = 0; i < menuBars.size(); i++)
+ if (((JMenuBar)menuBars.elementAt(i)).processKeyBinding(key, e, JComponent.WHEN_IN_FOCUSED_WINDOW, pressed))
+ return true;
+ return false;
+ }
+
+ /**
+ * Returns the Vector of JMenuBars associated with the top-level
+ * @param c the top-level container whose JMenuBar Vector we want
+ * @return the Vector of JMenuBars for this top level container
+ */
+ Vector getVectorForTopLevel(Container c)
+ {
+ Vector result = (Vector) menuBarLookup.get(c);
+ if (result == null)
+ {
+ result = new Vector();
+ menuBarLookup.put (c, result);
+ }
+ return result;
+ }
+
+ /**
+ * In processKeyStroke, KeyManager must give all JMenuBars in the
+ * focused top-level container a chance to process the event. So,
+ * JMenuBars must be registered in KeyManager and associated with a
+ * top-level container. That's what this method is for.
+ * @param menuBar the JMenuBar to register
+ */
+ public void registerJMenuBar (JMenuBar menuBar)
+ {
+ Container topLevel = findTopLevel(menuBar);
+ Vector menuBars = getVectorForTopLevel(topLevel);
+ if (!menuBars.contains(menuBar))
+ menuBars.add(menuBar);
+ }
+
+ /**
+ * Unregisters a JMenuBar from its top-level container. This is
+ * called before the JMenuBar is actually removed from the container
+ * so findTopLevel will still find us the correct top-level container.
+ * @param menuBar the JMenuBar to unregister.
+ */
+ public void unregisterJMenuBar (JMenuBar menuBar)
+ {
+ Container topLevel = findTopLevel(menuBar);
+ Vector menuBars = getVectorForTopLevel(topLevel);
+ if (menuBars.contains(menuBar))
+ menuBars.remove(menuBar);
+ }
+}
diff --git a/javax/swing/Popup.java b/javax/swing/Popup.java
index 5b2615d2f..cbb243e28 100644
--- a/javax/swing/Popup.java
+++ b/javax/swing/Popup.java
@@ -39,6 +39,7 @@ exception statement from your version. */
package javax.swing;
import java.awt.Component;
+import java.awt.FlowLayout;
import java.awt.Point;
@@ -224,7 +225,12 @@ public class Popup
* The panel that holds the content.
*/
private JPanel panel;
-
+
+ /**
+ * The layered pane of the owner.
+ */
+ private JLayeredPane layeredPane;
+
/**
* Constructs a new <code>LightweightPopup</code> given its owner,
* contents and the screen position where the popup
@@ -252,6 +258,10 @@ public class Popup
this.contents = contents;
this.x = x;
this.y = y;
+
+ JRootPane rootPane = SwingUtilities.getRootPane(owner);
+ JLayeredPane layeredPane = rootPane.getLayeredPane();
+ this.layeredPane = layeredPane;
}
/**
@@ -260,16 +270,15 @@ public class Popup
*/
public void show()
{
- JRootPane rootPane = SwingUtilities.getRootPane(owner);
- JLayeredPane layeredPane = rootPane.getLayeredPane();
// We insert a JPanel between the layered pane and the contents so we
// can fiddle with the setLocation() method without disturbing a
// JPopupMenu (which overrides setLocation in an unusual manner).
if (panel == null)
{
panel = new JPanel();
- panel.setLayout(null);
+ panel.setLayout(new FlowLayout(0, 0, 0));
}
+
panel.add(contents);
panel.setSize(contents.getSize());
Point layeredPaneLoc = layeredPane.getLocationOnScreen();
@@ -282,8 +291,6 @@ public class Popup
*/
public void hide()
{
- JRootPane rootPane = SwingUtilities.getRootPane(owner);
- JLayeredPane layeredPane = rootPane.getLayeredPane();
layeredPane.remove(panel);
}
}
diff --git a/javax/swing/RepaintManager.java b/javax/swing/RepaintManager.java
index 37281e03d..022122b87 100644
--- a/javax/swing/RepaintManager.java
+++ b/javax/swing/RepaintManager.java
@@ -48,6 +48,7 @@ import java.util.Collections;
import java.util.Comparator;
import java.util.HashMap;
import java.util.Iterator;
+import java.util.WeakHashMap;
/**
* <p>The repaint manager holds a set of dirty regions, invalid components,
@@ -65,7 +66,11 @@ import java.util.Iterator;
*/
public class RepaintManager
{
-
+ /**
+ * The current repaint managers, indexed by their ThreadGroups.
+ */
+ static WeakHashMap currentRepaintManagers;
+
/**
* <p>A helper class which is placed into the system event queue at
* various times in order to facilitate repainting and layout. There is
@@ -102,7 +107,9 @@ public class RepaintManager
public void run()
{
- RepaintManager rm = RepaintManager.globalManager;
+ ThreadGroup threadGroup = Thread.currentThread().getThreadGroup();
+ RepaintManager rm =
+ (RepaintManager) currentRepaintManagers.get(threadGroup);
setLive(false);
rm.validateInvalidComponents();
rm.paintDirtyRegions();
@@ -249,16 +256,6 @@ public class RepaintManager
/**
- * The global, shared RepaintManager instance. This is reused for all
- * components in all windows. This is package-private to avoid an accessor
- * method.
- *
- * @see #currentManager(JComponent)
- * @see #setCurrentManager
- */
- static RepaintManager globalManager;
-
- /**
* Create a new RepaintManager object.
*/
public RepaintManager()
@@ -275,31 +272,46 @@ public class RepaintManager
}
/**
- * Get the value of the shared {@link #globalManager} instance, possibly
- * returning a special manager associated with the specified
- * component. The default implementaiton ignores the component parameter.
+ * Returns the <code>RepaintManager</code> for the current thread's
+ * thread group. The default implementation ignores the
+ * <code>component</code> parameter and returns the same repaint manager
+ * for all components.
*
- * @param component A component to look up the manager of
+ * @param component a component to look up the manager of
*
- * @return The current repaint manager
+ * @return the current repaint manager for the calling thread's thread group
+ * and the specified component
*
* @see #setCurrentManager
*/
public static RepaintManager currentManager(Component component)
{
- if (globalManager == null)
- globalManager = new RepaintManager();
- return globalManager;
+ if (currentRepaintManagers == null)
+ currentRepaintManagers = new WeakHashMap();
+ ThreadGroup threadGroup = Thread.currentThread().getThreadGroup();
+ RepaintManager currentManager =
+ (RepaintManager) currentRepaintManagers.get(threadGroup);
+ if (currentManager == null)
+ {
+ currentManager = new RepaintManager();
+ currentRepaintManagers.put(threadGroup, currentManager);
+ }
+ return currentManager;
}
/**
- * Get the value of the shared {@link #globalManager} instance, possibly
- * returning a special manager associated with the specified
- * component. The default implementaiton ignores the component parameter.
+ * Returns the <code>RepaintManager</code> for the current thread's
+ * thread group. The default implementation ignores the
+ * <code>component</code> parameter and returns the same repaint manager
+ * for all components.
+ *
+ * This method is only here for backwards compatibility with older versions
+ * of Swing and simply forwards to {@link #currentManager(Component)}.
*
- * @param component A component to look up the manager of
+ * @param component a component to look up the manager of
*
- * @return The current repaint manager
+ * @return the current repaint manager for the calling thread's thread group
+ * and the specified component
*
* @see #setCurrentManager
*/
@@ -309,15 +321,20 @@ public class RepaintManager
}
/**
- * Set the value of the shared {@link #globalManager} instance.
+ * Sets the repaint manager for the calling thread's thread group.
*
- * @param manager The new value of the shared instance
+ * @param manager the repaint manager to set for the current thread's thread
+ * group
*
- * @see #currentManager(JComponent)
+ * @see #currentManager(Component)
*/
public static void setCurrentManager(RepaintManager manager)
{
- globalManager = manager;
+ if (currentRepaintManagers == null)
+ currentRepaintManagers = new WeakHashMap();
+
+ ThreadGroup threadGroup = Thread.currentThread().getThreadGroup();
+ currentRepaintManagers.put(threadGroup, manager);
}
/**
diff --git a/javax/swing/SizeRequirements.java b/javax/swing/SizeRequirements.java
index dc855dd32..b9b5c3223 100644
--- a/javax/swing/SizeRequirements.java
+++ b/javax/swing/SizeRequirements.java
@@ -142,13 +142,26 @@ public class SizeRequirements implements Serializable
public static SizeRequirements
getTiledSizeRequirements(SizeRequirements[] children)
{
- SizeRequirements result = new SizeRequirements();
+ long minimum = 0;
+ long preferred = 0;
+ long maximum = 0;
for (int i = 0; i < children.length; i++)
{
- result.minimum += children[i].minimum;
- result.preferred += children[i].preferred;
- result.maximum += children[i].maximum;
+ minimum += children[i].minimum;
+ preferred += children[i].preferred;
+ maximum += children[i].maximum;
}
+ // Overflow check.
+ if (minimum > Integer.MAX_VALUE)
+ minimum = Integer.MAX_VALUE;
+ if (preferred > Integer.MAX_VALUE)
+ preferred = Integer.MAX_VALUE;
+ if (maximum > Integer.MAX_VALUE)
+ maximum = Integer.MAX_VALUE;
+ SizeRequirements result = new SizeRequirements((int) minimum,
+ (int) preferred,
+ (int) maximum,
+ 0.5F);
return result;
}
@@ -338,12 +351,10 @@ public class SizeRequirements implements Serializable
int[] spans, int span)
{
// Sum up (maxSize - prefSize) over all children
- int sumDelta = 0;
+ long sumDelta = 0;
for (int i = 0; i < children.length; i++)
{
sumDelta += children[i].maximum - children[i].preferred;
- if (sumDelta < 0)
- sumDelta = Integer.MAX_VALUE;
}
// If we have sumDelta == 0, then all components have prefSize == maxSize
@@ -356,7 +367,7 @@ public class SizeRequirements implements Serializable
{
double factor = ((double) (children[i].maximum - children[i].preferred))
/ ((double) sumDelta);
- spans[i] -= factor * (span - allocated);
+ spans[i] += factor * (allocated - span);
}
}
diff --git a/javax/swing/SwingUtilities.java b/javax/swing/SwingUtilities.java
index 43f632b54..2d737eeb5 100644
--- a/javax/swing/SwingUtilities.java
+++ b/javax/swing/SwingUtilities.java
@@ -1138,14 +1138,12 @@ public class SwingUtilities
else
{
ActionMap parent = child.getParent();
- while(parent != null)
+ while (parent != null && !(parent instanceof ActionMapUIResource))
{
child = parent;
parent = child.getParent();
}
-
- if (child != null)
- child.setParent(uiActionMap);
+ child.setParent(uiActionMap);
}
}
@@ -1181,11 +1179,13 @@ public class SwingUtilities
component.setInputMap(condition, uiInputMap);
else
{
- while(child.getParent() != null
- && !(child.getParent() instanceof InputMapUIResource))
- child = child.getParent();
- if (child != null)
- child.setParent(uiInputMap);
+ InputMap parent = child.getParent();
+ while (parent != null && !(parent instanceof InputMapUIResource))
+ {
+ child = parent;
+ parent = parent.getParent();
+ }
+ child.setParent(uiInputMap);
}
}
diff --git a/javax/swing/Timer.java b/javax/swing/Timer.java
index f848a9490..5ed310d4e 100644
--- a/javax/swing/Timer.java
+++ b/javax/swing/Timer.java
@@ -46,7 +46,12 @@ import java.util.EventListener;
import javax.swing.event.EventListenerList;
/**
- * Fires one or more action events after the specified delay.
+ * Fires one or more action events after the specified delay. This is
+ * a specialised version of <code>java.util.Timer</code> just for
+ * firing <code>ActionEvent</code>s. All Timers share one (daemon)
+ * Thread (or java.util.Timer). All events are fired from the event
+ * queue.
+ *
* @author Ronald Veldema
* @author Audrius Meskauskas (audriusa@Bionformatics.org) - bug fixes
* and documentation comments
@@ -55,65 +60,19 @@ public class Timer
implements Serializable
{
/**
- * The timer thread
+ * Given to the shared java.util.Timer to (possibly repeatedly) call
+ * queueEvent().
*/
- private class Waker
- extends Thread
+ private class Task extends java.util.TimerTask
{
- /**
- * Fires events, pausing for required intervals.
- */
public void run()
{
- try
- {
- synchronized (queueLock)
- {
- try
- {
- queueLock.wait(initialDelay);
- }
- catch (InterruptedException e)
- {
- // Ignored
- }
-
- if (!running)
- return;
-
- queueEvent();
-
- if (repeats)
- while (running)
- {
- try
- {
- queueLock.wait(delay);
- }
- catch (InterruptedException e)
- {
- // Ignored
- }
-
- if (!running)
- break;
-
- queueEvent();
-
- if (logTimers)
- System.out.println("javax.swing.Timer -> clocktick");
-
- if (!repeats)
- break;
- }
- running = false;
- }
- }
- finally
- {
- // The timer is no longer running.
- running = false;
- }
+ if (logTimers)
+ System.out.println("javax.swing.Timer -> queueEvent()");
+ queueEvent();
+
+ if (!repeats)
+ task = null;
}
}
@@ -135,6 +94,14 @@ public class Timer
};
/**
+ * The static java.util.Timer daemon which will be used to schedule
+ * all javax.swing.Timer.Task objects. The daemon will always be
+ * running, even if there's no task scheduled in it.
+ */
+ private static java.util.Timer timer = new java.util.Timer("swing.Timer",
+ true);
+
+ /**
* If <code>true</code>, the timer prints a message to
* {@link System#out} when firing each event.
*/
@@ -156,12 +123,6 @@ public class Timer
boolean repeats = true;
/**
- * <code>true</code> if the timer is currently active, firing events
- * as scheduled.
- */
- boolean running;
-
- /**
* The delay between subsequent repetetive events.
*/
int delay;
@@ -179,10 +140,9 @@ public class Timer
int ticks;
/**
- * Stores the thread that posts events to the queue at required time
- * intervals.
+ * The task that calls queueEvent(). When null this Timer is stopped.
*/
- private Waker waker;
+ private Task task;
/**
* This object manages a "queue" of virtual actionEvents, maintained as a
@@ -377,7 +337,7 @@ public class Timer
*/
public boolean isRunning()
{
- return running;
+ return task != null;
}
/**
@@ -415,12 +375,15 @@ public class Timer
*/
public void start()
{
- synchronized (queueLock)
+ Task t = task;
+ if (t == null)
{
- if (waker != null)
- return;
- waker = new Waker();
- waker.start();
+ t = new Task();
+ if (isRepeats())
+ timer.schedule(t, getInitialDelay(), getDelay());
+ else
+ timer.schedule(t, getInitialDelay());
+ task = t;
}
}
@@ -429,13 +392,11 @@ public class Timer
*/
public void stop()
{
- synchronized (queueLock)
+ Task t = task;
+ if (t != null)
{
- running = false;
- queue = 0;
- if (waker != null)
- queueLock.notifyAll();
- waker = null;
+ t.cancel();
+ task = null;
}
}
@@ -496,11 +457,11 @@ public class Timer
*/
void queueEvent()
{
- synchronized (queueLock)
+ synchronized(queueLock)
{
- queue++;
- if (queue == 1)
- SwingUtilities.invokeLater(drainer);
+ queue++;
+ if (queue == 1)
+ SwingUtilities.invokeLater(drainer);
}
}
}
diff --git a/javax/swing/ToolTipManager.java b/javax/swing/ToolTipManager.java
index 03835794b..289149fb6 100644
--- a/javax/swing/ToolTipManager.java
+++ b/javax/swing/ToolTipManager.java
@@ -173,18 +173,9 @@ public class ToolTipManager extends MouseAdapter implements MouseMotionListener
/** The last known position of the mouse cursor. */
private static Point currentPoint;
-
- /**
- * The panel that holds the tooltip when the tooltip is displayed fully
- * inside the current container.
- */
- private static Container containerPanel;
-
- /**
- * The window used when the tooltip doesn't fit inside the current
- * container.
- */
- private static JDialog tooltipWindow;
+
+ /** */
+ private static Popup popup;
/**
* Creates a new ToolTipManager and sets up the timers.
@@ -369,26 +360,27 @@ public class ToolTipManager extends MouseAdapter implements MouseMotionListener
&& getContentPaneDeepestComponent(event) == currentComponent)
return;
currentPoint = event.getPoint();
+
currentComponent = (Component) event.getSource();
if (exitTimer.isRunning())
{
- exitTimer.stop();
- insideTimer.start();
- return;
+ exitTimer.stop();
+ showTip();
+ return;
}
-
// This should always be stopped unless we have just fake-exited.
- if (! enterTimer.isRunning())
+ if (!enterTimer.isRunning())
enterTimer.start();
}
/**
- * This method is called when the mouse exits a JComponent registered with
- * the ToolTipManager. When the mouse exits, the tooltip should be hidden
+ * This method is called when the mouse exits a JComponent registered with the
+ * ToolTipManager. When the mouse exits, the tooltip should be hidden
* immediately.
- *
- * @param event The MouseEvent.
+ *
+ * @param event
+ * The MouseEvent.
*/
public void mouseExited(MouseEvent event)
{
@@ -399,7 +391,7 @@ public class ToolTipManager extends MouseAdapter implements MouseMotionListener
currentComponent = null;
hideTip();
- if (! enterTimer.isRunning() && insideTimer.isRunning())
+ if (! enterTimer.isRunning())
exitTimer.start();
if (enterTimer.isRunning())
enterTimer.stop();
@@ -460,77 +452,36 @@ public class ToolTipManager extends MouseAdapter implements MouseMotionListener
void showTip()
{
if (!enabled || currentComponent == null || !currentComponent.isEnabled()
- || (currentTip != null && currentTip.isVisible()))
- return;
+ || !currentComponent.isShowing())
+ {
+ popup = null;
+ return;
+ }
if (currentTip == null || currentTip.getComponent() != currentComponent
&& currentComponent instanceof JComponent)
currentTip = ((JComponent) currentComponent).createToolTip();
- currentTip.setVisible(true);
- Container parent = currentComponent.getParent();
Point p = currentPoint;
+ Point cP = currentComponent.getLocationOnScreen();
Dimension dims = currentTip.getPreferredSize();
- if (parent instanceof JPopupMenu)
- setLightWeightPopupEnabled(((JPopupMenu) parent).isLightWeightPopupEnabled());
- else
- setLightWeightPopupEnabled(true);
-
- if (isLightWeightPopupEnabled())
- {
- JLayeredPane pane = null;
- JRootPane r = ((JRootPane) SwingUtilities.
- getAncestorOfClass(JRootPane.class, currentComponent));
- if (r != null)
- pane = r.getLayeredPane();
- if (pane == null)
- return;
-
- if (containerPanel != null)
- hideTip();
-
- containerPanel = new Panel();
- JRootPane root = new JRootPane();
- root.getContentPane().add(currentTip);
- containerPanel.add(root);
-
- LayoutManager lm = containerPanel.getLayout();
- if (lm instanceof FlowLayout)
- {
- FlowLayout fm = (FlowLayout) lm;
- fm.setVgap(0);
- fm.setHgap(0);
- }
-
- p = SwingUtilities.convertPoint(currentComponent, p, pane);
- p = adjustLocation(p, pane, dims);
-
- pane.add(containerPanel);
- containerPanel.setBounds(p.x, p.y, dims.width, dims.height);
- currentTip.setBounds(0, 0, dims.width, dims.height);
- containerPanel.validate();
- containerPanel.repaint();
- }
- else if (currentComponent.isShowing())
- {
- SwingUtilities.convertPointToScreen(p, currentComponent);
- p = adjustLocation(p, SwingUtilities.getWindowAncestor(currentComponent),
- dims);
-
- tooltipWindow = new JDialog();
- tooltipWindow.setContentPane(currentTip);
- tooltipWindow.setUndecorated(true);
- tooltipWindow.getRootPane().
- setWindowDecorationStyle(JRootPane.PLAIN_DIALOG);
- tooltipWindow.pack();
- tooltipWindow.setBounds(p.x, p.y, dims.width, dims.height);
- tooltipWindow.show();
- tooltipWindow.validate();
- tooltipWindow.repaint();
- currentTip.revalidate();
- currentTip.repaint();
- }
+ JLayeredPane pane = null;
+ JRootPane r = ((JRootPane) SwingUtilities.getAncestorOfClass(JRootPane.class,
+ currentComponent));
+ if (r != null)
+ pane = r.getLayeredPane();
+ if (pane == null)
+ return;
+
+ p.translate(cP.x, cP.y);
+ adjustLocation(p, pane, dims);
+
+ currentTip.setBounds(0, 0, dims.width, dims.height);
+
+ PopupFactory factory = PopupFactory.getSharedInstance();
+ popup = factory.getPopup(currentComponent, currentTip, p.x, p.y);
+ popup.show();
}
/**
@@ -550,7 +501,7 @@ public class ToolTipManager extends MouseAdapter implements MouseMotionListener
if (p.y + d.height < c.getHeight())
p.y += d.height;
if (p.y + d.height > c.getHeight())
- p.y -= d.height*2;
+ p.y -= d.height;
return p;
}
@@ -561,29 +512,8 @@ public class ToolTipManager extends MouseAdapter implements MouseMotionListener
*/
void hideTip()
{
- if (currentTip == null || ! currentTip.isVisible() || ! enabled)
- return;
- currentTip.setVisible(false);
- if (containerPanel != null)
- {
- Container parent = containerPanel.getParent();
- if (parent == null)
- return;
- parent.remove(containerPanel);
-
- parent = currentTip.getParent();
- if (parent == null)
- return;
- parent.remove(currentTip);
- containerPanel = null;
- }
- if (tooltipWindow != null)
- {
- tooltipWindow.hide();
- tooltipWindow.dispose();
- tooltipWindow = null;
- }
- currentTip = null;
+ if (popup != null)
+ popup.hide();
}
/**
diff --git a/javax/swing/TransferHandler.java b/javax/swing/TransferHandler.java
index 73479f5c8..486411092 100644
--- a/javax/swing/TransferHandler.java
+++ b/javax/swing/TransferHandler.java
@@ -75,30 +75,32 @@ public class TransferHandler implements Serializable
}
}
+ /**
+ * Get the system cliboard. If not available, create and return the VM-local
+ * clipboard.
+ *
+ * @param component a component, used to get the toolkit.
+ * @return the clipboard
+ */
private static Clipboard getClipboard(JComponent component)
{
- SecurityManager sm = System.getSecurityManager();
-
- if (sm != null)
- {
- try
- {
- sm.checkSystemClipboardAccess();
-
- // We may access system clipboard.
- return component.getToolkit().getSystemClipboard();
- }
- catch (SecurityException e)
- {
- // We may not access system clipboard.
- }
- }
-
- // Create VM-local clipboard if non exists yet.
- if (clipboard == null)
- clipboard = new Clipboard("Clipboard");
-
- return clipboard;
+ try
+ {
+ SecurityManager sm = System.getSecurityManager();
+ if (sm != null)
+ sm.checkSystemClipboardAccess();
+
+ // We may access the system clipboard.
+ return component.getToolkit().getSystemClipboard();
+ }
+ catch (Exception e)
+ {
+ // We may not access system clipboard.
+ // Create VM-local clipboard if none exists yet.
+ if (clipboard == null)
+ clipboard = new Clipboard("Clipboard");
+ return clipboard;
+ }
}
}
diff --git a/javax/swing/UIManager.java b/javax/swing/UIManager.java
index 15a781903..fbf1c7c79 100644
--- a/javax/swing/UIManager.java
+++ b/javax/swing/UIManager.java
@@ -132,6 +132,11 @@ public class UIManager implements Serializable
static UIDefaults currentUIDefaults;
+ /**
+ * UIDefaults set by the user.
+ */
+ static UIDefaults userUIDefaults;
+
/** Property change listener mechanism. */
static SwingPropertyChangeSupport listeners
= new SwingPropertyChangeSupport(UIManager.class);
@@ -305,7 +310,12 @@ public class UIManager implements Serializable
*/
public static Object get(Object key)
{
- return getLookAndFeelDefaults().get(key);
+ Object val = null;
+ if (userUIDefaults != null)
+ val = userUIDefaults.get(key);
+ if (val == null)
+ val = getLookAndFeelDefaults().get(key);
+ return val;
}
/**
@@ -318,7 +328,12 @@ public class UIManager implements Serializable
*/
public static Object get(Object key, Locale locale)
{
- return getLookAndFeelDefaults().get(key ,locale);
+ Object val = null;
+ if (userUIDefaults != null)
+ val = userUIDefaults.get(key, locale);
+ if (val == null)
+ val = getLookAndFeelDefaults().get(key, locale);
+ return val;
}
/**
@@ -329,7 +344,7 @@ public class UIManager implements Serializable
*/
public static boolean getBoolean(Object key)
{
- Boolean value = (Boolean) getLookAndFeelDefaults().get(key);
+ Boolean value = (Boolean) get(key);
return value != null ? value.booleanValue() : false;
}
@@ -341,7 +356,7 @@ public class UIManager implements Serializable
*/
public static boolean getBoolean(Object key, Locale locale)
{
- Boolean value = (Boolean) getLookAndFeelDefaults().get(key, locale);
+ Boolean value = (Boolean) get(key, locale);
return value != null ? value.booleanValue() : false;
}
@@ -350,7 +365,7 @@ public class UIManager implements Serializable
*/
public static Border getBorder(Object key)
{
- return (Border) getLookAndFeelDefaults().get(key);
+ return (Border) get(key);
}
/**
@@ -360,7 +375,7 @@ public class UIManager implements Serializable
*/
public static Border getBorder(Object key, Locale locale)
{
- return (Border) getLookAndFeelDefaults().get(key, locale);
+ return (Border) get(key, locale);
}
/**
@@ -368,7 +383,7 @@ public class UIManager implements Serializable
*/
public static Color getColor(Object key)
{
- return (Color) getLookAndFeelDefaults().get(key);
+ return (Color) get(key);
}
/**
@@ -376,7 +391,7 @@ public class UIManager implements Serializable
*/
public static Color getColor(Object key, Locale locale)
{
- return (Color) getLookAndFeelDefaults().get(key);
+ return (Color) get(key);
}
/**
@@ -405,7 +420,7 @@ public class UIManager implements Serializable
*/
public static Dimension getDimension(Object key)
{
- return (Dimension) getLookAndFeelDefaults().get(key);
+ return (Dimension) get(key);
}
/**
@@ -413,7 +428,7 @@ public class UIManager implements Serializable
*/
public static Dimension getDimension(Object key, Locale locale)
{
- return (Dimension) getLookAndFeelDefaults().get(key, locale);
+ return (Dimension) get(key, locale);
}
/**
@@ -426,7 +441,7 @@ public class UIManager implements Serializable
*/
public static Font getFont(Object key)
{
- return (Font) getLookAndFeelDefaults().get(key);
+ return (Font) get(key);
}
/**
@@ -439,7 +454,7 @@ public class UIManager implements Serializable
*/
public static Font getFont(Object key, Locale locale)
{
- return (Font) getLookAndFeelDefaults().get(key ,locale);
+ return (Font) get(key ,locale);
}
/**
@@ -447,7 +462,7 @@ public class UIManager implements Serializable
*/
public static Icon getIcon(Object key)
{
- return (Icon) getLookAndFeelDefaults().get(key);
+ return (Icon) get(key);
}
/**
@@ -455,7 +470,7 @@ public class UIManager implements Serializable
*/
public static Icon getIcon(Object key, Locale locale)
{
- return (Icon) getLookAndFeelDefaults().get(key, locale);
+ return (Icon) get(key, locale);
}
/**
@@ -463,7 +478,11 @@ public class UIManager implements Serializable
*/
public static Insets getInsets(Object key)
{
- return getLookAndFeelDefaults().getInsets(key);
+ Object o = get(key);
+ if (o instanceof Insets)
+ return (Insets) o;
+ else
+ return null;
}
/**
@@ -471,7 +490,11 @@ public class UIManager implements Serializable
*/
public static Insets getInsets(Object key, Locale locale)
{
- return getLookAndFeelDefaults().getInsets(key, locale);
+ Object o = get(key, locale);
+ if (o instanceof Insets)
+ return (Insets) o;
+ else
+ return null;
}
/**
@@ -487,7 +510,7 @@ public class UIManager implements Serializable
public static int getInt(Object key)
{
- Integer x = (Integer) getLookAndFeelDefaults().get(key);
+ Integer x = (Integer) get(key);
if (x == null)
return 0;
return x.intValue();
@@ -495,7 +518,7 @@ public class UIManager implements Serializable
public static int getInt(Object key, Locale locale)
{
- Integer x = (Integer) getLookAndFeelDefaults().get(key, locale);
+ Integer x = (Integer) get(key, locale);
if (x == null)
return 0;
return x.intValue();
@@ -529,7 +552,7 @@ public class UIManager implements Serializable
*/
public static String getString(Object key)
{
- return (String) getLookAndFeelDefaults().get(key);
+ return (String) get(key);
}
/**
@@ -537,7 +560,7 @@ public class UIManager implements Serializable
*/
public static String getString(Object key, Locale locale)
{
- return (String) getLookAndFeelDefaults().get(key, locale);
+ return (String) get(key, locale);
}
/**
@@ -562,7 +585,13 @@ public class UIManager implements Serializable
*/
public static ComponentUI getUI(JComponent target)
{
- return getLookAndFeelDefaults().getUI(target);
+ ComponentUI ui = null;
+ if (userUIDefaults != null
+ && userUIDefaults.get(target.getUIClassID()) != null)
+ ui = userUIDefaults.getUI(target);
+ if (ui == null)
+ ui = currentUIDefaults.getUI(target);
+ return ui;
}
/**
@@ -591,7 +620,11 @@ public class UIManager implements Serializable
*/
public static Object put(Object key, Object value)
{
- return getLookAndFeelDefaults().put(key,value);
+ Object old = get(key);
+ if (userUIDefaults == null)
+ userUIDefaults = new UIDefaults();
+ userUIDefaults.put(key, value);
+ return old;
}
/**
@@ -617,7 +650,6 @@ public class UIManager implements Serializable
{
if (newLookAndFeel != null && ! newLookAndFeel.isSupportedLookAndFeel())
throw new UnsupportedLookAndFeelException(newLookAndFeel.getName());
-
LookAndFeel oldLookAndFeel = currentLookAndFeel;
if (oldLookAndFeel != null)
oldLookAndFeel.uninitialize();
diff --git a/javax/swing/event/TreeModelEvent.java b/javax/swing/event/TreeModelEvent.java
index a217e3b40..8fa28a7ea 100644
--- a/javax/swing/event/TreeModelEvent.java
+++ b/javax/swing/event/TreeModelEvent.java
@@ -55,12 +55,12 @@ public class TreeModelEvent extends EventObject {
/**
* childIndices
*/
- protected int[] childIndices = new int[0];
+ protected int[] childIndices = null;
/**
* children
*/
- protected Object[] children = new Object[0];
+ protected Object[] children = null;
/**
* path
@@ -164,7 +164,9 @@ public class TreeModelEvent extends EventObject {
* @returns String representation
*/
public String toString() {
- return null; // TODO
+ return getClass() + " [Source: " + getSource() + ", TreePath: " + getTreePath() +
+ ", Child Indicies: " + getChildIndices() + ", Children: " + getChildren() +
+ ", Path: " + getPath() +"]";
} // toString()
diff --git a/javax/swing/plaf/ComponentUI.java b/javax/swing/plaf/ComponentUI.java
index ced3904c7..6a736f258 100644
--- a/javax/swing/plaf/ComponentUI.java
+++ b/javax/swing/plaf/ComponentUI.java
@@ -38,6 +38,7 @@ exception statement from your version. */
package javax.swing.plaf;
+import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Rectangle;
@@ -185,9 +186,10 @@ public abstract class ComponentUI
{
if (c.isOpaque())
{
+ Color oldColor = g.getColor();
g.setColor(c.getBackground());
- Rectangle clip = g.getClipBounds();
g.fillRect(0, 0, c.getWidth(), c.getHeight());
+ g.setColor(oldColor);
}
paint(g, c);
}
diff --git a/javax/swing/plaf/basic/BasicArrowButton.java b/javax/swing/plaf/basic/BasicArrowButton.java
index 69d441537..56e4e7073 100644
--- a/javax/swing/plaf/basic/BasicArrowButton.java
+++ b/javax/swing/plaf/basic/BasicArrowButton.java
@@ -162,8 +162,8 @@ public class BasicArrowButton extends JButton implements SwingConstants
super.paint(g);
Rectangle bounds = getBounds();
int size = bounds.height / 4;
- int x = (bounds.width - size) / 2;
- int y = (bounds.height - size) / 2;
+ int x = bounds.x + (bounds.width - size) / 2;
+ int y = (bounds.height - size) / 4;
ButtonModel m = getModel();
if (m.isArmed())
{
diff --git a/javax/swing/plaf/basic/BasicBorders.java b/javax/swing/plaf/basic/BasicBorders.java
index cec7bec85..5d4ce1893 100644
--- a/javax/swing/plaf/basic/BasicBorders.java
+++ b/javax/swing/plaf/basic/BasicBorders.java
@@ -51,7 +51,6 @@ import javax.swing.JButton;
import javax.swing.JPopupMenu;
import javax.swing.JSplitPane;
import javax.swing.JToolBar;
-import javax.swing.UIDefaults;
import javax.swing.UIManager;
import javax.swing.border.AbstractBorder;
import javax.swing.border.BevelBorder;
@@ -95,21 +94,18 @@ public class BasicBorders
*/
public static Border getButtonBorder()
{
- UIDefaults defaults;
Border outer;
- defaults = UIManager.getLookAndFeelDefaults();
-
/* The keys for UIDefaults have been determined by writing a
* test program that dumps the UIDefaults to stdout; that program
* was run on a JDK 1.4.1_01 for GNU/Linux. Note that in the API,
* the key "light" is usually called "highlight", and "highlight"
* is usually called "lightHighlight".
*/
- outer = new ButtonBorder(defaults.getColor("Button.shadow"),
- defaults.getColor("Button.darkShadow"),
- defaults.getColor("Button.light"),
- defaults.getColor("Button.highlight"));
+ outer = new ButtonBorder(UIManager.getColor("Button.shadow"),
+ UIManager.getColor("Button.darkShadow"),
+ UIManager.getColor("Button.light"),
+ UIManager.getColor("Button.highlight"));
/* While the inner border is shared between multiple buttons,
* we do not share the outer border because ButtonBorders store
@@ -145,11 +141,8 @@ public class BasicBorders
*/
public static Border getRadioButtonBorder()
{
- UIDefaults defaults;
Border outer;
- defaults = UIManager.getLookAndFeelDefaults();
-
/* The keys for UIDefaults have been determined by writing a
* test program that dumps the UIDefaults to stdout; that program
* was run on a JDK 1.4.1_01 for GNU/Linux. Note that in the API,
@@ -157,10 +150,10 @@ public class BasicBorders
* is usually called "lightHighlight".
*/
outer = new RadioButtonBorder(
- defaults.getColor("RadioButton.shadow"),
- defaults.getColor("RadioButton.darkShadow"),
- defaults.getColor("RadioButton.light"),
- defaults.getColor("RadioButton.highlight"));
+ UIManager.getColor("RadioButton.shadow"),
+ UIManager.getColor("RadioButton.darkShadow"),
+ UIManager.getColor("RadioButton.light"),
+ UIManager.getColor("RadioButton.highlight"));
/* While the inner border is shared between multiple buttons, we
* do not share the outer border because RadioButtonBorders, being
@@ -197,11 +190,8 @@ public class BasicBorders
*/
public static Border getToggleButtonBorder()
{
- UIDefaults defaults;
Border outer;
- defaults = UIManager.getLookAndFeelDefaults();
-
/* The keys for UIDefaults have been determined by writing a
* test program that dumps the UIDefaults to stdout; that program
* was run on a JDK 1.4.1_01 for GNU/Linux. Note that in the API,
@@ -209,10 +199,10 @@ public class BasicBorders
* is usually called "lightHighlight".
*/
outer = new ToggleButtonBorder(
- defaults.getColor("ToggleButton.shadow"),
- defaults.getColor("ToggleButton.darkShadow"),
- defaults.getColor("ToggleButton.light"),
- defaults.getColor("ToggleButton.highlight"));
+ UIManager.getColor("ToggleButton.shadow"),
+ UIManager.getColor("ToggleButton.darkShadow"),
+ UIManager.getColor("ToggleButton.light"),
+ UIManager.getColor("ToggleButton.highlight"));
/* While the inner border is shared between multiple buttons, we
* do not share the outer border because ToggleButtonBorders, being
@@ -247,12 +237,9 @@ public class BasicBorders
*/
public static Border getMenuBarBorder()
{
- UIDefaults defaults;
-
/* See comment in methods above for why this border is not shared. */
- defaults = UIManager.getLookAndFeelDefaults();
- return new MenuBarBorder(defaults.getColor("MenuBar.shadow"),
- defaults.getColor("MenuBar.highlight"));
+ return new MenuBarBorder(UIManager.getColor("MenuBar.shadow"),
+ UIManager.getColor("MenuBar.highlight"));
}
@@ -279,12 +266,9 @@ public class BasicBorders
*/
public static Border getSplitPaneBorder()
{
- UIDefaults defaults;
-
/* See comment in methods above for why this border is not shared. */
- defaults = UIManager.getLookAndFeelDefaults();
- return new SplitPaneBorder(defaults.getColor("SplitPane.highlight"),
- defaults.getColor("SplitPane.darkShadow"));
+ return new SplitPaneBorder(UIManager.getColor("SplitPane.highlight"),
+ UIManager.getColor("SplitPane.darkShadow"));
}
@@ -314,13 +298,10 @@ public class BasicBorders
*/
public static Border getSplitPaneDividerBorder()
{
- UIDefaults defaults;
-
/* See comment in methods above for why this border is not shared. */
- defaults = UIManager.getLookAndFeelDefaults();
return new SplitPaneDividerBorder(
- defaults.getColor("SplitPane.highlight"),
- defaults.getColor("SplitPane.darkShadow"));
+ UIManager.getColor("SplitPane.highlight"),
+ UIManager.getColor("SplitPane.darkShadow"));
}
@@ -346,15 +327,12 @@ public class BasicBorders
*/
public static Border getTextFieldBorder()
{
- UIDefaults defaults;
-
/* See comment in methods above for why this border is not shared. */
- defaults = UIManager.getLookAndFeelDefaults();
return new FieldBorder(
- defaults.getColor("TextField.shadow"),
- defaults.getColor("TextField.darkShadow"),
- defaults.getColor("TextField.light"),
- defaults.getColor("TextField.highlight"));
+ UIManager.getColor("TextField.shadow"),
+ UIManager.getColor("TextField.darkShadow"),
+ UIManager.getColor("TextField.light"),
+ UIManager.getColor("TextField.highlight"));
}
@@ -394,17 +372,14 @@ public class BasicBorders
*/
public static Border getInternalFrameBorder()
{
- UIDefaults defaults;
Color shadow, darkShadow, highlight, lightHighlight, line;
/* See comment in methods above for why this border is not shared. */
- defaults = UIManager.getLookAndFeelDefaults();
-
- shadow = defaults.getColor("InternalFrame.borderShadow");
- darkShadow = defaults.getColor("InternalFrame.borderDarkShadow");
- highlight = defaults.getColor("InternalFrame.borderLight");
- lightHighlight = defaults.getColor("InternalFrame.borderHighlight");
- line = defaults.getColor("InternalFrame.borderColor");
+ shadow = UIManager.getColor("InternalFrame.borderShadow");
+ darkShadow = UIManager.getColor("InternalFrame.borderDarkShadow");
+ highlight = UIManager.getColor("InternalFrame.borderLight");
+ lightHighlight = UIManager.getColor("InternalFrame.borderHighlight");
+ line = UIManager.getColor("InternalFrame.borderColor");
return new BorderUIResource.CompoundBorderUIResource(
/* outer border */
diff --git a/javax/swing/plaf/basic/BasicButtonUI.java b/javax/swing/plaf/basic/BasicButtonUI.java
index 2d3dbd350..7a63331b9 100644
--- a/javax/swing/plaf/basic/BasicButtonUI.java
+++ b/javax/swing/plaf/basic/BasicButtonUI.java
@@ -52,7 +52,6 @@ import javax.swing.JButton;
import javax.swing.JComponent;
import javax.swing.LookAndFeel;
import javax.swing.SwingUtilities;
-import javax.swing.UIDefaults;
import javax.swing.UIManager;
import javax.swing.plaf.ButtonUI;
import javax.swing.plaf.ComponentUI;
@@ -161,7 +160,6 @@ public class BasicButtonUI extends ButtonUI
b.setIconTextGap(UIManager.getInt(prefix + "textIconGap"));
b.setInputMap(JComponent.WHEN_FOCUSED,
(InputMap) UIManager.get(prefix + "focusInputMap"));
- b.setRolloverEnabled(UIManager.getBoolean(prefix + "rollover"));
}
/**
@@ -444,9 +442,8 @@ public class BasicButtonUI extends ButtonUI
}
else
{
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
String prefix = getPropertyPrefix();
- g.setColor(defaults.getColor(prefix + "disabledText"));
+ g.setColor(UIManager.getColor(prefix + "disabledText"));
g.drawString(text, textRect.x, textRect.y + fm.getAscent());
}
}
diff --git a/javax/swing/plaf/basic/BasicCheckBoxUI.java b/javax/swing/plaf/basic/BasicCheckBoxUI.java
index 3cf02a001..14dadb85c 100644
--- a/javax/swing/plaf/basic/BasicCheckBoxUI.java
+++ b/javax/swing/plaf/basic/BasicCheckBoxUI.java
@@ -40,7 +40,6 @@ package javax.swing.plaf.basic;
import javax.swing.Icon;
import javax.swing.JComponent;
-import javax.swing.UIDefaults;
import javax.swing.UIManager;
import javax.swing.plaf.ComponentUI;
@@ -53,12 +52,11 @@ public class BasicCheckBoxUI extends BasicRadioButtonUI
public Icon getDefaultIcon()
{
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
- return defaults.getIcon("CheckBox.icon");
+ return UIManager.getIcon("CheckBox.icon");
}
/**
- * Returns the prefix for entries in the {@link UIDefaults} table.
+ * Returns the prefix for entries in the {@link UIManager} defaults table.
*
* @return "CheckBox."
*/
diff --git a/javax/swing/plaf/basic/BasicComboBoxEditor.java b/javax/swing/plaf/basic/BasicComboBoxEditor.java
index be8c776aa..831dde8c3 100644
--- a/javax/swing/plaf/basic/BasicComboBoxEditor.java
+++ b/javax/swing/plaf/basic/BasicComboBoxEditor.java
@@ -45,35 +45,34 @@ import java.awt.event.FocusListener;
import javax.swing.ComboBoxEditor;
import javax.swing.JTextField;
-import javax.swing.border.EmptyBorder;
/**
- * This is a component that is responsible for displaying/editting selected
- * item in comboBox. By default, the JTextField is returned as
- * BasicComboBoxEditor.
+ * An editor used by the {@link BasicComboBoxUI} class. This editor uses a
+ * {@link JTextField} as the editor component.
*
* @author Olga Rodimina
*/
public class BasicComboBoxEditor extends Object implements ComboBoxEditor,
FocusListener
{
+ /** The editor component. */
protected JTextField editor;
/**
- * Creates a new BasicComboBoxEditor object.
+ * Creates a new <code>BasicComboBoxEditor</code> instance.
*/
public BasicComboBoxEditor()
{
editor = new JTextField();
- editor.setBorder(new EmptyBorder(1, 1, 1, 1));
+ editor.setBorder(null);
+ editor.setColumns(9);
}
/**
- * This method returns textfield that will be used by the combo box to
- * display/edit currently selected item in the combo box.
+ * Returns the component that will be used by the combo box to display and
+ * edit the currently selected item in the combo box.
*
- * @return textfield that will be used by the combo box to display/edit
- * currently selected item
+ * @return The editor component, which is a {@link JTextField} in this case.
*/
public Component getEditorComponent()
{
@@ -98,15 +97,18 @@ public class BasicComboBoxEditor extends Object implements ComboBoxEditor,
}
/**
- * This method returns item that is currently editable.
+ * Returns the text from the editor component.
*
- * @return item in the combo box that is currently editable
+ * @return The text from the editor component.
*/
public Object getItem()
{
return editor.getText();
}
+ /**
+ * Selects all the text in the editor component.
+ */
public void selectAll()
{
editor.selectAll();
@@ -136,8 +138,8 @@ public class BasicComboBoxEditor extends Object implements ComboBoxEditor,
}
/**
- * This method adds actionListener to the editor. If the user will edit
- * currently selected item in the textfield and pressEnter, then action
+ * Adds an {@link ActionListener} to the editor component. If the user will
+ * edit currently selected item in the textfield and pressEnter, then action
* will be performed. The actionPerformed of this ActionListener should
* change the selected item of the comboBox to the newly editted selected
* item.
@@ -147,24 +149,28 @@ public class BasicComboBoxEditor extends Object implements ComboBoxEditor,
*/
public void addActionListener(ActionListener l)
{
- // FIXME: Need to implement
+ editor.addActionListener(l);
}
/**
- * This method removes actionListener from the textfield.
+ * Removes the {@link ActionListener} from the editor component.
*
- * @param l the ActionListener to remove from the textfield.
+ * @param l the listener to remove.
*/
public void removeActionListener(ActionListener l)
{
- // FIXME: Need to implement
+ editor.removeActionListener(l);
}
+ /**
+ * A subclass of {@link BasicComboBoxEditor} that implements the
+ * {@link UIResource} interface.
+ */
public static class UIResource extends BasicComboBoxEditor
implements javax.swing.plaf.UIResource
{
/**
- * Creates a new UIResource object.
+ * Creates a new <code>BasicComboBoxEditor.UIResource</code> instance.
*/
public UIResource()
{
diff --git a/javax/swing/plaf/basic/BasicComboBoxUI.java b/javax/swing/plaf/basic/BasicComboBoxUI.java
index 7356423d3..78ceccb05 100644
--- a/javax/swing/plaf/basic/BasicComboBoxUI.java
+++ b/javax/swing/plaf/basic/BasicComboBoxUI.java
@@ -149,8 +149,11 @@ public class BasicComboBoxUI extends ComboBoxUI
* Popup list containing the combo box's menu items.
*/
protected ComboPopup popup;
+
protected KeyListener popupKeyListener;
+
protected MouseListener popupMouseListener;
+
protected MouseMotionListener popupMouseMotionListener;
/**
@@ -187,10 +190,19 @@ public class BasicComboBoxUI extends ComboBoxUI
*/
Dimension displaySize;
- // FIXME: This fields aren't used anywhere at this moment.
- protected Dimension cachedMinimumSize;
+ // FIXME: This field isn't used anywhere at this moment.
protected CellRendererPane currentValuePane;
- protected boolean isMinimumSizeDirty;
+
+ /**
+ * The current minimum size if isMinimumSizeDirty is false.
+ * Setup by getMinimumSize() and invalidated by the various listeners.
+ */
+ protected Dimension cachedMinimumSize;
+
+ /**
+ * Indicates whether or not the cachedMinimumSize field is valid or not.
+ */
+ protected boolean isMinimumSizeDirty = true;
/**
* Creates a new <code>BasicComboBoxUI</code> object.
@@ -283,6 +295,7 @@ public class BasicComboBoxUI extends ComboBoxUI
focusListener = createFocusListener();
comboBox.addFocusListener(focusListener);
+ listBox.addFocusListener(focusListener);
itemListener = createItemListener();
comboBox.addItemListener(itemListener);
@@ -332,6 +345,7 @@ public class BasicComboBoxUI extends ComboBoxUI
propertyChangeListener = null;
comboBox.removeFocusListener(focusListener);
+ listBox.removeFocusListener(focusListener);
focusListener = null;
comboBox.removeItemListener(itemListener);
@@ -480,9 +494,10 @@ public class BasicComboBoxUI extends ComboBoxUI
ComboBoxEditor currentEditor = comboBox.getEditor();
if (currentEditor == null || currentEditor instanceof UIResource)
{
- comboBox.setEditor(createEditor());
- editor = comboBox.getEditor().getEditorComponent();
- }
+ currentEditor = createEditor();
+ comboBox.setEditor(currentEditor);
+ }
+ editor = currentEditor.getEditorComponent();
comboBox.revalidate();
}
@@ -609,7 +624,10 @@ public class BasicComboBoxUI extends ComboBoxUI
public void setPopupVisible(JComboBox c, boolean v)
{
if (v)
- popup.show();
+ {
+ popup.show();
+ popup.getList().requestFocus();
+ }
else
popup.hide();
}
@@ -659,7 +677,7 @@ public class BasicComboBoxUI extends ComboBoxUI
/**
* Returns the minimum size for this {@link JComboBox} for this
- * look and feel.
+ * look and feel. Also makes sure cachedMinimimSize is setup correctly.
*
* @param c The {@link JComponent} to find the minimum size for.
*
@@ -667,10 +685,15 @@ public class BasicComboBoxUI extends ComboBoxUI
*/
public Dimension getMinimumSize(JComponent c)
{
- Dimension d = getDisplaySize();
- int arrowButtonWidth = d.height;
- Dimension result = new Dimension(d.width + arrowButtonWidth, d.height);
- return result;
+ if (isMinimumSizeDirty)
+ {
+ Dimension d = getDisplaySize();
+ int arrowButtonWidth = d.height;
+ cachedMinimumSize = new Dimension(d.width + arrowButtonWidth,
+ d.height);
+ isMinimumSizeDirty = false;
+ }
+ return new Dimension(cachedMinimumSize);
}
/** The value returned by the getMaximumSize() method. */
@@ -796,10 +819,10 @@ public class BasicComboBoxUI extends ComboBoxUI
isPressed, hasFocus);
if (! comboBox.isEnabled())
{
- comp.setBackground(UIManager.getLookAndFeelDefaults().getColor(
- "ComboBox.disabledBackground"));
- comp.setForeground(UIManager.getLookAndFeelDefaults().getColor(
- "ComboBox.disabledForeground"));
+ comp.setBackground(UIManager.getColor(
+ "ComboBox.disabledBackground"));
+ comp.setForeground(UIManager.getColor(
+ "ComboBox.disabledForeground"));
comp.setEnabled(false);
}
comp.setBounds(0, 0, bounds.width, bounds.height);
@@ -851,57 +874,75 @@ public class BasicComboBoxUI extends ComboBoxUI
}
/**
- * Returns size of the largest item in the combo box. This size will be the
- * size of the combo box, not including the arrowButton.
+ * Returns the size of the display area for the combo box. This size will be
+ * the size of the combo box, not including the arrowButton.
*
- * @return dimensions of the largest item in the combo box.
+ * @return The size of the display area for the combo box.
*/
protected Dimension getDisplaySize()
{
- Object prototype = comboBox.getPrototypeDisplayValue();
- if (prototype != null)
+ if (!comboBox.isEditable())
{
- // calculate result based on prototype
- ListCellRenderer renderer = comboBox.getRenderer();
- Component comp = renderer.getListCellRendererComponent(listBox,
- prototype, -1, false, false);
- Dimension compSize = comp.getPreferredSize();
- compSize.width += 2; // add 1 pixel margin around area
- compSize.height += 2;
- return compSize;
- }
- else
- {
- ComboBoxModel model = comboBox.getModel();
- int numItems = model.getSize();
-
- // if combo box doesn't have any items then simply
- // return its default size
- if (numItems == 0)
+ Object prototype = comboBox.getPrototypeDisplayValue();
+ if (prototype != null)
{
- displaySize = getDefaultSize();
- return displaySize;
+ // calculate result based on prototype
+ ListCellRenderer renderer = comboBox.getRenderer();
+ Component comp = renderer.getListCellRendererComponent(listBox,
+ prototype, -1, false, false);
+ Dimension compSize = comp.getPreferredSize();
+ compSize.width += 2; // add 1 pixel margin around area
+ compSize.height += 2;
+ return compSize;
}
-
- Dimension size = new Dimension(0, 0);
-
- // ComboBox's display size should be equal to the
- // size of the largest item in the combo box.
- ListCellRenderer renderer = comboBox.getRenderer();
-
- for (int i = 0; i < numItems; i++)
+ else
{
- Object item = model.getElementAt(i);
- Component comp = renderer.getListCellRendererComponent(listBox,
+ ComboBoxModel model = comboBox.getModel();
+ int numItems = model.getSize();
+
+ // if combo box doesn't have any items then simply
+ // return its default size
+ if (numItems == 0)
+ {
+ displaySize = getDefaultSize();
+ return displaySize;
+ }
+
+ Dimension size = new Dimension(0, 0);
+
+ // ComboBox's display size should be equal to the
+ // size of the largest item in the combo box.
+ ListCellRenderer renderer = comboBox.getRenderer();
+
+ for (int i = 0; i < numItems; i++)
+ {
+ Object item = model.getElementAt(i);
+ Component comp = renderer.getListCellRendererComponent(listBox,
item, -1, false, false);
- Dimension compSize = comp.getPreferredSize();
- if (compSize.width + 2 > size.width)
- size.width = compSize.width + 2;
- if (compSize.height + 2 > size.height)
- size.height = compSize.height + 2;
+ Dimension compSize = comp.getPreferredSize();
+ if (compSize.width + 2 > size.width)
+ size.width = compSize.width + 2;
+ if (compSize.height + 2 > size.height)
+ size.height = compSize.height + 2;
+ }
+ displaySize = size;
+ return displaySize;
}
- displaySize = size;
+ }
+ else // an editable combo,
+ {
+ Component comp = comboBox.getEditor().getEditorComponent();
+ Dimension prefSize = comp.getPreferredSize();
+ int width = prefSize.width;
+ int height = prefSize.height + 2;
+ Object prototype = comboBox.getPrototypeDisplayValue();
+ if (prototype != null)
+ {
+ FontMetrics fm = comboBox.getFontMetrics(comboBox.getFont());
+ width = Math.max(width, fm.stringWidth(prototype.toString()) + 2);
+ }
+ displaySize = new Dimension(width, height);
return displaySize;
}
}
@@ -1035,6 +1076,9 @@ public class BasicComboBoxUI extends ComboBoxUI
*/
public void focusGained(FocusEvent e)
{
+ // Lets assume every change invalidates the minimumsize.
+ isMinimumSizeDirty = true;
+
hasFocus = true;
comboBox.repaint();
}
@@ -1047,6 +1091,9 @@ public class BasicComboBoxUI extends ComboBoxUI
*/
public void focusLost(FocusEvent e)
{
+ // Lets assume every change invalidates the minimumsize.
+ isMinimumSizeDirty = true;
+
hasFocus = false;
setPopupVisible(comboBox, false);
comboBox.repaint();
@@ -1075,6 +1122,9 @@ public class BasicComboBoxUI extends ComboBoxUI
*/
public void itemStateChanged(ItemEvent e)
{
+ // Lets assume every change invalidates the minimumsize.
+ isMinimumSizeDirty = true;
+
if (e.getStateChange() == ItemEvent.SELECTED && comboBox.isEditable())
comboBox.getEditor().setItem(e.getItem());
comboBox.repaint();
@@ -1122,6 +1172,9 @@ public class BasicComboBoxUI extends ComboBoxUI
public void contentsChanged(ListDataEvent e)
{
// if the item is selected or deselected
+
+ // Lets assume every change invalidates the minimumsize.
+ isMinimumSizeDirty = true;
}
/**
@@ -1131,6 +1184,9 @@ public class BasicComboBoxUI extends ComboBoxUI
*/
public void intervalAdded(ListDataEvent e)
{
+ // Lets assume every change invalidates the minimumsize.
+ isMinimumSizeDirty = true;
+
ComboBoxModel model = comboBox.getModel();
ListCellRenderer renderer = comboBox.getRenderer();
@@ -1152,6 +1208,9 @@ public class BasicComboBoxUI extends ComboBoxUI
*/
public void intervalRemoved(ListDataEvent e)
{
+ // Lets assume every change invalidates the minimumsize.
+ isMinimumSizeDirty = true;
+
// recalculate display size of the JComboBox.
displaySize = getDisplaySize();
comboBox.repaint();
@@ -1179,6 +1238,9 @@ public class BasicComboBoxUI extends ComboBoxUI
*/
public void propertyChange(PropertyChangeEvent e)
{
+ // Lets assume every change invalidates the minimumsize.
+ isMinimumSizeDirty = true;
+
if (e.getPropertyName().equals("enabled"))
{
arrowButton.setEnabled(comboBox.isEnabled());
diff --git a/javax/swing/plaf/basic/BasicComboPopup.java b/javax/swing/plaf/basic/BasicComboPopup.java
index 7f3fab8f1..73979bb89 100644
--- a/javax/swing/plaf/basic/BasicComboPopup.java
+++ b/javax/swing/plaf/basic/BasicComboPopup.java
@@ -38,9 +38,9 @@ exception statement from your version. */
package javax.swing.plaf.basic;
+import java.awt.Color;
import java.awt.Component;
import java.awt.Dimension;
-import java.awt.Insets;
import java.awt.Point;
import java.awt.Rectangle;
import java.awt.event.ItemEvent;
@@ -56,6 +56,7 @@ import java.awt.event.MouseMotionListener;
import java.beans.PropertyChangeEvent;
import java.beans.PropertyChangeListener;
+import javax.swing.BorderFactory;
import javax.swing.ComboBoxModel;
import javax.swing.JComboBox;
import javax.swing.JLabel;
@@ -179,11 +180,8 @@ public class BasicComboPopup extends JPopupMenu implements ComboPopup
// to display number of rows equal to 'maximumRowCount' property
int popupHeight = getPopupHeightForRowCount(comboBox.getMaximumRowCount());
- list.setPreferredSize(new Dimension(cbBounds.width, popupHeight));
- Insets insets1 = getInsets();
- Insets insets2 = scroller.getInsets();
- super.setPopupSize(cbBounds.width, popupHeight + insets1.top
- + insets1.bottom + insets2.top + insets2.bottom);
+ scroller.setPreferredSize(new Dimension(cbBounds.width, popupHeight));
+ pack();
// Highlight selected item in the combo box's drop down list
if (comboBox.getSelectedIndex() != -1)
@@ -482,6 +480,7 @@ public class BasicComboPopup extends JPopupMenu implements ComboPopup
*/
protected void configureScroller()
{
+ scroller.setBorder(null);
scroller.getViewport().setView(list);
scroller.setHorizontalScrollBarPolicy(JScrollPane.HORIZONTAL_SCROLLBAR_NEVER);
}
@@ -492,6 +491,7 @@ public class BasicComboPopup extends JPopupMenu implements ComboPopup
*/
protected void configurePopup()
{
+ setBorder(BorderFactory.createLineBorder(Color.BLACK));
// initialize list that will be used to display combo box's items
this.list = createList();
((JLabel) list.getCellRenderer()).setHorizontalAlignment(SwingConstants.LEFT);
diff --git a/javax/swing/plaf/basic/BasicEditorPaneUI.java b/javax/swing/plaf/basic/BasicEditorPaneUI.java
index d5b34d9ee..d514a87c8 100644
--- a/javax/swing/plaf/basic/BasicEditorPaneUI.java
+++ b/javax/swing/plaf/basic/BasicEditorPaneUI.java
@@ -42,10 +42,7 @@ import javax.swing.JComponent;
import javax.swing.JEditorPane;
import javax.swing.plaf.ComponentUI;
import javax.swing.text.EditorKit;
-import javax.swing.text.Element;
import javax.swing.text.JTextComponent;
-import javax.swing.text.PlainView;
-import javax.swing.text.View;
/**
* The UI class for {@link JEditorPane}s.
@@ -76,14 +73,6 @@ public class BasicEditorPaneUI extends BasicTextUI
// Do nothing here.
}
- // FIXME: Should not be overridden here but instead be handled by the
- // JEditorPane's EditorKit. However, as long as we don't have styles in
- // place this doesn't make much sense.
- public View create(Element elem)
- {
- return new PlainView(elem);
- }
-
/**
* Returns the property prefix to be used by this UI class. This is
* <code>EditorPane</code> in this case.
diff --git a/javax/swing/plaf/basic/BasicFileChooserUI.java b/javax/swing/plaf/basic/BasicFileChooserUI.java
index 8229e366b..198529a99 100644
--- a/javax/swing/plaf/basic/BasicFileChooserUI.java
+++ b/javax/swing/plaf/basic/BasicFileChooserUI.java
@@ -37,19 +37,10 @@ exception statement from your version. */
package javax.swing.plaf.basic;
-import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Component;
-import java.awt.Dimension;
-import java.awt.Graphics;
-import java.awt.GridBagConstraints;
-import java.awt.GridBagLayout;
-import java.awt.Point;
-import java.awt.Polygon;
import java.awt.Window;
import java.awt.event.ActionEvent;
-import java.awt.event.ItemEvent;
-import java.awt.event.ItemListener;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.event.MouseListener;
@@ -62,19 +53,15 @@ import java.util.Hashtable;
import javax.swing.AbstractAction;
import javax.swing.Action;
-import javax.swing.ButtonGroup;
import javax.swing.Icon;
import javax.swing.JButton;
-import javax.swing.JComboBox;
import javax.swing.JComponent;
import javax.swing.JDialog;
import javax.swing.JFileChooser;
import javax.swing.JLabel;
import javax.swing.JList;
import javax.swing.JPanel;
-import javax.swing.JScrollPane;
import javax.swing.JTextField;
-import javax.swing.JToggleButton;
import javax.swing.ListCellRenderer;
import javax.swing.SwingConstants;
import javax.swing.SwingUtilities;
@@ -88,6 +75,7 @@ import javax.swing.filechooser.FileSystemView;
import javax.swing.filechooser.FileView;
import javax.swing.plaf.ComponentUI;
import javax.swing.plaf.FileChooserUI;
+import javax.swing.plaf.metal.MetalIconFactory;
/**
@@ -145,7 +133,7 @@ public class BasicFileChooserUI extends FileChooserUI
*/
protected ApproveSelectionAction()
{
- // Nothing to do here.
+ super("approveSelection");
}
/**
@@ -155,7 +143,7 @@ public class BasicFileChooserUI extends FileChooserUI
*/
public void actionPerformed(ActionEvent e)
{
- Object obj = new String(parentPath + entry.getText());
+ Object obj = new String(parentPath + getFileName());
if (obj != null)
{
File f = filechooser.getFileSystemView().createFileObject(
@@ -308,7 +296,7 @@ public class BasicFileChooserUI extends FileChooserUI
*/
protected CancelSelectionAction()
{
- // Nothing to do here.
+ super(null);
}
/**
@@ -336,7 +324,7 @@ public class BasicFileChooserUI extends FileChooserUI
*/
protected ChangeToParentDirectoryAction()
{
- // Nothing to do here.
+ super("Go Up");
}
/**
@@ -359,8 +347,6 @@ public class BasicFileChooserUI extends FileChooserUI
*/
protected class DoubleClickListener extends MouseAdapter
{
- /** A timer. */
- private Timer timer = null;
/** DOCUMENT ME! */
private Object lastSelected = null;
@@ -376,8 +362,6 @@ public class BasicFileChooserUI extends FileChooserUI
public DoubleClickListener(JList list)
{
this.list = list;
- timer = new Timer(1000, null);
- timer.setRepeats(false);
lastSelected = list.getSelectedValue();
setDirectorySelected(false);
}
@@ -392,11 +376,10 @@ public class BasicFileChooserUI extends FileChooserUI
if (list.getSelectedValue() == null)
return;
FileSystemView fsv = filechooser.getFileSystemView();
- if (timer.isRunning()
- && list.getSelectedValue().toString().equals(lastSelected.toString()))
+ if (e.getClickCount() >= 2 &&
+ list.getSelectedValue().toString().equals(lastSelected.toString()))
{
File f = fsv.createFileObject(lastSelected.toString());
- timer.stop();
if (filechooser.isTraversable(f))
{
filechooser.setCurrentDirectory(f);
@@ -425,8 +408,7 @@ public class BasicFileChooserUI extends FileChooserUI
}
lastSelected = path;
parentPath = path.substring(0, path.lastIndexOf("/") + 1);
- entry.setText(path.substring(path.lastIndexOf("/") + 1));
- timer.restart();
+ setFileName(path.substring(path.lastIndexOf("/") + 1));
}
}
@@ -454,7 +436,7 @@ public class BasicFileChooserUI extends FileChooserUI
*/
protected GoHomeAction()
{
- // Nothing to do here.
+ super("Go Home");
}
/**
@@ -484,7 +466,7 @@ public class BasicFileChooserUI extends FileChooserUI
*/
protected NewFolderAction()
{
- // Nothing to do here.
+ super("New Folder");
}
/**
@@ -530,7 +512,8 @@ public class BasicFileChooserUI extends FileChooserUI
*/
public void valueChanged(ListSelectionEvent e)
{
- Object f = filelist.getSelectedValue();
+ JList list = (JList) e.getSource();
+ Object f = list.getSelectedValue();
if (f == null)
return;
File file = filechooser.getFileSystemView().createFileObject(f.toString());
@@ -553,7 +536,7 @@ public class BasicFileChooserUI extends FileChooserUI
*/
protected UpdateAction()
{
- // Nothing to do here.
+ super(null);
}
/**
@@ -577,91 +560,13 @@ public class BasicFileChooserUI extends FileChooserUI
protected String cancelButtonToolTipText;
/** An icon representing a computer. */
- protected Icon computerIcon = new Icon()
- {
- public int getIconHeight()
- {
- return ICON_SIZE;
- }
-
- public int getIconWidth()
- {
- return ICON_SIZE;
- }
-
- public void paintIcon(Component c, Graphics g, int x, int y)
- {
- // FIXME: is this not implemented, or is the icon intentionally blank?
- }
- };
+ protected Icon computerIcon;
/** An icon for the "details view" button. */
- protected Icon detailsViewIcon = new Icon()
- {
- public int getIconHeight()
- {
- return ICON_SIZE;
- }
-
- public int getIconWidth()
- {
- return ICON_SIZE;
- }
-
- public void paintIcon(Component c, Graphics g, int x, int y)
- {
- Color saved = g.getColor();
- g.translate(x, y);
-
- g.setColor(Color.GRAY);
- g.drawRect(1, 1, 15, 20);
- g.drawLine(17, 6, 23, 6);
- g.drawLine(17, 12, 23, 12);
- g.drawLine(17, 18, 23, 18);
-
- g.setColor(saved);
- g.translate(-x, -y);
- }
- };
+ protected Icon detailsViewIcon;
/** An icon representing a directory. */
- protected Icon directoryIcon = new Icon()
- {
- public int getIconHeight()
- {
- return ICON_SIZE;
- }
-
- public int getIconWidth()
- {
- return ICON_SIZE;
- }
-
- public void paintIcon(Component c, Graphics g, int x, int y)
- {
- Color saved = g.getColor();
- g.translate(x, y);
-
- Point ap = new Point(3, 7);
- Point bp = new Point(3, 21);
- Point cp = new Point(21, 21);
- Point dp = new Point(21, 12);
- Point ep = new Point(16, 12);
- Point fp = new Point(13, 7);
-
- Polygon dir = new Polygon(new int[] { ap.x, bp.x, cp.x, dp.x, ep.x, fp.x },
- new int[] { ap.y, bp.y, cp.y, dp.y, ep.y, fp.y },
- 6);
-
- g.setColor(new Color(153, 204, 255));
- g.fillPolygon(dir);
- g.setColor(Color.BLACK);
- g.drawPolygon(dir);
-
- g.translate(-x, -y);
- g.setColor(saved);
- }
- };
+ protected Icon directoryIcon;
/** The localised Mnemonic for the open button. */
protected int directoryOpenButtonMnemonic;
@@ -673,82 +578,13 @@ public class BasicFileChooserUI extends FileChooserUI
protected String directoryOpenButtonToolTipText;
/** An icon representing a file. */
- protected Icon fileIcon = new Icon()
- {
- public int getIconHeight()
- {
- return ICON_SIZE;
- }
-
- public int getIconWidth()
- {
- return ICON_SIZE;
- }
-
- public void paintIcon(Component c, Graphics g, int x, int y)
- {
- Color saved = g.getColor();
- g.translate(x, y);
-
- Point a = new Point(5, 4);
- Point b = new Point(5, 20);
- Point d = new Point(19, 20);
- Point e = new Point(19, 7);
- Point f = new Point(16, 4);
-
- Polygon p = new Polygon(new int[] { a.x, b.x, d.x, e.x, f.x, },
- new int[] { a.y, b.y, d.y, e.y, f.y }, 5);
-
- g.setColor(Color.WHITE);
- g.fillPolygon(p);
- g.setColor(Color.BLACK);
- g.drawPolygon(p);
-
- g.drawLine(16, 4, 14, 6);
- g.drawLine(14, 6, 19, 7);
-
- g.setColor(saved);
- g.translate(-x, -y);
- }
- };
+ protected Icon fileIcon;
/** An icon representing a floppy drive. */
- protected Icon floppyDriveIcon = new Icon()
- {
- public int getIconHeight()
- {
- return ICON_SIZE;
- }
-
- public int getIconWidth()
- {
- return ICON_SIZE;
- }
-
- public void paintIcon(Component c, Graphics g, int x, int y)
- {
- // FIXME: is this not implemented, or is the icon intentionally blank?
- }
- };
+ protected Icon floppyDriveIcon;
/** An icon representing a hard drive. */
- protected Icon hardDriveIcon = new Icon()
- {
- public int getIconHeight()
- {
- return ICON_SIZE;
- }
-
- public int getIconWidth()
- {
- return ICON_SIZE;
- }
-
- public void paintIcon(Component c, Graphics g, int x, int y)
- {
- // FIXME: is this not implemented, or is the icon intentionally blank?
- }
- };
+ protected Icon hardDriveIcon;
/** The localised mnemonic for the "help" button. */
protected int helpButtonMnemonic;
@@ -760,86 +596,10 @@ public class BasicFileChooserUI extends FileChooserUI
protected String helpButtonToolTipText;
/** An icon representing the user's home folder. */
- protected Icon homeFolderIcon = new Icon()
- {
- public int getIconHeight()
- {
- return ICON_SIZE;
- }
-
- public int getIconWidth()
- {
- return ICON_SIZE;
- }
-
- public void paintIcon(Component c, Graphics g, int x, int y)
- {
- Color saved = g.getColor();
- g.translate(x, y);
-
- Point a = new Point(12, 3);
- Point b = new Point(4, 10);
- Point d = new Point(20, 10);
-
- Polygon p = new Polygon(new int[] { a.x, b.x, d.x },
- new int[] { a.y, b.y, d.y }, 3);
-
- g.setColor(new Color(104, 51, 0));
- g.fillPolygon(p);
- g.setColor(Color.BLACK);
- g.drawPolygon(p);
-
- g.setColor(Color.WHITE);
- g.fillRect(8, 10, 8, 10);
- g.setColor(Color.BLACK);
- g.drawRect(8, 10, 8, 10);
-
- g.setColor(saved);
- g.translate(-x, -y);
- }
- };
+ protected Icon homeFolderIcon;
/** An icon for the "list view" button. */
- protected Icon listViewIcon = new Icon()
- {
- public int getIconHeight()
- {
- return ICON_SIZE;
- }
-
- public int getIconWidth()
- {
- return ICON_SIZE;
- }
-
- // Not needed. Only simplifies things until we get real icons.
- private void paintPartial(Graphics g, int x, int y)
- {
- Color saved = g.getColor();
- g.translate(x, y);
-
- g.setColor(Color.GRAY);
- g.drawRect(1, 1, 7, 10);
- g.drawLine(8, 6, 11, 6);
-
- g.setColor(saved);
- g.translate(-x, -y);
- }
-
- public void paintIcon(Component c, Graphics g, int x, int y)
- {
- Color saved = g.getColor();
- g.translate(x, y);
-
- paintPartial(g, 0, 0);
- paintPartial(g, 12, 0);
- paintPartial(g, 0, 12);
- paintPartial(g, 12, 12);
-
- g.setColor(saved);
- g.translate(-x, -y);
- }
- };
+ protected Icon listViewIcon;
/** An icon for the "new folder" button. */
protected Icon newFolderIcon = directoryIcon;
@@ -872,65 +632,13 @@ public class BasicFileChooserUI extends FileChooserUI
protected String updateButtonToolTipText;
/** An icon for the "up folder" button. */
- protected Icon upFolderIcon = new Icon()
- {
- public int getIconHeight()
- {
- return ICON_SIZE;
- }
-
- public int getIconWidth()
- {
- return ICON_SIZE;
- }
-
- public void paintIcon(Component comp, Graphics g, int x, int y)
- {
- Color saved = g.getColor();
- g.translate(x, y);
-
- Point a = new Point(3, 7);
- Point b = new Point(3, 21);
- Point c = new Point(21, 21);
- Point d = new Point(21, 12);
- Point e = new Point(16, 12);
- Point f = new Point(13, 7);
-
- Polygon dir = new Polygon(new int[] { a.x, b.x, c.x, d.x, e.x, f.x },
- new int[] { a.y, b.y, c.y, d.y, e.y, f.y }, 6);
-
- g.setColor(new Color(153, 204, 255));
- g.fillPolygon(dir);
- g.setColor(Color.BLACK);
- g.drawPolygon(dir);
-
- a = new Point(12, 15);
- b = new Point(9, 18);
- c = new Point(15, 18);
-
- Polygon arrow = new Polygon(new int[] { a.x, b.x, c.x },
- new int[] { a.y, b.y, c.y }, 3);
-
- g.fillPolygon(arrow);
-
- g.drawLine(12, 15, 12, 22);
-
- g.translate(-x, -y);
- g.setColor(saved);
- }
- };
+ protected Icon upFolderIcon;
// -- begin private, but package local since used in inner classes --
/** The file chooser component represented by this UI delegate. */
JFileChooser filechooser;
- /** The file list. */
- JList filelist;
-
- /** The combo box used to display/select file filters. */
- JComboBox filters;
-
/** The model for the directory list. */
BasicDirectoryModel model;
@@ -940,30 +648,9 @@ public class BasicFileChooserUI extends FileChooserUI
/** The default file view. */
FileView fv = new BasicFileView();
- /** The icon size. */
- static final int ICON_SIZE = 24;
-
- /** A combo box for display/selection of parent directories. */
- JComboBox parents;
-
- /** The current file name. */
- String filename;
-
/** The accept (open/save) button. */
JButton accept;
- /** The cancel button. */
- JButton cancel;
-
- /** The button to move up to the parent directory. */
- JButton upFolderButton;
-
- /** The button to create a new directory. */
- JButton newFolderButton;
-
- /** The button to move to the user's home directory. */
- JButton homeFolderButton;
-
/** An optional accessory panel. */
JPanel accessoryPanel;
@@ -998,6 +685,42 @@ public class BasicFileChooserUI extends FileChooserUI
/** Current parent path */
String parentPath;
+ /**
+ * The action for the 'approve' button.
+ * @see #getApproveSelectionAction()
+ */
+ private ApproveSelectionAction approveSelectionAction;
+
+ /**
+ * The action for the 'cancel' button.
+ * @see #getCancelSelectionAction()
+ */
+ private CancelSelectionAction cancelSelectionAction;
+
+ /**
+ * The action for the 'go home' control button.
+ * @see #getGoHomeAction()
+ */
+ private GoHomeAction goHomeAction;
+
+ /**
+ * The action for the 'up folder' control button.
+ * @see #getChangeToParentDirectoryAction()
+ */
+ private ChangeToParentDirectoryAction changeToParentDirectoryAction;
+
+ /**
+ * The action for the 'new folder' control button.
+ * @see #getNewFolderAction()
+ */
+ private NewFolderAction newFolderAction;
+
+ /**
+ * The action for ???. // FIXME: what is this?
+ * @see #getUpdateAction()
+ */
+ private UpdateAction updateAction;
+
// -- end private --
private class ListLabelRenderer extends JLabel implements ListCellRenderer
{
@@ -1057,7 +780,6 @@ public class BasicFileChooserUI extends FileChooserUI
*/
public BasicFileChooserUI(JFileChooser b)
{
- this.filechooser = b;
}
/**
@@ -1082,6 +804,7 @@ public class BasicFileChooserUI extends FileChooserUI
if (c instanceof JFileChooser)
{
JFileChooser fc = (JFileChooser) c;
+ this.filechooser = fc;
fc.resetChoosableFileFilters();
createModel();
clearIconCache();
@@ -1131,78 +854,7 @@ public class BasicFileChooserUI extends FileChooserUI
if (parentFiles.size() == 0)
return;
- if (parents.getItemCount() > 0)
- parents.removeAllItems();
- for (int i = parentFiles.size() - 1; i >= 0; i--)
- parents.addItem(parentFiles.get(i));
- parents.setSelectedIndex(parentFiles.size() - 1);
- parents.revalidate();
- parents.repaint();
- }
-
- /**
- * DOCUMENT ME!
- *
- * @return DOCUMENT ME!
- */
- private ItemListener createBoxListener()
- {
- return new ItemListener()
- {
- public void itemStateChanged(ItemEvent e)
- {
- if (parents.getItemCount() - 1 == parents.getSelectedIndex())
- return;
- StringBuffer dir = new StringBuffer();
- for (int i = 0; i <= parents.getSelectedIndex(); i++)
- {
- dir.append(parents.getItemAt(i));
- dir.append(File.separatorChar);
- }
- filechooser.setCurrentDirectory(filechooser.getFileSystemView()
- .createFileObject(dir
- .toString()));
- }
- };
- }
-
- /**
- * DOCUMENT ME!
- *
- * @return DOCUMENT ME!
- */
- private ItemListener createFilterListener()
- {
- return new ItemListener()
- {
- public void itemStateChanged(ItemEvent e)
- {
- int index = filters.getSelectedIndex();
- if (index == -1)
- return;
- filechooser.setFileFilter(filechooser.getChoosableFileFilters()[index]);
- }
- };
- }
-
- void filterEntries()
- {
- FileFilter[] list = filechooser.getChoosableFileFilters();
- if (filters.getItemCount() > 0)
- filters.removeAllItems();
-
- int index = -1;
- String selected = filechooser.getFileFilter().getDescription();
- for (int i = 0; i < list.length; i++)
- {
- if (selected.equals(list[i].getDescription()))
- index = i;
- filters.addItem(list[i].getDescription());
- }
- filters.setSelectedIndex(index);
- filters.revalidate();
- filters.repaint();
- }
+ }
/**
* Creates and install the subcomponents for the file chooser.
@@ -1211,121 +863,6 @@ public class BasicFileChooserUI extends FileChooserUI
*/
public void installComponents(JFileChooser fc)
{
- JLabel look = new JLabel("Look In:");
-
- parents = new JComboBox();
- parents.setRenderer(new BasicComboBoxRenderer());
- boxEntries();
- look.setLabelFor(parents);
- JPanel parentsPanel = new JPanel();
- parentsPanel.add(look);
- parentsPanel.add(parents);
- JPanel buttonPanel = new JPanel();
-
- upFolderButton = new JButton();
- upFolderButton.setIcon(upFolderIcon);
- buttonPanel.add(upFolderButton);
-
- homeFolderButton = new JButton();
- homeFolderButton = new JButton(homeFolderIcon);
- buttonPanel.add(homeFolderButton);
-
- newFolderButton = new JButton();
- newFolderButton.setIcon(newFolderIcon);
- buttonPanel.add(newFolderButton);
-
- ButtonGroup toggles = new ButtonGroup();
- JToggleButton listViewButton = new JToggleButton();
- listViewButton.setIcon(listViewIcon);
- toggles.add(listViewButton);
- buttonPanel.add(listViewButton);
-
- JToggleButton detailsViewButton = new JToggleButton();
- detailsViewButton.setIcon(detailsViewIcon);
- toggles.add(detailsViewButton);
- buttonPanel.add(detailsViewButton);
-
- JPanel topPanel = new JPanel();
- parentsPanel.add(buttonPanel);
- topPanel.setLayout(new java.awt.FlowLayout(java.awt.FlowLayout.LEFT, 0, 0));
- topPanel.add(parentsPanel);
-
- accessoryPanel = new JPanel();
- if (filechooser.getAccessory() != null)
- accessoryPanel.add(filechooser.getAccessory(), BorderLayout.CENTER);
-
- filelist = new JList(model);
- filelist.setVisibleRowCount(6);
- JScrollPane scrollp = new JScrollPane(filelist);
- scrollp.setPreferredSize(new Dimension(400, 175));
- filelist.setBackground(Color.WHITE);
-
- filelist.setLayoutOrientation(JList.VERTICAL_WRAP);
- filelist.setCellRenderer(new ListLabelRenderer());
-
- GridBagConstraints c = new GridBagConstraints();
- c.gridx = 0;
- c.gridy = 0;
- c.fill = GridBagConstraints.BOTH;
- c.weightx = 1;
- c.weighty = 1;
-
- JPanel centrePanel = new JPanel();
- centrePanel.setLayout(new GridBagLayout());
- centrePanel.add(scrollp, c);
-
- c.gridx = 1;
- centrePanel.add(accessoryPanel, c);
-
- JLabel fileNameLabel = new JLabel("File Name:");
- JLabel fileTypesLabel = new JLabel("Files of Type:");
-
- entry = new JTextField();
- filters = new JComboBox();
- filterEntries();
-
- fileNameLabel.setLabelFor(entry);
- fileNameLabel.setHorizontalTextPosition(SwingConstants.LEFT);
- fileTypesLabel.setLabelFor(filters);
- fileTypesLabel.setHorizontalTextPosition(SwingConstants.LEFT);
-
- closePanel = new JPanel();
- accept = getApproveButton(filechooser);
- cancel = new JButton(cancelButtonText);
- cancel.setMnemonic(cancelButtonMnemonic);
- cancel.setToolTipText(cancelButtonToolTipText);
- closePanel.add(accept);
- closePanel.add(cancel);
-
- c.anchor = GridBagConstraints.WEST;
- c.weighty = 0;
- c.weightx = 0;
- c.gridx = 0;
-
- bottomPanel = new JPanel();
- bottomPanel.setLayout(new GridBagLayout());
- bottomPanel.add(fileNameLabel, c);
-
- c.gridy = 1;
- bottomPanel.add(fileTypesLabel, c);
- c.gridx = 1;
- c.gridy = 0;
- c.weightx = 1;
- c.weighty = 1;
- bottomPanel.add(entry, c);
-
- c.gridy = 1;
- bottomPanel.add(filters, c);
-
- c.fill = GridBagConstraints.NONE;
- c.gridy = 2;
- c.anchor = GridBagConstraints.EAST;
- bottomPanel.add(closePanel, c);
-
- filechooser.setLayout(new BorderLayout());
- filechooser.add(topPanel, BorderLayout.NORTH);
- filechooser.add(centrePanel, BorderLayout.CENTER);
- filechooser.add(bottomPanel, BorderLayout.SOUTH);
}
/**
@@ -1335,15 +872,6 @@ public class BasicFileChooserUI extends FileChooserUI
*/
public void uninstallComponents(JFileChooser fc)
{
- parents = null;
-
- accept = null;
- cancel = null;
- upFolderButton = null;
- homeFolderButton = null;
- newFolderButton = null;
-
- filelist = null;
}
/**
@@ -1355,17 +883,6 @@ public class BasicFileChooserUI extends FileChooserUI
{
propertyChangeListener = createPropertyChangeListener(filechooser);
filechooser.addPropertyChangeListener(propertyChangeListener);
-
- //parents.addItemListener(createBoxListener());
- accept.addActionListener(getApproveSelectionAction());
- cancel.addActionListener(getCancelSelectionAction());
- upFolderButton.addActionListener(getChangeToParentDirectoryAction());
- homeFolderButton.addActionListener(getGoHomeAction());
- newFolderButton.addActionListener(getNewFolderAction());
- filters.addItemListener(createFilterListener());
-
- filelist.addMouseListener(createDoubleClickListener(filechooser, filelist));
- filelist.addListSelectionListener(createListSelectionListener(filechooser));
}
/**
@@ -1402,24 +919,42 @@ public class BasicFileChooserUI extends FileChooserUI
}
/**
- * Installs the icons for this UI delegate (NOT YET IMPLEMENTED).
+ * Installs the icons for this UI delegate.
*
- * @param fc the file chooser.
+ * @param fc the file chooser (ignored).
*/
protected void installIcons(JFileChooser fc)
{
- // FIXME: Implement.
+ UIDefaults defaults = UIManager.getLookAndFeelDefaults();
+ computerIcon = MetalIconFactory.getTreeComputerIcon();
+ detailsViewIcon = defaults.getIcon("FileChooser.detailsViewIcon");
+ directoryIcon = new MetalIconFactory.TreeFolderIcon();
+ fileIcon = new MetalIconFactory.TreeLeafIcon();
+ floppyDriveIcon = MetalIconFactory.getTreeFloppyDriveIcon();
+ hardDriveIcon = MetalIconFactory.getTreeHardDriveIcon();
+ homeFolderIcon = defaults.getIcon("FileChooser.homeFolderIcon");
+ listViewIcon = defaults.getIcon("FileChooser.listViewIcon");
+ newFolderIcon = defaults.getIcon("FileChooser.newFolderIcon");
+ upFolderIcon = defaults.getIcon("FileChooser.upFolderIcon");
}
/**
- * Uninstalls the icons previously added by this UI delegate (NOT YET
- * IMPLEMENTED).
+ * Uninstalls the icons previously added by this UI delegate.
*
* @param fc the file chooser.
*/
protected void uninstallIcons(JFileChooser fc)
{
- // FIXME: Implement.
+ computerIcon = null;
+ detailsViewIcon = null;
+ directoryIcon = null;
+ fileIcon = null;
+ floppyDriveIcon = null;
+ hardDriveIcon = null;
+ homeFolderIcon = null;
+ listViewIcon = null;
+ newFolderIcon = null;
+ upFolderIcon = null;
}
/**
@@ -1431,25 +966,34 @@ public class BasicFileChooserUI extends FileChooserUI
{
UIDefaults defaults = UIManager.getLookAndFeelDefaults();
- acceptAllFileFilterText = defaults.getString("FileChooser.acceptAllFileFilterText");
- cancelButtonMnemonic = defaults.getInt("FileChooser.cancelButtonMnemonic");
- cancelButtonText = defaults.getString("FileChooser.cancelButtonText");
- cancelButtonToolTipText = defaults.getString("FileChooser.cancelButtonToolTipText");
-
dirDescText = defaults.getString("FileChooser.directoryDescriptionText");
fileDescText = defaults.getString("FileChooser.fileDescriptionText");
+ acceptAllFileFilterText = defaults.getString("FileChooser.acceptAllFileFilterText");
+ cancelButtonText = "Cancel";
+ cancelButtonToolTipText = "Abort file chooser dialog";
+ cancelButtonMnemonic = defaults.getInt("FileChooser.cancelButtonMnemonic");
+
+ directoryOpenButtonText = "Open";
+ directoryOpenButtonToolTipText = "Open selected directory";
+ directoryOpenButtonMnemonic
+ = defaults.getInt("FileChooser.directoryOpenButtonMnemonic");
+
+ helpButtonText = "Help";
+ helpButtonToolTipText = "FileChooser help";
helpButtonMnemonic = defaults.getInt("FileChooser.helpButtonMnemonic");
- helpButtonText = defaults.getString("FileChooser.helpButtonText");
- helpButtonToolTipText = defaults.getString("FileChooser.helpButtonToolTipText");
+ openButtonText = "Open";
+ openButtonToolTipText = "Open selected file";
openButtonMnemonic = defaults.getInt("FileChooser.openButtonMnemonic");
- openButtonText = defaults.getString("FileChooser.openButtonText");
- openButtonToolTipText = defaults.getString("FileChooser.openButtonToolTipText");
- saveButtonMnemonic = defaults.getInt("FileChooser.saveButtonMnemonic");
- saveButtonText = defaults.getString("FileChooser.saveButtonText");
- saveButtonToolTipText = defaults.getString("FileChooser.saveButtonToolTipText");
+ saveButtonText = "Save";
+ saveButtonToolTipText = "Save selected file";
+ saveButtonMnemonic = UIManager.getInt("FileChooser.saveButtonMnemonic");
+
+ updateButtonText = "Update";
+ updateButtonToolTipText = "Update directory listing";
+ updateButtonMnemonic = defaults.getInt("FileChooser.updateButtonMnemonic");
}
/**
@@ -1460,24 +1004,26 @@ public class BasicFileChooserUI extends FileChooserUI
protected void uninstallStrings(JFileChooser fc)
{
acceptAllFileFilterText = null;
- cancelButtonMnemonic = 0;
+ dirDescText = null;
+ fileDescText = null;
+
cancelButtonText = null;
cancelButtonToolTipText = null;
- dirDescText = null;
- fileDescText = null;
+ directoryOpenButtonText = null;
+ directoryOpenButtonToolTipText = null;
- helpButtonMnemonic = 0;
helpButtonText = null;
helpButtonToolTipText = null;
- openButtonMnemonic = 0;
openButtonText = null;
openButtonToolTipText = null;
- saveButtonMnemonic = 0;
saveButtonText = null;
saveButtonToolTipText = null;
+
+ updateButtonText = null;
+ updateButtonToolTipText = null;
}
/**
@@ -1512,110 +1058,6 @@ public class BasicFileChooserUI extends FileChooserUI
{
public void propertyChange(PropertyChangeEvent e)
{
- // FIXME: Multiple file selection waiting on JList multiple selection
- // bug.
- if (e.getPropertyName().equals(
- JFileChooser.SELECTED_FILE_CHANGED_PROPERTY))
- {
- if (filechooser.getSelectedFile() == null)
- setFileName(null);
- else
- setFileName(filechooser.getSelectedFile().toString());
- int index = -1;
- File file = filechooser.getSelectedFile();
- for (index = 0; index < model.getSize(); index++)
- if (((File) model.getElementAt(index)).equals(file))
- break;
- if (index == -1)
- return;
- filelist.setSelectedIndex(index);
- filelist.ensureIndexIsVisible(index);
- filelist.revalidate();
- filelist.repaint();
- }
- else if (e.getPropertyName().equals(
- JFileChooser.DIRECTORY_CHANGED_PROPERTY))
- {
- filelist.clearSelection();
- filelist.revalidate();
- filelist.repaint();
- setDirectorySelected(false);
- setDirectory(filechooser.getCurrentDirectory());
- boxEntries();
- }
- else if (e.getPropertyName().equals(
- JFileChooser.CHOOSABLE_FILE_FILTER_CHANGED_PROPERTY)
- || e.getPropertyName().equals(
- JFileChooser.FILE_FILTER_CHANGED_PROPERTY))
- filterEntries();
- else if (e.getPropertyName().equals(
- JFileChooser.DIALOG_TYPE_CHANGED_PROPERTY)
- || e.getPropertyName().equals(
- JFileChooser.DIALOG_TITLE_CHANGED_PROPERTY))
- {
- Window owner = SwingUtilities.windowForComponent(filechooser);
- if (owner instanceof JDialog)
- ((JDialog) owner).setTitle(getDialogTitle(filechooser));
- accept.setText(getApproveButtonText(filechooser));
- accept.setToolTipText(getApproveButtonToolTipText(filechooser));
- accept.setMnemonic(getApproveButtonMnemonic(filechooser));
- }
- else if (e.getPropertyName().equals(
- JFileChooser.APPROVE_BUTTON_TEXT_CHANGED_PROPERTY))
- accept.setText(getApproveButtonText(filechooser));
- else if (e.getPropertyName().equals(
- JFileChooser.APPROVE_BUTTON_TOOL_TIP_TEXT_CHANGED_PROPERTY))
- accept.setToolTipText(getApproveButtonToolTipText(filechooser));
- else if (e.getPropertyName().equals(
- JFileChooser.APPROVE_BUTTON_MNEMONIC_CHANGED_PROPERTY))
- accept.setMnemonic(getApproveButtonMnemonic(filechooser));
- else if (e.getPropertyName().equals(
- JFileChooser.CONTROL_BUTTONS_ARE_SHOWN_CHANGED_PROPERTY))
- {
- if (filechooser.getControlButtonsAreShown())
- {
- GridBagConstraints c = new GridBagConstraints();
- c.gridy = 1;
- bottomPanel.add(filters, c);
-
- c.fill = GridBagConstraints.BOTH;
- c.gridy = 2;
- c.anchor = GridBagConstraints.EAST;
- bottomPanel.add(closePanel, c);
- bottomPanel.revalidate();
- bottomPanel.repaint();
- bottomPanel.doLayout();
- }
- else
- bottomPanel.remove(closePanel);
- }
- else if (e.getPropertyName().equals(
- JFileChooser.ACCEPT_ALL_FILE_FILTER_USED_CHANGED_PROPERTY))
- {
- if (filechooser.isAcceptAllFileFilterUsed())
- filechooser.addChoosableFileFilter(getAcceptAllFileFilter(filechooser));
- else
- filechooser.removeChoosableFileFilter(getAcceptAllFileFilter(filechooser));
- }
- else if (e.getPropertyName().equals(
- JFileChooser.ACCESSORY_CHANGED_PROPERTY))
- {
- JComponent old = (JComponent) e.getOldValue();
- if (old != null)
- getAccessoryPanel().remove(old);
- JComponent newval = (JComponent) e.getNewValue();
- if (newval != null)
- getAccessoryPanel().add(newval);
- }
- if (e.getPropertyName().equals(JFileChooser.DIRECTORY_CHANGED_PROPERTY)
- || e.getPropertyName().equals(
- JFileChooser.FILE_FILTER_CHANGED_PROPERTY)
- || e.getPropertyName().equals(
- JFileChooser.FILE_HIDING_CHANGED_PROPERTY))
- rescanCurrentDirectory(filechooser);
-
- filechooser.revalidate();
- filechooser.repaint();
}
};
}
@@ -1627,7 +1069,9 @@ public class BasicFileChooserUI extends FileChooserUI
*/
public String getFileName()
{
- return filename;
+ // FIXME: I'm thinking that this method just provides access to the
+ // text value in the JTextField component...but not sure yet
+ return null; //filename;
}
/**
@@ -1652,7 +1096,9 @@ public class BasicFileChooserUI extends FileChooserUI
*/
public void setFileName(String filename)
{
- this.filename = filename;
+ // FIXME: it might be the case that this method provides an access
+ // point for the JTextField (or whatever) a subclass is using...
+ //this.filename = filename;
}
/**
@@ -1675,7 +1121,6 @@ public class BasicFileChooserUI extends FileChooserUI
public void rescanCurrentDirectory(JFileChooser fc)
{
getModel().validateFileCache();
- filelist.revalidate();
}
/**
@@ -1711,17 +1156,14 @@ public class BasicFileChooserUI extends FileChooserUI
}
/**
- * Creates and returns an approve (open or save) button for the dialog.
+ * Returns the approve (open or save) button for the dialog.
*
* @param fc the file chooser.
*
* @return The button.
*/
- public JButton getApproveButton(JFileChooser fc)
+ protected JButton getApproveButton(JFileChooser fc)
{
- accept = new JButton(getApproveButtonText(fc));
- accept.setMnemonic(getApproveButtonMnemonic(fc));
- accept.setToolTipText(getApproveButtonToolTipText(fc));
return accept;
}
@@ -1833,9 +1275,8 @@ public class BasicFileChooserUI extends FileChooserUI
}
/**
- * Returns the file view for the file chooser. This returns either the
- * file view that has been explicitly set for the {@link JFileChooser}, or
- * a default file view.
+ * Returns the default file view (NOT the file view from the file chooser,
+ * if there is one).
*
* @param fc the file chooser component.
*
@@ -1859,24 +1300,10 @@ public class BasicFileChooserUI extends FileChooserUI
*/
public String getDialogTitle(JFileChooser fc)
{
- String ret = fc.getDialogTitle();
- if (ret != null)
- return ret;
- switch (fc.getDialogType())
- {
- case JFileChooser.OPEN_DIALOG:
- ret = openButtonText;
- break;
- case JFileChooser.SAVE_DIALOG:
- ret = saveButtonText;
- break;
- default:
- ret = fc.getApproveButtonText();
- break;
- }
- if (ret == null)
- ret = openButtonText;
- return ret;
+ String result = fc.getDialogTitle();
+ if (result == null)
+ result = getApproveButtonText(fc);
+ return result;
}
/**
@@ -1909,23 +1336,28 @@ public class BasicFileChooserUI extends FileChooserUI
*/
public String getApproveButtonText(JFileChooser fc)
{
- if (fc.getApproveButtonText() != null)
- return fc.getApproveButtonText();
- else if (fc.getDialogType() == JFileChooser.SAVE_DIALOG)
- return saveButtonText;
- else
- return openButtonText;
+ String result = fc.getApproveButtonText();
+ if (result == null)
+ {
+ if (fc.getDialogType() == JFileChooser.SAVE_DIALOG)
+ result = saveButtonText;
+ else
+ result = openButtonText;
+ }
+ return result;
}
/**
* Creates and returns a new action that will be used with the "new folder"
* button.
*
- * @return A new instance of {@link GoHomeAction}.
+ * @return A new instance of {@link NewFolderAction}.
*/
public Action getNewFolderAction()
{
- return new NewFolderAction();
+ if (newFolderAction == null)
+ newFolderAction = new NewFolderAction();
+ return newFolderAction;
}
/**
@@ -1936,49 +1368,56 @@ public class BasicFileChooserUI extends FileChooserUI
*/
public Action getGoHomeAction()
{
- return new GoHomeAction();
+ if (goHomeAction == null)
+ goHomeAction = new GoHomeAction();
+ return goHomeAction;
}
/**
- * Creates and returns a new action that will be used with the "up folder"
- * button.
+ * Returns the action that handles events for the "up folder" control button.
*
- * @return A new instance of {@link ChangeToParentDirectoryAction}.
+ * @return An instance of {@link ChangeToParentDirectoryAction}.
*/
public Action getChangeToParentDirectoryAction()
{
- return new ChangeToParentDirectoryAction();
+ if (changeToParentDirectoryAction == null)
+ changeToParentDirectoryAction = new ChangeToParentDirectoryAction();
+ return changeToParentDirectoryAction;
}
/**
- * Creates and returns a new action that will be used with the "approve"
- * button.
+ * Returns the action that handles events for the "approve" button.
*
- * @return A new instance of {@link ApproveSelectionAction}.
+ * @return An instance of {@link ApproveSelectionAction}.
*/
public Action getApproveSelectionAction()
{
- return new ApproveSelectionAction();
+ if (approveSelectionAction == null)
+ approveSelectionAction = new ApproveSelectionAction();
+ return approveSelectionAction;
}
/**
- * Creates and returns a new action that will be used with the "cancel"
- * button.
+ * Returns the action that handles events for the "cancel" button.
*
- * @return A new instance of {@link CancelSelectionAction}.
+ * @return An instance of {@link CancelSelectionAction}.
*/
public Action getCancelSelectionAction()
{
- return new CancelSelectionAction();
+ if (cancelSelectionAction == null)
+ cancelSelectionAction = new CancelSelectionAction();
+ return cancelSelectionAction;
}
/**
- * Creates and returns a new instance of {@link UpdateAction}.
+ * Returns the update action (an instance of {@link UpdateAction}).
*
* @return An action.
*/
public Action getUpdateAction()
{
- return new UpdateAction();
+ if (updateAction == null)
+ updateAction = new UpdateAction();
+ return updateAction;
}
}
diff --git a/javax/swing/plaf/basic/BasicInternalFrameTitlePane.java b/javax/swing/plaf/basic/BasicInternalFrameTitlePane.java
index aced2769a..56022f333 100644
--- a/javax/swing/plaf/basic/BasicInternalFrameTitlePane.java
+++ b/javax/swing/plaf/basic/BasicInternalFrameTitlePane.java
@@ -66,7 +66,6 @@ import javax.swing.JMenuBar;
import javax.swing.JMenuItem;
import javax.swing.SwingConstants;
import javax.swing.SwingUtilities;
-import javax.swing.UIDefaults;
import javax.swing.UIManager;
/**
@@ -718,13 +717,11 @@ public class BasicInternalFrameTitlePane extends JComponent
*/
protected void installDefaults()
{
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
-
- title.setFont(defaults.getFont("InternalFrame.titleFont"));
- selectedTextColor = defaults.getColor("InternalFrame.activeTitleForeground");
- selectedTitleColor = defaults.getColor("InternalFrame.activeTitleBackground");
- notSelectedTextColor = defaults.getColor("InternalFrame.inactiveTitleForeground");
- notSelectedTitleColor = defaults.getColor("InternalFrame.inactiveTitleBackground");
+ title.setFont(UIManager.getFont("InternalFrame.titleFont"));
+ selectedTextColor = UIManager.getColor("InternalFrame.activeTitleForeground");
+ selectedTitleColor = UIManager.getColor("InternalFrame.activeTitleBackground");
+ notSelectedTextColor = UIManager.getColor("InternalFrame.inactiveTitleForeground");
+ notSelectedTitleColor = UIManager.getColor("InternalFrame.inactiveTitleBackground");
closeIcon = UIManager.getIcon("InternalFrame.closeIcon");
iconIcon = UIManager.getIcon("InternalFrame.iconifyIcon");
@@ -771,11 +768,11 @@ public class BasicInternalFrameTitlePane extends JComponent
*/
protected void setButtonIcons()
{
- if (closeIcon != null)
+ if (closeIcon != null && closeButton != null)
closeButton.setIcon(closeIcon);
- if (iconIcon != null)
+ if (iconIcon != null && iconButton != null)
iconButton.setIcon(iconIcon);
- if (maxIcon != null)
+ if (maxIcon != null && maxButton != null)
maxButton.setIcon(maxIcon);
}
@@ -901,6 +898,9 @@ public class BasicInternalFrameTitlePane extends JComponent
*/
protected void paintTitleBackground(Graphics g)
{
+ if (!isOpaque())
+ return;
+
Color saved = g.getColor();
Dimension dims = getSize();
diff --git a/javax/swing/plaf/basic/BasicInternalFrameUI.java b/javax/swing/plaf/basic/BasicInternalFrameUI.java
index 6bc3aace3..f9653bd2e 100644
--- a/javax/swing/plaf/basic/BasicInternalFrameUI.java
+++ b/javax/swing/plaf/basic/BasicInternalFrameUI.java
@@ -46,6 +46,7 @@ import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Insets;
import java.awt.LayoutManager;
+import java.awt.LayoutManager2;
import java.awt.Point;
import java.awt.Rectangle;
import java.awt.event.ComponentEvent;
@@ -751,7 +752,7 @@ public class BasicInternalFrameUI extends InternalFrameUI
int y = me.getY();
// Find the candidate which should receive this event.
- Component parent = frame.getContentPane();
+ Component parent = frame.getLayeredPane();
if (parent == null)
return;
Component candidate = null;
@@ -1164,9 +1165,6 @@ public class BasicInternalFrameUI extends InternalFrameUI
{
frame = (JInternalFrame) c;
- internalFrameLayout = createLayoutManager();
- frame.setLayout(internalFrameLayout);
-
((JComponent) frame.getRootPane().getGlassPane()).setOpaque(false);
frame.getRootPane().getGlassPane().setVisible(true);
@@ -1192,7 +1190,6 @@ public class BasicInternalFrameUI extends InternalFrameUI
uninstallListeners();
uninstallDefaults();
- frame.setLayout(null);
((JComponent) frame.getRootPane().getGlassPane()).setOpaque(true);
frame.getRootPane().getGlassPane().setVisible(false);
@@ -1204,6 +1201,8 @@ public class BasicInternalFrameUI extends InternalFrameUI
*/
protected void installDefaults()
{
+ internalFrameLayout = createLayoutManager();
+ frame.setLayout(internalFrameLayout);
LookAndFeel.installBorder(frame, "InternalFrame.border");
frame.setFrameIcon(UIManager.getIcon("InternalFrame.icon"));
// InternalFrames are invisible by default.
@@ -1256,6 +1255,8 @@ public class BasicInternalFrameUI extends InternalFrameUI
protected void uninstallDefaults()
{
frame.setBorder(null);
+ frame.setLayout(null);
+ internalFrameLayout = null;
}
/**
@@ -1329,7 +1330,13 @@ public class BasicInternalFrameUI extends InternalFrameUI
*/
public Dimension getPreferredSize(JComponent x)
{
- return internalFrameLayout.preferredLayoutSize(x);
+ Dimension pref = null;
+ LayoutManager layout = frame.getLayout();
+ if (frame == x && layout != null)
+ pref = layout.preferredLayoutSize(frame);
+ else
+ pref = new Dimension(100, 100);
+ return pref;
}
/**
@@ -1341,7 +1348,13 @@ public class BasicInternalFrameUI extends InternalFrameUI
*/
public Dimension getMinimumSize(JComponent x)
{
- return internalFrameLayout.minimumLayoutSize(x);
+ Dimension min = null;
+ LayoutManager layout = frame.getLayout();
+ if (frame == x && layout != null)
+ min = layout.minimumLayoutSize(frame);
+ else
+ min = new Dimension(0, 0);
+ return min;
}
/**
@@ -1353,7 +1366,13 @@ public class BasicInternalFrameUI extends InternalFrameUI
*/
public Dimension getMaximumSize(JComponent x)
{
- return new Dimension(Integer.MAX_VALUE, Integer.MAX_VALUE);
+ Dimension max = null;
+ LayoutManager layout = frame.getLayout();
+ if (frame == x && layout != null && layout instanceof LayoutManager2)
+ max = ((LayoutManager2) layout).maximumLayoutSize(frame);
+ else
+ max = new Dimension(Integer.MAX_VALUE, Integer.MAX_VALUE);
+ return max;
}
/**
diff --git a/javax/swing/plaf/basic/BasicLabelUI.java b/javax/swing/plaf/basic/BasicLabelUI.java
index c8f677fa0..fd4cff568 100644
--- a/javax/swing/plaf/basic/BasicLabelUI.java
+++ b/javax/swing/plaf/basic/BasicLabelUI.java
@@ -39,7 +39,6 @@ package javax.swing.plaf.basic;
import java.awt.Color;
import java.awt.Dimension;
-import java.awt.Font;
import java.awt.FontMetrics;
import java.awt.Graphics;
import java.awt.Insets;
@@ -104,7 +103,7 @@ public class BasicLabelUI extends LabelUI implements PropertyChangeListener
Rectangle ir = new Rectangle();
Rectangle tr = new Rectangle();
Insets insets = lab.getInsets();
- FontMetrics fm = lab.getToolkit().getFontMetrics(lab.getFont());
+ FontMetrics fm = lab.getFontMetrics(lab.getFont());
layoutCL(lab, fm, lab.getText(), lab.getIcon(), vr, ir, tr);
Rectangle cr = tr.union(ir);
return new Dimension(insets.left + cr.width + insets.right, insets.top
@@ -150,17 +149,11 @@ public class BasicLabelUI extends LabelUI implements PropertyChangeListener
{
JLabel b = (JLabel) c;
- Font saved_font = g.getFont();
-
Rectangle tr = new Rectangle();
Rectangle ir = new Rectangle();
Rectangle vr = new Rectangle();
- Font f = c.getFont();
-
- g.setFont(f);
- FontMetrics fm = g.getFontMetrics(f);
-
+ FontMetrics fm = g.getFontMetrics();
vr = SwingUtilities.calculateInnerArea(c, vr);
if (vr.width < 0)
@@ -182,8 +175,6 @@ public class BasicLabelUI extends LabelUI implements PropertyChangeListener
else
paintDisabledText(b, g, text, tr.x, tr.y + fm.getAscent());
}
-
- g.setFont(saved_font);
}
/**
diff --git a/javax/swing/plaf/basic/BasicListUI.java b/javax/swing/plaf/basic/BasicListUI.java
index 1616d5e4f..7a6319274 100644
--- a/javax/swing/plaf/basic/BasicListUI.java
+++ b/javax/swing/plaf/basic/BasicListUI.java
@@ -38,7 +38,6 @@ exception statement from your version. */
package javax.swing.plaf.basic;
-import java.awt.Color;
import java.awt.Component;
import java.awt.Dimension;
import java.awt.Graphics;
@@ -51,7 +50,6 @@ import java.awt.event.ComponentEvent;
import java.awt.event.ComponentListener;
import java.awt.event.FocusEvent;
import java.awt.event.FocusListener;
-import java.awt.event.KeyEvent;
import java.awt.event.MouseEvent;
import java.beans.PropertyChangeEvent;
import java.beans.PropertyChangeListener;
@@ -76,6 +74,7 @@ import javax.swing.event.ListDataListener;
import javax.swing.event.ListSelectionEvent;
import javax.swing.event.ListSelectionListener;
import javax.swing.event.MouseInputListener;
+import javax.swing.plaf.ActionMapUIResource;
import javax.swing.plaf.ComponentUI;
import javax.swing.plaf.InputMapUIResource;
import javax.swing.plaf.ListUI;
@@ -191,7 +190,10 @@ public class BasicListUI extends ListUI
*/
public void valueChanged(ListSelectionEvent e)
{
- // TODO: Implement this properly.
+ int index1 = e.getFirstIndex();
+ int index2 = e.getLastIndex();
+ Rectangle damaged = getCellBounds(list, index1, index2);
+ list.repaint(damaged);
}
}
@@ -522,7 +524,14 @@ public class BasicListUI extends ListUI
*/
public void mouseDragged(MouseEvent event)
{
- // TODO: What should be done here, if anything?
+ Point click = event.getPoint();
+ int index = locationToIndex(list, click);
+ if (index == -1)
+ return;
+ if (!event.isShiftDown() && !event.isControlDown())
+ list.setSelectedIndex(index);
+
+ list.ensureIndexIsVisible(list.getLeadSelectionIndex());
}
/**
@@ -573,7 +582,6 @@ public class BasicListUI extends ListUI
updateLayoutStateNeeded += prototypeCellValueChanged;
else if (e.getPropertyName().equals("cellRenderer"))
updateLayoutStateNeeded += cellRendererChanged;
-
BasicListUI.this.damageLayout();
}
}
@@ -648,7 +656,11 @@ public class BasicListUI extends ListUI
/** Saved reference to the list this UI was created for. */
protected JList list;
- /** The height of a single cell in the list. */
+ /**
+ * The height of a single cell in the list. This field is used when the
+ * fixedCellHeight property of the list is set. Otherwise this field is
+ * set to <code>-1</code> and {@link #cellHeights} is used instead.
+ */
protected int cellHeight;
/** The width of a single cell in the list. */
@@ -656,7 +668,9 @@ public class BasicListUI extends ListUI
/**
* An array of varying heights of cells in the list, in cases where each
- * cell might have a different height.
+ * cell might have a different height. This field is used when the
+ * <code>fixedCellHeight</code> property of the list is not set. Otherwise
+ * this field is <code>null</code> and {@link #cellHeight} is used.
*/
protected int[] cellHeights;
@@ -696,12 +710,17 @@ public class BasicListUI extends ListUI
*/
protected int getRowHeight(int row)
{
- if (row < 0 || row >= cellHeights.length)
- return -1;
- else if (cellHeight != -1)
- return cellHeight;
+ int height;
+ if (cellHeights == null)
+ height = cellHeight;
else
- return cellHeights[row];
+ {
+ if (row < 0 || row >= cellHeights.length)
+ height = -1;
+ else
+ height = cellHeights[row];
+ }
+ return height;
}
/**
@@ -770,19 +789,49 @@ public class BasicListUI extends ListUI
* @param y0 The Y coordinate to calculate the row number for
*
* @return The row number containing the specified Y value, or <code>-1</code>
- * if the specified Y coordinate is invalid
+ * if the list model is empty
+ *
+ * @specnote This method is specified to return -1 for an invalid Y
+ * coordinate. However, some simple tests show that the behaviour
+ * is to return the index of the last list element for an Y
+ * coordinate that lies outside of the list bounds (even for
+ * negative indices). <code>-1</code>
+ * is only returned if the list model is empty.
*/
protected int convertYToRow(int y0)
{
- for (int row = 0; row < cellHeights.length; ++row)
- {
- int h = getRowHeight(row);
+ if (list.getModel().getSize() == 0)
+ return -1;
- if (y0 < h)
- return row;
- y0 -= h;
+ // When y0 < 0, then the JDK returns the maximum row index of the list. So
+ // do we.
+ if (y0 < 0)
+ return list.getModel().getSize() - 1;
+
+ // Update the layout if necessary.
+ maybeUpdateLayoutState();
+
+ int index = list.getModel().getSize() - 1;;
+
+ // If a fixed cell height is set, then we can work more efficient.
+ if (cellHeight > 0)
+ index = Math.min(y0 / cellHeight, index);
+ // If we have no fixed cell height, we must add up each cell height up
+ // to y0.
+ else
+ {
+ int h = 0;
+ for (int row = 0; row < cellHeights.length; ++row)
+ {
+ h += cellHeights[row];
+ if (y0 < h)
+ {
+ index = row;
+ break;
+ }
+ }
}
- return -1;
+ return index;
}
/**
@@ -797,29 +846,47 @@ public class BasicListUI extends ListUI
cellWidth = -1;
if (cellHeights == null || cellHeights.length != nrows)
cellHeights = new int[nrows];
- if (list.getFixedCellHeight() == -1 || list.getFixedCellWidth() == -1)
+ ListCellRenderer rend = list.getCellRenderer();
+ // Update the cellHeight(s) fields.
+ int fixedCellHeight = list.getFixedCellHeight();
+ if (fixedCellHeight > 0)
+ {
+ cellHeight = fixedCellHeight;
+ cellHeights = null;
+ }
+ else
{
- ListCellRenderer rend = list.getCellRenderer();
+ cellHeight = -1;
for (int i = 0; i < nrows; ++i)
{
- Component flyweight = rend.getListCellRendererComponent(list,
- list.getModel()
- .getElementAt(i),
- 0, false,
- false);
+ Component flyweight =
+ rend.getListCellRendererComponent(list,
+ list.getModel().getElementAt(i),
+ i, list.isSelectedIndex(i),
+ list.getSelectionModel().getAnchorSelectionIndex() == i);
Dimension dim = flyweight.getPreferredSize();
cellHeights[i] = dim.height;
- // compute average cell height (little hack here)
- cellHeight = (cellHeight * i + cellHeights[i]) / (i + 1);
- cellWidth = Math.max(cellWidth, dim.width);
- if (list.getLayoutOrientation() == JList.VERTICAL)
- cellWidth = Math.max(cellWidth, list.getSize().width);
}
}
+
+ // Update the cellWidth field.
+ int fixedCellWidth = list.getFixedCellWidth();
+ if (fixedCellWidth > 0)
+ cellWidth = fixedCellWidth;
else
{
- cellHeight = list.getFixedCellHeight();
- cellWidth = list.getFixedCellWidth();
+ for (int i = 0; i < nrows; ++i)
+ {
+ Component flyweight =
+ rend.getListCellRendererComponent(list,
+ list.getModel().getElementAt(i),
+ i, list.isSelectedIndex(i),
+ list.getSelectionModel().getAnchorSelectionIndex() == i);
+ Dimension dim = flyweight.getPreferredSize();
+ cellWidth = Math.max(cellWidth, dim.width);
+ }
+ if (list.getLayoutOrientation() == JList.VERTICAL)
+ cellWidth = Math.max(cellWidth, list.getSize().width);
}
}
@@ -878,7 +945,6 @@ public class BasicListUI extends ListUI
*/
protected void uninstallDefaults()
{
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
list.setForeground(null);
list.setBackground(null);
list.setSelectionForeground(null);
@@ -912,8 +978,8 @@ public class BasicListUI extends ListUI
// FIXME: Are these two really needed? At least they are not documented.
//keyListener = new KeyHandler();
- list.addComponentListener(componentListener);
componentListener = new ComponentHandler();
+ list.addComponentListener(componentListener);
//list.addKeyListener(keyListener);
}
@@ -936,11 +1002,10 @@ public class BasicListUI extends ListUI
*/
protected void installKeyboardActions()
{
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
- InputMap focusInputMap = (InputMap)defaults.get("List.focusInputMap");
+ InputMap focusInputMap = (InputMap) UIManager.get("List.focusInputMap");
InputMapUIResource parentInputMap = new InputMapUIResource();
// FIXME: The JDK uses a LazyActionMap for parentActionMap
- ActionMap parentActionMap = new ActionMap();
+ ActionMap parentActionMap = new ActionMapUIResource();
action = new ListAction();
Object keys[] = focusInputMap.allKeys();
// Register key bindings in the UI InputMap-ActionMap pair
@@ -1046,22 +1111,6 @@ public class BasicListUI extends ListUI
}
/**
- * Paints the packground of the list using the background color
- * of the specified component.
- *
- * @param g The graphics context to paint in
- * @param c The component to paint the background of
- */
- private void paintBackground(Graphics g, JComponent c)
- {
- Dimension size = getPreferredSize(c);
- Color save = g.getColor();
- g.setColor(c.getBackground());
- g.fillRect(0, 0, size.width, size.height);
- g.setColor(save);
- }
-
- /**
* Paints a single cell in the list.
*
* @param g The graphics context to paint in
@@ -1083,14 +1132,12 @@ public class BasicListUI extends ListUI
Component comp = rend.getListCellRendererComponent(list,
data.getElementAt(row),
0, isSel, hasFocus);
- //comp.setBounds(new Rectangle(0, 0, bounds.width, bounds.height));
- //comp.paint(g);
rendererPane.paintComponent(g, comp, list, bounds);
}
/**
- * Paints the list by calling {@link #paintBackground} and then repeatedly
- * calling {@link #paintCell} for each visible cell in the list.
+ * Paints the list by repeatedly calling {@link #paintCell} for each visible
+ * cell in the list.
*
* @param g The graphics context to paint with
* @param c Ignored; uses the saved {@link JList} reference
@@ -1107,9 +1154,12 @@ public class BasicListUI extends ListUI
ListSelectionModel sel = list.getSelectionModel();
int lead = sel.getLeadSelectionIndex();
Rectangle clip = g.getClipBounds();
- paintBackground(g, list);
- for (int row = 0; row < nrows; ++row)
+ int startIndex = list.locationToIndex(new Point(clip.x, clip.y));
+ int endIndex = list.locationToIndex(new Point(clip.x + clip.width,
+ clip.y + clip.height));
+
+ for (int row = startIndex; row <= endIndex; ++row)
{
Rectangle bounds = getCellBounds(list, row, row);
if (bounds.intersects(clip))
@@ -1118,13 +1168,15 @@ public class BasicListUI extends ListUI
}
/**
- * Computes the index of a list cell given a point within the list.
+ * Computes the index of a list cell given a point within the list. If the
+ * location lies outside the bounds of the list, the greatest index in the
+ * list model is returned.
*
* @param list the list which on which the computation is based on
* @param location the coordinates
*
* @return the index of the list item that is located at the given
- * coordinates or <code>null</code> if the location is invalid
+ * coordinates or <code>-1</code> if the list model is empty
*/
public int locationToIndex(JList list, Point location)
{
@@ -1174,7 +1226,6 @@ public class BasicListUI extends ListUI
int numberOfItems2 = list.getModel().getSize();
int cellsPerRow2 = numberOfItems2 / visibleRows2 + 1;
- Dimension listDim2 = list.getSize();
int gridX2 = Math.min(location.x / cellWidth, cellsPerRow2 - 1);
int gridY2 = Math.min(location.y / cellHeight, visibleRows2);
index = gridY2 + gridX2 * visibleRows2;
diff --git a/javax/swing/plaf/basic/BasicLookAndFeel.java b/javax/swing/plaf/basic/BasicLookAndFeel.java
index ab779945b..13c78add6 100644
--- a/javax/swing/plaf/basic/BasicLookAndFeel.java
+++ b/javax/swing/plaf/basic/BasicLookAndFeel.java
@@ -707,16 +707,17 @@ public abstract class BasicLookAndFeel extends LookAndFeel
"PopupMenu.border", new BorderUIResource.BevelBorderUIResource(0),
"PopupMenu.font", new FontUIResource("Dialog", Font.PLAIN, 12),
"PopupMenu.foreground", new ColorUIResource(darkShadow),
- "ProgressBar.background", new ColorUIResource(light),
- "ProgressBar.border", new BorderUIResource.LineBorderUIResource(Color.darkGray),
+ "ProgressBar.background", new ColorUIResource(Color.LIGHT_GRAY),
+ "ProgressBar.border",
+ new BorderUIResource.LineBorderUIResource(Color.GREEN, 2),
"ProgressBar.cellLength", new Integer(1),
"ProgressBar.cellSpacing", new Integer(0),
"ProgressBar.font", new FontUIResource("Dialog", Font.PLAIN, 12),
- "ProgressBar.foreground", new ColorUIResource(Color.black),
- "ProgressBar.selectionBackground", new ColorUIResource(Color.black),
- "ProgressBar.selectionForeground", new ColorUIResource(light),
- "ProgressBar.repaintInterval", new Integer(250),
- "ProgressBar.cycleTime", new Integer(6000),
+ "ProgressBar.foreground", new ColorUIResource(0, 0, 128),
+ "ProgressBar.selectionBackground", new ColorUIResource(0, 0, 128),
+ "ProgressBar.selectionForeground", new ColorUIResource(Color.LIGHT_GRAY),
+ "ProgressBar.repaintInterval", new Integer(50),
+ "ProgressBar.cycleTime", new Integer(3000),
"RadioButton.background", new ColorUIResource(light),
"RadioButton.border", new BorderUIResource.CompoundBorderUIResource(null,
null),
@@ -1158,7 +1159,7 @@ public abstract class BasicLookAndFeel extends LookAndFeel
"Tree.hash", new ColorUIResource(new Color(128, 128, 128)),
"Tree.leftChildIndent", new Integer(7),
"Tree.rightChildIndent", new Integer(13),
- "Tree.rowHeight", new Integer(16),
+ "Tree.rowHeight", new Integer(0),
"Tree.scrollsOnExpand", Boolean.TRUE,
"Tree.selectionBackground", new ColorUIResource(Color.black),
"Tree.nonSelectionBackground", new ColorUIResource(new Color(255, 255, 255)),
diff --git a/javax/swing/plaf/basic/BasicMenuItemUI.java b/javax/swing/plaf/basic/BasicMenuItemUI.java
index f8f577a76..c8754a3e0 100644
--- a/javax/swing/plaf/basic/BasicMenuItemUI.java
+++ b/javax/swing/plaf/basic/BasicMenuItemUI.java
@@ -46,14 +46,20 @@ import java.awt.FontMetrics;
import java.awt.Graphics;
import java.awt.Insets;
import java.awt.Rectangle;
-import java.awt.event.KeyEvent;
-import java.awt.event.MouseEvent;
+import java.awt.event.ActionEvent;
import java.awt.event.ItemEvent;
import java.awt.event.ItemListener;
+import java.awt.event.KeyEvent;
+import java.awt.event.MouseEvent;
+import java.beans.PropertyChangeEvent;
+import java.beans.PropertyChangeListener;
import java.util.ArrayList;
+import javax.swing.AbstractAction;
+import javax.swing.ActionMap;
import javax.swing.ButtonModel;
import javax.swing.Icon;
+import javax.swing.InputMap;
import javax.swing.JCheckBoxMenuItem;
import javax.swing.JComponent;
import javax.swing.JMenu;
@@ -72,6 +78,8 @@ import javax.swing.event.MenuDragMouseListener;
import javax.swing.event.MenuKeyEvent;
import javax.swing.event.MenuKeyListener;
import javax.swing.event.MouseInputListener;
+import javax.swing.plaf.ActionMapUIResource;
+import javax.swing.plaf.ComponentInputMapUIResource;
import javax.swing.plaf.ComponentUI;
import javax.swing.plaf.MenuItemUI;
@@ -169,9 +177,57 @@ public class BasicMenuItemUI extends MenuItemUI
private int defaultAcceleratorLabelGap = 10;
/**
- * Number of spaces between the text and the arrow icon.
+ * The gap between different menus on the MenuBar.
*/
- private int defaultTextArrowIconGap = 10;
+ private int MenuGap = 10;
+
+ /** A PropertyChangeListener to make UI updates after property changes **/
+ PropertyChangeHandler propertyChangeListener;
+
+ /**
+ * A class to handle PropertChangeEvents for the JMenuItem
+ * @author Anthony Balkissoon abalkiss at redhat dot com.
+ */
+ class PropertyChangeHandler implements PropertyChangeListener
+ {
+ /**
+ * This method is called when a property of the menuItem is changed.
+ * Currently it is only used to update the accelerator key bindings.
+ *
+ * @param e
+ * the PropertyChangeEvent
+ */
+ public void propertyChange(PropertyChangeEvent e)
+ {
+ if (e.getPropertyName() == "accelerator")
+ {
+ InputMap map = SwingUtilities.getUIInputMap(menuItem, JComponent.WHEN_IN_FOCUSED_WINDOW);
+ if (map != null)
+ map.remove((KeyStroke)e.getOldValue());
+ else
+ map = new ComponentInputMapUIResource(menuItem);
+ map.put((KeyStroke)e.getNewValue(), "doClick");
+ }
+ }
+ }
+
+ /**
+ * A class to handle accelerator keys. This is the Action we will
+ * perform when the accelerator key for this JMenuItem is pressed.
+ * @author Anthony Balkissoon abalkiss at redhat dot com
+ *
+ */
+ class ClickAction extends AbstractAction
+ {
+ /**
+ * This is what is done when the accelerator key for the JMenuItem is
+ * pressed.
+ */
+ public void actionPerformed(ActionEvent event)
+ {
+ doClick(MenuSelectionManager.defaultManager());
+ }
+ }
/**
* Creates a new BasicMenuItemUI object.
@@ -182,6 +238,7 @@ public class BasicMenuItemUI extends MenuItemUI
menuDragMouseListener = createMenuDragMouseListener(menuItem);
menuKeyListener = createMenuKeyListener(menuItem);
itemListener = new ItemHandler();
+ propertyChangeListener = new PropertyChangeHandler();
}
/**
@@ -320,7 +377,7 @@ public class BasicMenuItemUI extends MenuItemUI
JMenuItem m = (JMenuItem) c;
Dimension d = BasicGraphicsUtils.getPreferredButtonSize(m,
defaultTextIconGap);
-
+
// if menu item has accelerator then take accelerator's size into account
// when calculating preferred size.
KeyStroke accelerator = m.getAccelerator();
@@ -342,7 +399,7 @@ public class BasicMenuItemUI extends MenuItemUI
if (checkIcon != null)
{
- d.width = d.width + checkIcon.getIconWidth() + defaultTextIconGap;
+ d.width += checkIcon.getIconWidth() + defaultTextIconGap;
if (checkIcon.getIconHeight() > d.height)
d.height = checkIcon.getIconHeight();
@@ -350,12 +407,17 @@ public class BasicMenuItemUI extends MenuItemUI
if (arrowIcon != null && (c instanceof JMenu))
{
- d.width = d.width + arrowIcon.getIconWidth() + defaultTextArrowIconGap;
-
+ int pWidth = m.getParent().getWidth();
+ if (!((JMenu)c).isTopLevelMenu() && d.width < pWidth)
+ d.width = pWidth
+ - m.getInsets().left - m.getInsets().right;
+ else
+ d.width += arrowIcon.getIconWidth() + MenuGap;
+
if (arrowIcon.getIconHeight() > d.height)
d.height = arrowIcon.getIconHeight();
}
-
+
return d;
}
@@ -413,7 +475,6 @@ public class BasicMenuItemUI extends MenuItemUI
menuItem.setHorizontalTextPosition(SwingConstants.TRAILING);
menuItem.setHorizontalAlignment(SwingConstants.LEADING);
- menuItem.setOpaque(true);
}
/**
@@ -421,7 +482,17 @@ public class BasicMenuItemUI extends MenuItemUI
*/
protected void installKeyboardActions()
{
- // FIXME: Need to implement
+ InputMap focusedWindowMap = SwingUtilities.getUIInputMap(menuItem, JComponent.WHEN_IN_FOCUSED_WINDOW);
+ if (focusedWindowMap == null)
+ focusedWindowMap = new ComponentInputMapUIResource(menuItem);
+ focusedWindowMap.put(menuItem.getAccelerator(), "doClick");
+ SwingUtilities.replaceUIInputMap(menuItem, JComponent.WHEN_IN_FOCUSED_WINDOW, focusedWindowMap);
+
+ ActionMap UIActionMap = SwingUtilities.getUIActionMap(menuItem);
+ if (UIActionMap == null)
+ UIActionMap = new ActionMapUIResource();
+ UIActionMap.put("doClick", new ClickAction());
+ SwingUtilities.replaceUIActionMap(menuItem, UIActionMap);
}
/**
@@ -434,6 +505,7 @@ public class BasicMenuItemUI extends MenuItemUI
menuItem.addMenuDragMouseListener(menuDragMouseListener);
menuItem.addMenuKeyListener(menuKeyListener);
menuItem.addItemListener(itemListener);
+ menuItem.addPropertyChangeListener(propertyChangeListener);
}
/**
@@ -451,6 +523,7 @@ public class BasicMenuItemUI extends MenuItemUI
installDefaults();
installComponents(menuItem);
installListeners();
+ installKeyboardActions();
}
/**
@@ -479,11 +552,20 @@ public class BasicMenuItemUI extends MenuItemUI
*/
protected void paintBackground(Graphics g, JMenuItem menuItem, Color bgColor)
{
- Dimension size = getPreferredSize(menuItem);
- Color foreground = g.getColor();
- g.setColor(bgColor);
- g.drawRect(0, 0, size.width, size.height);
- g.setColor(foreground);
+ // Menu item is considered to be highlighted when it is selected.
+ // But we don't want to paint the background of JCheckBoxMenuItems
+ ButtonModel mod = menuItem.getModel();
+ if ((menuItem.isSelected() && checkIcon == null) || (mod != null &&
+ mod.isArmed())
+ && (menuItem.getParent() instanceof MenuElement))
+ {
+ if (menuItem.isContentAreaFilled())
+ {
+ g.setColor(selectionBackground);
+ g.fillRect(0, 0, menuItem.getWidth(), menuItem.getHeight());
+ }
+ }
+
}
/**
@@ -520,7 +602,7 @@ public class BasicMenuItemUI extends MenuItemUI
int horAlign = m.getHorizontalAlignment();
int vertTextPos = m.getVerticalTextPosition();
int horTextPos = m.getHorizontalTextPosition();
-
+
Font f = m.getFont();
g.setFont(f);
FontMetrics fm = g.getFontMetrics(f);
@@ -538,28 +620,6 @@ public class BasicMenuItemUI extends MenuItemUI
br.width += insets.right + insets.left;
br.height += insets.top + insets.bottom;
- // Menu item is considered to be highlighted when it is selected.
- // But we don't want to paint the background of JCheckBoxMenuItems
- ButtonModel mod = m.getModel();
- if ((m.isSelected() && checkIcon == null) || (mod != null &&
- mod.isArmed())
- && (m.getParent() instanceof MenuElement))
- {
- if (m.isContentAreaFilled())
- {
- g.setColor(selectionBackground);
- g.fillRect(br.x, br.y, br.width, br.height);
- }
- }
- else
- {
- if (m.isContentAreaFilled())
- {
- g.setColor(m.getBackground());
- g.fillRect(br.x, br.y, br.width, br.height);
- }
- }
-
// If this menu item is a JCheckBoxMenuItem then paint check icon
if (checkIcon != null)
{
@@ -709,8 +769,9 @@ public class BasicMenuItemUI extends MenuItemUI
* Uninstalls any keyboard actions.
*/
protected void uninstallKeyboardActions()
- {
- // FIXME: need to implement
+ {
+ SwingUtilities.replaceUIInputMap(menuItem,
+ JComponent.WHEN_IN_FOCUSED_WINDOW, null);
}
/**
@@ -722,6 +783,7 @@ public class BasicMenuItemUI extends MenuItemUI
menuItem.removeMenuDragMouseListener(menuDragMouseListener);
menuItem.removeMenuKeyListener(menuKeyListener);
menuItem.removeItemListener(itemListener);
+ menuItem.removePropertyChangeListener(propertyChangeListener);
}
/**
diff --git a/javax/swing/plaf/basic/BasicMenuUI.java b/javax/swing/plaf/basic/BasicMenuUI.java
index 827cbb0f5..e638b68e1 100644
--- a/javax/swing/plaf/basic/BasicMenuUI.java
+++ b/javax/swing/plaf/basic/BasicMenuUI.java
@@ -211,7 +211,6 @@ public class BasicMenuUI extends BasicMenuItemUI
selectionForeground = UIManager.getColor("Menu.selectionForeground");
arrowIcon = UIManager.getIcon("Menu.arrowIcon");
oldBorderPainted = UIManager.getBoolean("Menu.borderPainted");
- menuItem.setOpaque(true);
}
/**
diff --git a/javax/swing/plaf/basic/BasicOptionPaneUI.java b/javax/swing/plaf/basic/BasicOptionPaneUI.java
index 6b37d315f..005a3b394 100644
--- a/javax/swing/plaf/basic/BasicOptionPaneUI.java
+++ b/javax/swing/plaf/basic/BasicOptionPaneUI.java
@@ -774,7 +774,7 @@ public class BasicOptionPaneUI extends OptionPaneUI
// it will create a box and burst the string.
// otherwise, it will just create a label and re-call
// this method with the label o.O
- if (msg.toString().length() > maxll)
+ if (msg.toString().length() > maxll || msg.toString().contains("\n"))
{
Box tmp = new Box(BoxLayout.Y_AXIS);
burstStringInto(tmp, msg.toString(), maxll);
@@ -796,17 +796,35 @@ public class BasicOptionPaneUI extends OptionPaneUI
*/
protected void burstStringInto(Container c, String d, int maxll)
{
- // FIXME: Verify that this is the correct behaviour.
- // One interpretation of the spec is that this method
- // should recursively call itself to create (and add)
- // JLabels to the container if the length of the String d
- // is greater than maxll.
- // but in practice, even with a really long string, this is
- // all that happens.
if (d == null || c == null)
return;
- JLabel label = new JLabel(d);
+
+ int newlineIndex = d.indexOf('\n');
+ String line;
+ String remainder;
+ if (newlineIndex >= 0 && newlineIndex < maxll)
+ {
+ line = d.substring(0, newlineIndex);
+ remainder = d.substring(newlineIndex + 1);
+ }
+ else
+ {
+ line = d.substring(0, maxll);
+ remainder = d.substring(maxll);
+ }
+ JLabel label = new JLabel(line);
c.add(label);
+
+ // If there is nothing left to burst, then we can stop.
+ if (remainder.length() == 0)
+ return;
+
+ // Recursivly call ourselves to burst the remainder of the string,
+ if ((remainder.length() > maxll || remainder.contains("\n")))
+ burstStringInto(c, remainder, maxll);
+ else
+ // Add the remainder to the container and be done.
+ c.add(new JLabel(remainder));
}
/**
diff --git a/javax/swing/plaf/basic/BasicPopupMenuUI.java b/javax/swing/plaf/basic/BasicPopupMenuUI.java
index 46bcd3679..e15a17bab 100644
--- a/javax/swing/plaf/basic/BasicPopupMenuUI.java
+++ b/javax/swing/plaf/basic/BasicPopupMenuUI.java
@@ -273,23 +273,26 @@ public class BasicPopupMenuUI extends PopupMenuUI
RootPaneContainer rootContainer = (RootPaneContainer) SwingUtilities
.getRoot(invoker);
- ((Container) rootContainer).removeComponentListener(topWindowListener);
-
- // If this popup menu is the last popup menu visible on the screen, then
- // stop interrupting mouse events in the glass pane before hiding this
- // last popup menu.
- boolean topLevelMenu = (popupMenu.getInvoker() instanceof JMenu)
- && ((JMenu) popupMenu.getInvoker())
- .isTopLevelMenu();
-
- if (topLevelMenu || ! (popupMenu.getInvoker() instanceof MenuElement))
+ if (rootContainer != null)
{
- // set glass pane not to interrupt mouse events and remove
- // mouseInputListener
- Container glassPane = (Container) rootContainer.getGlassPane();
- glassPane.setVisible(false);
- glassPane.removeMouseListener(mouseInputListener);
- mouseInputListener = null;
+ ((Container) rootContainer).removeComponentListener(topWindowListener);
+
+ // If this popup menu is the last popup menu visible on the screen,
+ // then
+ // stop interrupting mouse events in the glass pane before hiding this
+ // last popup menu.
+ boolean topLevelMenu = (popupMenu.getInvoker() instanceof JMenu)
+ && ((JMenu) popupMenu.getInvoker()).isTopLevelMenu();
+
+ if (topLevelMenu || !(popupMenu.getInvoker() instanceof MenuElement))
+ {
+ // set glass pane not to interrupt mouse events and remove
+ // mouseInputListener
+ Container glassPane = (Container) rootContainer.getGlassPane();
+ glassPane.setVisible(false);
+ glassPane.removeMouseListener(mouseInputListener);
+ mouseInputListener = null;
+ }
}
}
diff --git a/javax/swing/plaf/basic/BasicProgressBarUI.java b/javax/swing/plaf/basic/BasicProgressBarUI.java
index 744ddf712..d3674664d 100644
--- a/javax/swing/plaf/basic/BasicProgressBarUI.java
+++ b/javax/swing/plaf/basic/BasicProgressBarUI.java
@@ -46,11 +46,12 @@ import java.awt.Graphics;
import java.awt.Insets;
import java.awt.Point;
import java.awt.Rectangle;
+import java.awt.Shape;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
-import java.awt.font.FontRenderContext;
-import java.awt.geom.AffineTransform;
-import java.awt.geom.Rectangle2D;
+import java.awt.event.ComponentAdapter;
+import java.awt.event.ComponentEvent;
+import java.awt.event.ComponentListener;
import java.beans.PropertyChangeEvent;
import java.beans.PropertyChangeListener;
@@ -61,6 +62,8 @@ import javax.swing.SwingConstants;
import javax.swing.SwingUtilities;
import javax.swing.Timer;
import javax.swing.UIManager;
+import javax.swing.event.AncestorEvent;
+import javax.swing.event.AncestorListener;
import javax.swing.event.ChangeEvent;
import javax.swing.event.ChangeListener;
import javax.swing.plaf.ComponentUI;
@@ -110,14 +113,56 @@ public class BasicProgressBarUI extends ProgressBarUI
{
// Only need to listen for indeterminate changes.
// All other things are done on a repaint.
- if (e.getPropertyName().equals("inderterminate"))
- if (((Boolean) e.getNewValue()).booleanValue())
- startAnimationTimer();
- else
- stopAnimationTimer();
- else
- progressBar.repaint();
+ if (e.getPropertyName().equals("indeterminate"))
+ if (((Boolean) e.getNewValue()).booleanValue()
+ && progressBar.isShowing())
+ startAnimationTimer();
+ else
+ stopAnimationTimer();
+ }
+ }
+
+ /**
+ * Receives notification when the progressbar is becoming visible or
+ * invisible and starts/stops the animation timer accordingly.
+ *
+ * @author Roman Kennke (kennke@aicas.com)
+ */
+ private class AncestorHandler implements AncestorListener
+ {
+
+ /**
+ * Receives notification when the progressbar is becoming visible. This
+ * starts the animation timer if the progressbar is indeterminate.
+ *
+ * @param event the ancestor event
+ */
+ public void ancestorAdded(AncestorEvent event)
+ {
+ if (progressBar.isIndeterminate())
+ startAnimationTimer();
+ }
+
+ /**
+ * Receives notification when the progressbar is becoming invisible. This
+ * stops the animation timer if the progressbar is indeterminate.
+ *
+ * @param event the ancestor event
+ */
+ public void ancestorRemoved(AncestorEvent event)
+ {
+ stopAnimationTimer();
+ }
+
+ /**
+ * Receives notification when an ancestor has been moved. We don't need to
+ * do anything here.
+ */
+ public void ancestorMoved(AncestorEvent event)
+ {
+ // Nothing to do here.
}
+
}
/**
@@ -141,6 +186,37 @@ public class BasicProgressBarUI extends ProgressBarUI
}
}
+ /**
+ * Receives notification when the size of the progress bar changes and
+ * invalidates the layout information for the box calculation in
+ * {@link BasicProgressBarUI#getBox(Rectangle)}.
+ *
+ * @author Roman Kennke (kennke@aicas.com)
+ */
+ private class ComponentHandler extends ComponentAdapter
+ {
+ /**
+ * Receives notification when the size of the progress bar changes and
+ * invalidates the layout information for the box calculation in
+ * {@link BasicProgressBarUI#getBox}.
+ *
+ * @param e the component event
+ */
+ public void componentResized(ComponentEvent e)
+ {
+ boxDependent = -1;
+ boxIndependent = -1;
+ incr = -1;
+ }
+ }
+
+ /**
+ * Holds the value of the bouncing box that is returned by {@link #getBox}.
+ *
+ * @since 1.5
+ */
+ protected Rectangle boxRect;
+
/** The timer used to move the bouncing box. */
private transient Timer animationTimer;
@@ -172,6 +248,27 @@ public class BasicProgressBarUI extends ProgressBarUI
/** The progressBar for this UI. */
protected JProgressBar progressBar;
+
+ /**
+ * The size of the box returned by {@link #getBox} in the orientation
+ * direction of the progress bar. This is package private to avoid accessor
+ * method.
+ */
+ transient double boxDependent = - 1;
+
+ /**
+ * The size of the box returned by {@link #getBox} against the orientation
+ * direction of the progress bar. This is package private to avoid accessor
+ * method.
+ */
+ transient int boxIndependent = - 1;
+
+ /**
+ * The increment for box animation. This is package private to avoid accessor
+ * method.
+ */
+ transient double incr = -1;
+
/** The length of the cell. The cell is the painted part. */
private transient int cellLength;
@@ -185,6 +282,18 @@ public class BasicProgressBarUI extends ProgressBarUI
private transient Color selectionForeground;
/**
+ * Listens for notification when the component becomes showing and
+ * starts/stops the animation timer.
+ */
+ private AncestorListener ancestorListener;
+
+ /**
+ * Listens for resize events on the progress bar and invalidates some
+ * layout info.
+ */
+ private ComponentListener componentListener;
+
+ /**
* Creates a new BasicProgressBarUI object.
*/
public BasicProgressBarUI()
@@ -248,48 +357,49 @@ public class BasicProgressBarUI extends ProgressBarUI
{
if (!progressBar.isIndeterminate())
return null;
- //numFrames has to be an even number as defined by spec.
- int iterations = numFrames / 2 + 1;
+ if (r == null)
+ r = new Rectangle();
- double boxDependent;
- double boxIndependent;
+ Rectangle vr = new Rectangle();
+ SwingUtilities.calculateInnerArea(progressBar, vr);
- if (progressBar.getOrientation() == JProgressBar.HORIZONTAL)
- {
- Dimension dims = getPreferredInnerHorizontal();
- boxDependent = (double) dims.width / iterations;
- boxIndependent = dims.height;
- }
- else
+ // Recalculate the metrics only when size of the progressbar has changed.
+ if (incr == -1 || boxDependent == -1 || boxIndependent == -1)
{
- Dimension dims = getPreferredInnerVertical();
- boxDependent = (double) dims.height / iterations;
- boxIndependent = dims.width;
+ //numFrames has to be an even number as defined by spec.
+ int iterations = numFrames / 2;
+ if (progressBar.getOrientation() == JProgressBar.HORIZONTAL)
+ {
+ boxDependent = vr.width / 6.;
+ incr = ((double) (vr.width - boxDependent)) / (double) iterations;
+ boxIndependent = vr.height;
+ }
+ else
+ {
+ boxDependent = vr.height / 6.;
+ incr = ((double) (vr.height - boxDependent)) / (double) iterations;
+ boxIndependent = vr.width;
+ }
}
- Rectangle vr = new Rectangle();
- SwingUtilities.calculateInnerArea(progressBar, vr);
-
int index = getAnimationIndex();
- if (animationIndex > (numFrames + 1) / 2)
+ if (animationIndex > (numFrames) / 2)
index = numFrames - getAnimationIndex();
if (progressBar.getOrientation() == JProgressBar.HORIZONTAL)
{
- r.x = vr.x + (int) (index * boxDependent);
- r.y = vr.y;
- r.width = (int) boxDependent;
- r.height = (int) boxIndependent;
+ r.x = vr.x + (int) (incr * index);
+ r.y = vr.y;
+ r.width = (int) boxDependent;
+ r.height = (int) boxIndependent;
}
else
{
- index++;
- r.x = vr.x;
- r.y = vr.height - (int) (index * boxDependent) + vr.y;
- r.width = (int) boxIndependent;
- r.height = (int) boxDependent;
+ r.x = vr.x;
+ r.y = vr.height - (int) (incr * index) + vr.y - (int) boxDependent;
+ r.width = (int) boxIndependent;
+ r.height = (int) boxDependent;
}
-
return r;
}
@@ -324,7 +434,22 @@ public class BasicProgressBarUI extends ProgressBarUI
*/
public Dimension getMaximumSize(JComponent c)
{
- return getPreferredSize(c);
+ Insets insets = c.getInsets();
+ Dimension ret;
+ int orientation = progressBar.getOrientation();
+ if (orientation == JProgressBar.VERTICAL)
+ {
+ ret = getPreferredInnerVertical();
+ ret.height = Short.MAX_VALUE;
+ ret.width += insets.left + insets.right;
+ }
+ else
+ {
+ ret = getPreferredInnerHorizontal();
+ ret.width = Short.MAX_VALUE;
+ ret.height += insets.top + insets.bottom;
+ }
+ return ret;
}
/**
@@ -338,7 +463,22 @@ public class BasicProgressBarUI extends ProgressBarUI
*/
public Dimension getMinimumSize(JComponent c)
{
- return getPreferredSize(c);
+ Insets insets = c.getInsets();
+ Dimension ret;
+ int orientation = progressBar.getOrientation();
+ if (orientation == JProgressBar.VERTICAL)
+ {
+ ret = getPreferredInnerVertical();
+ ret.height = 10;
+ ret.width += insets.left + insets.right;
+ }
+ else
+ {
+ ret = getPreferredInnerHorizontal();
+ ret.width = 10;
+ ret.height += insets.top + insets.bottom;
+ }
+ return ret;
}
/**
@@ -351,11 +491,22 @@ public class BasicProgressBarUI extends ProgressBarUI
*/
protected Dimension getPreferredInnerHorizontal()
{
- Rectangle vr = new Rectangle();
+ Font font = progressBar.getFont();
+ FontMetrics fm = progressBar.getFontMetrics(font);
- SwingUtilities.calculateInnerArea(progressBar, vr);
+ int stringWidth = 0;
+ String str = progressBar.getString();
+ if (str != null)
+ stringWidth = fm.stringWidth(progressBar.getString());
+ Insets i = progressBar.getInsets();
+ int prefWidth = Math.max(200 - i.left - i.right, stringWidth);
+
+ int stringHeight = 0;
+ if (str != null)
+ stringHeight = fm.getHeight();
+ int prefHeight = Math.max(16 - i.top - i.bottom, stringHeight);
- return new Dimension(vr.width, vr.height);
+ return new Dimension(prefWidth, prefHeight);
}
/**
@@ -368,11 +519,22 @@ public class BasicProgressBarUI extends ProgressBarUI
*/
protected Dimension getPreferredInnerVertical()
{
- Rectangle vr = new Rectangle();
+ Font font = progressBar.getFont();
+ FontMetrics fm = progressBar.getFontMetrics(font);
- SwingUtilities.calculateInnerArea(progressBar, vr);
+ int stringWidth = 0;
+ String str = progressBar.getString();
+ if (str != null)
+ stringWidth = fm.stringWidth(progressBar.getString());
+ Insets i = progressBar.getInsets();
+ int prefHeight = Math.max(200 - i.left - i.right, stringWidth);
- return new Dimension(vr.width, vr.height);
+ int stringHeight = 0;
+ if (str != null)
+ stringHeight = fm.getHeight();
+ int prefWidth = Math.max(16 - i.top - i.bottom, stringHeight);
+
+ return new Dimension(prefWidth, prefHeight);
}
/**
@@ -386,36 +548,16 @@ public class BasicProgressBarUI extends ProgressBarUI
*/
public Dimension getPreferredSize(JComponent c)
{
- // The only thing we need to worry about is
- // the text size.
Insets insets = c.getInsets();
-
- // make a fontrenderer context so that we can make assumptions about
- // the string bounds
- FontRenderContext ctx = new FontRenderContext(new AffineTransform(),
- false, false);
- Rectangle2D bounds = c.getFont().getStringBounds(progressBar.getString(),
- ctx);
- int textW = (int) bounds.getWidth();
- int textH = (int) bounds.getHeight();
-
- if (progressBar.getOrientation() == JProgressBar.HORIZONTAL)
- {
- if (textH < 20)
- textH = 20;
- if (textW < 200)
- textW = 200;
- }
+ Dimension ret;
+ int orientation = progressBar.getOrientation();
+ if (orientation == JProgressBar.VERTICAL)
+ ret = getPreferredInnerVertical();
else
- {
- if (textH < 200)
- textH = 200;
- if (textW < 20)
- textW = 20;
- }
- textW += insets.left + insets.right;
- textH += insets.top + insets.bottom;
- return new Dimension(textW, textH);
+ ret = getPreferredInnerHorizontal();
+ ret.width += insets.left + insets.right;
+ ret.height += insets.top + insets.bottom;
+ return ret;
}
/**
@@ -514,66 +656,22 @@ public class BasicProgressBarUI extends ProgressBarUI
int min = progressBar.getMinimum();
int value = progressBar.getValue();
- Rectangle vr = new Rectangle();
- SwingUtilities.calculateInnerArea(c, vr);
-
- Rectangle or = c.getBounds();
-
+ Rectangle vr = SwingUtilities.calculateInnerArea(c, new Rectangle());
+ Rectangle or = progressBar.getBounds();
Insets insets = c.getInsets();
int amountFull = getAmountFull(insets, or.width, or.height);
- g.setColor(c.getBackground());
- g.fill3DRect(vr.x, vr.y, vr.width, vr.height, false);
-
- if (max != min && len != 0 && value > min)
- {
- int iterations = value / (space + len);
-
if (progressBar.getOrientation() == JProgressBar.HORIZONTAL)
{
- double spaceInUnits = space * (double) vr.width / (max - min);
- double lenInUnits = len * (double) vr.width / (max - min);
- double currX = vr.x;
-
g.setColor(c.getForeground());
- g.fill3DRect(vr.x, vr.y, amountFull, vr.height, true);
-
- g.setColor(c.getBackground());
- if (spaceInUnits != 0)
- {
- for (int i = 0; i < iterations; i++)
- {
- currX += lenInUnits;
- g.fill3DRect((int) currX, vr.y, (int) spaceInUnits,
- vr.height, true);
- currX += spaceInUnits;
- }
- }
+ g.fillRect(vr.x, vr.y, amountFull, vr.height);
}
else
{
- double currY = vr.y;
- double spaceInUnits = space * (double) vr.height / (max - min);
- double lenInUnits = len * (double) vr.height / (max - min);
-
g.setColor(c.getForeground());
- g.fill3DRect(vr.x, vr.y + vr.height - amountFull, vr.width,
- amountFull, true);
-
- g.setColor(c.getBackground());
-
- if (spaceInUnits != 0)
- {
- for (int i = 0; i < iterations; i++)
- {
- currY -= lenInUnits + spaceInUnits;
- g.fill3DRect(vr.x, (int) currY, vr.width,
- (int) spaceInUnits, true);
- }
- }
+ g.fillRect(vr.x, vr.y + vr.height - amountFull, vr.width, amountFull);
}
- }
if (progressBar.isStringPainted() && !progressBar.getString().equals(""))
paintString(g, 0, 0, or.width, or.height, amountFull, insets);
@@ -599,13 +697,12 @@ public class BasicProgressBarUI extends ProgressBarUI
SwingUtilities.calculateInnerArea(c, vr);
g.setColor(c.getBackground());
- g.fill3DRect(vr.x, vr.y, vr.width, vr.height, false);
+ g.fillRect(vr.x, vr.y, vr.width, vr.height);
- Rectangle box = new Rectangle();
- getBox(box);
+ boxRect = getBox(boxRect);
g.setColor(c.getForeground());
- g.fill3DRect(box.x, box.y, box.width, box.height, true);
+ g.fillRect(boxRect.x, boxRect.y, boxRect.width, boxRect.height);
if (progressBar.isStringPainted() && !progressBar.getString().equals(""))
paintString(g, 0, 0, or.width, or.height,
@@ -628,23 +725,34 @@ public class BasicProgressBarUI extends ProgressBarUI
protected void paintString(Graphics g, int x, int y, int width, int height,
int amountFull, Insets b)
{
+ // FIXME: We do not support vertical text painting because Java2D is needed
+ // for this.
+ if (progressBar.getOrientation() == JProgressBar.VERTICAL)
+ return;
+
// We want to place in the exact center of the bar.
Point placement = getStringPlacement(g, progressBar.getString(),
x + b.left, y + b.top,
width - b.left - b.right,
height - b.top - b.bottom);
- Color saved = g.getColor();
-
- // FIXME: The Color of the text should use selectionForeground and selectionBackground
- // but that can't be done right now, so we'll use white in the mean time.
- g.setColor(Color.WHITE);
+ Color savedColor = g.getColor();
+ Shape savedClip = g.getClip();
FontMetrics fm = g.getFontMetrics(progressBar.getFont());
+ int full = getAmountFull(b, width, height);
+ String str = progressBar.getString();
- g.drawString(progressBar.getString(), placement.x,
- placement.y + fm.getAscent());
-
- g.setColor(saved);
+ // We draw this string two times with different clips so that the text
+ // over the filled area is painted with selectionForeground and over
+ // the clear area with selectionBackground.
+ g.setColor(getSelectionForeground());
+ g.setClip(0, 0, full + b.left, height);
+ g.drawString(str, placement.x, placement.y + fm.getAscent());
+ g.setColor(getSelectionBackground());
+ g.setClip(full + b.left, 0, width - full, height);
+ g.drawString(str, placement.x, placement.y + fm.getAscent());
+ g.setClip(savedClip);
+ g.setColor(savedColor);
}
/**
@@ -766,6 +874,12 @@ public class BasicProgressBarUI extends ProgressBarUI
progressBar.addChangeListener(changeListener);
progressBar.addPropertyChangeListener(propertyListener);
animationTimer.addActionListener(animation);
+
+ ancestorListener = new AncestorHandler();
+ progressBar.addAncestorListener(ancestorListener);
+
+ componentListener = new ComponentHandler();
+ progressBar.addComponentListener(componentListener);
}
/**
@@ -781,6 +895,14 @@ public class BasicProgressBarUI extends ProgressBarUI
changeListener = null;
propertyListener = null;
animation = null;
+
+ if (ancestorListener != null)
+ progressBar.removeAncestorListener(ancestorListener);
+ ancestorListener = null;
+
+ if (componentListener != null)
+ progressBar.removeComponentListener(componentListener);
+ componentListener = null;
}
/**
@@ -804,6 +926,8 @@ public class BasicProgressBarUI extends ProgressBarUI
installDefaults();
installListeners();
}
+ if (progressBar.isIndeterminate())
+ startAnimationTimer();
}
/**
@@ -822,4 +946,5 @@ public class BasicProgressBarUI extends ProgressBarUI
animationTimer = null;
progressBar = null;
}
+
}
diff --git a/javax/swing/plaf/basic/BasicRadioButtonUI.java b/javax/swing/plaf/basic/BasicRadioButtonUI.java
index f3698e859..66e538037 100644
--- a/javax/swing/plaf/basic/BasicRadioButtonUI.java
+++ b/javax/swing/plaf/basic/BasicRadioButtonUI.java
@@ -48,7 +48,6 @@ import javax.swing.AbstractButton;
import javax.swing.Icon;
import javax.swing.JComponent;
import javax.swing.SwingUtilities;
-import javax.swing.UIDefaults;
import javax.swing.UIManager;
import javax.swing.plaf.ComponentUI;
@@ -122,8 +121,7 @@ public class BasicRadioButtonUI extends BasicToggleButtonUI
*/
public Icon getDefaultIcon()
{
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
- return defaults.getIcon(getPropertyPrefix() + "icon");
+ return UIManager.getIcon(getPropertyPrefix() + "icon");
}
/**
diff --git a/javax/swing/plaf/basic/BasicScrollBarUI.java b/javax/swing/plaf/basic/BasicScrollBarUI.java
index 2f5eaf391..a2f5b82db 100644
--- a/javax/swing/plaf/basic/BasicScrollBarUI.java
+++ b/javax/swing/plaf/basic/BasicScrollBarUI.java
@@ -62,7 +62,6 @@ import javax.swing.LookAndFeel;
import javax.swing.SwingConstants;
import javax.swing.SwingUtilities;
import javax.swing.Timer;
-import javax.swing.UIDefaults;
import javax.swing.UIManager;
import javax.swing.event.ChangeEvent;
import javax.swing.event.ChangeListener;
@@ -501,14 +500,12 @@ public class BasicScrollBarUI extends ScrollBarUI implements LayoutManager,
*/
protected void configureScrollBarColors()
{
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
-
- trackColor = defaults.getColor("ScrollBar.track");
- trackHighlightColor = defaults.getColor("ScrollBar.trackHighlight");
- thumbColor = defaults.getColor("ScrollBar.thumb");
- thumbHighlightColor = defaults.getColor("ScrollBar.thumbHighlight");
- thumbDarkShadowColor = defaults.getColor("ScrollBar.thumbDarkShadow");
- thumbLightShadowColor = defaults.getColor("ScrollBar.thumbShadow");
+ trackColor = UIManager.getColor("ScrollBar.track");
+ trackHighlightColor = UIManager.getColor("ScrollBar.trackHighlight");
+ thumbColor = UIManager.getColor("ScrollBar.thumb");
+ thumbHighlightColor = UIManager.getColor("ScrollBar.thumbHighlight");
+ thumbDarkShadowColor = UIManager.getColor("ScrollBar.thumbDarkShadow");
+ thumbLightShadowColor = UIManager.getColor("ScrollBar.thumbShadow");
}
/**
@@ -660,11 +657,7 @@ public class BasicScrollBarUI extends ScrollBarUI implements LayoutManager,
width += decrButton.getPreferredSize().getWidth();
width += (scrollbar.getMaximum() - scrollbar.getMinimum());
-
- height = Math.max(incrButton.getPreferredSize().height,
- decrButton.getPreferredSize().height);
- height = Math.max(getMinimumThumbSize().height, height);
- height = Math.min(getMaximumThumbSize().height, height);
+ height = UIManager.getInt("ScrollBar.width");
}
else
{
@@ -672,11 +665,7 @@ public class BasicScrollBarUI extends ScrollBarUI implements LayoutManager,
height += decrButton.getPreferredSize().getHeight();
height += (scrollbar.getMaximum() - scrollbar.getMinimum());
-
- width = Math.max(incrButton.getPreferredSize().width,
- decrButton.getPreferredSize().width);
- width = Math.max(getMinimumThumbSize().width, width);
- width = Math.min(getMaximumThumbSize().width, width);
+ width = UIManager.getInt("ScrollBar.width");
}
Insets insets = scrollbar.getInsets();
diff --git a/javax/swing/plaf/basic/BasicSplitPaneDivider.java b/javax/swing/plaf/basic/BasicSplitPaneDivider.java
index 69ed2be7c..a6369c2e3 100644
--- a/javax/swing/plaf/basic/BasicSplitPaneDivider.java
+++ b/javax/swing/plaf/basic/BasicSplitPaneDivider.java
@@ -45,6 +45,7 @@ import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Insets;
import java.awt.LayoutManager;
+import java.awt.Point;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.event.MouseMotionListener;
@@ -376,6 +377,11 @@ public class BasicSplitPaneDivider extends Container
dividerSize = getSize();
border.paintBorder(this, g, 0, 0, dividerSize.width, dividerSize.height);
}
+ if (splitPane.isOneTouchExpandable())
+ {
+ ((BasicArrowButton) rightButton).paint(g);
+ ((BasicArrowButton) leftButton).paint(g);
+ }
}
/**
diff --git a/javax/swing/plaf/basic/BasicSplitPaneUI.java b/javax/swing/plaf/basic/BasicSplitPaneUI.java
index f9b558eab..cf31e8b5d 100644
--- a/javax/swing/plaf/basic/BasicSplitPaneUI.java
+++ b/javax/swing/plaf/basic/BasicSplitPaneUI.java
@@ -126,14 +126,14 @@ public class BasicSplitPaneUI extends SplitPaneUI
{
int i = 0;
if (place == null)
- i = 2;
+ i = 2;
else if (place.equals(JSplitPane.TOP) || place.equals(JSplitPane.LEFT))
- i = 0;
+ i = 0;
else if (place.equals(JSplitPane.BOTTOM)
|| place.equals(JSplitPane.RIGHT))
- i = 1;
+ i = 1;
else
- throw new IllegalArgumentException("Illegal placement in JSplitPane");
+ throw new IllegalArgumentException("Illegal placement in JSplitPane");
components[i] = component;
resetSizeAt(i);
splitPane.revalidate();
@@ -164,7 +164,7 @@ public class BasicSplitPaneUI extends SplitPaneUI
protected int getInitialLocation(Insets insets)
{
if (insets != null)
- return insets.left;
+ return insets.left;
return 0;
}
@@ -205,7 +205,7 @@ public class BasicSplitPaneUI extends SplitPaneUI
{
Dimension dims = c.getPreferredSize();
if (dims != null)
- return dims.width;
+ return dims.width;
return 0;
}
@@ -250,23 +250,23 @@ public class BasicSplitPaneUI extends SplitPaneUI
{
if (container instanceof JSplitPane)
{
- JSplitPane split = (JSplitPane) container;
- distributeExtraSpace();
- Insets insets = split.getInsets();
- int width = getInitialLocation(insets);
- Dimension dims = split.getSize();
- for (int i = 0; i < components.length; i += 2)
- {
- if (components[i] == null)
- continue;
- setComponentToSize(components[i], sizes[i], width, insets, dims);
- width += sizes[i];
- }
- if (components[1] != null)
- {
- setComponentToSize(components[1], sizes[1], width, insets, dims);
- width += sizes[1];
- }
+ JSplitPane split = (JSplitPane) container;
+ distributeExtraSpace();
+ Insets insets = split.getInsets();
+ int width = getInitialLocation(insets);
+ Dimension dims = split.getSize();
+ for (int i = 0; i < components.length; i += 2)
+ {
+ if (components[i] == null)
+ continue;
+ setComponentToSize(components[i], sizes[i], width, insets, dims);
+ width += sizes[i];
+ }
+ if (components[1] != null)
+ {
+ setComponentToSize(components[1], sizes[1], width, insets, dims);
+ width += sizes[1];
+ }
}
}
@@ -297,23 +297,23 @@ public class BasicSplitPaneUI extends SplitPaneUI
{
if (target instanceof JSplitPane)
{
- JSplitPane split = (JSplitPane) target;
- Insets insets = target.getInsets();
-
- int height = 0;
- int width = 0;
- for (int i = 0; i < components.length; i++)
- {
- if (components[i] == null)
- continue;
- Dimension dims = components[i].getMinimumSize();
- if (dims != null)
- {
- width += dims.width;
- height = Math.max(height, dims.height);
- }
- }
- return new Dimension(width, height);
+ JSplitPane split = (JSplitPane) target;
+ Insets insets = target.getInsets();
+
+ int height = 0;
+ int width = 0;
+ for (int i = 0; i < components.length; i++)
+ {
+ if (components[i] == null)
+ continue;
+ Dimension dims = components[i].getMinimumSize();
+ if (dims != null)
+ {
+ width += dims.width;
+ height = Math.max(height, dims.height);
+ }
+ }
+ return new Dimension(width, height);
}
return null;
}
@@ -331,24 +331,24 @@ public class BasicSplitPaneUI extends SplitPaneUI
{
if (target instanceof JSplitPane)
{
- JSplitPane split = (JSplitPane) target;
- Insets insets = target.getInsets();
-
- int height = 0;
- int width = 0;
- for (int i = 0; i < components.length; i++)
- {
- if (components[i] == null)
- continue;
- Dimension dims = components[i].getPreferredSize();
- if (dims != null)
- {
- width += dims.width;
- if (! (components[i] instanceof BasicSplitPaneDivider))
- height = Math.max(height, dims.height);
- }
- }
- return new Dimension(width, height);
+ JSplitPane split = (JSplitPane) target;
+ Insets insets = target.getInsets();
+
+ int height = 0;
+ int width = 0;
+ for (int i = 0; i < components.length; i++)
+ {
+ if (components[i] == null)
+ continue;
+ Dimension dims = components[i].getPreferredSize();
+ if (dims != null)
+ {
+ width += dims.width;
+ if (!(components[i] instanceof BasicSplitPaneDivider))
+ height = Math.max(height, dims.height);
+ }
+ }
+ return new Dimension(width, height);
}
return null;
}
@@ -362,11 +362,11 @@ public class BasicSplitPaneUI extends SplitPaneUI
{
for (int i = 0; i < components.length; i++)
{
- if (component == components[i])
- {
- components[i] = null;
- sizes[i] = 0;
- }
+ if (component == components[i])
+ {
+ components[i] = null;
+ sizes[i] = 0;
+ }
}
}
@@ -378,7 +378,7 @@ public class BasicSplitPaneUI extends SplitPaneUI
protected void resetSizeAt(int index)
{
if (components[index] != null)
- sizes[index] = getPreferredSizeOfComponent(components[index]);
+ sizes[index] = getPreferredSizeOfComponent(components[index]);
}
/**
@@ -387,7 +387,7 @@ public class BasicSplitPaneUI extends SplitPaneUI
public void resetToPreferredSizes()
{
for (int i = 0; i < components.length; i++)
- resetSizeAt(i);
+ resetSizeAt(i);
}
/**
@@ -433,13 +433,13 @@ public class BasicSplitPaneUI extends SplitPaneUI
if (left != null)
{
- components[0] = left;
- resetSizeAt(0);
+ components[0] = left;
+ resetSizeAt(0);
}
if (right != null)
{
- components[1] = right;
- resetSizeAt(1);
+ components[1] = right;
+ resetSizeAt(1);
}
components[2] = divider;
resetSizeAt(2);
@@ -480,9 +480,9 @@ public class BasicSplitPaneUI extends SplitPaneUI
{
Dimension dims = components[index].getMinimumSize();
if (dims != null)
- return dims.width;
+ return dims.width;
else
- return 0;
+ return 0;
}
} //end BasicHorizontalLayoutManager
@@ -534,7 +534,7 @@ public class BasicSplitPaneUI extends SplitPaneUI
{
Dimension dims = c.getPreferredSize();
if (dims != null)
- return dims.height;
+ return dims.height;
return 0;
}
@@ -563,23 +563,23 @@ public class BasicSplitPaneUI extends SplitPaneUI
{
if (container instanceof JSplitPane)
{
- JSplitPane split = (JSplitPane) container;
- Insets insets = container.getInsets();
-
- int height = 0;
- int width = 0;
- for (int i = 0; i < components.length; i++)
- {
- if (components[i] == null)
- continue;
- Dimension dims = components[i].getMinimumSize();
- if (dims != null)
- {
- height += dims.height;
- width = Math.max(width, dims.width);
- }
- }
- return new Dimension(width, height);
+ JSplitPane split = (JSplitPane) container;
+ Insets insets = container.getInsets();
+
+ int height = 0;
+ int width = 0;
+ for (int i = 0; i < components.length; i++)
+ {
+ if (components[i] == null)
+ continue;
+ Dimension dims = components[i].getMinimumSize();
+ if (dims != null)
+ {
+ height += dims.height;
+ width = Math.max(width, dims.width);
+ }
+ }
+ return new Dimension(width, height);
}
return null;
}
@@ -597,23 +597,23 @@ public class BasicSplitPaneUI extends SplitPaneUI
{
if (container instanceof JSplitPane)
{
- JSplitPane split = (JSplitPane) container;
- Insets insets = container.getInsets();
-
- int height = 0;
- int width = 0;
- for (int i = 0; i < components.length; i++)
- {
- if (components[i] == null)
- continue;
- Dimension dims = components[i].getPreferredSize();
- if (dims != null)
- {
- height += dims.height;
- width = Math.max(width, dims.width);
- }
- }
- return new Dimension(width, height);
+ JSplitPane split = (JSplitPane) container;
+ Insets insets = container.getInsets();
+
+ int height = 0;
+ int width = 0;
+ for (int i = 0; i < components.length; i++)
+ {
+ if (components[i] == null)
+ continue;
+ Dimension dims = components[i].getPreferredSize();
+ if (dims != null)
+ {
+ height += dims.height;
+ width = Math.max(width, dims.width);
+ }
+ }
+ return new Dimension(width, height);
}
return null;
}
@@ -652,9 +652,9 @@ public class BasicSplitPaneUI extends SplitPaneUI
{
Dimension dims = components[index].getMinimumSize();
if (dims != null)
- return dims.height;
+ return dims.height;
else
- return 0;
+ return 0;
}
}
@@ -813,27 +813,27 @@ public class BasicSplitPaneUI extends SplitPaneUI
{
if (e.getPropertyName().equals(JSplitPane.DIVIDER_SIZE_PROPERTY))
{
- int newSize = splitPane.getDividerSize();
- int[] tmpSizes = layoutManager.getSizes();
- dividerSize = tmpSizes[2];
- int newSpace = newSize - tmpSizes[2];
- tmpSizes[2] = newSize;
-
- tmpSizes[0] += newSpace / 2;
- tmpSizes[1] += newSpace / 2;
+ int newSize = splitPane.getDividerSize();
+ int[] tmpSizes = layoutManager.getSizes();
+ dividerSize = tmpSizes[2];
+ int newSpace = newSize - tmpSizes[2];
+ tmpSizes[2] = newSize;
+
+ tmpSizes[0] += newSpace / 2;
+ tmpSizes[1] += newSpace / 2;
- layoutManager.setSizes(tmpSizes);
+ layoutManager.setSizes(tmpSizes);
}
else if (e.getPropertyName().equals(JSplitPane.ORIENTATION_PROPERTY))
{
- int max = layoutManager.getAvailableSize(splitPane.getSize(),
- splitPane.getInsets());
- int dividerLoc = getDividerLocation(splitPane);
- double prop = ((double) dividerLoc) / max;
-
- resetLayoutManager();
- if (prop <= 1 && prop >= 0)
- splitPane.setDividerLocation(prop);
+ int max = layoutManager.getAvailableSize(splitPane.getSize(),
+ splitPane.getInsets());
+ int dividerLoc = getDividerLocation(splitPane);
+ double prop = ((double) dividerLoc) / max;
+
+ resetLayoutManager();
+ if (prop <= 1 && prop >= 0)
+ splitPane.setDividerLocation(prop);
}
layoutManager.layoutContainer(splitPane);
splitPane.repaint();
@@ -843,13 +843,13 @@ public class BasicSplitPaneUI extends SplitPaneUI
// Don't have to deal with resize_weight (as there
// will be no extra space associated with this
// event - the changes to the weighting will
- // be taken into account the next time the
+ // be taken into account the next time the
// sizes change.)
- // Don't have to deal with divider_location
+ // Don't have to deal with divider_location
// The method in JSplitPane calls our setDividerLocation
// so we'll know about those anyway.
// Don't have to deal with last_divider_location
- // Although I'm not sure why, it doesn't seem to
+ // Although I'm not sure why, it doesn't seem to
// have any effect on Sun's JSplitPane.
// one_touch_expandable changes are dealt with
// by our divider.
@@ -962,10 +962,10 @@ public class BasicSplitPaneUI extends SplitPaneUI
{
if (c instanceof JSplitPane)
{
- splitPane = (JSplitPane) c;
- installDefaults();
- installListeners();
- installKeyboardActions();
+ splitPane = (JSplitPane) c;
+ installDefaults();
+ installListeners();
+ installKeyboardActions();
}
}
@@ -1218,8 +1218,8 @@ public class BasicSplitPaneUI extends SplitPaneUI
{
if (nonContinuousLayoutDivider == null)
{
- nonContinuousLayoutDivider = new Canvas();
- nonContinuousLayoutDivider.setBackground(Color.DARK_GRAY);
+ nonContinuousLayoutDivider = new Canvas();
+ nonContinuousLayoutDivider.setBackground(Color.DARK_GRAY);
}
return nonContinuousLayoutDivider;
}
@@ -1300,12 +1300,14 @@ public class BasicSplitPaneUI extends SplitPaneUI
{
location = validLocation(location);
Container p = jc.getParent();
- Dimension rightPrefSize = jc.getRightComponent().getPreferredSize();
+ Component right = jc.getRightComponent();
+ Dimension rightPrefSize = right == null ? new Dimension(0, 0)
+ : right.getPreferredSize();
Dimension size = jc.getSize();
// check if the size has been set for the splitpane
if (size.width == 0 && size.height == 0)
size = jc.getPreferredSize();
-
+
if (getOrientation() == 0 && location > size.height)
{
location = size.height;
@@ -1324,11 +1326,11 @@ public class BasicSplitPaneUI extends SplitPaneUI
p = p.getParent();
}
}
-
+
setLastDragLocation(getDividerLocation(splitPane));
splitPane.setLastDividerLocation(getDividerLocation(splitPane));
int[] tmpSizes = layoutManager.getSizes();
- tmpSizes[0] = location
+ tmpSizes[0] = location
- layoutManager.getInitialLocation(splitPane.getInsets());
tmpSizes[1] = layoutManager.getAvailableSize(splitPane.getSize(),
splitPane.getInsets())
@@ -1361,11 +1363,9 @@ public class BasicSplitPaneUI extends SplitPaneUI
*/
public int getMinimumDividerLocation(JSplitPane jc)
{
- int value = layoutManager.getInitialLocation(jc.getInsets())
- - layoutManager.getAvailableSize(jc.getSize(), jc.getInsets())
- + splitPane.getDividerSize();
- if (layoutManager.components[1] != null)
- value += layoutManager.minimumSizeOfComponent(1);
+ int value = layoutManager.getInitialLocation(jc.getInsets());
+ if (layoutManager.components[0] != null)
+ value -= layoutManager.minimumSizeOfComponent(0);
return value;
}
@@ -1485,19 +1485,21 @@ public class BasicSplitPaneUI extends SplitPaneUI
*/
protected void startDragging()
{
+ Component left = splitPane.getLeftComponent();
+ Component right = splitPane.getRightComponent();
dividerSize = divider.getDividerSize();
setLastDragLocation(-1);
- if (! splitPane.getLeftComponent().isLightweight()
- || ! splitPane.getRightComponent().isLightweight())
+ if ((left != null && !left.isLightweight())
+ || (right != null && !right.isLightweight()))
draggingHW = true;
if (splitPane.isContinuousLayout())
nonContinuousLayoutDivider.setVisible(false);
else
{
- nonContinuousLayoutDivider.setVisible(true);
- nonContinuousLayoutDivider.setBounds(divider.getBounds());
+ nonContinuousLayoutDivider.setVisible(true);
+ nonContinuousLayoutDivider.setBounds(divider.getBounds());
}
splitPane.revalidate();
splitPane.repaint();
@@ -1520,12 +1522,12 @@ public class BasicSplitPaneUI extends SplitPaneUI
splitPane.setDividerLocation(location);
else
{
- Point p = nonContinuousLayoutDivider.getLocation();
- if (getOrientation() == JSplitPane.HORIZONTAL_SPLIT)
- p.x = location;
- else
- p.y = location;
- nonContinuousLayoutDivider.setLocation(p);
+ Point p = nonContinuousLayoutDivider.getLocation();
+ if (getOrientation() == JSplitPane.HORIZONTAL_SPLIT)
+ p.x = location;
+ else
+ p.y = location;
+ nonContinuousLayoutDivider.setLocation(p);
}
setLastDragLocation(location);
splitPane.repaint();
diff --git a/javax/swing/plaf/basic/BasicTabbedPaneUI.java b/javax/swing/plaf/basic/BasicTabbedPaneUI.java
index ce9ea3ec7..1ee041097 100644
--- a/javax/swing/plaf/basic/BasicTabbedPaneUI.java
+++ b/javax/swing/plaf/basic/BasicTabbedPaneUI.java
@@ -208,7 +208,7 @@ public class BasicTabbedPaneUI extends TabbedPaneUI implements SwingConstants
incrButton = createIncreaseButton();
decrButton = createDecreaseButton();
}
- tabPane.layout();
+ tabPane.revalidate();
tabPane.repaint();
}
}
@@ -241,6 +241,9 @@ public class BasicTabbedPaneUI extends TabbedPaneUI implements SwingConstants
*/
public void calculateLayoutInfo()
{
+ assureRectsCreated(tabPane.getTabCount());
+ contentRect = SwingUtilities.calculateInnerArea(tabPane, contentRect);
+
calculateTabRects(tabPane.getTabPlacement(), tabPane.getTabCount());
if (tabPane.getSelectedIndex() != -1)
@@ -286,8 +289,6 @@ public class BasicTabbedPaneUI extends TabbedPaneUI implements SwingConstants
componentWidth = Math.max(componentWidth, dims.width);
}
}
- Insets insets = tabPane.getInsets();
-
if (tabPlacement == SwingConstants.TOP
|| tabPlacement == SwingConstants.BOTTOM)
{
@@ -331,7 +332,6 @@ public class BasicTabbedPaneUI extends TabbedPaneUI implements SwingConstants
{
if (tabCount == 0)
return;
- assureRectsCreated(tabCount);
FontMetrics fm = getFontMetrics();
SwingUtilities.calculateInnerArea(tabPane, calcRect);
@@ -944,13 +944,11 @@ public class BasicTabbedPaneUI extends TabbedPaneUI implements SwingConstants
{
if (tabCount == 0)
return;
- assureRectsCreated(tabCount);
FontMetrics fm = getFontMetrics();
SwingUtilities.calculateInnerArea(tabPane, calcRect);
Insets tabAreaInsets = getTabAreaInsets(tabPlacement);
Insets insets = tabPane.getInsets();
- int max = 0;
int runs = 1;
int start = 0;
int top = 0;
@@ -959,7 +957,6 @@ public class BasicTabbedPaneUI extends TabbedPaneUI implements SwingConstants
{
int maxHeight = calculateMaxTabHeight(tabPlacement);
calcRect.width -= tabAreaInsets.left + tabAreaInsets.right;
- max = calcRect.width + tabAreaInsets.left + insets.left;
start = tabAreaInsets.left + insets.left;
int width = 0;
int runWidth = start;
@@ -996,7 +993,6 @@ public class BasicTabbedPaneUI extends TabbedPaneUI implements SwingConstants
int maxWidth = calculateMaxTabWidth(tabPlacement);
calcRect.height -= tabAreaInsets.top + tabAreaInsets.bottom;
- max = calcRect.height + tabAreaInsets.top;
int height = 0;
start = tabAreaInsets.top + insets.top;
int runHeight = start;
@@ -1048,8 +1044,8 @@ public class BasicTabbedPaneUI extends TabbedPaneUI implements SwingConstants
if (tabCount == 0)
return;
int tabPlacement = tabPane.getTabPlacement();
- incrButton.hide();
- decrButton.hide();
+ incrButton.setVisible(false);
+ decrButton.setVisible(false);
if (tabPlacement == SwingConstants.TOP
|| tabPlacement == SwingConstants.BOTTOM)
{
@@ -1068,8 +1064,8 @@ public class BasicTabbedPaneUI extends TabbedPaneUI implements SwingConstants
decrDims.width, tabAreaRect.height);
tabAreaRect.width -= decrDims.width + incrDims.width;
- incrButton.show();
- decrButton.show();
+ incrButton.setVisible(true);
+ decrButton.setVisible(true);
}
}
@@ -1092,8 +1088,8 @@ public class BasicTabbedPaneUI extends TabbedPaneUI implements SwingConstants
incrDims.height);
tabAreaRect.height -= decrDims.height + incrDims.height;
- incrButton.show();
- decrButton.show();
+ incrButton.setVisible(true);
+ decrButton.setVisible(true);
}
}
viewport.setBounds(tabAreaRect.x, tabAreaRect.y, tabAreaRect.width,
@@ -1348,6 +1344,8 @@ public class BasicTabbedPaneUI extends TabbedPaneUI implements SwingConstants
public BasicTabbedPaneUI()
{
super();
+ rects = new Rectangle[0];
+ tabRuns = new int[10];
}
/**
@@ -1460,7 +1458,6 @@ public class BasicTabbedPaneUI extends TabbedPaneUI implements SwingConstants
layoutManager = createLayoutManager();
tabPane.setLayout(layoutManager);
- tabPane.layout();
}
}
@@ -1884,7 +1881,8 @@ public class BasicTabbedPaneUI extends TabbedPaneUI implements SwingConstants
protected void paintIcon(Graphics g, int tabPlacement, int tabIndex,
Icon icon, Rectangle iconRect, boolean isSelected)
{
- icon.paintIcon(tabPane, g, iconRect.x, iconRect.y);
+ if (icon != null)
+ icon.paintIcon(tabPane, g, iconRect.x, iconRect.y);
}
/**
@@ -2110,7 +2108,6 @@ public class BasicTabbedPaneUI extends TabbedPaneUI implements SwingConstants
protected void paintContentBorder(Graphics g, int tabPlacement,
int selectedIndex)
{
- Insets insets = getContentBorderInsets(tabPlacement);
int x = contentRect.x;
int y = contentRect.y;
int w = contentRect.width;
@@ -2396,16 +2393,13 @@ public class BasicTabbedPaneUI extends TabbedPaneUI implements SwingConstants
*/
protected void assureRectsCreated(int tabCount)
{
- if (rects == null)
- rects = new Rectangle[tabCount];
- if (tabCount == rects.length)
- return;
- else
+ if (rects.length < tabCount)
{
- int numToCopy = Math.min(tabCount, rects.length);
- Rectangle[] tmp = new Rectangle[tabCount];
- System.arraycopy(rects, 0, tmp, 0, numToCopy);
- rects = tmp;
+ Rectangle[] old = rects;
+ rects = new Rectangle[tabCount];
+ System.arraycopy(old, 0, rects, 0, old.length);
+ for (int i = old.length; i < rects.length; i++)
+ rects[i] = new Rectangle();
}
}
@@ -2763,7 +2757,7 @@ public class BasicTabbedPaneUI extends TabbedPaneUI implements SwingConstants
*/
protected FontMetrics getFontMetrics()
{
- FontMetrics fm = tabPane.getToolkit().getFontMetrics(tabPane.getFont());
+ FontMetrics fm = tabPane.getFontMetrics(tabPane.getFont());
return fm;
}
diff --git a/javax/swing/plaf/basic/BasicTableHeaderUI.java b/javax/swing/plaf/basic/BasicTableHeaderUI.java
index ec0467a74..9c8a5ef95 100644
--- a/javax/swing/plaf/basic/BasicTableHeaderUI.java
+++ b/javax/swing/plaf/basic/BasicTableHeaderUI.java
@@ -139,6 +139,7 @@ public class BasicTableHeaderUI extends TableHeaderUI
public void installUI(JComponent c)
{
header = (JTableHeader) c;
+ rendererPane = new CellRendererPane();
installDefaults();
installKeyboardActions();
installListeners();
@@ -194,18 +195,15 @@ public class BasicTableHeaderUI extends TableHeaderUI
false, // isSelected
false, // isFocused
-1, i);
+ // FIXME: The following settings should be performed in
+ // rend.getTableCellRendererComponent().
comp.setFont(header.getFont());
comp.setBackground(header.getBackground());
comp.setForeground(header.getForeground());
if (comp instanceof JComponent)
((JComponent)comp).setBorder(cellBorder);
- gfx.translate(bounds.x, bounds.y);
- gfx.setClip(0, 0, bounds.width, bounds.height);
- comp.setSize(bounds.width, bounds.height);
- comp.setLocation(0,0);
- comp.paint(gfx);
- gfx.translate(-bounds.x, -bounds.y);
- gfx.setClip(oldClip);
+ rendererPane.paintComponent(gfx, comp, header, bounds.x, bounds.y,
+ bounds.width, bounds.height);
}
}
diff --git a/javax/swing/plaf/basic/BasicTableUI.java b/javax/swing/plaf/basic/BasicTableUI.java
index 5946a3bdd..18b69120d 100644
--- a/javax/swing/plaf/basic/BasicTableUI.java
+++ b/javax/swing/plaf/basic/BasicTableUI.java
@@ -66,11 +66,11 @@ import javax.swing.JTextField;
import javax.swing.KeyStroke;
import javax.swing.ListSelectionModel;
import javax.swing.LookAndFeel;
-import javax.swing.UIDefaults;
import javax.swing.UIManager;
import javax.swing.border.Border;
import javax.swing.event.ChangeEvent;
import javax.swing.event.MouseInputListener;
+import javax.swing.plaf.ActionMapUIResource;
import javax.swing.plaf.ComponentUI;
import javax.swing.plaf.InputMapUIResource;
import javax.swing.plaf.TableUI;
@@ -397,11 +397,10 @@ public class BasicTableUI extends TableUI
protected void installKeyboardActions()
{
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
- InputMap ancestorMap = (InputMap)defaults.get("Table.ancestorInputMap");
+ InputMap ancestorMap = (InputMap) UIManager.get("Table.ancestorInputMap");
InputMapUIResource parentInputMap = new InputMapUIResource();
// FIXME: The JDK uses a LazyActionMap for parentActionMap
- ActionMap parentActionMap = new ActionMap();
+ ActionMap parentActionMap = new ActionMapUIResource();
action = new TableAction();
Object keys[] = ancestorMap.allKeys();
// Register key bindings in the UI InputMap-ActionMap pair
@@ -1194,29 +1193,9 @@ public class BasicTableUI extends TableUI
TableCellRenderer rend, TableModel data,
int rowLead, int colLead)
{
- boolean rowSelAllowed = table.getRowSelectionAllowed();
- boolean colSelAllowed = table.getColumnSelectionAllowed();
- boolean isSel = false;
- if (rowSelAllowed && colSelAllowed || !rowSelAllowed && !colSelAllowed)
- isSel = table.isCellSelected(row, col);
- else
- isSel = table.isRowSelected(row) && table.getRowSelectionAllowed()
- || table.isColumnSelected(col) && table.getColumnSelectionAllowed();
-
- // Determine the focused cell. The focused cell is the cell at the
- // leadSelectionIndices of the row and column selection model.
- ListSelectionModel rowSel = table.getSelectionModel();
- ListSelectionModel colSel = table.getColumnModel().getSelectionModel();
- boolean hasFocus = table.hasFocus() && table.isEnabled()
- && rowSel.getLeadSelectionIndex() == row
- && colSel.getLeadSelectionIndex() == col;
-
- Component comp = rend.getTableCellRendererComponent(table,
- data.getValueAt(row, col),
- isSel, hasFocus, row, col);
-
+ Component comp = table.prepareRenderer(rend, row, col);
rendererPane.paintComponent(g, comp, table, bounds);
-
+
// FIXME: this is manual painting of the Caret, why doesn't the
// JTextField take care of this itself?
if (comp instanceof JTextField)
@@ -1264,7 +1243,7 @@ public class BasicTableUI extends TableUI
width - gap.width + 1,
height - gap.height);
if (bounds.intersects(clip))
- {
+ {
paintCell(gfx, r, c, bounds, table.getCellRenderer(r, c),
table.getModel(),
table.getSelectionModel().getLeadSelectionIndex(),
@@ -1287,12 +1266,10 @@ public class BasicTableUI extends TableUI
x = x0;
Color save = gfx.getColor();
gfx.setColor(grid);
- boolean paintedLine = false;
for (int c = 0; c < ncols && x < xmax; ++c)
{
x += cols.getColumn(c).getWidth();
gfx.drawLine(x, y0, x, ymax);
- paintedLine = true;
}
gfx.setColor(save);
}
@@ -1303,12 +1280,10 @@ public class BasicTableUI extends TableUI
y = y0;
Color save = gfx.getColor();
gfx.setColor(grid);
- boolean paintedLine = false;
for (int r = 0; r < nrows && y < ymax; ++r)
{
y += height;
gfx.drawLine(x0, y, xmax, y);
- paintedLine = true;
}
gfx.setColor(save);
}
diff --git a/javax/swing/plaf/basic/BasicTextFieldUI.java b/javax/swing/plaf/basic/BasicTextFieldUI.java
index e1422c438..4e2ca9f93 100644
--- a/javax/swing/plaf/basic/BasicTextFieldUI.java
+++ b/javax/swing/plaf/basic/BasicTextFieldUI.java
@@ -90,7 +90,8 @@ public class BasicTextFieldUI extends BasicTextUI
{
if (event.getPropertyName().equals("editable"))
{
- if (textComponent.isEditable())
+ boolean editable = ((Boolean) event.getNewValue()).booleanValue();
+ if (editable)
textComponent.setBackground(background);
else
textComponent.setBackground(inactiveBackground);
diff --git a/javax/swing/plaf/basic/BasicTextPaneUI.java b/javax/swing/plaf/basic/BasicTextPaneUI.java
index decbed568..a988c5a63 100644
--- a/javax/swing/plaf/basic/BasicTextPaneUI.java
+++ b/javax/swing/plaf/basic/BasicTextPaneUI.java
@@ -45,12 +45,9 @@ import javax.swing.JTextPane;
import javax.swing.plaf.ColorUIResource;
import javax.swing.UIDefaults;
import javax.swing.plaf.ComponentUI;
-import javax.swing.text.Element;
-import javax.swing.text.PlainView;
import javax.swing.text.Style;
import javax.swing.text.StyleConstants;
import javax.swing.text.StyleContext;
-import javax.swing.text.View;
public class BasicTextPaneUI extends BasicEditorPaneUI
{
@@ -64,11 +61,6 @@ public class BasicTextPaneUI extends BasicEditorPaneUI
return new BasicTextPaneUI();
}
- public View create(Element elem)
- {
- return new PlainView(elem);
- }
-
/**
* Returns the prefix for entries in the {@link UIDefaults} table.
*
diff --git a/javax/swing/plaf/basic/BasicTextUI.java b/javax/swing/plaf/basic/BasicTextUI.java
index 225c4a9dd..be668671b 100644
--- a/javax/swing/plaf/basic/BasicTextUI.java
+++ b/javax/swing/plaf/basic/BasicTextUI.java
@@ -56,8 +56,8 @@ import javax.swing.ActionMap;
import javax.swing.InputMap;
import javax.swing.JComponent;
import javax.swing.LookAndFeel;
+import javax.swing.SwingConstants;
import javax.swing.SwingUtilities;
-import javax.swing.UIDefaults;
import javax.swing.UIManager;
import javax.swing.event.DocumentEvent;
import javax.swing.event.DocumentListener;
@@ -329,6 +329,34 @@ public abstract class BasicTextUI extends TextUI
{
view.changedUpdate(ev, shape, vf);
}
+
+ /**
+ * Returns the document position that is (visually) nearest to the given
+ * document position <code>pos</code> in the given direction <code>d</code>.
+ *
+ * @param pos the document position
+ * @param b the bias for <code>pos</code>
+ * @param a the allocation for the view
+ * @param d the direction, must be either {@link SwingConstants#NORTH},
+ * {@link SwingConstants#SOUTH}, {@link SwingConstants#WEST} or
+ * {@link SwingConstants#EAST}
+ * @param biasRet an array of {@link Position.Bias} that can hold at least
+ * one element, which is filled with the bias of the return position
+ * on method exit
+ *
+ * @return the document position that is (visually) nearest to the given
+ * document position <code>pos</code> in the given direction
+ * <code>d</code>
+ *
+ * @throws BadLocationException if <code>pos</code> is not a valid offset in
+ * the document model
+ */
+ public int getNextVisualPositionFrom(int pos, Position.Bias b, Shape a,
+ int d, Position.Bias[] biasRet)
+ throws BadLocationException
+ {
+ return view.getNextVisualPositionFrom(pos, b, a, d, biasRet);
+ }
}
/**
@@ -522,10 +550,12 @@ public abstract class BasicTextUI extends TextUI
caret.setBlinkRate(UIManager.getInt(prefix + ".caretBlinkRate"));
// Fetch the colors for enabled/disabled text components.
+ background = UIManager.getColor(prefix + ".background");
inactiveBackground = UIManager.getColor(prefix + ".inactiveBackground");
textComponent.setDisabledTextColor
(UIManager.getColor(prefix + ".inactiveForeground"));
textComponent.setSelectedTextColor(UIManager.getColor(prefix + ".selectionForeground"));
+ textComponent.setSelectionColor(UIManager.getColor(prefix + ".selectionBackground"));
}
/**
@@ -586,13 +616,14 @@ public abstract class BasicTextUI extends TextUI
protected Keymap createKeymap()
{
String prefix = getPropertyPrefix();
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
JTextComponent.KeyBinding[] bindings =
- (JTextComponent.KeyBinding[]) defaults.get(prefix + ".keyBindings");
+ (JTextComponent.KeyBinding[]) UIManager.get(prefix + ".keyBindings");
if (bindings == null)
{
bindings = new JTextComponent.KeyBinding[0];
- defaults.put(prefix + ".keyBindings", bindings);
+ // FIXME: Putting something into the defaults map is certainly wrong.
+ // Must be fixed somehow.
+ UIManager.put(prefix + ".keyBindings", bindings);
}
Keymap km = JTextComponent.addKeymap(getKeymapName(),
@@ -629,17 +660,16 @@ public abstract class BasicTextUI extends TextUI
InputMap getInputMap(int condition)
{
String prefix = getPropertyPrefix();
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
switch (condition)
{
case JComponent.WHEN_IN_FOCUSED_WINDOW:
// FIXME: is this the right string? nobody seems to use it.
- return (InputMap) defaults.get(prefix + ".windowInputMap");
+ return (InputMap) UIManager.get(prefix + ".windowInputMap");
case JComponent.WHEN_ANCESTOR_OF_FOCUSED_COMPONENT:
- return (InputMap) defaults.get(prefix + ".ancestorInputMap");
+ return (InputMap) UIManager.get(prefix + ".ancestorInputMap");
default:
case JComponent.WHEN_FOCUSED:
- return (InputMap) defaults.get(prefix + ".focusInputMap");
+ return (InputMap) UIManager.get(prefix + ".focusInputMap");
}
}
@@ -653,12 +683,14 @@ public abstract class BasicTextUI extends TextUI
ActionMap getActionMap()
{
String prefix = getPropertyPrefix();
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
- ActionMap am = (ActionMap) defaults.get(prefix + ".actionMap");
+ ActionMap am = (ActionMap) UIManager.get(prefix + ".actionMap");
if (am == null)
{
am = createActionMap();
- defaults.put(prefix + ".actionMap", am);
+ // FIXME: Putting something in the UIDefaults map is certainly wrong.
+ // However, the whole method seems wrong and must be replaced by
+ // something that is less wrong.
+ UIManager.put(prefix + ".actionMap", am);
}
return am;
}
@@ -716,6 +748,7 @@ public abstract class BasicTextUI extends TextUI
protected void uninstallListeners()
{
textComponent.removeFocusListener(focuslistener);
+ textComponent.getDocument().removeDocumentListener(documentHandler);
}
/**
@@ -769,6 +802,18 @@ public abstract class BasicTextUI extends TextUI
}
/**
+ * Returns the minimum size for text components. This returns the size
+ * of the component's insets.
+ *
+ * @return the minimum size for text components
+ */
+ public Dimension getMinimumSize(JComponent c)
+ {
+ Insets i = c.getInsets();
+ return new Dimension(i.left + i.right, i.top + i.bottom);
+ }
+
+ /**
* Paints the text component.
*
* @param g the <code>Graphics</code> context to paint to
@@ -788,10 +833,10 @@ public abstract class BasicTextUI extends TextUI
{
Caret caret = textComponent.getCaret();
Highlighter highlighter = textComponent.getHighlighter();
-
+
if (textComponent.isOpaque())
paintBackground(g);
-
+
if (highlighter != null
&& textComponent.getSelectionStart() != textComponent.getSelectionEnd())
highlighter.paint(g);
@@ -1013,6 +1058,7 @@ public abstract class BasicTextUI extends TextUI
*/
protected Rectangle getVisibleEditorRect()
{
+ JTextComponent textComponent = getComponent();
int width = textComponent.getWidth();
int height = textComponent.getHeight();
@@ -1021,8 +1067,8 @@ public abstract class BasicTextUI extends TextUI
Insets insets = textComponent.getInsets();
return new Rectangle(insets.left, insets.top,
- width - insets.left + insets.right,
- height - insets.top + insets.bottom);
+ width - insets.left - insets.right,
+ height - insets.top - insets.bottom);
}
/**
diff --git a/javax/swing/plaf/basic/BasicToolBarUI.java b/javax/swing/plaf/basic/BasicToolBarUI.java
index ef4ed835f..261db687a 100644
--- a/javax/swing/plaf/basic/BasicToolBarUI.java
+++ b/javax/swing/plaf/basic/BasicToolBarUI.java
@@ -404,6 +404,8 @@ public class BasicToolBarUI extends ToolBarUI implements SwingConstants
boolean tmp = ((loc == SwingConstants.NORTH)
|| (loc == SwingConstants.SOUTH) || (loc == -1));
+ cachedOrientation = toolBar.getOrientation();
+ cachedBounds = toolBar.getSize();
if (((cachedOrientation == SwingConstants.HORIZONTAL) && tmp)
|| ((cachedOrientation == VERTICAL) && ! tmp))
{
@@ -571,9 +573,6 @@ public class BasicToolBarUI extends ToolBarUI implements SwingConstants
dragWindow = createDragWindow(toolBar);
- cachedBounds = toolBar.getPreferredSize();
- cachedOrientation = toolBar.getOrientation();
-
nonRolloverBorder = createNonRolloverBorder();
rolloverBorder = createRolloverBorder();
@@ -1061,7 +1060,7 @@ public class BasicToolBarUI extends ToolBarUI implements SwingConstants
isDragging = true;
if (dragWindow != null)
- dragWindow.setOffset(new Point(e.getX(), e.getY()));
+ dragWindow.setOffset(new Point(cachedBounds.width/2, cachedBounds.height/2));
dragTo(e.getPoint(), origin);
}
diff --git a/javax/swing/plaf/basic/BasicTreeUI.java b/javax/swing/plaf/basic/BasicTreeUI.java
index e42e0e1d6..4100442a0 100644
--- a/javax/swing/plaf/basic/BasicTreeUI.java
+++ b/javax/swing/plaf/basic/BasicTreeUI.java
@@ -81,7 +81,6 @@ import javax.swing.KeyStroke;
import javax.swing.LookAndFeel;
import javax.swing.SwingUtilities;
import javax.swing.Timer;
-import javax.swing.UIDefaults;
import javax.swing.UIManager;
import javax.swing.event.CellEditorListener;
import javax.swing.event.ChangeEvent;
@@ -92,6 +91,7 @@ import javax.swing.event.TreeModelEvent;
import javax.swing.event.TreeModelListener;
import javax.swing.event.TreeSelectionEvent;
import javax.swing.event.TreeSelectionListener;
+import javax.swing.plaf.ActionMapUIResource;
import javax.swing.plaf.ComponentUI;
import javax.swing.plaf.InputMapUIResource;
import javax.swing.plaf.TreeUI;
@@ -238,14 +238,14 @@ public class BasicTreeUI extends TreeUI
/** Boolean to keep track of editing. */
boolean isEditing;
- /** The bounds of the current cell. */
- Rectangle bounds;
-
/** The current path of the visible nodes in the tree. */
TreePath currentVisiblePath;
/** The gap between the icon and text. */
int gap = 4;
+
+ /** Default row height, if none was set. */
+ int rowHeight = 20;
/** Listeners */
private PropertyChangeListener propertyChangeListener;
@@ -303,7 +303,7 @@ public class BasicTreeUI extends TreeUI
*/
protected Color getHashColor()
{
- return UIManager.getLookAndFeelDefaults().getColor("Tree.hash");
+ return UIManager.getColor("Tree.hash");
}
/**
@@ -314,8 +314,8 @@ public class BasicTreeUI extends TreeUI
*/
protected void setHashColor(Color color)
{
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
- defaults.put("Tree.hash", color);
+ // FIXME: Putting something in the UIDefaults map is certainly wrong.
+ UIManager.put("Tree.hash", color);
}
/**
@@ -436,6 +436,8 @@ public class BasicTreeUI extends TreeUI
*/
protected void setRowHeight(int rowHeight)
{
+ if (rowHeight == 0)
+ rowHeight = this.rowHeight;
treeState.setRowHeight(rowHeight);
}
@@ -623,22 +625,19 @@ public class BasicTreeUI extends TreeUI
*/
public Rectangle getPathBounds(JTree tree, TreePath path)
{
+ Rectangle bounds = null;
+ int row = -1;
+ Object cell = null;
if (path != null)
{
- Object cell = path.getLastPathComponent();
-
- if (treeModel != null)
- {
- Object root = treeModel.getRoot();
-
- if (!tree.isRootVisible() && tree.isExpanded(new TreePath(root)))
- root = getNextNode(root);
-
- Point loc = getCellLocation(0, 0, tree, treeModel, cell, root);
- return getCellBounds(loc.x, loc.y, cell);
- }
+ row = getRowForPath(tree, path);
+ cell = path.getLastPathComponent();
+ bounds = new Rectangle(0, row * getRowHeight(), 0, 0);
}
- return null;
+ return nodeDimensions.getNodeDimensions(cell, row,
+ getLevel(cell),
+ tree.isExpanded(path),
+ bounds);
}
/**
@@ -721,9 +720,6 @@ public class BasicTreeUI extends TreeUI
*/
public TreePath getClosestPathForLocation(JTree tree, int x, int y)
{
- // FIXME: what if root is hidden? should not depend on (0,0)
- // should start counting rows from where root is.
-
int row = Math.round(y / getRowHeight());
TreePath path = getPathForRow(tree, row);
@@ -1037,7 +1033,9 @@ public class BasicTreeUI extends TreeUI
*/
protected void uninstallKeyboardActions()
{
- // TODO: Implement this properly.
+ action = null;
+ tree.getInputMap(JComponent.WHEN_ANCESTOR_OF_FOCUSED_COMPONENT).setParent(null);
+ tree.getActionMap().setParent(null);
}
/**
@@ -1181,8 +1179,7 @@ public class BasicTreeUI extends TreeUI
for (int i = 0; i < path.length; i++)
{
TreePath curr = new TreePath(getPathToRoot(path[i], 0));
- Rectangle bounds = getPathBounds(tree, curr);
-
+ Rectangle bounds = getPathBounds(tree, curr);
if (treeModel != null)
isLeaf = treeModel.isLeaf(path[i]);
if (!isLeaf && hasControlIcons())
@@ -1230,7 +1227,7 @@ public class BasicTreeUI extends TreeUI
rightChildIndent = UIManager.getInt("Tree.rightChildIndent");
leftChildIndent = UIManager.getInt("Tree.leftChildIndent");
setRowHeight(UIManager.getInt("Tree.rowHeight"));
- tree.setRowHeight(UIManager.getInt("Tree.rowHeight"));
+ tree.setRowHeight(getRowHeight());
tree.requestFocusInWindow(false);
tree.setScrollsOnExpand(UIManager.getBoolean("Tree.scrollsOnExpand"));
setExpandedIcon(UIManager.getIcon("Tree.expandedIcon"));
@@ -1242,10 +1239,9 @@ public class BasicTreeUI extends TreeUI
*/
protected void installKeyboardActions()
{
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
- InputMap focusInputMap = (InputMap) defaults.get("Tree.focusInputMap");
+ InputMap focusInputMap = (InputMap) UIManager.get("Tree.focusInputMap");
InputMapUIResource parentInputMap = new InputMapUIResource();
- ActionMap parentActionMap = new ActionMap();
+ ActionMap parentActionMap = new ActionMapUIResource();
action = new TreeAction();
Object keys[] = focusInputMap.allKeys();
@@ -1412,14 +1408,30 @@ public class BasicTreeUI extends TreeUI
JTree tree = (JTree) c;
if (currentVisiblePath == null)
updateCurrentVisiblePath();
-
- if (treeModel != null)
+
+ Rectangle clip = g.getClipBounds();
+ Insets insets = tree.getInsets();
+
+ if (clip != null && treeModel != null && currentVisiblePath != null)
{
- Object root = treeModel.getRoot();
- paintRecursive(g, 0, 0, 0, tree, treeModel, root);
-
- if (hasControlIcons())
- paintControlIcons(g, 0, 0, 0, tree, treeModel, root);
+ int startIndex = tree.getClosestRowForLocation(clip.x, clip.y);
+ int endIndex = tree.getClosestRowForLocation(clip.x + clip.width,
+ clip.y + clip.height);
+
+ paintVerticalPartOfLeg(g, clip, insets, currentVisiblePath);
+ for (int i = startIndex; i <= endIndex; i++)
+ {
+ Object curr = currentVisiblePath.getPathComponent(i);
+ boolean isLeaf = treeModel.isLeaf(curr);
+ TreePath path = new TreePath(getPathToRoot(curr, 0));
+
+ boolean isExpanded = tree.isExpanded(path);
+ Rectangle bounds = getPathBounds(tree, path);
+ paintHorizontalPartOfLeg(g, clip, insets, bounds, path, i,
+ isExpanded, false, isLeaf);
+ paintRow(g, clip, insets, bounds, path, i, isExpanded, false,
+ isLeaf);
+ }
}
}
@@ -1593,7 +1605,7 @@ public class BasicTreeUI extends TreeUI
int y;
if (event == null)
{
- bounds = getPathBounds(tree, path);
+ Rectangle bounds = getPathBounds(tree, path);
x = bounds.x;
y = bounds.y;
}
@@ -1673,7 +1685,7 @@ public class BasicTreeUI extends TreeUI
if (!isLeaf(row))
{
- bounds = getPathBounds(tree, path);
+ Rectangle bounds = getPathBounds(tree, path);
if (hasControlIcons() && (mouseX < bounds.x)
&& (mouseX > (bounds.x - getCurrentControlIcon(path).getIconWidth() - gap)))
@@ -1994,7 +2006,7 @@ public class BasicTreeUI extends TreeUI
}
/**
- * Creats, if necessary, and starts a Timer to check if needed to resize the
+ * Creates, if necessary, and starts a Timer to check if needed to resize the
* bounds
*/
protected void startTimer()
@@ -2230,7 +2242,7 @@ public class BasicTreeUI extends TreeUI
if (path != null)
{
- bounds = getPathBounds(tree, path);
+ Rectangle bounds = getPathBounds(tree, path);
int row = getRowForPath(tree, path);
boolean cntlClick = isLocationInExpandControl(path, click.x, click.y);
@@ -2259,15 +2271,19 @@ public class BasicTreeUI extends TreeUI
boolean inBounds = bounds.contains(click.x, click.y);
if ((inBounds || cntlClick) && tree.isVisible(path))
{
- selectPath(tree, path);
- if (inBounds && e.getClickCount() == 2 && !isLeaf(row))
- toggleExpandState(path);
+ if (inBounds)
+ {
+ selectPath(tree, path);
+ if (e.getClickCount() == 2 && !isLeaf(row))
+ toggleExpandState(path);
+ }
if (cntlClick)
{
handleExpandControlClick(path, click.x, click.y);
if (cellEditor != null)
cellEditor.cancelCellEditing();
+ tree.scrollPathToVisible(path);
}
else if (tree.isEditable())
startEditing(path, e);
@@ -2451,9 +2467,12 @@ public class BasicTreeUI extends TreeUI
}
/**
- * Responsible for getting the size of a particular node.
+ * Returns, by reference in bounds, the size and x origin to place value at.
+ * The calling method is responsible for determining the Y location.
+ * If bounds is null, a newly created Rectangle should be returned,
+ * otherwise the value should be placed in bounds and returned.
*
- * @param value
+ * @param cell
* the value to be represented
* @param row
* row being queried
@@ -2465,10 +2484,23 @@ public class BasicTreeUI extends TreeUI
* a Rectangle containing the size needed to represent value
* @return containing the node dimensions, or null if node has no dimension
*/
- public Rectangle getNodeDimensions(Object value, int row, int depth,
+ public Rectangle getNodeDimensions(Object cell, int row, int depth,
boolean expanded, Rectangle size)
{
- return null;
+ if (size == null || cell == null)
+ return null;
+
+ String s = cell.toString();
+ Font f = tree.getFont();
+ FontMetrics fm = tree.getToolkit().getFontMetrics(f);
+
+ if (s != null)
+ {
+ size.x = getRowX(row, depth);
+ size.width = SwingUtilities.computeStringWidth(fm, s);
+ size.height = fm.getHeight();
+ }
+ return size;
}
/**
@@ -2478,7 +2510,9 @@ public class BasicTreeUI extends TreeUI
*/
protected int getRowX(int row, int depth)
{
- return 0;
+ if (row == 0)
+ return 0;
+ return depth * rightChildIndent;
}
}// NodeDimensionsHandler
@@ -2507,7 +2541,13 @@ public class BasicTreeUI extends TreeUI
*/
public void propertyChange(PropertyChangeEvent event)
{
- // TODO: What should be done here, if anything?
+ if ((event.getPropertyName()).equals("rootVisible"))
+ {
+ validCachedPreferredSize = false;
+ updateCurrentVisiblePath();
+ tree.revalidate();
+ tree.repaint();
+ }
}
}
@@ -2706,7 +2746,7 @@ public class BasicTreeUI extends TreeUI
if (e.getActionCommand().equals("selectPreviousChangeLead"))
{
Object prev = getPreviousVisibleNode(last);
-
+
if (prev != null)
{
TreePath newPath = new TreePath(getPathToRoot(prev, 0));
@@ -2727,6 +2767,7 @@ public class BasicTreeUI extends TreeUI
else if (e.getActionCommand().equals("selectPrevious"))
{
Object prev = getPreviousVisibleNode(last);
+
if (prev != null)
{
TreePath newPath = new TreePath(getPathToRoot(prev, 0));
@@ -2736,6 +2777,7 @@ public class BasicTreeUI extends TreeUI
else if (e.getActionCommand().equals("selectNext"))
{
Object next = getNextVisibleNode(last);
+
if (next != null)
{
TreePath newPath = new TreePath(getPathToRoot(next, 0));
@@ -2857,8 +2899,11 @@ public class BasicTreeUI extends TreeUI
*/
public void treeStructureChanged(TreeModelEvent e)
{
- validCachedPreferredSize = false;
+ if (e.getPath().length == 1
+ && !e.getPath()[0].equals(treeModel.getRoot()))
+ tree.expandPath(new TreePath(treeModel.getRoot()));
updateCurrentVisiblePath();
+ validCachedPreferredSize = false;
tree.revalidate();
tree.repaint();
}
@@ -3046,236 +3091,6 @@ public class BasicTreeUI extends TreeUI
}
/**
- * Returns the cell bounds for painting selected cells Package private for use
- * in inner classes.
- *
- * @param x
- * is the x location of the cell
- * @param y
- * is the y location of the cell
- * @param cell
- * is the Object to get the bounds for
- * @returns Rectangle that represents the cell bounds
- */
- Rectangle getCellBounds(int x, int y, Object cell)
- {
- if (cell != null)
- {
- String s = cell.toString();
- Font f = tree.getFont();
- FontMetrics fm = tree.getToolkit().getFontMetrics(f);
-
- if (s != null)
- return new Rectangle(x, y, SwingUtilities.computeStringWidth(fm, s),
- fm.getHeight());
- }
- return new Rectangle(x, y, 0, 0);
- }
-
- /**
- * Retrieves the location of some node, recursively starting at from some
- * node. Package private for use in inner classes.
- *
- * @param x
- * is the starting x position, offset
- * @param y
- * is the starting y position, offset
- * @param tree
- * is the tree to traverse
- * @param mod
- * is the TreeModel to use
- * @param node
- * is the node to get the location for
- * @param startNode
- * is the node to start searching from
- * @return Point - the location of node
- */
- Point getCellLocation(int x, int y, JTree tree, TreeModel mod, Object node,
- Object startNode)
- {
- int rowHeight = getRowHeight();
- if (startNode == null || startNode.equals(node))
- {
- int level = getLevel(node);
- if (level == 0)
- return new Point(x, y);
- if (!tree.isRootVisible() &&
- tree.isExpanded(new TreePath(mod.getRoot())))
- return new Point(x + ((level - 1) * rightChildIndent), y);
- return new Point(x + (level * rightChildIndent), y);
- }
- return getCellLocation(x, y + rowHeight, tree, mod, node,
- getNextVisibleNode(startNode));
- }
-
- /**
- * Recursively paints all elements of the tree Package private for use in
- * inner classes.
- *
- * @param g
- * the Graphics context in which to paint
- * @param indentation
- * of the current object
- * @param descent
- * is the number of elements drawn
- * @param depth
- * is the depth of the current object in the tree
- * @param tree
- * is the tree to draw to
- * @param mod
- * is the TreeModel we are using to draw
- * @param curr
- * is the current object to draw
- * @return int - current descent of the tree
- */
- int paintRecursive(Graphics g, int indentation, int descent,
- int depth, JTree tree, TreeModel mod, Object curr)
- {
- Rectangle clip = tree.getVisibleRect();
- if (indentation > clip.x + clip.width + rightChildIndent
- || descent > clip.y + clip.height + getRowHeight())
- return descent;
-
- TreePath path = new TreePath(getPathToRoot(curr, 0));
- int halfHeight = getRowHeight() / 2;
- int halfWidth = rightChildIndent / 2;
- int y0 = descent + halfHeight;
- int heightOfLine = descent + halfHeight;
- int row = getRowForPath(tree, path);
- boolean isRootVisible = tree.isRootVisible();
- boolean isExpanded = tree.isExpanded(path);
- boolean isLeaf = mod.isLeaf(curr);
- Rectangle bounds = getPathBounds(tree, path);
- Object root = mod.getRoot();
-
- if (isLeaf)
- {
- paintRow(g, clip, null, bounds, path, row, true, false, true);
- descent += getRowHeight();
- }
- else
- {
- if (depth > 0 || isRootVisible)
- {
- paintRow(g, clip, null, bounds, path, row, isExpanded, false, false);
- descent += getRowHeight();
- y0 += halfHeight;
- }
-
- int max = mod.getChildCount(curr);
- if (isExpanded)
- {
- for (int i = 0; i < max; i++)
- {
- int indent = indentation + rightChildIndent;
- if (!isRootVisible && depth == 0)
- indent = 0;
- else if (isRootVisible ||
- (!isRootVisible && !curr.equals(root)))
- {
- g.setColor(getHashColor());
- heightOfLine = descent + halfHeight;
- paintHorizontalLine(g, (JComponent) tree, heightOfLine,
- indentation + halfWidth, indentation + rightChildIndent);
- }
-
- descent = paintRecursive(g, indent, descent, depth + 1,
- tree, mod, mod.getChild(curr, i));
- }
- }
- }
-
- if (isExpanded)
- if (y0 != heightOfLine && !isLeaf
- && mod.getChildCount(curr) > 0)
- {
- g.setColor(getHashColor());
- paintVerticalLine(g, (JComponent) tree, indentation + halfWidth,
- y0, heightOfLine);
- }
-
- return descent;
- }
-
- /**
- * Recursively paints all the control icons on the tree. Package private for
- * use in inner classes.
- *
- * @param g
- * the Graphics context in which to paint
- * @param indentation
- * of the current object
- * @param descent
- * is the number of elements drawn
- * @param depth
- * is the depth of the current object in the tree
- * @param tree
- * is the tree to draw to
- * @param mod
- * is the TreeModel we are using to draw
- * @param node
- * is the current object to draw
- * @return int current descent of the tree
- */
- int paintControlIcons(Graphics g, int indentation, int descent,
- int depth, JTree tree, TreeModel mod,
- Object node)
- {
- int rowHeight = getRowHeight();
- TreePath path = new TreePath(getPathToRoot(node, 0));
- Icon icon = getCurrentControlIcon(path);
-
- Rectangle clip = tree.getVisibleRect();
- if (indentation > clip.x + clip.width + rightChildIndent
- || descent > clip.y + clip.height + getRowHeight())
- return descent;
-
- if (mod.isLeaf(node))
- descent += rowHeight;
- else
- {
- if (!node.equals(mod.getRoot()) &&
- (tree.isRootVisible() || getLevel(node) != 1))
- {
- int width = icon.getIconWidth();
- int height = icon.getIconHeight() + 2;
- int posX = indentation - rightChildIndent;
- int posY = descent;
- if (width > rightChildIndent)
- posX -= gap;
- else posX += width/2;
-
- if (height < rowHeight)
- posY += height/2;
-
- icon.paintIcon(tree, g, posX, posY);
- }
-
- if (depth > 0 || tree.isRootVisible())
- descent += rowHeight;
-
- if (tree.isExpanded(path))
- {
- int max = 0;
- if (!mod.isLeaf(node))
- max = mod.getChildCount(node);
-
- for (int i = 0; i < max; i++)
- {
- int indent = indentation + rightChildIndent;
- if (depth == 0 && !tree.isRootVisible())
- indent = 1;
-
- descent = paintControlIcons(g, indent, descent, depth + 1,
- tree, mod, mod.getChild(node, i));
- }
- }
- }
-
- return descent;
- }
-
- /**
* Returns true if the LookAndFeel implements the control icons. Package
* private for use in inner classes.
*
@@ -3312,8 +3127,10 @@ public class BasicTreeUI extends TreeUI
*/
Object getParent(Object root, Object node)
{
- if (root == null || node == null)
+ if (root == null || node == null ||
+ root.equals(node))
return null;
+
if (node instanceof TreeNode)
return ((TreeNode) node).getParent();
return findNode(root, node);
@@ -3330,21 +3147,23 @@ public class BasicTreeUI extends TreeUI
*/
private Object findNode(Object root, Object node)
{
- int size = 0;
- if (!treeModel.isLeaf(root))
- size = treeModel.getChildCount(root);
- for (int i = 0; i < size; i++)
+ if (!treeModel.isLeaf(root) && !root.equals(node))
{
- if (treeModel.getIndexOfChild(root, node) != -1)
- return root;
+ int size = treeModel.getChildCount(root);
+ for (int j = 0; j < size; j++)
+ {
+ Object child = treeModel.getChild(root, j);
+ if (node.equals(child))
+ return root;
- Object n = findNode(treeModel.getChild(root, i), node);
- if (n != null)
- return n;
+ Object n = findNode(child, node);
+ if (n != null)
+ return n;
+ }
}
return null;
}
-
+
/**
* Get previous visible node in the tree. Package private for use in inner
* classes.
@@ -3363,7 +3182,7 @@ public class BasicTreeUI extends TreeUI
while (i < nodes.length && !node.equals(nodes[i]))
i++;
// return the next node
- if (i-1 > 0)
+ if (i-1 >= 0)
return nodes[i-1];
}
return null;
@@ -3383,14 +3202,13 @@ public class BasicTreeUI extends TreeUI
Object node = curr;
Object sibling = null;
-
do
{
sibling = getNextSibling(node);
node = getParent(treeModel.getRoot(), node);
}
while (sibling == null && node != null);
-
+
return sibling;
}
@@ -3452,7 +3270,7 @@ public class BasicTreeUI extends TreeUI
return treeModel.getChild(parent, index);
}
-
+
/**
* Returns the previous sibling in the tree Package private for use in inner
* classes.
@@ -3548,15 +3366,22 @@ public class BasicTreeUI extends TreeUI
int getLevel(Object node)
{
int count = -1;
+
Object current = node;
- do
+ if (treeModel != null)
{
- current = getParent(treeModel.getRoot(), current);
- count++;
+ Object root = treeModel.getRoot();
+ if (!tree.isRootVisible() && tree.isExpanded(new TreePath(root)))
+ count--;
+
+ do
+ {
+ current = getParent(root, current);
+ count++;
+ }
+ while (current != null);
}
- while (current != null);
-
return count;
}
@@ -3577,6 +3402,8 @@ public class BasicTreeUI extends TreeUI
protected void paintVerticalLine(Graphics g, JComponent c, int x, int top,
int bottom)
{
+ // FIXME: Check if drawing a dashed line or not.
+ g.setColor(getHashColor());
g.drawLine(x, top, x, bottom);
}
@@ -3597,6 +3424,8 @@ public class BasicTreeUI extends TreeUI
protected void paintHorizontalLine(Graphics g, JComponent c, int y, int left,
int right)
{
+ // FIXME: Check if drawing a dashed line or not.
+ g.setColor(getHashColor());
g.drawLine(left, y, right, y);
}
@@ -3612,14 +3441,19 @@ public class BasicTreeUI extends TreeUI
* @param x
* is the center position in x-direction
* @param y
- * is the center position in y-direction FIXME what to do if x <
- * (icon.width / 2). Same with y
+ * is the center position in y-direction
*/
protected void drawCentered(Component c, Graphics g, Icon icon, int x, int y)
{
- int beginPositionX = x - icon.getIconWidth() / 2;
- int beginPositionY = y - icon.getIconHeight() / 2;
- icon.paintIcon(c, g, beginPositionX, beginPositionY);
+ x -= icon.getIconWidth() / 2;
+ y -= icon.getIconHeight() / 2;
+
+ if (x < 0)
+ x = 0;
+ if (y < 0)
+ y = 0;
+
+ icon.paintIcon(c, g, x, y);
}
/**
@@ -3632,6 +3466,7 @@ public class BasicTreeUI extends TreeUI
*/
protected void drawDashedHorizontalLine(Graphics g, int y, int x1, int x2)
{
+ g.setColor(getHashColor());
for (int i = x1; i < x2; i += 2)
g.drawLine(i, y, i + 1, y);
}
@@ -3646,6 +3481,7 @@ public class BasicTreeUI extends TreeUI
*/
protected void drawDashedVerticalLine(Graphics g, int x, int y1, int y2)
{
+ g.setColor(getHashColor());
for (int i = y1; i < y2; i += 2)
g.drawLine(x, i, x, i + 1);
}
@@ -3670,8 +3506,15 @@ public class BasicTreeUI extends TreeUI
boolean isExpanded, boolean hasBeenExpanded,
boolean isLeaf)
{
- if (treeModel != null && hasControlIcons())
- paintControlIcons(g, 0, 0, 0, tree, treeModel, path.getLastPathComponent());
+ if (shouldPaintExpandControl(path, row, isExpanded, hasBeenExpanded, isLeaf))
+ {
+ Icon icon = getCurrentControlIcon(path);
+ int iconW = icon.getIconWidth();
+ int x = bounds.x - rightChildIndent + iconW/2;
+ if (x + iconW > bounds.x)
+ x = bounds.x - rightChildIndent - gap;
+ icon.paintIcon(tree, g, x, bounds.y + bounds.height/2 - icon.getIconHeight()/2);
+ }
}
/**
@@ -3682,9 +3525,9 @@ public class BasicTreeUI extends TreeUI
* @param g - the graphics configuration
* @param clipBounds -
* @param insets -
- * @param bounds - bounds of expand control
- * @param path - path to draw control for
- * @param row - row to draw control for
+ * @param bounds - bounds of the cell
+ * @param path - path to draw leg for
+ * @param row - row to start drawing at
* @param isExpanded - is the row expanded
* @param hasBeenExpanded - has the row already been expanded
* @param isLeaf - is the path a leaf
@@ -3695,7 +3538,9 @@ public class BasicTreeUI extends TreeUI
boolean isExpanded, boolean hasBeenExpanded,
boolean isLeaf)
{
- // FIXME: not implemented
+ if (row != 0)
+ paintHorizontalLine(g, tree, bounds.y + bounds.height/2, bounds.x - gap - 2,
+ bounds.x);
}
/**
@@ -3710,7 +3555,24 @@ public class BasicTreeUI extends TreeUI
protected void paintVerticalPartOfLeg(Graphics g, Rectangle clipBounds,
Insets insets, TreePath path)
{
- // FIXME: not implemented
+ int max = tree.getVisibleRowCount();
+ for (int i = 0; i < max; i++)
+ {
+ Object curr = path.getPathComponent(i);
+ TreePath currPath = new TreePath(getPathToRoot(curr, 0));
+ int numChild = treeModel.getChildCount(curr);
+ if (numChild > 0 && tree.isExpanded(currPath))
+ {
+ Rectangle bounds = getPathBounds(tree, currPath);
+ Rectangle lastChildBounds = getPathBounds(tree,
+ new TreePath(getPathToRoot(
+ treeModel.getChild(curr, numChild - 1),
+ 0)));
+ paintVerticalLine(g, tree, bounds.x + gap + 2, bounds.y +
+ bounds.height - 2, lastChildBounds.y +
+ lastChildBounds.height/2);
+ }
+ }
}
/**
@@ -3739,8 +3601,15 @@ public class BasicTreeUI extends TreeUI
if (tree.isVisible(path))
{
- bounds.width = preferredSize.width;
- bounds.x += gap;
+ if (!validCachedPreferredSize)
+ updateCachedPreferredSize();
+
+
+ paintExpandControl(g, clipBounds, insets, bounds, path, row, isExpanded, hasBeenExpanded, isLeaf);
+
+ if (row != 0)
+ bounds.x += gap;
+ bounds.width = preferredSize.width + bounds.x;
if (editingComponent != null && editingPath != null && isEditing(tree)
&& node.equals(editingPath.getLastPathComponent()))
@@ -3755,7 +3624,7 @@ public class BasicTreeUI extends TreeUI
dtcr = createDefaultCellRenderer();
Component c = dtcr.getTreeCellRendererComponent(tree, node,
- selected, isExpanded, isLeaf, row, false);
+ selected, isExpanded, isLeaf, row, tree.hasFocus());
rendererPane.paintComponent(g, c, c.getParent(), bounds);
}
}
@@ -3785,10 +3654,7 @@ public class BasicTreeUI extends TreeUI
boolean isLeaf)
{
Object node = path.getLastPathComponent();
- if (treeModel != null && (!isLeaf && !node.equals(treeModel.getRoot())) &&
- (tree.isRootVisible() || getLevel(node) != 1))
- return true;
- return false;
+ return (!isLeaf && getLevel(node) != 0 && hasControlIcons());
}
/**
@@ -3801,32 +3667,62 @@ public class BasicTreeUI extends TreeUI
return;
Object next = treeModel.getRoot();
- Rectangle bounds = getCellBounds(0, 0, next);
+ TreePath rootPath = new TreePath(next);
+ Rectangle bounds = getPathBounds(tree, rootPath);
// If root is not a valid size to be visible, or is
// not visible and the tree is expanded, then the next node acts
// as the root
- if ((bounds.width == 0 && bounds.height == 0) || (!isRootVisible()
+ if ((bounds.width == 0 && bounds.height == 0) || (!isRootVisible()
&& tree.isExpanded(new TreePath(next))))
- next = getNextNode(next);
+ {
+ next = getNextNode(next);
+ rootPath = new TreePath(next);
+ }
+
+ Object root = next;
TreePath current = null;
-
while (next != null)
{
if (current == null)
- current = new TreePath(next);
- else
- current = current.pathByAddingChild(next);
+ current = rootPath;
+ else
+ current = current.pathByAddingChild(next);
+
do
- next = getNextNode(next);
+ {
+ TreePath path = new TreePath(getPathToRoot(next, 0));
+ if ((tree.isVisible(path) && tree.isExpanded(path))
+ || treeModel.isLeaf(next))
+ next = getNextNode(next);
+ else
+ {
+ Object pNext = next;
+ next = getNextSibling(pNext);
+ // if no next sibling, check parent's next sibling.
+ if (next == null)
+ {
+ Object parent = getParent(root, pNext);
+ while (next == null && parent != null)
+ {
+ next = getNextSibling(parent);
+ if (next == null)
+ parent = getParent(root, parent);
+ }
+ }
+ }
+ }
while (next != null &&
!tree.isVisible(new TreePath(getPathToRoot(next, 0))));
}
+
currentVisiblePath = current;
tree.setVisibleRowCount(getRowCount(tree));
+
if (tree.getSelectionModel() != null && tree.getSelectionCount() == 0 &&
currentVisiblePath != null)
- tree.addSelectionRow(0);
+ selectPath(tree, new TreePath(getPathToRoot(currentVisiblePath.
+ getPathComponent(0), 0)));
}
/**
diff --git a/javax/swing/plaf/metal/MetalBorders.java b/javax/swing/plaf/metal/MetalBorders.java
index 4fa3b3640..28143d51e 100644
--- a/javax/swing/plaf/metal/MetalBorders.java
+++ b/javax/swing/plaf/metal/MetalBorders.java
@@ -56,7 +56,6 @@ import javax.swing.JTextField;
import javax.swing.JToggleButton;
import javax.swing.JToolBar;
import javax.swing.SwingConstants;
-import javax.swing.UIDefaults;
import javax.swing.UIManager;
import javax.swing.border.AbstractBorder;
import javax.swing.border.Border;
@@ -131,6 +130,82 @@ public class MetalBorders
public void paintBorder(Component c, Graphics g, int x, int y, int w,
int h)
{
+ // With the OceanTheme the button border is painted entirely different.
+ // However, I couldn't figure out how this is determined besides checking
+ // for instanceof OceanTheme. The button painting is definitely not
+ // influenced by a UI default property and it is definitely performed
+ // by the same Border class.
+ if (MetalLookAndFeel.getCurrentTheme() instanceof OceanTheme)
+ paintOceanButtonBorder(c, g, x, y, w, h);
+ else
+ {
+ ButtonModel bmodel = null;
+
+ if (c instanceof AbstractButton)
+ bmodel = ((AbstractButton) c).getModel();
+
+ Color darkShadow = MetalLookAndFeel.getControlDarkShadow();
+ Color shadow = MetalLookAndFeel.getControlShadow();
+ Color light = MetalLookAndFeel.getControlHighlight();
+ Color middle = MetalLookAndFeel.getControl();
+
+ if (c.isEnabled())
+ {
+ // draw dark border
+ g.setColor(darkShadow);
+ g.drawRect(x, y, w - 2, h - 2);
+
+ if (!bmodel.isPressed())
+ {
+ // draw light border
+ g.setColor(light);
+ g.drawRect(x + 1, y + 1, w - 2, h - 2);
+
+ // draw crossing pixels of both borders
+ g.setColor(middle);
+ g.drawLine(x + 1, y + h - 2, x + 1, y + h - 2);
+ g.drawLine(x + w - 2, y + 1, x + w - 2, y + 1);
+ }
+ else
+ {
+ // draw light border
+ g.setColor(light);
+ g.drawLine(x + w - 1, y + 1, x + w - 1, y + h - 1);
+ g.drawLine(x + 1, y + h - 1, x + w - 1, y + h - 1);
+
+ // draw shadow border
+ g.setColor(middle);
+ g.drawLine(x + 1, y + 1, x + w - 2, y + 1);
+ g.drawLine(x + 1, y + 1, x + 1, y + h - 2);
+
+ // draw crossing pixels of both borders
+ g.setColor(shadow);
+ g.drawRect(x + 1, y + h - 2, 0, 0);
+ g.drawRect(x + w - 2, y + 1, 0, 0);
+ }
+ }
+ else
+ {
+ // draw disabled border
+ g.setColor(MetalLookAndFeel.getInactiveControlTextColor());
+ g.drawRect(x, y, w - 2, h - 2);
+ }
+ }
+ }
+
+ /**
+ * Paints the button border for the OceanTheme.
+ *
+ * @param c the button
+ * @param g the graphics context
+ * @param x the X coordinate of the upper left corner of the painting rect
+ * @param y the Y coordinate of the upper left corner of the painting rect
+ * @param w the width of the painting rect
+ * @param h the height of the painting rect
+ */
+ private void paintOceanButtonBorder(Component c, Graphics g, int x,
+ int y, int w, int h)
+ {
ButtonModel bmodel = null;
if (c instanceof AbstractButton)
@@ -138,44 +213,31 @@ public class MetalBorders
Color darkShadow = MetalLookAndFeel.getControlDarkShadow();
Color shadow = MetalLookAndFeel.getControlShadow();
- Color light = MetalLookAndFeel.getWhite();
+ Color light = MetalLookAndFeel.getControlHighlight();
Color middle = MetalLookAndFeel.getControl();
if (c.isEnabled())
- {
- // draw dark border
- g.setColor(darkShadow);
- g.drawRect(x, y, w - 2, h - 2);
-
- if (!bmodel.isPressed())
- {
- // draw light border
- g.setColor(light);
- g.drawRect(x + 1, y + 1, w - 2, h - 2);
-
- // draw crossing pixels of both borders
- g.setColor(middle);
- g.drawRect(x + 1, y + h - 2, 0, 0);
- g.drawRect(x + w - 2, y + 1, 0, 0);
- }
- else
- {
- // draw light border
- g.setColor(light);
- g.drawLine(x + w - 1, y + 1, x + w - 1, y + h - 1);
- g.drawLine(x + 1, y + h - 1, x + w - 1, y + h - 1);
-
- // draw shadow border
- g.setColor(middle);
- g.drawLine(x + 1, y + 1, x + w - 2, y + 1);
- g.drawLine(x + 1, y + 1, x + 1, y + h - 2);
-
- // draw crossing pixels of both borders
- g.setColor(shadow);
- g.drawRect(x + 1, y + h - 2, 0, 0);
- g.drawRect(x + w - 2, y + 1, 0, 0);
- }
- }
+ {
+ if (bmodel.isPressed())
+ {
+ // draw fat border
+ g.drawLine(x + 1, y + 1, x + w - 2, y + 1);
+ g.drawLine(x + 1, y + 1, x + 1, y + h - 2);
+ }
+ else if (bmodel.isRollover())
+ {
+ g.setColor(shadow);
+ g.drawRect(x, y, w - 1, h - 1);
+ g.drawRect(x + 2, y + 2, w - 5, h - 5);
+ g.setColor(darkShadow);
+ g.drawRect(x + 1, y + 1, w - 3, h - 3);
+ }
+ else
+ {
+ g.setColor(darkShadow);
+ g.drawRect(x, y, w - 1, h - 1);
+ }
+ }
else
{
// draw disabled border
@@ -654,24 +716,23 @@ public class MetalBorders
{
JOptionPane pane = (JOptionPane) f.getContentPane();
int type = pane.getMessageType();
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
if (type == JOptionPane.QUESTION_MESSAGE)
{
- Color bc = defaults.getColor(
+ Color bc = UIManager.getColor(
"OptionPane.questionDialog.border.background");
if (bc != null)
g.setColor(bc);
}
if (type == JOptionPane.WARNING_MESSAGE)
{
- Color bc = defaults.getColor(
+ Color bc = UIManager.getColor(
"OptionPane.warningDialog.border.background");
if (bc != null)
g.setColor(bc);
}
else if (type == JOptionPane.ERROR_MESSAGE)
{
- Color bc = defaults.getColor(
+ Color bc = UIManager.getColor(
"OptionPane.errorDialog.border.background");
if (bc != null)
g.setColor(bc);
diff --git a/javax/swing/plaf/metal/MetalButtonUI.java b/javax/swing/plaf/metal/MetalButtonUI.java
index 4e148dbe9..10e511173 100644
--- a/javax/swing/plaf/metal/MetalButtonUI.java
+++ b/javax/swing/plaf/metal/MetalButtonUI.java
@@ -47,7 +47,7 @@ import java.awt.Rectangle;
import javax.swing.AbstractButton;
import javax.swing.JButton;
import javax.swing.JComponent;
-import javax.swing.UIDefaults;
+import javax.swing.SwingConstants;
import javax.swing.UIManager;
import javax.swing.plaf.ComponentUI;
import javax.swing.plaf.UIResource;
@@ -78,10 +78,9 @@ public class MetalButtonUI
public MetalButtonUI()
{
super();
- UIDefaults def = UIManager.getLookAndFeelDefaults();
- focusColor = def.getColor(getPropertyPrefix() + "focus");
- selectColor = def.getColor(getPropertyPrefix() + "select");
- disabledTextColor = def.getColor(getPropertyPrefix() + "disabledText");
+ focusColor = UIManager.getColor(getPropertyPrefix() + "focus");
+ selectColor = UIManager.getColor(getPropertyPrefix() + "select");
+ disabledTextColor = UIManager.getColor(getPropertyPrefix() + "disabledText");
}
/**
@@ -135,11 +134,8 @@ public class MetalButtonUI
public void installDefaults(AbstractButton button)
{
super.installDefaults(button);
- if (button.isRolloverEnabled())
- {
- if (button.getBorder() instanceof UIResource)
- button.setBorder(MetalBorders.getRolloverBorder());
- }
+ button.setRolloverEnabled(UIManager.getBoolean(
+ getPropertyPrefix() + "rollover"));
}
/**
@@ -148,8 +144,7 @@ public class MetalButtonUI
public void uninstallDefaults(AbstractButton button)
{
super.uninstallDefaults(button);
- if (button.getBorder() instanceof UIResource)
- button.setBorder(null);
+ button.setRolloverEnabled(false);
}
/**
@@ -192,13 +187,13 @@ public class MetalButtonUI
*/
protected void paintFocus(Graphics g, AbstractButton b, Rectangle viewRect,
Rectangle textRect, Rectangle iconRect) {
- if (b.hasFocus() && b.isFocusPainted())
+ if (b.isEnabled() && b.hasFocus() && b.isFocusPainted())
{
Color savedColor = g.getColor();
g.setColor(getFocusColor());
Rectangle focusRect = iconRect.union(textRect);
- g.drawRect(focusRect.x - 1, focusRect.y - 1,
- focusRect.width + 1, focusRect.height + 1);
+ g.drawRect(focusRect.x - 1, focusRect.y,
+ focusRect.width + 1, focusRect.height);
g.setColor(savedColor);
}
}
@@ -230,4 +225,24 @@ public class MetalButtonUI
g.drawString(text, textRect.x, textRect.y + fm.getAscent());
}
}
+
+ /**
+ * If the property <code>Button.gradient</code> is set, then a gradient is
+ * painted as background, otherwise the normal superclass behaviour is
+ * called.
+ */
+ public void update(Graphics g, JComponent c)
+ {
+ AbstractButton b = (AbstractButton) c;
+ if (b.isOpaque() && UIManager.get(getPropertyPrefix() + "gradient") != null
+ && !b.getModel().isPressed() && b.isEnabled())
+ {
+ MetalUtils.paintGradient(g, 0, 0, c.getWidth(), c.getHeight(),
+ SwingConstants.VERTICAL,
+ getPropertyPrefix() + "gradient");
+ paint(g, c);
+ }
+ else
+ super.update(g, c);
+ }
}
diff --git a/javax/swing/plaf/metal/MetalCheckBoxIcon.java b/javax/swing/plaf/metal/MetalCheckBoxIcon.java
index 6b9f31b85..fb8280e44 100644
--- a/javax/swing/plaf/metal/MetalCheckBoxIcon.java
+++ b/javax/swing/plaf/metal/MetalCheckBoxIcon.java
@@ -44,6 +44,8 @@ import java.io.Serializable;
import javax.swing.Icon;
import javax.swing.JCheckBox;
+import javax.swing.SwingConstants;
+import javax.swing.UIManager;
import javax.swing.plaf.UIResource;
/**
@@ -128,6 +130,9 @@ public class MetalCheckBoxIcon
*/
public void paintIcon(Component c, Graphics g, int x, int y)
{
+ if (UIManager.get("CheckBox.gradient") != null)
+ MetalUtils.paintGradient(g, x, y, getIconWidth(), getIconHeight(),
+ SwingConstants.VERTICAL, "CheckBox.gradient");
border.paintBorder(c, g, x, y, getIconWidth(), getIconHeight());
JCheckBox cb = (JCheckBox) c;
if (cb.isSelected())
diff --git a/javax/swing/plaf/metal/MetalComboBoxEditor.java b/javax/swing/plaf/metal/MetalComboBoxEditor.java
index c2bea9f5f..a531079cb 100644
--- a/javax/swing/plaf/metal/MetalComboBoxEditor.java
+++ b/javax/swing/plaf/metal/MetalComboBoxEditor.java
@@ -129,7 +129,7 @@ public class MetalComboBoxEditor extends BasicComboBoxEditor
}
/** The editor's border insets. */
- protected static Insets editorBorderInsets = new Insets(2, 2, 2, 2);
+ protected static Insets editorBorderInsets = new Insets(4, 2, 4, 0);
/**
* Creates a new editor.
@@ -137,7 +137,6 @@ public class MetalComboBoxEditor extends BasicComboBoxEditor
public MetalComboBoxEditor()
{
super();
- editor = new JTextField();
editor.setBorder(new MetalComboBoxEditorBorder());
}
diff --git a/javax/swing/plaf/metal/MetalComboBoxUI.java b/javax/swing/plaf/metal/MetalComboBoxUI.java
index 81bb3e768..0006b78fe 100644
--- a/javax/swing/plaf/metal/MetalComboBoxUI.java
+++ b/javax/swing/plaf/metal/MetalComboBoxUI.java
@@ -295,15 +295,58 @@ public class MetalComboBoxUI extends BasicComboBoxUI
*/
public Dimension getMinimumSize(JComponent c)
{
+ Dimension d = getDisplaySize();
MetalComboBoxButton b = (MetalComboBoxButton) arrowButton;
- Icon icon = b.getComboIcon();
Insets insets = b.getInsets();
- Dimension d = getDisplaySize();
int insetsH = insets.top + insets.bottom;
int insetsW = insets.left + insets.right;
- int iconWidth = icon.getIconWidth() + 6;
- return new Dimension(d.width + insetsW + iconWidth,
- d.height + insetsH);
+ if (!comboBox.isEditable())
+ {
+ Icon icon = b.getComboIcon();
+ int iconWidth = icon.getIconWidth() + 6;
+ return new Dimension(d.width + insetsW + iconWidth, d.height + insetsH);
+ }
+ else
+ // FIXME: the following dimensions pass most of the Mauve tests, but
+ // I don't yet understand the logic behind this...it is probably wrong
+ return new Dimension(d.width + insetsW + (d.height + insetsH) - 4,
+ d.height + insetsH + 1);
+ }
+
+ /**
+ * Configures the editor for this combo box.
+ */
+ public void configureEditor()
+ {
+ ComboBoxEditor cbe = comboBox.getEditor();
+ if (cbe != null)
+ {
+ cbe.getEditorComponent().setFont(comboBox.getFont());
+ cbe.setItem(comboBox.getSelectedItem());
+ cbe.addActionListener(comboBox);
+ }
}
+ /**
+ * Unconfigures the editor for this combo box.
+ */
+ public void unconfigureEditor()
+ {
+ ComboBoxEditor cbe = comboBox.getEditor();
+ if (cbe != null)
+ {
+ cbe.getEditorComponent().setFont(null);
+ cbe.setItem(null);
+ cbe.removeActionListener(comboBox);
+ }
+ }
+
+ /**
+ * Lays out the ComboBox
+ */
+ public void layoutComboBox(Container parent,
+ MetalComboBoxUI.MetalComboBoxLayoutManager manager)
+ {
+ manager.layoutContainer(parent);
+ }
}
diff --git a/javax/swing/plaf/metal/MetalFileChooserUI.java b/javax/swing/plaf/metal/MetalFileChooserUI.java
index 3a2e1c135..d6ede95c4 100644
--- a/javax/swing/plaf/metal/MetalFileChooserUI.java
+++ b/javax/swing/plaf/metal/MetalFileChooserUI.java
@@ -38,39 +38,206 @@ exception statement from your version. */
package javax.swing.plaf.metal;
+import java.awt.BorderLayout;
import java.awt.Component;
+import java.awt.Container;
+import java.awt.Dimension;
+import java.awt.GridLayout;
+import java.awt.Insets;
+import java.awt.LayoutManager;
+import java.awt.Rectangle;
+import java.awt.Window;
import java.awt.event.ActionEvent;
+import java.awt.event.MouseAdapter;
+import java.awt.event.MouseEvent;
+
import java.beans.PropertyChangeEvent;
import java.beans.PropertyChangeListener;
+
import java.io.File;
-import java.util.List;
import javax.swing.AbstractAction;
import javax.swing.AbstractListModel;
+import javax.swing.ActionMap;
+import javax.swing.BorderFactory;
+import javax.swing.ButtonGroup;
import javax.swing.ComboBoxModel;
import javax.swing.DefaultListCellRenderer;
+import javax.swing.Icon;
+import javax.swing.JButton;
+import javax.swing.JComboBox;
import javax.swing.JComponent;
+import javax.swing.JDialog;
import javax.swing.JFileChooser;
+import javax.swing.JLabel;
import javax.swing.JList;
+import javax.swing.JPanel;
+import javax.swing.JScrollPane;
+import javax.swing.JTextField;
+import javax.swing.JToggleButton;
+import javax.swing.ListSelectionModel;
+import javax.swing.SwingUtilities;
import javax.swing.UIManager;
+import javax.swing.event.ListSelectionEvent;
+import javax.swing.event.ListSelectionListener;
import javax.swing.filechooser.FileFilter;
import javax.swing.filechooser.FileSystemView;
import javax.swing.filechooser.FileView;
import javax.swing.plaf.ComponentUI;
import javax.swing.plaf.basic.BasicFileChooserUI;
+import java.util.List;
+
/**
* A UI delegate for the {@link JFileChooser} component. This class is only
* partially implemented and is not usable yet.
*/
-public class MetalFileChooserUI extends BasicFileChooserUI
+public class MetalFileChooserUI
+ extends BasicFileChooserUI
{
+
+ /**
+ * A property change listener.
+ */
+ class MetalFileChooserPropertyChangeListener
+ implements PropertyChangeListener
+ {
+ /**
+ * Default constructor.
+ */
+ public MetalFileChooserPropertyChangeListener()
+ {
+ }
+
+ /**
+ * Handles a property change event.
+ *
+ * @param e the event.
+ */
+ public void propertyChange(PropertyChangeEvent e)
+ {
+ JFileChooser filechooser = getFileChooser();
+
+ String n = e.getPropertyName();
+ if (n.equals(JFileChooser.MULTI_SELECTION_ENABLED_CHANGED_PROPERTY))
+ {
+ if (filechooser.isMultiSelectionEnabled())
+ fileList.setSelectionMode(ListSelectionModel.MULTIPLE_INTERVAL_SELECTION);
+ else
+ fileList.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);
+ }
+ else if (n.equals(JFileChooser.SELECTED_FILE_CHANGED_PROPERTY))
+ {
+ File file = filechooser.getSelectedFile();
+ if (file == null)
+ setFileName(null);
+ else
+ setFileName(file.getName());
+ int index = -1;
+ index = getModel().indexOf(file);
+ if (index >= 0)
+ {
+ fileList.setSelectedIndex(index);
+ fileList.ensureIndexIsVisible(index);
+ fileList.revalidate();
+ fileList.repaint();
+ }
+ }
+
+ else if (n.equals(JFileChooser.DIRECTORY_CHANGED_PROPERTY))
+ {
+ fileList.clearSelection();
+ fileList.revalidate();
+ fileList.repaint();
+ setDirectorySelected(false);
+ File currentDirectory = filechooser.getCurrentDirectory();
+ setDirectory(currentDirectory);
+ boolean hasParent = (currentDirectory.getParentFile() != null);
+ getChangeToParentDirectoryAction().setEnabled(hasParent);
+ }
+
+ else if (n.equals(JFileChooser.CHOOSABLE_FILE_FILTER_CHANGED_PROPERTY))
+ {
+ filterModel.propertyChange(e);
+ }
+ else if (n.equals(JFileChooser.FILE_FILTER_CHANGED_PROPERTY))
+ {
+ filterModel.propertyChange(e);
+ }
+ else if (n.equals(JFileChooser.DIALOG_TYPE_CHANGED_PROPERTY)
+ || n.equals(JFileChooser.DIALOG_TITLE_CHANGED_PROPERTY))
+ {
+ Window owner = SwingUtilities.windowForComponent(filechooser);
+ if (owner instanceof JDialog)
+ ((JDialog) owner).setTitle(getDialogTitle(filechooser));
+ approveButton.setText(getApproveButtonText(filechooser));
+ approveButton.setToolTipText(
+ getApproveButtonToolTipText(filechooser));
+ approveButton.setMnemonic(getApproveButtonMnemonic(filechooser));
+ }
+
+ else if (n.equals(JFileChooser.APPROVE_BUTTON_TEXT_CHANGED_PROPERTY))
+ approveButton.setText(getApproveButtonText(filechooser));
+
+ else if (n.equals(
+ JFileChooser.APPROVE_BUTTON_TOOL_TIP_TEXT_CHANGED_PROPERTY))
+ approveButton.setToolTipText(getApproveButtonToolTipText(filechooser));
+
+ else if (n.equals(JFileChooser.APPROVE_BUTTON_MNEMONIC_CHANGED_PROPERTY))
+ approveButton.setMnemonic(getApproveButtonMnemonic(filechooser));
+
+ else if (n.equals(
+ JFileChooser.CONTROL_BUTTONS_ARE_SHOWN_CHANGED_PROPERTY))
+ {
+ if (filechooser.getControlButtonsAreShown())
+ {
+ topPanel.add(controls, BorderLayout.EAST);
+ }
+ else
+ topPanel.remove(controls);
+ topPanel.revalidate();
+ topPanel.repaint();
+ topPanel.doLayout();
+ }
+
+ else if (n.equals(
+ JFileChooser.ACCEPT_ALL_FILE_FILTER_USED_CHANGED_PROPERTY))
+ {
+ if (filechooser.isAcceptAllFileFilterUsed())
+ filechooser.addChoosableFileFilter(
+ getAcceptAllFileFilter(filechooser));
+ else
+ filechooser.removeChoosableFileFilter(
+ getAcceptAllFileFilter(filechooser));
+ }
+
+ else if (n.equals(JFileChooser.ACCESSORY_CHANGED_PROPERTY))
+ {
+ JComponent old = (JComponent) e.getOldValue();
+ if (old != null)
+ getAccessoryPanel().remove(old);
+ JComponent newval = (JComponent) e.getNewValue();
+ if (newval != null)
+ getAccessoryPanel().add(newval);
+ }
+
+ if (n.equals(JFileChooser.DIRECTORY_CHANGED_PROPERTY)
+ || n.equals(JFileChooser.FILE_FILTER_CHANGED_PROPERTY)
+ || n.equals(JFileChooser.FILE_HIDING_CHANGED_PROPERTY))
+ rescanCurrentDirectory(filechooser);
+
+ filechooser.revalidate();
+ filechooser.repaint();
+ }
+ };
+
/**
* A combo box model containing the selected directory and all its parent
* directories.
*/
- protected class DirectoryComboBoxModel extends AbstractListModel
+ protected class DirectoryComboBoxModel
+ extends AbstractListModel
implements ComboBoxModel
{
/** Storage for the items in the model. */
@@ -161,7 +328,8 @@ public class MetalFileChooserUI extends BasicFileChooserUI
/**
* Handles changes to the selection in the directory combo box.
*/
- protected class DirectoryComboBoxAction extends AbstractAction
+ protected class DirectoryComboBoxAction
+ extends AbstractAction
{
/**
* Creates a new action.
@@ -184,9 +352,60 @@ public class MetalFileChooserUI extends BasicFileChooserUI
}
/**
+ * A renderer for the items in the directory combo box.
+ */
+ class DirectoryComboBoxRenderer
+ extends DefaultListCellRenderer
+ {
+ /**
+ * Creates a new renderer.
+ */
+ public DirectoryComboBoxRenderer(JFileChooser fc)
+ {
+ }
+
+ /**
+ * Returns a component that can be used to paint the given value within
+ * the list.
+ *
+ * @param list the list.
+ * @param value the value (a {@link File}).
+ * @param index the item index.
+ * @param isSelected is the item selected?
+ * @param cellHasFocus does the list cell have focus?
+ *
+ * @return The list cell renderer.
+ */
+ public Component getListCellRendererComponent(JList list, Object value,
+ int index, boolean isSelected, boolean cellHasFocus)
+ {
+ FileView fileView = getFileView(getFileChooser());
+ File file = (File) value;
+ setIcon(fileView.getIcon(file));
+ setText(fileView.getName(file));
+
+ if (isSelected)
+ {
+ setBackground(list.getSelectionBackground());
+ setForeground(list.getSelectionForeground());
+ }
+ else
+ {
+ setBackground(list.getBackground());
+ setForeground(list.getForeground());
+ }
+
+ setEnabled(list.isEnabled());
+ setFont(list.getFont());
+ return this;
+ }
+ }
+
+ /**
* A renderer for the files and directories in the file chooser.
*/
- protected class FileRenderer extends DefaultListCellRenderer
+ protected class FileRenderer
+ extends DefaultListCellRenderer
{
/**
@@ -215,6 +434,7 @@ public class MetalFileChooserUI extends BasicFileChooserUI
File f = (File) value;
setText(v.getName(f));
setIcon(v.getIcon(f));
+ setOpaque(true);
if (isSelected)
{
setBackground(list.getSelectionBackground());
@@ -249,7 +469,7 @@ public class MetalFileChooserUI extends BasicFileChooserUI
protected FileFilter[] filters;
/** The index of the selected file filter. */
- private int selectedIndex;
+ private Object selected;
/**
* Creates a new model.
@@ -258,7 +478,7 @@ public class MetalFileChooserUI extends BasicFileChooserUI
{
filters = new FileFilter[1];
filters[0] = getAcceptAllFileFilter(getFileChooser());
- selectedIndex = 0;
+ selected = filters[0];
}
/**
@@ -270,11 +490,11 @@ public class MetalFileChooserUI extends BasicFileChooserUI
{
if (e.getPropertyName().equals(JFileChooser.FILE_FILTER_CHANGED_PROPERTY))
{
- selectedIndex = -1;
- FileFilter selected = (FileFilter) e.getNewValue();
- for (int i = 0; i < filters.length; i++)
- if (filters[i].equals(selected))
- selectedIndex = i;
+ JFileChooser fc = getFileChooser();
+ FileFilter[] choosableFilters = fc.getChoosableFileFilters();
+ filters = choosableFilters;
+ fireContentsChanged(this, 0, filters.length);
+ selected = e.getNewValue();
fireContentsChanged(this, -1, -1);
}
else if (e.getPropertyName().equals(
@@ -291,13 +511,15 @@ public class MetalFileChooserUI extends BasicFileChooserUI
/**
* Sets the selected filter.
*
- * @param filter the filter.
+ * @param filter the filter (<code>null</code> ignored).
*/
public void setSelectedItem(Object filter)
{
- // change the filter in the file chooser and let the property change
- // event trigger the change to the selected item
- getFileChooser().setFileFilter((FileFilter) filter);
+ if (filter != null)
+ {
+ selected = filter;
+ fireContentsChanged(this, -1, -1);
+ }
}
/**
@@ -307,9 +529,7 @@ public class MetalFileChooserUI extends BasicFileChooserUI
*/
public Object getSelectedItem()
{
- if (selectedIndex >= 0)
- return filters[selectedIndex];
- return null;
+ return selected;
}
/**
@@ -339,7 +559,8 @@ public class MetalFileChooserUI extends BasicFileChooserUI
/**
* A renderer for the items in the file filter combo box.
*/
- public class FilterComboBoxRenderer extends DefaultListCellRenderer
+ public class FilterComboBoxRenderer
+ extends DefaultListCellRenderer
{
/**
* Creates a new renderer.
@@ -359,20 +580,220 @@ public class MetalFileChooserUI extends BasicFileChooserUI
* @param isSelected is the item selected?
* @param cellHasFocus does the list cell have focus?
*
- * @return A component.
+ * @return This component as the renderer.
*/
public Component getListCellRendererComponent(JList list, Object value,
int index, boolean isSelected, boolean cellHasFocus)
{
+ super.getListCellRendererComponent(list, value, index, isSelected,
+ cellHasFocus);
FileFilter filter = (FileFilter) value;
- return super.getListCellRendererComponent(list, filter.getDescription(),
- index, isSelected, cellHasFocus);
+ setText(filter.getDescription());
+ return this;
}
}
+ /**
+ * A listener for selection events in the file list.
+ *
+ * @see #createListSelectionListener(JFileChooser)
+ */
+ class MetalFileChooserSelectionListener
+ implements ListSelectionListener
+ {
+ /**
+ * Creates a new <code>SelectionListener</code> object.
+ */
+ protected MetalFileChooserSelectionListener()
+ {
+ // Do nothing here.
+ }
+
+ /**
+ * Makes changes to different properties when
+ * a value has changed in the filechooser's selection.
+ *
+ * @param e - the list selection event that occured.
+ */
+ public void valueChanged(ListSelectionEvent e)
+ {
+ File f = (File) fileList.getSelectedValue();
+ if (f == null)
+ return;
+ JFileChooser filechooser = getFileChooser();
+ if (! filechooser.isTraversable(f))
+ filechooser.setSelectedFile(f);
+ else
+ filechooser.setSelectedFile(null);
+ }
+ }
+
+ /**
+ * A mouse listener for the {@link JFileChooser}.
+ * This listener is used for editing filenames.
+ */
+ protected class SingleClickListener
+ extends MouseAdapter
+ {
+
+ /** Stores instance of the list */
+ JList list;
+
+ /**
+ * Stores the current file that is being edited.
+ * It is null if nothing is currently being edited.
+ */
+ File editFile;
+
+ /** The current file chooser. */
+ JFileChooser fc;
+
+ /** The last file selected. */
+ Object lastSelected;
+
+ /** The textfield used for editing. */
+ JTextField editField;
+
+ /**
+ * Creates a new listener.
+ *
+ * @param list the directory/file list.
+ */
+ public SingleClickListener(JList list)
+ {
+ this.list = list;
+ editFile = null;
+ fc = getFileChooser();
+ lastSelected = null;
+ }
+
+ /**
+ * Receives notification of a mouse click event.
+ *
+ * @param e the event.
+ */
+ public void mouseClicked(MouseEvent e)
+ {
+ if (e.getClickCount() == 1)
+ {
+ int index = list.locationToIndex(e.getPoint());
+ File[] sf = fc.getSelectedFiles();
+ if ((!fc.isMultiSelectionEnabled() || (sf != null && sf.length <= 1))
+ && index >= 0 && editFile == null && list.isSelectedIndex(index))
+ {
+ Object tmp = list.getModel().getElementAt(index);
+ if (lastSelected != null && lastSelected.equals(tmp))
+ editFile(index);
+ lastSelected = tmp;
+ }
+ else if (editFile != null)
+ {
+ completeEditing();
+ editFile = null;
+ lastSelected = null;
+ }
+ }
+ }
+
+ /**
+ * Sets up the text editor for the current file.
+ *
+ * @param index -
+ * the current index of the item in the list to be edited.
+ */
+ private void editFile(int index)
+ {
+ list.ensureIndexIsVisible(index);
+ editFile = (File) list.getModel().getElementAt(index);
+ if (editFile.canWrite())
+ {
+ Rectangle bounds = list.getCellBounds(index, index);
+ Icon icon = getFileView(fc).getIcon(editFile);
+ editField = new JTextField(editFile.getName());
+ // FIXME: add action listener for typing
+ // FIXME: painting for textfield is messed up when typing
+ list.add(editField);
+ editField.requestFocus();
+ editField.selectAll();
+
+ if (icon != null)
+ bounds.x += icon.getIconWidth() + 4;
+ editField.setBounds(bounds);
+ }
+ else
+ {
+ editField = null;
+ editFile = null;
+ lastSelected = null;
+ }
+ }
+
+ /**
+ * Completes the editing.
+ */
+ private void completeEditing()
+ {
+ if (editField != null)
+ {
+ String text = editField.getText();
+ if (text != null && !text.equals(""))
+ editFile.renameTo(new File(text));
+ list.remove(editField);
+ list.revalidate();
+ list.repaint();
+ }
+ }
+ }
+
+ /** The text for a label describing the directory combo box. */
+ private String directoryLabel;
+
+ private JComboBox directoryComboBox;
+
/** The model for the directory combo box. */
DirectoryComboBoxModel directoryModel;
+ /** The text for a label describing the file text field. */
+ private String fileLabel;
+
+ /** The file name text field. */
+ private JTextField fileTextField;
+
+ /** The text for a label describing the filter combo box. */
+ private String filterLabel;
+
+ /**
+ * The top panel (contains the directory combo box and the control buttons).
+ */
+ private JPanel topPanel;
+
+ /** A panel containing the control buttons ('up', 'home' etc.). */
+ private JPanel controls;
+
+ /**
+ * The panel that contains the filename field and the filter combobox.
+ */
+ private JPanel bottomPanel;
+
+ /**
+ * The panel that contains the 'Open' (or 'Save') and 'Cancel' buttons.
+ */
+ private JPanel buttonPanel;
+
+ private JButton approveButton;
+
+ /** The file list. */
+ private JList fileList;
+
+ /** The panel containing the file list. */
+ private JPanel fileListPanel;
+
+ /** The filter combo box model. */
+ private FilterComboBoxModel filterModel;
+
+ /** The action map. */
+ private ActionMap actionMap;
+
/**
* A factory method that returns a UI delegate for the specified
* component.
@@ -393,9 +814,303 @@ public class MetalFileChooserUI extends BasicFileChooserUI
public MetalFileChooserUI(JFileChooser filechooser)
{
super(filechooser);
+ bottomPanel = new JPanel(new GridLayout(3, 2));
+ buttonPanel = new JPanel();
+ }
+
+ public void installUI(JComponent c)
+ {
+ super.installUI(c);
+ actionMap = createActionMap();
+ }
+
+ public void uninstallUI(JComponent c)
+ {
+ super.uninstallUI(c);
+ actionMap = null;
+ }
+
+ /**
+ * Installs the sub-components of the file chooser.
+ *
+ * @param fc the file chooser component.
+ */
+ public void installComponents(JFileChooser fc)
+ {
+ fc.setLayout(new BorderLayout());
+ topPanel = new JPanel(new BorderLayout());
+ topPanel.add(new JLabel(directoryLabel), BorderLayout.WEST);
+ this.controls = new JPanel();
+ addControlButtons();
+
+ JPanel dirPanel = new JPanel(new VerticalMidLayout());
+ dirPanel.setBorder(BorderFactory.createEmptyBorder(0, 5, 0, 0));
+ directoryModel = createDirectoryComboBoxModel(fc);
+ directoryComboBox = new JComboBox(directoryModel);
+ directoryComboBox.setRenderer(createDirectoryComboBoxRenderer(fc));
+ dirPanel.add(directoryComboBox);
+ topPanel.add(dirPanel);
+ topPanel.add(controls, BorderLayout.EAST);
+ fc.add(topPanel, BorderLayout.NORTH);
+ fileListPanel = createList(fc);
+ fc.add(fileListPanel);
+ JPanel bottomPanel = getBottomPanel();
+ filterModel = createFilterComboBoxModel();
+ JComboBox fileFilterCombo = new JComboBox(filterModel);
+ fileFilterCombo.setRenderer(createFilterComboBoxRenderer());
+
+ fileTextField = new JTextField();
+ JPanel fileNamePanel = new JPanel(new VerticalMidLayout());
+ fileNamePanel.add(fileTextField);
+ JPanel row1 = new JPanel(new BorderLayout());
+ row1.add(new JLabel(this.fileLabel), BorderLayout.WEST);
+ row1.add(fileNamePanel);
+ bottomPanel.add(row1);
+
+ JPanel filterPanel = new JPanel(new VerticalMidLayout());
+ filterPanel.add(fileFilterCombo);
+ JPanel row2 = new JPanel(new BorderLayout());
+ row2.add(new JLabel(this.filterLabel), BorderLayout.WEST);
+ row2.add(filterPanel);
+ bottomPanel.add(row2);
+ JPanel buttonPanel = new JPanel(new ButtonLayout());
+ buttonPanel.setBorder(BorderFactory.createEmptyBorder(4, 4, 4, 0));
+
+ approveButton = new JButton(getApproveSelectionAction());
+ approveButton.setText(getApproveButtonText(fc));
+ approveButton.setToolTipText(getApproveButtonToolTipText(fc));
+ approveButton.setMnemonic(getApproveButtonMnemonic(fc));
+ buttonPanel.add(approveButton);
+
+ JButton cancelButton = new JButton(getCancelSelectionAction());
+ cancelButton.setText(cancelButtonText);
+ cancelButton.setToolTipText(cancelButtonToolTipText);
+ cancelButton.setMnemonic(cancelButtonMnemonic);
+ buttonPanel.add(cancelButton);
+ bottomPanel.add(buttonPanel);
+ fc.add(bottomPanel, BorderLayout.SOUTH);
+ }
+
+ /**
+ * Uninstalls the components added by
+ * {@link #installComponents(JFileChooser)}.
+ *
+ * @param fc the file chooser.
+ */
+ public void uninstallComponents(JFileChooser fc)
+ {
+ fc.remove(bottomPanel);
+ bottomPanel = null;
+ fc.remove(fileListPanel);
+ fileListPanel = null;
+ fc.remove(topPanel);
+ topPanel = null;
+
+ directoryModel = null;
+ fileTextField = null;
+ directoryComboBox = null;
+ }
+
+ /**
+ * Returns the panel that contains the 'Open' (or 'Save') and 'Cancel'
+ * buttons.
+ *
+ * @return The panel.
+ */
+ protected JPanel getButtonPanel()
+ {
+ return buttonPanel;
+ }
+
+ /**
+ * Creates and returns a new panel that will be used for the controls at
+ * the bottom of the file chooser.
+ *
+ * @return A new panel.
+ */
+ protected JPanel getBottomPanel()
+ {
+ if (bottomPanel == null)
+ bottomPanel = new JPanel(new GridLayout(3, 2));
+ return bottomPanel;
+ }
+
+ /**
+ * Fetches localised strings for use by the labels and buttons on the
+ * file chooser.
+ *
+ * @param fc the file chooser.
+ */
+ protected void installStrings(JFileChooser fc)
+ {
+ super.installStrings(fc);
+ directoryLabel = "Look In: ";
+ fileLabel = "File Name: ";
+ filterLabel = "Files of Type: ";
+
+ this.cancelButtonMnemonic = 0;
+ this.cancelButtonText = "Cancel";
+ this.cancelButtonToolTipText = "Abort file chooser dialog";
+
+ this.directoryOpenButtonMnemonic = 0;
+ this.directoryOpenButtonText = "Open";
+ this.directoryOpenButtonToolTipText = "Open selected directory";
+
+ this.helpButtonMnemonic = 0;
+ this.helpButtonText = "Help";
+ this.helpButtonToolTipText = "Filechooser help";
+
+ this.openButtonMnemonic = 0;
+ this.openButtonText = "Open";
+ this.openButtonToolTipText = "Open selected file";
+
+ this.saveButtonMnemonic = 0;
+ this.saveButtonText = "Save";
+ this.saveButtonToolTipText = "Save selected file";
+
+ this.updateButtonMnemonic = 0;
+ this.updateButtonText = "Update";
+ this.updateButtonToolTipText = "Update directory listing";
+ }
+
+ /**
+ * Installs the listeners required.
+ *
+ * @param fc the file chooser.
+ */
+ protected void installListeners(JFileChooser fc)
+ {
+ directoryComboBox.setAction(new DirectoryComboBoxAction());
+ fileList.addListSelectionListener(createListSelectionListener(fc));
+ fileList.addMouseListener(this.createDoubleClickListener(fc, fileList));
+ fileList.addMouseListener(new SingleClickListener(fileList));
+ fc.addPropertyChangeListener(filterModel);
+ super.installListeners(fc);
+ }
+
+ protected void uninstallListeners(JFileChooser fc)
+ {
+ super.uninstallListeners(fc);
+ fc.removePropertyChangeListener(filterModel);
+ }
+
+ protected ActionMap getActionMap()
+ {
+ if (actionMap == null)
+ actionMap = createActionMap();
+ return actionMap;
+ }
+
+ /**
+ * Creates and returns an action map.
+ *
+ * @return The action map.
+ */
+ protected ActionMap createActionMap()
+ {
+ ActionMap map = new ActionMap();
+ map.put("approveSelection", getApproveSelectionAction());
+ map.put("cancelSelection", null); // FIXME: implement this one
+ map.put("Go Up", getChangeToParentDirectoryAction());
+ return map;
+ }
+
+ /**
+ * Creates a panel containing a list of files.
+ *
+ * @param fc the file chooser.
+ *
+ * @return A panel.
+ */
+ protected JPanel createList(JFileChooser fc)
+ {
+ JPanel panel = new JPanel(new BorderLayout());
+ fileList = new JList(getModel());
+ fileList.setLayoutOrientation(JList.VERTICAL_WRAP);
+ fileList.setVisibleRowCount(0);
+ fileList.setCellRenderer(new FileRenderer());
+ panel.add(new JScrollPane(fileList));
+ return panel;
+ }
+
+ /**
+ * Creates a panel containing a table within a scroll pane.
+ *
+ * @param fc the file chooser.
+ *
+ * @return The details view.
+ */
+ protected JPanel createDetailsView(JFileChooser fc)
+ {
+ // FIXME: implement this. The details view is a panel containing a table
+ // inside a JScrollPane - it gets displayed when the user clicks on the
+ // "details" button.
+ return new JPanel();
+ }
+
+ /**
+ * Creates a listener that monitors selections in the directory/file list
+ * and keeps the {@link JFileChooser} component up to date.
+ *
+ * @param fc the file chooser.
+ *
+ * @return The listener.
+ *
+ * @see #installListeners(JFileChooser)
+ */
+ public ListSelectionListener createListSelectionListener(JFileChooser fc)
+ {
+ return new MetalFileChooserSelectionListener();
}
/**
+ * Returns the preferred size for the file chooser component.
+ *
+ * @return The preferred size.
+ */
+ public Dimension getPreferredSize(JComponent c)
+ {
+ // FIXME: not likely to be a fixed value
+ return new Dimension(500, 326);
+ }
+
+ /**
+ * Returns the minimum size for the file chooser component.
+ *
+ * @return The minimum size.
+ */
+ public Dimension getMinimumSize(JComponent c)
+ {
+ // FIXME: not likely to be a fixed value
+ return new Dimension(506, 326);
+ }
+
+ /**
+ * Returns the maximum size for the file chooser component.
+ *
+ * @return The maximum size.
+ */
+ public Dimension getMaximumSize(JComponent c)
+ {
+ return new Dimension(Integer.MAX_VALUE, Integer.MAX_VALUE);
+ }
+
+ /**
+ * Creates a property change listener that monitors the {@link JFileChooser}
+ * for property change events and updates the component display accordingly.
+ *
+ * @param fc the file chooser.
+ *
+ * @return The property change listener.
+ *
+ * @see #installListeners(JFileChooser)
+ */
+ public PropertyChangeListener createPropertyChangeListener(JFileChooser fc)
+ {
+ return new MetalFileChooserPropertyChangeListener();
+ }
+
+ /**
* Creates and returns a new instance of {@link DirectoryComboBoxModel}.
*
* @return A new instance of {@link DirectoryComboBoxModel}.
@@ -407,6 +1122,20 @@ public class MetalFileChooserUI extends BasicFileChooserUI
}
/**
+ * Creates a new instance of the renderer used in the directory
+ * combo box.
+ *
+ * @param fc the file chooser.
+ *
+ * @return The renderer.
+ */
+ protected DirectoryComboBoxRenderer createDirectoryComboBoxRenderer(
+ JFileChooser fc)
+ {
+ return new DirectoryComboBoxRenderer(fc);
+ }
+
+ /**
* Creates and returns a new instance of {@link FilterComboBoxModel}.
*
* @return A new instance of {@link FilterComboBoxModel}.
@@ -427,4 +1156,305 @@ public class MetalFileChooserUI extends BasicFileChooserUI
return new FilterComboBoxRenderer();
}
+ /**
+ * Adds the control buttons ('up', 'home' etc.) to the panel.
+ */
+ protected void addControlButtons()
+ {
+ JButton upButton = new JButton(getChangeToParentDirectoryAction());
+ upButton.setText(null);
+ upButton.setIcon(this.upFolderIcon);
+ upButton.setMargin(new Insets(0, 0, 0, 0));
+ controls.add(upButton);
+
+ JButton homeButton = new JButton(getGoHomeAction());
+ homeButton.setText(null);
+ homeButton.setIcon(this.homeFolderIcon);
+ homeButton.setMargin(new Insets(0, 0, 0, 0));
+ controls.add(homeButton);
+
+ JButton newFolderButton = new JButton(getNewFolderAction());
+ newFolderButton.setText(null);
+ newFolderButton.setIcon(this.newFolderIcon);
+ newFolderButton.setMargin(new Insets(0, 0, 0, 0));
+ controls.add(newFolderButton);
+
+ JToggleButton listButton = new JToggleButton();
+ listButton.setIcon(this.listViewIcon);
+ listButton.setMargin(new Insets(0, 0, 0, 0));
+ // FIXME: this button needs an action that handles a click
+ controls.add(listButton);
+
+ JToggleButton detailButton = new JToggleButton(this.detailsViewIcon);
+ detailButton.setMargin(new Insets(0, 0, 0, 0));
+ // FIXME: this button needs an action that handles a click
+ controls.add(detailButton);
+
+ ButtonGroup buttonGroup = new ButtonGroup();
+ buttonGroup.add(listButton);
+ buttonGroup.add(detailButton);
+ }
+
+ protected void removeControlButtons()
+ {
+ controls.removeAll();
+ }
+
+ public void ensureFileIsVisible(JFileChooser fc, File f)
+ {
+ // FIXME: do something here - probably this figures out whether the
+ // list or table view is current, and forwards the request to the
+ // appropriate one...
+ super.ensureFileIsVisible(fc, f);
+ }
+
+ public void rescanCurrentDirectory(JFileChooser fc)
+ {
+ // FIXME: this will need to take into account whether the list view or
+ // the table view is current
+ directoryModel.setSelectedItem(fc.getCurrentDirectory());
+ getModel().validateFileCache();
+ fileList.revalidate();
+ }
+
+ /**
+ * Returns the file name in the text field.
+ *
+ * @return The file name.
+ */
+ public String getFileName()
+ {
+ String result = null;
+ if (fileTextField != null)
+ result = fileTextField.getText();
+ return result;
+ }
+
+ /**
+ * Sets the file name in the text field.
+ *
+ * @param filename the file name.
+ */
+ public void setFileName(String filename)
+ {
+ fileTextField.setText(filename);
+ }
+
+ protected void setDirectorySelected(boolean directorySelected)
+ {
+ // FIXME: do something here
+ super.setDirectorySelected(directorySelected);
+ }
+
+ public String getDirectoryName()
+ {
+ // FIXME: do something here
+ return super.getDirectoryName();
+ }
+
+ public void setDirectoryName(String dirname)
+ {
+ // FIXME: do something here
+ super.setDirectoryName(dirname);
+ }
+
+ public void valueChanged(ListSelectionEvent e)
+ {
+ // FIXME: implement
+ }
+
+ /**
+ * Returns the approve button.
+ *
+ * @return The approve button.
+ */
+ protected JButton getApproveButton(JFileChooser fc)
+ {
+ return approveButton;
+ }
+
+ /**
+ * A layout manager that is used to arrange the subcomponents of the
+ * {@link JFileChooser}.
+ */
+ class VerticalMidLayout implements LayoutManager
+ {
+ /**
+ * Performs the layout.
+ *
+ * @param parent the container.
+ */
+ public void layoutContainer(Container parent)
+ {
+ int count = parent.getComponentCount();
+ if (count > 0)
+ {
+ Insets insets = parent.getInsets();
+ Component c = parent.getComponent(0);
+ Dimension prefSize = c.getPreferredSize();
+ int h = parent.getHeight() - insets.top - insets.bottom;
+ int adj = Math.max(0, (h - prefSize.height) / 2);
+ c.setBounds(insets.left, insets.top + adj, parent.getWidth()
+ - insets.left - insets.right,
+ (int) Math.min(prefSize.getHeight(), h));
+ }
+ }
+
+ /**
+ * Returns the minimum layout size.
+ *
+ * @param parent the container.
+ *
+ * @return The minimum layout size.
+ */
+ public Dimension minimumLayoutSize(Container parent)
+ {
+ return preferredLayoutSize(parent);
+ }
+
+ /**
+ * Returns the preferred layout size.
+ *
+ * @param parent the container.
+ *
+ * @return The preferred layout size.
+ */
+ public Dimension preferredLayoutSize(Container parent)
+ {
+ if (parent.getComponentCount() > 0)
+ {
+ return parent.getComponent(0).getPreferredSize();
+ }
+ else return null;
+ }
+
+ /**
+ * This layout manager does not need to track components, so this
+ * method does nothing.
+ *
+ * @param name the name the component is associated with.
+ * @param component the component.
+ */
+ public void addLayoutComponent(String name, Component component)
+ {
+ // do nothing
+ }
+
+ /**
+ * This layout manager does not need to track components, so this
+ * method does nothing.
+ *
+ * @param component the component.
+ */
+ public void removeLayoutComponent(Component component) {
+ // do nothing
+ }
+ }
+
+ /**
+ * A layout manager that is used to arrange buttons for the
+ * {@link JFileChooser}.
+ */
+ class ButtonLayout implements LayoutManager
+ {
+ static final int GAP = 4;
+
+ /**
+ * Performs the layout.
+ *
+ * @param parent the container.
+ */
+ public void layoutContainer(Container parent)
+ {
+ int count = parent.getComponentCount();
+ if (count > 0)
+ {
+ // first find the widest button
+ int maxW = 0;
+ for (int i = 0; i < count; i++)
+ {
+ Component c = parent.getComponent(i);
+ Dimension prefSize = c.getPreferredSize();
+ maxW = Math.max(prefSize.width, maxW);
+ }
+
+ // then position the buttons
+ Insets insets = parent.getInsets();
+ int availableH = parent.getHeight() - insets.top - insets.bottom;
+ int currentX = parent.getWidth() - insets.right;
+ for (int i = count - 1; i >= 0; i--)
+ {
+ Component c = parent.getComponent(i);
+ Dimension prefSize = c.getPreferredSize();
+ int adj = Math.max(0, (availableH - prefSize.height) / 2);
+ currentX = currentX - prefSize.width;
+ c.setBounds(currentX, insets.top + adj, prefSize.width,
+ (int) Math.min(prefSize.getHeight(), availableH));
+ currentX = currentX - GAP;
+ }
+ }
+ }
+
+ /**
+ * Returns the minimum layout size.
+ *
+ * @param parent the container.
+ *
+ * @return The minimum layout size.
+ */
+ public Dimension minimumLayoutSize(Container parent)
+ {
+ return preferredLayoutSize(parent);
+ }
+
+ /**
+ * Returns the preferred layout size.
+ *
+ * @param parent the container.
+ *
+ * @return The preferred layout size.
+ */
+ public Dimension preferredLayoutSize(Container parent)
+ {
+ Insets insets = parent.getInsets();
+ int maxW = 0;
+ int maxH = 0;
+ int count = parent.getComponentCount();
+ if (count > 0)
+ {
+ for (int i = 0; i < count; i++)
+ {
+ Component c = parent.getComponent(i);
+ Dimension d = c.getPreferredSize();
+ maxW = Math.max(d.width, maxW);
+ maxH = Math.max(d.height, maxH);
+ }
+ }
+ return new Dimension(maxW * count + GAP * (count - 1) + insets.left
+ + insets.right, maxH + insets.top + insets.bottom);
+ }
+
+ /**
+ * This layout manager does not need to track components, so this
+ * method does nothing.
+ *
+ * @param name the name the component is associated with.
+ * @param component the component.
+ */
+ public void addLayoutComponent(String name, Component component)
+ {
+ // do nothing
+ }
+
+ /**
+ * This layout manager does not need to track components, so this
+ * method does nothing.
+ *
+ * @param component the component.
+ */
+ public void removeLayoutComponent(Component component) {
+ // do nothing
+ }
+ }
+
}
diff --git a/javax/swing/plaf/metal/MetalIconFactory.java b/javax/swing/plaf/metal/MetalIconFactory.java
index 6f4feccfc..0b644f300 100644
--- a/javax/swing/plaf/metal/MetalIconFactory.java
+++ b/javax/swing/plaf/metal/MetalIconFactory.java
@@ -52,6 +52,8 @@ import javax.swing.JInternalFrame;
import javax.swing.JRadioButton;
import javax.swing.JRadioButtonMenuItem;
import javax.swing.JSlider;
+import javax.swing.SwingConstants;
+import javax.swing.UIManager;
import javax.swing.plaf.UIResource;
@@ -66,6 +68,12 @@ public class MetalIconFactory implements Serializable
/** A constant representing "light". */
public static final boolean LIGHT = true;
+
+ /** A shared instance of the MenuArrowIcon. */
+ private static Icon menuArrow;
+
+ /** A shared instance of the MenuItemArrowIcon. */
+ private static Icon menuItemArrow;
/**
* An icon displayed for {@link JCheckBoxMenuItem} components.
@@ -779,6 +787,10 @@ public class MetalIconFactory implements Serializable
*/
public void paintIcon(Component c, Graphics g, int x, int y)
{
+ if (UIManager.get("RadioButton.gradient") != null)
+ MetalUtils.paintGradient(g, x, y, getIconWidth(), getIconHeight(),
+ SwingConstants.VERTICAL, "RadioButton.gradient");
+
Color savedColor = g.getColor();
JRadioButton b = (JRadioButton) c;
@@ -2461,4 +2473,102 @@ public class MetalIconFactory implements Serializable
return treeHardDriveIcon;
}
+ /**
+ * Returns a new instance of a 4 x 8 icon showing a small black triangle that
+ * points to the right. This is displayed in menu items that have a
+ * sub menu.
+ *
+ * @return The icon.
+ */
+ public static Icon getMenuArrowIcon()
+ {
+ if (menuArrow == null)
+ menuArrow = new Icon()
+ {
+ public int getIconHeight()
+ {
+ return 8;
+ }
+
+ public int getIconWidth()
+ {
+ return 4;
+ }
+
+ public void paintIcon(Component c, Graphics g, int x, int y)
+ {
+ Color saved = g.getColor();
+ g.setColor(Color.BLACK);
+ for (int i = 0; i < 4; i++)
+ g.drawLine(x + i, y + i, x + i, y + 7 - i);
+ g.setColor(saved);
+ }
+ };
+ return menuArrow;
+ }
+
+ /**
+ * Returns a new instance of a 4 x 8 icon showing a small black triangle that
+ * points to the right. This is displayed in menu items that have a sub menu.
+ *
+ * @return The icon.
+ */
+ public static Icon getMenuItemArrowIcon()
+ {
+ if (menuItemArrow == null)
+ menuItemArrow = new Icon()
+ {
+ public int getIconHeight()
+ {
+ return 8;
+ }
+
+ public int getIconWidth()
+ {
+ return 4;
+ }
+
+ public void paintIcon(Component c, Graphics g, int x, int y)
+ {
+ Color saved = g.getColor();
+ g.setColor(Color.BLACK);
+ for (int i = 0; i < 4; i++)
+ g.drawLine(x + i, y + i, x + i, y + 7 - i);
+ g.setColor(saved);
+ }
+ };
+ return menuItemArrow;
+ }
+
+ /**
+ * Returns a new instance of a 13 x 13 icon showing a small black check mark.
+ *
+ * @return The icon.
+ */
+ public static Icon getMenuItemCheckIcon()
+ {
+ return new Icon()
+ {
+ public int getIconHeight()
+ {
+ return 13;
+ }
+
+ public int getIconWidth()
+ {
+ return 13;
+ }
+
+ public void paintIcon(Component c, Graphics g, int x, int y)
+ {
+ Color saved = g.getColor();
+ g.setColor(Color.BLACK);
+ g.drawLine(3 + x, 5 + y, 3 + x, 9 + y);
+ g.drawLine(4 + x, 5 + y, 4 + x, 9 + y);
+ g.drawLine(5 + x, 7 + y, 9 + x, 3 + y);
+ g.drawLine(5 + x, 8 + y, 9 + x, 4 + y);
+ g.setColor(saved);
+ }
+ };
+ }
}
diff --git a/javax/swing/plaf/metal/MetalInternalFrameTitlePane.java b/javax/swing/plaf/metal/MetalInternalFrameTitlePane.java
index 33eb3491a..2cf5f67d5 100644
--- a/javax/swing/plaf/metal/MetalInternalFrameTitlePane.java
+++ b/javax/swing/plaf/metal/MetalInternalFrameTitlePane.java
@@ -55,7 +55,6 @@ import javax.swing.JLabel;
import javax.swing.JMenu;
import javax.swing.SwingConstants;
import javax.swing.SwingUtilities;
-import javax.swing.UIDefaults;
import javax.swing.UIManager;
import javax.swing.plaf.basic.BasicInternalFrameTitlePane;
@@ -260,9 +259,8 @@ public class MetalInternalFrameTitlePane extends BasicInternalFrameTitlePane
notSelectedTextColor = MetalLookAndFeel.getInactiveControlTextColor();
notSelectedTitleColor = MetalLookAndFeel.getWindowTitleInactiveBackground();
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
- paletteTitleHeight = defaults.getInt("InternalFrame.paletteTitleHeight");
- paletteCloseIcon = defaults.getIcon("InternalFrame.paletteCloseIcon");
+ paletteTitleHeight = UIManager.getInt("InternalFrame.paletteTitleHeight");
+ paletteCloseIcon = UIManager.getIcon("InternalFrame.paletteCloseIcon");
minIcon = MetalIconFactory.getInternalFrameAltMaximizeIcon(16);
title = new JLabel(frame.getTitle(),
@@ -351,8 +349,14 @@ public class MetalInternalFrameTitlePane extends BasicInternalFrameTitlePane
{
Color savedColor = g.getColor();
Rectangle b = SwingUtilities.getLocalBounds(this);
- g.setColor(MetalLookAndFeel.getPrimaryControlShadow());
- g.fillRect(b.x, b.y, b.width, b.height);
+
+ if (UIManager.get("InternalFrame.activeTitleGradient") != null
+ && frame.isSelected())
+ {
+ MetalUtils.paintGradient(g, b.x, b.y, b.width, b.height,
+ SwingConstants.VERTICAL,
+ "InternalFrame.activeTitleGradient");
+ }
MetalUtils.fillMetalPattern(this, g, b.x + 4, b.y + 2, b.width
- paletteCloseIcon.getIconWidth() - 13, b.height - 5,
MetalLookAndFeel.getPrimaryControlHighlight(),
@@ -393,6 +397,14 @@ public class MetalInternalFrameTitlePane extends BasicInternalFrameTitlePane
g.drawLine(0, d.height - 1, d.width - 1, d.height - 1);
// draw the metal pattern
+ if (UIManager.get("InternalFrame.activeTitleGradient") != null
+ && frame.isSelected())
+ {
+ MetalUtils.paintGradient(g, 0, 0, getWidth(), getHeight(),
+ SwingConstants.VERTICAL,
+ "InternalFrame.activeTitleGradient");
+ }
+
Rectangle b = title.getBounds();
int startX = b.x + b.width + 5;
int endX = startX;
diff --git a/javax/swing/plaf/metal/MetalLabelUI.java b/javax/swing/plaf/metal/MetalLabelUI.java
index e4eaa7172..12b858e0a 100644
--- a/javax/swing/plaf/metal/MetalLabelUI.java
+++ b/javax/swing/plaf/metal/MetalLabelUI.java
@@ -43,7 +43,6 @@ import java.awt.Graphics;
import javax.swing.JComponent;
import javax.swing.JLabel;
-import javax.swing.UIDefaults;
import javax.swing.UIManager;
import javax.swing.plaf.ComponentUI;
import javax.swing.plaf.basic.BasicGraphicsUtils;
@@ -83,22 +82,20 @@ public class MetalLabelUI
/**
* Draws the text for a disabled label, using the color defined in the
- * {@link UIDefaults} with the key <code>Label.disabledForeground</code>.
+ * {@link UIManager} defaults with the key
+ * <code>Label.disabledForeground</code>.
*
* @param l the label.
* @param g the graphics device.
* @param s the label text.
* @param textX the x-coordinate for the label.
* @param textY the y-coordinate for the label.
- *
- * @see UIManager#getLookAndFeelDefaults()
*/
protected void paintDisabledText(JLabel l, Graphics g, String s, int textX,
int textY)
{
Color savedColor = g.getColor();
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
- g.setColor(defaults.getColor("Label.disabledForeground"));
+ g.setColor(UIManager.getColor("Label.disabledForeground"));
int mnemIndex = l.getDisplayedMnemonicIndex();
if (mnemIndex != -1)
BasicGraphicsUtils.drawStringUnderlineCharAt(g, s, mnemIndex, textX,
diff --git a/javax/swing/plaf/metal/MetalLookAndFeel.java b/javax/swing/plaf/metal/MetalLookAndFeel.java
index 5542c0b76..30dc6c8c6 100644
--- a/javax/swing/plaf/metal/MetalLookAndFeel.java
+++ b/javax/swing/plaf/metal/MetalLookAndFeel.java
@@ -40,7 +40,6 @@ package javax.swing.plaf.metal;
import java.awt.Color;
import java.awt.Font;
-import java.awt.Insets;
import javax.swing.LookAndFeel;
import javax.swing.UIDefaults;
@@ -55,7 +54,17 @@ import javax.swing.plaf.basic.BasicLookAndFeel;
/**
* A custom look and feel that is designed to look similar across different
- * operating systems.
+ * operating systems. To install this look and feel, add the following code
+ * (or something similar) near the start of your application:</p>
+ * <pre>
+ * try
+ * {
+ * &nbsp;&nbsp;UIManager.setLookAndFeel(new MetalLookAndFeel());
+ * }
+ * catch (UnsupportedLookAndFeelException e)
+ * {
+ * &nbsp;&nbsp;e.printStackTrace();
+ * }</pre>
*/
public class MetalLookAndFeel extends BasicLookAndFeel
{
@@ -691,8 +700,10 @@ public class MetalLookAndFeel extends BasicLookAndFeel
"CheckBoxUI", "javax.swing.plaf.metal.MetalCheckBoxUI",
"ComboBoxUI", "javax.swing.plaf.metal.MetalComboBoxUI",
"DesktopIconUI", "javax.swing.plaf.metal.MetalDesktopIconUI",
+ "FileChooserUI", "javax.swing.plaf.metal.MetalFileChooserUI",
"InternalFrameUI", "javax.swing.plaf.metal.MetalInternalFrameUI",
"LabelUI", "javax.swing.plaf.metal.MetalLabelUI",
+ "MenuBarUI", "javax.swing.plaf.metal.MetalMenuBarUI",
"PopupMenuSeparatorUI",
"javax.swing.plaf.metal.MetalPopupMenuSeparatorUI",
"ProgressBarUI", "javax.swing.plaf.metal.MetalProgressBarUI",
@@ -857,6 +868,17 @@ public class MetalLookAndFeel extends BasicLookAndFeel
"FormattedTextField.selectionBackground", getTextHighlightColor(),
"FormattedTextField.selectionForeground", getHighlightedTextColor(),
+ "FileChooser.upFolderIcon",
+ MetalIconFactory.getFileChooserUpFolderIcon(),
+ "FileChooser.listViewIcon",
+ MetalIconFactory.getFileChooserListViewIcon(),
+ "FileChooser.newFolderIcon",
+ MetalIconFactory.getFileChooserNewFolderIcon(),
+ "FileChooser.homeFolderIcon",
+ MetalIconFactory.getFileChooserHomeFolderIcon(),
+ "FileChooser.detailsViewIcon",
+ MetalIconFactory.getFileChooserDetailViewIcon(),
+
"FileView.computerIcon", MetalIconFactory.getTreeComputerIcon(),
"FileView.directoryIcon", MetalIconFactory.getTreeFolderIcon(),
"FileView.fileIcon", MetalIconFactory.getTreeLeafIcon(),
@@ -901,9 +923,11 @@ public class MetalLookAndFeel extends BasicLookAndFeel
"Menu.acceleratorFont", new FontUIResource("Dialog", Font.PLAIN, 10),
"Menu.acceleratorForeground", getAcceleratorForeground(),
"Menu.acceleratorSelectionForeground", getAcceleratorSelectedForeground(),
+ "Menu.arrowIcon", MetalIconFactory.getMenuArrowIcon(),
"Menu.background", getMenuBackground(),
"Menu.border", new MetalBorders.MenuItemBorder(),
"Menu.borderPainted", Boolean.TRUE,
+ "Menu.checkIcon", MetalIconFactory.getMenuItemCheckIcon(),
"Menu.disabledForeground", getMenuDisabledForeground(),
"Menu.font", getControlTextFont(),
"Menu.foreground", getMenuForeground(),
@@ -920,6 +944,7 @@ public class MetalLookAndFeel extends BasicLookAndFeel
"MenuItem.acceleratorFont", new FontUIResource("Dialog", Font.PLAIN, 10),
"MenuItem.acceleratorForeground", getAcceleratorForeground(),
"MenuItem.acceleratorSelectionForeground", getAcceleratorSelectedForeground(),
+ "MenuItem.arrowIcon", MetalIconFactory.getMenuItemArrowIcon(),
"MenuItem.background", getMenuBackground(),
"MenuItem.border", new MetalBorders.MenuItemBorder(),
"MenuItem.disabledForeground", getMenuDisabledForeground(),
@@ -1162,7 +1187,7 @@ public class MetalLookAndFeel extends BasicLookAndFeel
"Tree.line", getPrimaryControl(),
"Tree.openIcon", MetalIconFactory.getTreeFolderIcon(),
"Tree.rightChildIndent", new Integer(13),
- "Tree.rowHeight", new Integer(20),
+ "Tree.rowHeight", new Integer(0),
"Tree.scrollsOnExpand", Boolean.TRUE,
"Tree.selectionBackground", getTextHighlightColor(),
"Tree.selectionBorder", new BorderUIResource.LineBorderUIResource(new Color(102, 102, 153)),
@@ -1201,4 +1226,13 @@ public class MetalLookAndFeel extends BasicLookAndFeel
defaults.putDefaults(uiDefaults);
}
+ /**
+ * Returns the current theme setting for the Metal L&amp;F.
+ *
+ * @return the current theme setting for the Metal L&amp;F
+ */
+ public static MetalTheme getCurrentTheme()
+ {
+ return theme;
+ }
}
diff --git a/javax/swing/plaf/metal/MetalMenuBarUI.java b/javax/swing/plaf/metal/MetalMenuBarUI.java
new file mode 100644
index 000000000..31d8d671f
--- /dev/null
+++ b/javax/swing/plaf/metal/MetalMenuBarUI.java
@@ -0,0 +1,88 @@
+/* MetalMenuBarUI.java -- MenuBar UI for the Metal L&F
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.swing.plaf.metal;
+
+import java.awt.Graphics;
+
+import javax.swing.JComponent;
+import javax.swing.SwingConstants;
+import javax.swing.UIManager;
+import javax.swing.plaf.ComponentUI;
+import javax.swing.plaf.basic.BasicMenuBarUI;
+
+/**
+ * A UI implementation for MenuBar in the Metal Look &amp; Feel.
+ *
+ * @author Roman Kennke (kennke@aicas.com)
+ *
+ * @since 1.5
+ */
+public class MetalMenuBarUI extends BasicMenuBarUI
+{
+ /**
+ * Creates and returns a new instance of this UI for the specified component.
+ *
+ * @param c the component to create a UI for
+ *
+ * @return the UI for the component
+ */
+ public static ComponentUI createUI(JComponent c)
+ {
+ return new MetalMenuBarUI();
+ }
+
+
+ /**
+ * If the property <code>MenuBar.gradient</code> is set, then a gradient
+ * is painted as background, otherwise the normal superclass behaviour is
+ * called.
+ */
+ public void update(Graphics g, JComponent c)
+ {
+ if (c.isOpaque() && UIManager.get("MenuBar.gradient") != null)
+ {
+ MetalUtils.paintGradient(g, 0, 0, c.getWidth(), c.getHeight(),
+ SwingConstants.VERTICAL, "MenuBar.gradient");
+ paint(g, c);
+ }
+ else
+ super.update(g, c);
+ }
+
+}
diff --git a/javax/swing/plaf/metal/MetalProgressBarUI.java b/javax/swing/plaf/metal/MetalProgressBarUI.java
index 9241cf13c..0f28818b9 100644
--- a/javax/swing/plaf/metal/MetalProgressBarUI.java
+++ b/javax/swing/plaf/metal/MetalProgressBarUI.java
@@ -38,6 +38,10 @@ exception statement from your version. */
package javax.swing.plaf.metal;
+import java.awt.Color;
+import java.awt.Graphics;
+import java.awt.Insets;
+
import javax.swing.JComponent;
import javax.swing.JProgressBar;
import javax.swing.plaf.ComponentUI;
@@ -67,4 +71,77 @@ public class MetalProgressBarUI extends BasicProgressBarUI
{
return new MetalProgressBarUI();
}
+
+ /**
+ * Performs the painting for determinate progress bars. This calls the
+ * superclass behaviour and then adds some highlighting to the upper and left
+ * edge of the progress bar.
+ *
+ * @param g the graphics context
+ * @param c not used here
+ */
+ public void paintDeterminate(Graphics g, JComponent c)
+ {
+ super.paintDeterminate(g, c);
+ Color saved = g.getColor();
+ Insets i = progressBar.getInsets();
+ int w = progressBar.getWidth();
+ int h = progressBar.getHeight();
+ int orientation = progressBar.getOrientation();
+
+ Color shadow = MetalLookAndFeel.getControlShadow();
+ g.setColor(shadow);
+
+ g.drawLine(i.left, i.top, w - i.right, i.top);
+ g.drawLine(i.left, i.top, i.left, h - i.bottom);
+ int full = getAmountFull(i, w, h);
+ if (full > 0)
+ {
+ Color darkShadow = MetalLookAndFeel.getPrimaryControlDarkShadow();
+ g.setColor(darkShadow);
+ if (orientation == JProgressBar.HORIZONTAL)
+ {
+ g.drawLine(i.left, i.top, i.left, h - i.bottom);
+ g.drawLine(i.left, i.top, i.left + full - 1, i.top);
+ }
+ else
+ {
+ if (full >= (h - i.top - i.bottom))
+ g.drawLine(i.left, i.top, w - i.right, i.top);
+ g.drawLine(i.left, h - i.bottom, i.left, h - i.bottom - full);
+ }
+ }
+ g.setColor(saved);
+ }
+
+ /**
+ * Performs the painting for indeterminate progress bars. This calls the
+ * superclass behaviour and then adds some highlighting to the upper and left
+ * edge of the progress bar.
+ *
+ * @param g the graphics context
+ * @param c not used here
+ */
+ public void paintIndeterminate(Graphics g, JComponent c)
+ {
+ super.paintIndeterminate(g, c);
+ Color saved = g.getColor();
+ Insets i = progressBar.getInsets();
+ int w = progressBar.getWidth();
+ int h = progressBar.getHeight();
+ Color shadow = MetalLookAndFeel.getControlShadow();
+ g.setColor(shadow);
+ g.drawLine(i.left, i.top, w - i.right, i.top);
+ g.drawLine(i.left, i.top, i.left, h - i.bottom);
+
+ boxRect = getBox(boxRect);
+ Color darkShadow = MetalLookAndFeel.getPrimaryControlDarkShadow();
+ g.setColor(darkShadow);
+ int orientation = progressBar.getOrientation();
+ if (orientation == JProgressBar.HORIZONTAL)
+ g.drawLine(boxRect.x, i.top, boxRect.x + boxRect.width - 1, i.top);
+ else
+ g.drawLine(i.left, boxRect.y, i.left, boxRect.y + boxRect.height - 1);
+ g.setColor(saved);
+ }
}
diff --git a/javax/swing/plaf/metal/MetalRadioButtonUI.java b/javax/swing/plaf/metal/MetalRadioButtonUI.java
index c2e4ca546..de71fe8e5 100644
--- a/javax/swing/plaf/metal/MetalRadioButtonUI.java
+++ b/javax/swing/plaf/metal/MetalRadioButtonUI.java
@@ -46,7 +46,6 @@ import java.awt.Rectangle;
import javax.swing.AbstractButton;
import javax.swing.JComponent;
import javax.swing.JRadioButton;
-import javax.swing.UIDefaults;
import javax.swing.UIManager;
import javax.swing.plaf.ComponentUI;
import javax.swing.plaf.basic.BasicRadioButtonUI;
@@ -96,10 +95,9 @@ public class MetalRadioButtonUI
public void installDefaults(AbstractButton b)
{
super.installDefaults(b);
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
- disabledTextColor = defaults.getColor("RadioButton.disabledText");
- focusColor = defaults.getColor("RadioButton.focus");
- selectColor = defaults.getColor("RadioButton.select");
+ disabledTextColor = UIManager.getColor("RadioButton.disabledText");
+ focusColor = UIManager.getColor("RadioButton.focus");
+ selectColor = UIManager.getColor("RadioButton.select");
}
/**
@@ -118,7 +116,7 @@ public class MetalRadioButtonUI
/**
* Returns the color used to fill the {@link JRadioButton}'s icon when the
* button is pressed. The default color is obtained from the
- * {@link UIDefaults} via an entry with the key
+ * {@link UIManager} defaults via an entry with the key
* <code>RadioButton.select</code>.
*
* @return The select color.
@@ -130,8 +128,8 @@ public class MetalRadioButtonUI
/**
* Returns the color for the {@link JRadioButton}'s text when the button is
- * disabled. The default color is obtained from the {@link UIDefaults} via
- * an entry with the key <code>RadioButton.disabledText</code>.
+ * disabled. The default color is obtained from the {@link UIManager}
+ * defaults via an entry with the key <code>RadioButton.disabledText</code>.
*
* @return The disabled text color.
*/
@@ -143,7 +141,7 @@ public class MetalRadioButtonUI
/**
* Returns the color used to draw the focus rectangle when the
* {@link JRadioButton} has the focus. The default color is obtained from
- * the {@link UIDefaults} via an entry with the key
+ * the {@link UIManager} defaults via an entry with the key
* <code>RadioButton.focus</code>.
*
* @return The color used to draw the focus rectangle.
@@ -178,9 +176,7 @@ public class MetalRadioButtonUI
protected void paintFocus(Graphics g, Rectangle t, Dimension d)
{
g.setColor(focusColor);
- // minus 2 because of line thickness. Prevents border
- // from being cutoff.
- g.drawRect(t.x, t.y, t.width - 2, t.height - 2);
+ g.drawRect(t.x - 1, t.y + 2, t.width + 2, t.height - 4);
}
}
diff --git a/javax/swing/plaf/metal/MetalScrollBarUI.java b/javax/swing/plaf/metal/MetalScrollBarUI.java
index 9602ade99..0ff501f89 100644
--- a/javax/swing/plaf/metal/MetalScrollBarUI.java
+++ b/javax/swing/plaf/metal/MetalScrollBarUI.java
@@ -48,7 +48,6 @@ import java.beans.PropertyChangeListener;
import javax.swing.JButton;
import javax.swing.JComponent;
import javax.swing.JScrollBar;
-import javax.swing.UIDefaults;
import javax.swing.UIManager;
import javax.swing.plaf.ComponentUI;
import javax.swing.plaf.basic.BasicScrollBarUI;
@@ -195,8 +194,7 @@ public class MetalScrollBarUI extends BasicScrollBarUI
*/
protected JButton createDecreaseButton(int orientation)
{
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
- scrollBarWidth = defaults.getInt("ScrollBar.width");
+ scrollBarWidth = UIManager.getInt("ScrollBar.width");
decreaseButton = new MetalScrollButton(orientation, scrollBarWidth,
isFreeStanding);
return decreaseButton;
@@ -213,8 +211,7 @@ public class MetalScrollBarUI extends BasicScrollBarUI
*/
protected JButton createIncreaseButton(int orientation)
{
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
- scrollBarWidth = defaults.getInt("ScrollBar.width");
+ scrollBarWidth = UIManager.getInt("ScrollBar.width");
increaseButton = new MetalScrollButton(orientation, scrollBarWidth,
isFreeStanding);
return increaseButton;
@@ -403,8 +400,7 @@ public class MetalScrollBarUI extends BasicScrollBarUI
}
// draw the shadow line
- UIDefaults def = UIManager.getLookAndFeelDefaults();
- g.setColor(def.getColor("ScrollBar.shadow"));
+ g.setColor(UIManager.getColor("ScrollBar.shadow"));
g.drawLine(x + w, y + 1, x + w, y + h - 1);
}
@@ -456,8 +452,7 @@ public class MetalScrollBarUI extends BasicScrollBarUI
}
// draw the shadow line
- UIDefaults def = UIManager.getLookAndFeelDefaults();
- g.setColor(def.getColor("ScrollBar.shadow"));
+ g.setColor(UIManager.getColor("ScrollBar.shadow"));
g.drawLine(x + 1, y + h, x + w - 2, y + h);
}
diff --git a/javax/swing/plaf/metal/MetalScrollPaneUI.java b/javax/swing/plaf/metal/MetalScrollPaneUI.java
index d5bf175f9..ae14af3ca 100644
--- a/javax/swing/plaf/metal/MetalScrollPaneUI.java
+++ b/javax/swing/plaf/metal/MetalScrollPaneUI.java
@@ -38,7 +38,10 @@ exception statement from your version. */
package javax.swing.plaf.metal;
+import java.beans.PropertyChangeListener;
+
import javax.swing.JComponent;
+import javax.swing.JScrollBar;
import javax.swing.JScrollPane;
import javax.swing.plaf.ComponentUI;
import javax.swing.plaf.basic.BasicScrollPaneUI;
@@ -68,4 +71,89 @@ public class MetalScrollPaneUI
{
return new MetalScrollPaneUI();
}
+
+ /**
+ * Configures the specified component appropriate for the look and feel.
+ * This method is invoked when the ComponentUI instance is being installed
+ * as the UI delegate on the specified component. This method should
+ * completely configure the component for the look and feel,
+ * including the following:
+ * 1. Install any default property values for color, fonts, borders,
+ * icons, opacity, etc. on the component. Whenever possible, property
+ * values initialized by the client program should not be overridden.
+ * 2. Install a LayoutManager on the component if necessary.
+ * 3. Create/add any required sub-components to the component.
+ * 4. Create/install event listeners on the component.
+ * 5. Create/install a PropertyChangeListener on the component in order
+ * to detect and respond to component property changes appropriately.
+ * 6. Install keyboard UI (mnemonics, traversal, etc.) on the component.
+ * 7. Initialize any appropriate instance data.
+ *
+ * @param c - the component to install the ui on
+ */
+ public void installUI(JComponent c)
+ {
+ super.installUI(c);
+ JScrollBar hsb = scrollpane.getHorizontalScrollBar();
+ hsb.putClientProperty(MetalScrollBarUI.FREE_STANDING_PROP, Boolean.FALSE);
+ JScrollBar vsb = scrollpane.getVerticalScrollBar();
+ vsb.putClientProperty(MetalScrollBarUI.FREE_STANDING_PROP, Boolean.FALSE);
+ }
+
+ /**
+ * Reverses configuration which was done on the specified component
+ * during installUI. This method is invoked when this UIComponent
+ * instance is being removed as the UI delegate for the specified
+ * component. This method should undo the configuration performed in
+ * installUI, being careful to leave the JComponent instance in a
+ * clean state (no extraneous listeners, look-and-feel-specific property
+ * objects, etc.). This should include the following:
+ * 1. Remove any UI-set borders from the component.
+ * 2. Remove any UI-set layout managers on the component.
+ * 3. Remove any UI-added sub-components from the component.
+ * 4. Remove any UI-added event/property listeners from the component.
+ * 5. Remove any UI-installed keyboard UI from the component.
+ * 6. Nullify any allocated instance data objects to allow for GC.
+ *
+ * @param c - the component to uninstall the ui on
+ */
+ public void uninstallUI(JComponent c)
+ {
+ JScrollBar hsb = scrollpane.getHorizontalScrollBar();
+ hsb.putClientProperty(MetalScrollBarUI.FREE_STANDING_PROP, null);
+ JScrollBar vsb = scrollpane.getVerticalScrollBar();
+ vsb.putClientProperty(MetalScrollBarUI.FREE_STANDING_PROP, null);
+ super.uninstallUI(c);
+ }
+
+ /**
+ * Installs listeners on scrollPane
+ *
+ * @param scrollPane - the component to install the listeners on
+ */
+ public void installListeners(JScrollPane scrollPane)
+ {
+ super.installListeners(scrollPane);
+ }
+
+ /**
+ * Uninstalls listeners on scrollPane
+ *
+ * @param scrollPane - the component to uninstall the listeners on
+ */
+ public void uninstallListeners(JScrollPane scrollPane)
+ {
+ super.uninstallListeners(scrollPane);
+ }
+
+ /**
+ * TODO
+ *
+ * @return TODO
+ */
+ protected PropertyChangeListener createScrollBarSwapListener()
+ {
+ // FIXME: Anything else to do here?
+ return super.createPropertyChangeListener();
+ }
}
diff --git a/javax/swing/plaf/metal/MetalSplitPaneDivider.java b/javax/swing/plaf/metal/MetalSplitPaneDivider.java
index 016e09557..e9adfe46e 100644
--- a/javax/swing/plaf/metal/MetalSplitPaneDivider.java
+++ b/javax/swing/plaf/metal/MetalSplitPaneDivider.java
@@ -38,9 +38,16 @@ exception statement from your version. */
package javax.swing.plaf.metal;
import java.awt.Color;
+import java.awt.Component;
+import java.awt.Container;
import java.awt.Dimension;
import java.awt.Graphics;
+import java.awt.LayoutManager;
+import java.awt.Point;
+import javax.swing.JSplitPane;
+import javax.swing.SwingConstants;
+import javax.swing.plaf.basic.BasicArrowButton;
import javax.swing.plaf.basic.BasicSplitPaneDivider;
/**
@@ -56,7 +63,13 @@ class MetalSplitPaneDivider extends BasicSplitPaneDivider
/** The light color in the pattern. */
Color light;
+
+ /** The JSplitPane the divider is on. */
+ JSplitPane splitPane;
+ /** The split pane orientation. */
+ int orientation;
+
/**
* Creates a new instance of MetalSplitPaneDivider.
*
@@ -65,6 +78,9 @@ class MetalSplitPaneDivider extends BasicSplitPaneDivider
public MetalSplitPaneDivider(MetalSplitPaneUI ui, Color light, Color dark)
{
super(ui);
+ setLayout(new MetalDividerLayout());
+ this.splitPane = super.splitPane;
+ this.orientation = super.orientation;
this.light = light;
this.dark = dark;
}
@@ -76,9 +92,127 @@ class MetalSplitPaneDivider extends BasicSplitPaneDivider
*/
public void paint(Graphics g)
{
- //super.paint(g);
Dimension s = getSize();
MetalUtils.fillMetalPattern(splitPane, g, 2, 2, s.width - 4, s.height - 4,
light, dark);
+ if (splitPane.isOneTouchExpandable())
+ {
+ ((BasicArrowButton) rightButton).paint(g);
+ ((BasicArrowButton) leftButton).paint(g);
+ }
+ }
+
+ /**
+ * This helper class acts as the Layout Manager for the divider.
+ */
+ protected class MetalDividerLayout implements LayoutManager
+ {
+ /** The right button. */
+ BasicArrowButton rb;
+
+ /** The left button. */
+ BasicArrowButton lb;
+
+ /**
+ * Creates a new DividerLayout object.
+ */
+ protected MetalDividerLayout()
+ {
+ // Nothing to do here
+ }
+
+ /**
+ * This method is called when a Component is added.
+ *
+ * @param string The constraints string.
+ * @param c The Component to add.
+ */
+ public void addLayoutComponent(String string, Component c)
+ {
+ // Nothing to do here, constraints are set depending on
+ // orientation in layoutContainer
+ }
+
+ /**
+ * This method is called to lay out the container.
+ *
+ * @param c The container to lay out.
+ */
+ public void layoutContainer(Container c)
+ {
+ // The only components we care about setting up are the
+ // one touch buttons.
+ if (splitPane.isOneTouchExpandable())
+ {
+ if (c.getComponentCount() == 2)
+ {
+ Component c1 = c.getComponent(0);
+ Component c2 = c.getComponent(1);
+ if ((c1 instanceof BasicArrowButton)
+ && (c2 instanceof BasicArrowButton))
+ {
+ lb = ((BasicArrowButton) c1);
+ rb = ((BasicArrowButton) c2);
+ }
+ }
+ if (rb != null && lb != null)
+ {
+ Point p = getLocation();
+ lb.setSize(lb.getPreferredSize());
+ rb.setSize(rb.getPreferredSize());
+ lb.setLocation(p.x, p.y);
+
+ if (orientation == JSplitPane.HORIZONTAL_SPLIT)
+ {
+ rb.setDirection(SwingConstants.EAST);
+ lb.setDirection(SwingConstants.WEST);
+ rb.setLocation(p.x, p.y + lb.getHeight());
+ }
+ else
+ {
+ rb.setDirection(SwingConstants.SOUTH);
+ lb.setDirection(SwingConstants.NORTH);
+ rb.setLocation(p.x + lb.getWidth(), p.y);
+ }
+ }
+ }
+ }
+
+ /**
+ * This method returns the minimum layout size.
+ *
+ * @param c The container to calculate for.
+ *
+ * @return The minimum layout size.
+ */
+ public Dimension minimumLayoutSize(Container c)
+ {
+ return preferredLayoutSize(c);
+ }
+
+ /**
+ * This method returns the preferred layout size.
+ *
+ * @param c The container to calculate for.
+ *
+ * @return The preferred layout size.
+ */
+ public Dimension preferredLayoutSize(Container c)
+ {
+ int dividerSize = getDividerSize();
+ return new Dimension(dividerSize, dividerSize);
+ }
+
+ /**
+ * This method is called when a component is removed.
+ *
+ * @param c The component to remove.
+ */
+ public void removeLayoutComponent(Component c)
+ {
+ // Nothing to do here. If buttons are removed
+ // they will not be layed out when layoutContainer is
+ // called.
+ }
}
}
diff --git a/javax/swing/plaf/metal/MetalSplitPaneUI.java b/javax/swing/plaf/metal/MetalSplitPaneUI.java
index b39fb2336..dbcc0910d 100644
--- a/javax/swing/plaf/metal/MetalSplitPaneUI.java
+++ b/javax/swing/plaf/metal/MetalSplitPaneUI.java
@@ -42,7 +42,6 @@ import java.awt.Color;
import javax.swing.JComponent;
import javax.swing.JSplitPane;
-import javax.swing.UIDefaults;
import javax.swing.UIManager;
import javax.swing.plaf.ComponentUI;
import javax.swing.plaf.basic.BasicSplitPaneDivider;
@@ -83,9 +82,8 @@ public class MetalSplitPaneUI extends BasicSplitPaneUI
*/
public BasicSplitPaneDivider createDefaultDivider()
{
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
- Color light = defaults.getColor("SplitPane.highlight");
- Color dark = defaults.getColor("SplitPane.darkShadow");
+ Color light = UIManager.getColor("SplitPane.highlight");
+ Color dark = UIManager.getColor("SplitPane.darkShadow");
return new MetalSplitPaneDivider(this, light, dark);
}
}
diff --git a/javax/swing/plaf/metal/MetalTabbedPaneUI.java b/javax/swing/plaf/metal/MetalTabbedPaneUI.java
index 68aeaaf7c..c6c46ffe6 100644
--- a/javax/swing/plaf/metal/MetalTabbedPaneUI.java
+++ b/javax/swing/plaf/metal/MetalTabbedPaneUI.java
@@ -38,11 +38,14 @@ exception statement from your version. */
package javax.swing.plaf.metal;
+import java.awt.Color;
import java.awt.Graphics;
import java.awt.LayoutManager;
+import java.awt.Rectangle;
import javax.swing.JComponent;
import javax.swing.JTabbedPane;
+import javax.swing.UIManager;
import javax.swing.plaf.ComponentUI;
import javax.swing.plaf.basic.BasicTabbedPaneUI;
@@ -101,6 +104,29 @@ public class MetalTabbedPaneUI extends BasicTabbedPaneUI
}
/**
+ * The minimum tab width.
+ */
+ protected int minTabWidth;
+
+ /**
+ * The color for the selected tab.
+ */
+ protected Color selectColor;
+
+ /**
+ * The color for a highlighted selected tab.
+ */
+ protected Color selectHighlight;
+
+ /**
+ * The background color used for the tab area.
+ */
+ protected Color tabAreaBackground;
+
+ /** The graphics to draw the highlight below the tab. */
+ private Graphics hg;
+
+ /**
* Constructs a new instance of MetalTabbedPaneUI.
*/
public MetalTabbedPaneUI()
@@ -127,7 +153,7 @@ public class MetalTabbedPaneUI extends BasicTabbedPaneUI
*/
protected LayoutManager createLayoutManager()
{
- return new TabbedPaneLayout();
+ return super.createLayoutManager();
}
/**
@@ -175,6 +201,16 @@ public class MetalTabbedPaneUI extends BasicTabbedPaneUI
protected void paintTopTabBorder(int tabIndex, Graphics g, int x, int y,
int w, int h, int btm, int rght, boolean isSelected)
{
+ int currentRun = getRunForTab(tabPane.getTabCount(), tabIndex);
+ if (shouldFillGap(currentRun, tabIndex, x, y))
+ {
+ g.translate(x, y);
+ g.setColor(getColorForGap(currentRun, x, y));
+ g.fillRect(1, 0, 5, 3);
+ g.fillRect(1, 3, 2, 2);
+ g.translate(-x, -y);
+ }
+
if (isSelected)
{
g.setColor(MetalLookAndFeel.getControlHighlight());
@@ -267,6 +303,16 @@ public class MetalTabbedPaneUI extends BasicTabbedPaneUI
protected void paintBottomTabBorder(int tabIndex, Graphics g, int x, int y,
int w, int h, int btm, int rght, boolean isSelected)
{
+ int currentRun = getRunForTab(tabPane.getTabCount(), tabIndex);
+ if (shouldFillGap(currentRun, tabIndex, x, y))
+ {
+ g.translate(x, y);
+ g.setColor(getColorForGap(currentRun, x, y));
+ g.fillRect(1, h - 5, 3, 5);
+ g.fillRect(4, h - 2, 2, 2);
+ g.translate(-x, -y);
+ }
+
if (isSelected)
{
g.setColor(MetalLookAndFeel.getControlHighlight());
@@ -297,9 +343,16 @@ public class MetalTabbedPaneUI extends BasicTabbedPaneUI
int tabIndex, int x, int y, int w, int h, boolean isSelected)
{
if (isSelected)
- g.setColor(MetalLookAndFeel.getControl());
+ g.setColor(UIManager.getColor("TabbedPane.selected"));
else
- g.setColor(MetalLookAndFeel.getControlShadow());
+ {
+ // This is only present in the OceanTheme, so we must check if it
+ // is actually there
+ Color background = UIManager.getColor("TabbedPane.unselectedBackground");
+ if (background == null)
+ background = UIManager.getColor("TabbedPane.background");
+ g.setColor(background);
+ }
int[] px, py;
if (tabPlacement == TOP)
{
@@ -324,6 +377,8 @@ public class MetalTabbedPaneUI extends BasicTabbedPaneUI
else
throw new AssertionError("Unrecognised 'tabPlacement' argument.");
g.fillPolygon(px, py, 5);
+ hg = g;
+ paintHighlightBelowTab();
}
/**
@@ -342,5 +397,94 @@ public class MetalTabbedPaneUI extends BasicTabbedPaneUI
// (which is drawn at the very top for tabPlacement == TOP)
return run < this.runCount - 1;
}
+
+ /**
+ * Installs the defaults for this UI. This method calls super.installDefaults
+ * and then loads the Metal specific defaults for TabbedPane.
+ */
+ protected void installDefaults()
+ {
+ super.installDefaults();
+ selectColor = UIManager.getColor("TabbedPane.selected");
+ selectHighlight = UIManager.getColor("TabbedPane.selectHighlight");
+ tabAreaBackground = UIManager.getColor("TabbedPane.tabAreaBackground");
+ minTabWidth = 0;
+ }
+ /**
+ * Returns the color for the gap.
+ *
+ * @param currentRun - The current run to return the color for
+ * @param x - The x position of the current run
+ * @param y - The y position of the current run
+ *
+ * @return the color for the gap in the current run.
+ */
+ protected Color getColorForGap(int currentRun, int x, int y)
+ {
+ int index = tabForCoordinate(tabPane, x, y);
+ int selected = tabPane.getSelectedIndex();
+ if (selected == index)
+ return selectColor;
+ return tabAreaBackground;
+ }
+
+ /**
+ * Returns true if the gap should be filled in.
+ *
+ * @param currentRun - The current run
+ * @param tabIndex - The current tab
+ * @param x - The x position of the tab
+ * @param y - The y position of the tab
+ *
+ * @return true if the gap at the current run should be filled
+ */
+ protected boolean shouldFillGap(int currentRun, int tabIndex, int x, int y)
+ {
+ // As far as I can tell, the gap is never filled in.
+ return false;
+ }
+
+ /**
+ * Paints the highlight below the tab, if there is one.
+ */
+ protected void paintHighlightBelowTab()
+ {
+ int selected = tabPane.getSelectedIndex();
+ int tabPlacement = tabPane.getTabPlacement();
+ Rectangle bounds = getTabBounds(tabPane, selected);
+
+ hg.setColor(selectColor);
+ int x = bounds.x;
+ int y = bounds.y;
+ int w = bounds.width;
+ int h = bounds.height;
+
+ if (tabPlacement == TOP)
+ hg.fillRect(x, y + h - 2, w, 30);
+ else if (tabPlacement == LEFT)
+ hg.fillRect(x + w - 1, y, 20, h);
+ else if (tabPlacement == BOTTOM)
+ hg.fillRect(x, y - h + 2, w, 30);
+ else if (tabPlacement == RIGHT)
+ hg.fillRect(x - 18, y, 20, h);
+ else
+ throw new AssertionError("Unrecognised 'tabPlacement' argument.");
+ hg = null;
+ }
+
+ /**
+ * Returns true if we should rotate the tab runs.
+ *
+ * @param tabPlacement - The current tab placement.
+ * @param selectedRun - The selected run.
+ *
+ * @return true if the tab runs should be rotated.
+ */
+ protected boolean shouldRotateTabRuns(int tabPlacement,
+ int selectedRun)
+ {
+ // false because tab runs are not rotated in the MetalLookAndFeel
+ return false;
+ }
}
diff --git a/javax/swing/plaf/metal/MetalTextFieldUI.java b/javax/swing/plaf/metal/MetalTextFieldUI.java
index 6984daecc..30738b37c 100644
--- a/javax/swing/plaf/metal/MetalTextFieldUI.java
+++ b/javax/swing/plaf/metal/MetalTextFieldUI.java
@@ -38,6 +38,8 @@ exception statement from your version. */
package javax.swing.plaf.metal;
+import java.beans.PropertyChangeEvent;
+
import javax.swing.JComponent;
import javax.swing.JTextField;
import javax.swing.plaf.ComponentUI;
@@ -67,4 +69,14 @@ public class MetalTextFieldUI extends BasicTextFieldUI
{
return new MetalTextFieldUI();
}
+
+ /**
+ * This method gets called when a bound property is changed on the associated
+ * JTextComponent. This is a hook which UI implementations may change to
+ * reflect how the UI displays bound properties of JTextComponent subclasses.
+ */
+ public void propertyChange(PropertyChangeEvent evt)
+ {
+ super.propertyChange(evt);
+ }
}
diff --git a/javax/swing/plaf/metal/MetalToggleButtonUI.java b/javax/swing/plaf/metal/MetalToggleButtonUI.java
index 46a19bdbe..0b56d5914 100644
--- a/javax/swing/plaf/metal/MetalToggleButtonUI.java
+++ b/javax/swing/plaf/metal/MetalToggleButtonUI.java
@@ -47,8 +47,8 @@ import java.awt.Rectangle;
import javax.swing.AbstractButton;
import javax.swing.JComponent;
import javax.swing.JToggleButton;
+import javax.swing.SwingConstants;
import javax.swing.SwingUtilities;
-import javax.swing.UIDefaults;
import javax.swing.UIManager;
import javax.swing.plaf.ComponentUI;
import javax.swing.plaf.basic.BasicButtonUI;
@@ -131,10 +131,9 @@ public class MetalToggleButtonUI
public void installDefaults(AbstractButton b)
{
super.installDefaults(b);
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
- focusColor = defaults.getColor(getPropertyPrefix() + "focus");
- selectColor = defaults.getColor(getPropertyPrefix() + "select");
- disabledTextColor = defaults.getColor(getPropertyPrefix() + "disabledText");
+ focusColor = UIManager.getColor(getPropertyPrefix() + "focus");
+ selectColor = UIManager.getColor(getPropertyPrefix() + "select");
+ disabledTextColor = UIManager.getColor(getPropertyPrefix() + "disabledText");
}
/**
@@ -200,5 +199,23 @@ public class MetalToggleButtonUI
g.drawRect(fr.x - 1, fr.y - 1, fr.width + 1, fr.height + 1);
g.setColor(saved);
}
+
+ /**
+ * If the property <code>ToggleButton.gradient</code> is set, then a gradient
+ * is painted as background, otherwise the normal superclass behaviour is
+ * called.
+ */
+ public void update(Graphics g, JComponent c)
+ {
+ if (c.isOpaque() && UIManager.get(getPropertyPrefix() + "gradient") != null)
+ {
+ MetalUtils.paintGradient(g, 0, 0, c.getWidth(), c.getHeight(),
+ SwingConstants.VERTICAL,
+ getPropertyPrefix() + "gradient");
+ paint(g, c);
+ }
+ else
+ super.update(g, c);
+ }
}
diff --git a/javax/swing/plaf/metal/MetalToolBarUI.java b/javax/swing/plaf/metal/MetalToolBarUI.java
index c5ca91399..16e22ac52 100644
--- a/javax/swing/plaf/metal/MetalToolBarUI.java
+++ b/javax/swing/plaf/metal/MetalToolBarUI.java
@@ -38,12 +38,16 @@ exception statement from your version. */
package javax.swing.plaf.metal;
+import java.awt.Point;
import java.awt.event.ContainerListener;
+import java.awt.event.MouseEvent;
+
import java.beans.PropertyChangeListener;
import javax.swing.JComponent;
import javax.swing.JToolBar;
import javax.swing.border.Border;
+import javax.swing.event.MouseInputListener;
import javax.swing.plaf.ComponentUI;
import javax.swing.plaf.basic.BasicToolBarUI;
@@ -158,5 +162,67 @@ public class MetalToolBarUI extends BasicToolBarUI
{
return MetalBorders.getToolbarButtonBorder();
}
-
+
+ /**
+ * Sets the offset for the window used for dragging the toolbar.
+ * It is set as long as the window is not null (it has been installed).
+ */
+ protected void setDragOffset(Point p)
+ {
+ if (dragWindow != null)
+ dragWindow.setOffset(p);
+ }
+
+ /**
+ * Creates and returns an instance of MetalDockingListener.
+ *
+ * @return an instance of MetalDockingListener.
+ */
+ protected MouseInputListener createDockingListener()
+ {
+ return new MetalDockingListener(toolBar);
+ }
+
+ /**
+ * This is the MouseHandler class that allows the user to drag the JToolBar
+ * in and out of the parent and dock it if it can.
+ */
+ protected class MetalDockingListener extends BasicToolBarUI.DockingListener
+ {
+ /**
+ * Creates a new DockingListener object.
+ *
+ * @param t The JToolBar this DockingListener is being used for.
+ */
+ public MetalDockingListener(JToolBar t)
+ {
+ super(t);
+ }
+
+ /**
+ * This method is called when the mouse is pressed in the JToolBar. If the
+ * press doesn't occur in a place where it causes the JToolBar to be
+ * dragged, it returns. Otherwise, it starts a drag session.
+ *
+ * @param e The MouseEvent.
+ */
+ public void mousePressed(MouseEvent e)
+ {
+ super.mousePressed(e);
+ setDragOffset(new Point(e.getX(), e.getY()));
+ }
+
+ /**
+ * This method is called when the mouse is dragged. It delegates the drag
+ * painting to the dragTo method.
+ *
+ * @param e The MouseEvent.
+ */
+ public void mouseDragged(MouseEvent e)
+ {
+ // Does not do anything differently than dragging
+ // BasicToolBarUI.DockingListener
+ super.mouseDragged(e);
+ }
+ }
}
diff --git a/javax/swing/plaf/metal/MetalToolTipUI.java b/javax/swing/plaf/metal/MetalToolTipUI.java
index 5085d170a..f183ed5a1 100644
--- a/javax/swing/plaf/metal/MetalToolTipUI.java
+++ b/javax/swing/plaf/metal/MetalToolTipUI.java
@@ -56,7 +56,6 @@ import javax.swing.JToolTip;
import javax.swing.KeyStroke;
import javax.swing.SwingConstants;
import javax.swing.SwingUtilities;
-import javax.swing.UIDefaults;
import javax.swing.UIManager;
import javax.swing.border.Border;
import javax.swing.plaf.ComponentUI;
@@ -107,13 +106,12 @@ public class MetalToolTipUI
public MetalToolTipUI()
{
super();
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
- activeBorder = defaults.getBorder("ToolTip.border");
- inactiveBorder = defaults.getBorder("ToolTip.borderInactive");
- isAcceleratorHidden = defaults.getBoolean("ToolTip.hideAccelerator");
- acceleratorFont = defaults.getFont("MenuItem.acceleratorFont");
- acceleratorForeground = defaults.getColor("MenuItem.acceleratorForeground");
- acceleratorDelimiter = defaults.getString("MenuItem.acceleratorDelimiter");
+ activeBorder = UIManager.getBorder("ToolTip.border");
+ inactiveBorder = UIManager.getBorder("ToolTip.borderInactive");
+ isAcceleratorHidden = UIManager.getBoolean("ToolTip.hideAccelerator");
+ acceleratorFont = UIManager.getFont("MenuItem.acceleratorFont");
+ acceleratorForeground = UIManager.getColor("MenuItem.acceleratorForeground");
+ acceleratorDelimiter = UIManager.getString("MenuItem.acceleratorDelimiter");
}
/**
diff --git a/javax/swing/plaf/metal/MetalTreeUI.java b/javax/swing/plaf/metal/MetalTreeUI.java
index 0ffa0d174..24432a2b5 100644
--- a/javax/swing/plaf/metal/MetalTreeUI.java
+++ b/javax/swing/plaf/metal/MetalTreeUI.java
@@ -41,24 +41,10 @@ package javax.swing.plaf.metal;
import java.awt.Graphics;
import java.awt.Insets;
import java.awt.Rectangle;
-import java.awt.event.ComponentListener;
-import java.awt.event.FocusListener;
-import java.awt.event.KeyListener;
-import java.awt.event.MouseListener;
-import java.beans.PropertyChangeListener;
-import java.util.Hashtable;
import javax.swing.JComponent;
import javax.swing.JTree;
-import javax.swing.UIDefaults;
-import javax.swing.UIManager;
-import javax.swing.tree.TreeCellEditor;
-import javax.swing.tree.TreeModel;
import javax.swing.tree.TreePath;
-import javax.swing.event.CellEditorListener;
-import javax.swing.event.TreeExpansionListener;
-import javax.swing.event.TreeModelListener;
-import javax.swing.event.TreeSelectionListener;
import javax.swing.plaf.ComponentUI;
import javax.swing.plaf.basic.BasicTreeUI;
@@ -67,19 +53,6 @@ import javax.swing.plaf.basic.BasicTreeUI;
*/
public class MetalTreeUI extends BasicTreeUI
{
-
- /** Listeners */
- private PropertyChangeListener propertyChangeListener;
- private FocusListener focusListener;
- private TreeSelectionListener treeSelectionListener;
- private MouseListener mouseListener;
- private KeyListener keyListener;
- private PropertyChangeListener selectionModelPropertyChangeListener;
- private ComponentListener componentListener;
- private CellEditorListener cellEditorListener;
- private TreeExpansionListener treeExpansionListener;
- private TreeModelListener treeModelListener;
-
/**
* Constructs a new instance of <code>MetalTreeUI</code>.
*/
@@ -128,71 +101,8 @@ public class MetalTreeUI extends BasicTreeUI
*/
public void installUI(JComponent c)
{
- tree = (JTree) c;
- configureLayoutCache();
-
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
- tree.setFont(defaults.getFont("Tree.font"));
- tree.setForeground(defaults.getColor("Tree.foreground"));
- tree.setBackground(defaults.getColor("Tree.background"));
- tree.setOpaque(true);
- tree.setScrollsOnExpand(defaults.getBoolean("Tree.scrollsOnExpand"));
- rightChildIndent = defaults.getInt("Tree.rightChildIndent");
- leftChildIndent = defaults.getInt("Tree.leftChildIndent");
- setRowHeight(defaults.getInt("Tree.rowHeight"));
- tree.setRowHeight(defaults.getInt("Tree.rowHeight"));
- tree.requestFocusInWindow(false);
-
- setExpandedIcon(defaults.getIcon("Tree.expandedIcon"));
- setCollapsedIcon(defaults.getIcon("Tree.collapsedIcon"));
-
- currentCellRenderer = createDefaultCellRenderer();
- rendererPane = createCellRendererPane();
- createdRenderer = true;
- setCellEditor(createDefaultCellEditor());
- createdCellEditor = true;
- TreeModel mod = tree.getModel();
- setModel(mod);
-
- treeSelectionModel = tree.getSelectionModel();
- drawingCache = new Hashtable();
- nodeDimensions = createNodeDimensions();
-
- propertyChangeListener = createPropertyChangeListener();
- focusListener = createFocusListener();
- treeSelectionListener = createTreeSelectionListener();
- mouseListener = createMouseListener();
- keyListener = createKeyListener();
- selectionModelPropertyChangeListener = createSelectionModelPropertyChangeListener();
- componentListener = createComponentListener();
- cellEditorListener = createCellEditorListener();
- treeExpansionListener = createTreeExpansionListener();
- treeModelListener = createTreeModelListener();
-
- editingRow = -1;
- lastSelectedRow = -1;
-
- installKeyboardActions();
-
- tree.addPropertyChangeListener(propertyChangeListener);
- tree.addFocusListener(focusListener);
- tree.addTreeSelectionListener(treeSelectionListener);
- tree.addMouseListener(mouseListener);
- tree.addKeyListener(keyListener);
- tree.addPropertyChangeListener(selectionModelPropertyChangeListener);
- tree.addComponentListener(componentListener);
- tree.addTreeExpansionListener(treeExpansionListener);
- if (treeModel != null)
- treeModel.addTreeModelListener(treeModelListener);
-
- if (mod != null)
- {
- TreePath path = new TreePath(mod.getRoot());
- if (!tree.isExpanded(path))
- toggleExpandState(path);
- }
-
- completeUIInstall();
+ // TODO: What to do here, if anything?
+ super.installUI(c);
}
/**
@@ -212,31 +122,8 @@ public class MetalTreeUI extends BasicTreeUI
*/
public void uninstallUI(JComponent c)
{
- tree.setFont(null);
- tree.setForeground(null);
- tree.setBackground(null);
-
- uninstallKeyboardActions();
-
- tree.removePropertyChangeListener(propertyChangeListener);
- tree.removeFocusListener(focusListener);
- tree.removeTreeSelectionListener(treeSelectionListener);
- tree.removeMouseListener(mouseListener);
- tree.removeKeyListener(keyListener);
- tree.removePropertyChangeListener(selectionModelPropertyChangeListener);
- tree.removeComponentListener(componentListener);
- tree.removeTreeExpansionListener(treeExpansionListener);
-
- TreeCellEditor tce = tree.getCellEditor();
- if (tce != null)
- tce.removeCellEditorListener(cellEditorListener);
- TreeModel tm = tree.getModel();
- if (tm != null)
- tm.removeTreeModelListener(treeModelListener);
-
- tree = null;
- uninstallComponents();
- completeUIUninstall();
+ // TODO: What to do here?
+ super.uninstallUI(c);
}
/**
diff --git a/javax/swing/plaf/metal/MetalUtils.java b/javax/swing/plaf/metal/MetalUtils.java
index 991518d11..50112ce21 100644
--- a/javax/swing/plaf/metal/MetalUtils.java
+++ b/javax/swing/plaf/metal/MetalUtils.java
@@ -44,6 +44,10 @@ import java.awt.Graphics2D;
import java.awt.TexturePaint;
import java.awt.geom.Rectangle2D;
import java.awt.image.BufferedImage;
+import java.util.List;
+
+import javax.swing.SwingConstants;
+import javax.swing.UIManager;
/**
* Some utility and helper methods for the Metal Look &amp; Feel.
@@ -129,7 +133,7 @@ class MetalUtils
// Prepare the texture.
TexturePaint texture =
- new TexturePaint(pattern2D, new Rectangle2D.Double(0., 0., 4., 2.));
+ new TexturePaint(pattern2D, new Rectangle2D.Double(0., 0., 4., 4.));
g2d.setPaint(texture);
g2d.fillRect(x, y, w, h);
}
@@ -139,7 +143,7 @@ class MetalUtils
*/
static void initializePattern(Color light, Color dark)
{
- pattern2D = new BufferedImage(4, 4, BufferedImage.TYPE_INT_RGB);
+ pattern2D = new BufferedImage(4, 4, BufferedImage.TYPE_INT_ARGB);
lightColor = light;
darkColor = dark;
Graphics g = pattern2D.getGraphics();
@@ -151,4 +155,252 @@ class MetalUtils
g.fillRect(3, 3, 1, 1);
g.dispose();
}
+
+ /**
+ * Paints the typical Metal gradient. See {@link #paintGradient(Graphics,
+ * int, int, int, int, double, double, Color, Color, Color, int)}
+ * for more details.
+ *
+ * The parameters are fetched from the UIManager using the key
+ * <code>uiProp</code>. The value is expected to be a {@link List} that
+ * contains 4 values: two {@link Double}s and 3 {@link Color} object that
+ * together make up the parameters passed to the painting method.
+ *
+ * @param g the graphics context to use
+ * @param x the X coordinate of the upper left corner of the rectangle
+ * @param y the Y coordinate of the upper left corner of the rectangle
+ * @param w the width of the rectangle
+ * @param h the height of the rectangle
+ * @param dir the direction of the gradient, either
+ * @param uiProp the key of the UIManager property that has the parameters
+ */
+ static void paintGradient(Graphics g, int x, int y, int w, int h,
+ int dir, String uiProp)
+ {
+ List params = (List) UIManager.get(uiProp);
+ double g1 = ((Double) params.get(0)).doubleValue();
+ double g2 = ((Double) params.get(1)).doubleValue();
+ Color c1 = (Color) params.get(2);
+ Color c2 = (Color) params.get(3);
+ Color c3 = (Color) params.get(4);
+ paintGradient(g, x, y, w, h, g1, g2, c1, c2, c3, dir);
+ }
+
+ /**
+ * Paints the typical Metal gradient. The gradient is painted as follows:
+ * <pre>
+ *
+ * +-------+--------+--------+-----------------------------+
+ * | | | | |
+ * +-------+--------+--------+-----------------------------+
+ * c1 -> c2 -- c2 -> c1 --------> c3
+ * < -g1- > < -g2- > < -g1- >
+ * </pre>
+ *
+ * There are 4 distinct areas in this gradient:
+ * <ol>
+ * <li>A gradient from color 1 to color 2 with the relative width specified
+ * by <code>g1</code></li>
+ * <li>A solid area with the color 2 and the relative width specified by
+ * <code>g2</code></li>
+ * <li>A gradient from color 2 to color 1 with the relative width specified
+ * by <code>g1</code></li>
+ *
+ * @param g the graphics context to use
+ * @param x the X coordinate of the upper left corner of the rectangle
+ * @param y the Y coordinate of the upper left corner of the rectangle
+ * @param w the width of the rectangle
+ * @param h the height of the rectangle
+ * @param g1 the relative width of the c1->c2 gradients
+ * @param g2 the relative width of the c2 solid area
+ * @param c1 the color 1
+ * @param c2 the color 2
+ * @param c3 the color 3
+ * @param dir the direction of the gradient, either
+ * {@link SwingConstants#HORIZONTAL} or {@link SwingConstants#VERTICAL}
+ */
+ static void paintGradient(Graphics g, int x, int y, int w, int h, double g1,
+ double g2, Color c1, Color c2, Color c3, int dir)
+ {
+ if (dir == SwingConstants.HORIZONTAL)
+ paintHorizontalGradient(g, x, y, w, h, g1, g2, c1, c2, c3);
+ else
+ paintVerticalGradient(g, x, y, w, h, g1, g2, c1, c2, c3);
+ }
+
+ /**
+ * Paints a horizontal gradient. See {@link #paintGradient(Graphics, int,
+ * int, int, int, double, double, Color, Color, Color, int)} for details.
+ *
+ * @param x the X coordinate of the upper left corner of the rectangle
+ * @param y the Y coordinate of the upper left corner of the rectangle
+ * @param w the width of the rectangle
+ * @param h the height of the rectangle
+ * @param g1 the relative width of the c1->c2 gradients
+ * @param g2 the relative width of the c2 solid area
+ * @param c1 the color 1
+ * @param c2 the color 2
+ * @param c3 the color 3
+ */
+ static void paintHorizontalGradient(Graphics g, int x, int y, int w, int h,
+ double g1, double g2, Color c1, Color c2,
+ Color c3)
+ {
+ // Calculate the coordinates.
+ // The size of the first gradient area (c1->2).
+ int w1 = (int) (w * g1);
+ // The size of the solid c2 area.
+ int w2 = (int) (w * g2);
+ int x0 = x;
+ int x1 = x0 + w1;
+ int x2 = x1 + w2;
+ int x3 = x2 + w1;
+ int x4 = x + w;
+
+ // Paint first gradient area (c1->c2).
+ int xc; // The current y coordinate.
+ for (xc = x0; xc < x1; xc++)
+ {
+ if (xc > x + w)
+ break;
+
+ // Perform color interpolation;
+ double factor = (xc - x0) / (double) w1;
+ int rInt = (int) ((c2.getRed() - c1.getRed()) * factor + c1.getRed());
+ int gInt = (int) ((c2.getGreen() - c1.getGreen()) * factor
+ + c1.getGreen());
+ int bInt = (int) ((c2.getBlue() - c1.getBlue()) * factor
+ + c1.getBlue());
+ Color interpolated = new Color(rInt, gInt, bInt);
+ g.setColor(interpolated);
+ g.drawLine(xc, y, xc, y + h);
+ }
+ // Paint solid c2 area.
+ g.setColor(c2);
+ g.fillRect(x1, y, x2 - x1, h);
+
+ // Paint second gradient area (c2->c1).
+ for (xc = x2; xc < x3; xc++)
+ {
+ if (xc > x + w)
+ break;
+
+ // Perform color interpolation;
+ double factor = (xc - x2) / (double) w1;
+ int rInt = (int) ((c1.getRed() - c2.getRed()) * factor + c2.getRed());
+ int gInt = (int) ((c1.getGreen() - c2.getGreen()) * factor
+ + c2.getGreen());
+ int bInt = (int) ((c1.getBlue() - c2.getBlue()) * factor
+ + c2.getBlue());
+ Color interpolated = new Color(rInt, gInt, bInt);
+ g.setColor(interpolated);
+ g.drawLine(xc, y, xc, y + h);
+ }
+
+ // Paint third gradient area (c1->c3).
+ for (xc = x3; xc < x4; xc++)
+ {
+ if (xc > x + w)
+ break;
+
+ // Perform color interpolation;
+ double factor = (xc - x3) / (double) (x4 - x3);
+ int rInt = (int) ((c3.getRed() - c1.getRed()) * factor + c1.getRed());
+ int gInt = (int) ((c3.getGreen() - c1.getGreen()) * factor
+ + c1.getGreen());
+ int bInt = (int) ((c3.getBlue() - c1.getBlue()) * factor
+ + c1.getBlue());
+ Color interpolated = new Color(rInt, gInt, bInt);
+ g.setColor(interpolated);
+ g.drawLine(xc, y, xc, y + h);
+ }
+ }
+
+ /**
+ * Paints a vertical gradient. See {@link #paintGradient(Graphics, int, int,
+ * int, int, double, double, Color, Color, Color, int)} for details.
+ *
+ * @param x the X coordinate of the upper left corner of the rectangle
+ * @param y the Y coordinate of the upper left corner of the rectangle
+ * @param w the width of the rectangle
+ * @param h the height of the rectangle
+ * @param g1 the relative width of the c1->c2 gradients
+ * @param g2 the relative width of the c2 solid area
+ * @param c1 the color 1
+ * @param c2 the color 2
+ * @param c3 the color 3
+ */
+ static void paintVerticalGradient(Graphics g, int x, int y, int w, int h,
+ double g1, double g2, Color c1, Color c2,
+ Color c3)
+ {
+ // Calculate the coordinates.
+ // The size of the first gradient area (c1->2).
+ int w1 = (int) (h * g1);
+ // The size of the solid c2 area.
+ int w2 = (int) (h * g2);
+ int y0 = y;
+ int y1 = y0 + w1;
+ int y2 = y1 + w2;
+ int y3 = y2 + w1;
+ int y4 = y + h;
+
+ // Paint first gradient area (c1->c2).
+ int yc; // The current y coordinate.
+ for (yc = y0; yc < y1; yc++)
+ {
+ if (yc > y + h)
+ break;
+
+ // Perform color interpolation;
+ double factor = (yc - y0) / (double) w1;
+ int rInt = (int) ((c2.getRed() - c1.getRed()) * factor + c1.getRed());
+ int gInt = (int) ((c2.getGreen() - c1.getGreen()) * factor
+ + c1.getGreen());
+ int bInt = (int) ((c2.getBlue() - c1.getBlue()) * factor
+ + c1.getBlue());
+ Color interpolated = new Color(rInt, gInt, bInt);
+ g.setColor(interpolated);
+ g.drawLine(x, yc, x + w, yc);
+ }
+ // Paint solid c2 area.
+ g.setColor(c2);
+ g.fillRect(x, y1, w, y2 - y1);
+
+ // Paint second gradient area (c2->c1).
+ for (yc = y2; yc < y3; yc++)
+ {
+ if (yc > y + h)
+ break;
+
+ // Perform color interpolation;
+ double factor = (yc - y2) / (double) w1;
+ int rInt = (int) ((c1.getRed() - c2.getRed()) * factor + c2.getRed());
+ int gInt = (int) ((c1.getGreen() - c2.getGreen()) * factor
+ + c2.getGreen());
+ int bInt = (int) ((c1.getBlue() - c2.getBlue()) * factor
+ + c2.getBlue());
+ Color interpolated = new Color(rInt, gInt, bInt);
+ g.setColor(interpolated);
+ g.drawLine(x, yc, x + w, yc);
+ }
+
+ // Paint third gradient area (c1->c3).
+ for (yc = y3; yc < y4; yc++)
+ {
+ if (yc > y + h)
+ break;
+
+ // Perform color interpolation;
+ double factor = (yc - y3) / (double) (y4 - y3);
+ int rInt = (int) ((c3.getRed() - c1.getRed()) * factor + c1.getRed());
+ int gInt = (int) ((c3.getGreen() - c1.getGreen()) * factor
+ + c1.getGreen());
+ int bInt = (int) ((c3.getBlue() - c1.getBlue()) * factor
+ + c1.getBlue());
+ Color interpolated = new Color(rInt, gInt, bInt);
+ g.setColor(interpolated);
+ g.drawLine(x, yc, x + w, yc);
+ }
+ }
}
diff --git a/javax/swing/plaf/metal/OceanTheme.java b/javax/swing/plaf/metal/OceanTheme.java
index 85a8cb1ff..d1fc4cfec 100644
--- a/javax/swing/plaf/metal/OceanTheme.java
+++ b/javax/swing/plaf/metal/OceanTheme.java
@@ -37,6 +37,9 @@ exception statement from your version. */
package javax.swing.plaf.metal;
+import java.awt.Color;
+import java.util.Arrays;
+
import javax.swing.UIDefaults;
import javax.swing.plaf.ColorUIResource;
@@ -204,6 +207,41 @@ public class OceanTheme extends DefaultMetalTheme
*/
public void addCustomEntriesToTable(UIDefaults defaults)
{
+ defaults.put("Button.gradient", Arrays.asList(new Object[]
+ {new Double(0.3), new Double(0.0), new ColorUIResource(221, 232, 243),
+ new ColorUIResource(Color.WHITE), new ColorUIResource(184, 207, 229)}));
+ defaults.put("CheckBox.gradient", Arrays.asList(new Object[]
+ {new Double(0.3), new Double(0.0), new ColorUIResource(221, 232, 243),
+ new ColorUIResource(Color.WHITE), new ColorUIResource(184, 207, 229)}));
+ defaults.put("CheckBoxMenuItem.gradient", Arrays.asList(new Object[]
+ {new Double(0.3), new Double(0.0), new ColorUIResource(221, 232, 243),
+ new ColorUIResource(Color.WHITE), new ColorUIResource(184, 207, 229)}));
+ defaults.put("MenuBar.gradient", Arrays.asList(new Object[]
+ {new Double(1.0), new Double(0.0), new ColorUIResource(Color.WHITE),
+ new ColorUIResource(218, 218, 218), new ColorUIResource(218, 218, 218)}));
+ defaults.put("RadioButton.gradient", Arrays.asList(new Object[]
+ {new Double(0.3), new Double(0.0), new ColorUIResource(221, 232, 243),
+ new ColorUIResource(Color.WHITE), new ColorUIResource(184, 207, 229)}));
+ defaults.put("RadioButtonMenuItem.gradient", Arrays.asList(new Object[]
+ {new Double(0.3), new Double(0.0), new ColorUIResource(221, 232, 243),
+ new ColorUIResource(Color.WHITE), new ColorUIResource(184, 207, 229)}));
+ defaults.put("ScrollBar.gradient", Arrays.asList(new Object[]
+ {new Double(1.0), new Double(0.0), new ColorUIResource(Color.WHITE),
+ new ColorUIResource(218, 218, 218), new ColorUIResource(218, 218, 218)}));
+ defaults.put("Slider.gradient", Arrays.asList(new Object[]
+ {new Double(0.3), new Double(0.2), new ColorUIResource(200, 221, 242),
+ new ColorUIResource(Color.WHITE), new ColorUIResource(184, 207, 229)}));
+ defaults.put("ToggleButton.gradient", Arrays.asList(new Object[]
+ {new Double(0.3), new Double(0.0), new ColorUIResource(221, 232, 243),
+ new ColorUIResource(Color.WHITE), new ColorUIResource(184, 207, 229)}));
+ defaults.put("InternalFrame.activeTitleGradient", Arrays.asList(new Object[]
+ {new Double(0.3), new Double(0.0), new ColorUIResource(221, 232, 243),
+ new ColorUIResource(Color.WHITE), new ColorUIResource(184, 207, 229)}));
+
+
defaults.put("Button.rollover", Boolean.TRUE);
+
+ defaults.put("TabbedPane.selected", new ColorUIResource(200, 221, 242));
+ defaults.put("TabbedPane.unselectedBackground", SECONDARY3);
}
}
diff --git a/javax/swing/table/DefaultTableCellRenderer.java b/javax/swing/table/DefaultTableCellRenderer.java
index ef80a7e22..233528c7d 100644
--- a/javax/swing/table/DefaultTableCellRenderer.java
+++ b/javax/swing/table/DefaultTableCellRenderer.java
@@ -71,6 +71,16 @@ public class DefaultTableCellRenderer extends JLabel
}
/**
+ * Stores the color set by setForeground().
+ */
+ Color foreground;
+
+ /**
+ * Stores the color set by setBackground().
+ */
+ Color background;
+
+ /**
* Creates a default table cell renderer with an empty border.
*/
public DefaultTableCellRenderer()
@@ -86,6 +96,7 @@ public class DefaultTableCellRenderer extends JLabel
public void setForeground(Color c)
{
super.setForeground(c);
+ foreground = c;
}
/**
@@ -96,6 +107,7 @@ public class DefaultTableCellRenderer extends JLabel
public void setBackground(Color c)
{
super.setBackground(c);
+ background = c;
}
/**
@@ -107,6 +119,8 @@ public class DefaultTableCellRenderer extends JLabel
public void updateUI()
{
super.updateUI();
+ background = null;
+ foreground = null;
}
/**
@@ -140,25 +154,40 @@ public class DefaultTableCellRenderer extends JLabel
if (isSelected)
{
- setBackground(table.getSelectionBackground());
- setForeground(table.getSelectionForeground());
+ super.setBackground(table.getSelectionBackground());
+ super.setForeground(table.getSelectionForeground());
}
else
{
- setBackground(table.getBackground());
- setForeground(table.getForeground());
+ if (background != null)
+ super.setBackground(background);
+ else
+ super.setBackground(table.getBackground());
+ if (foreground != null)
+ super.setForeground(foreground);
+ else
+ super.setForeground(table.getForeground());
}
+
if (hasFocus)
{
- setBackground(table.getBackground());
setBorder(UIManager.getBorder("Table.focusCellHighlightBorder"));
+ if (table.isCellEditable(row, column))
+ {
+ super.setBackground(UIManager.getColor("Table.focusCellBackground"));
+ super.setForeground(UIManager.getColor("Table.focusCellForeground"));
+ }
}
else
setBorder(BorderFactory.createEmptyBorder(1, 1, 1, 1));
- setEnabled(table.isEnabled());
setFont(table.getFont());
+ // If the current background is equal to the table's background, then we
+ // can avoid filling the background by setting the renderer opaque.
+ Color back = getBackground();
+ setOpaque(back != null && back.equals(table.getBackground()));
+
return this;
}
diff --git a/javax/swing/text/AbstractDocument.java b/javax/swing/text/AbstractDocument.java
index 9dd4c125a..35188234c 100644
--- a/javax/swing/text/AbstractDocument.java
+++ b/javax/swing/text/AbstractDocument.java
@@ -544,7 +544,8 @@ public abstract class AbstractDocument implements Document, Serializable
insertUpdate(event, attributes);
writeUnlock();
- fireInsertUpdate(event);
+ if (event.modified)
+ fireInsertUpdate(event);
if (undo != null)
fireUndoableEditUpdate(new UndoableEditEvent(this, undo));
}
@@ -672,20 +673,8 @@ public abstract class AbstractDocument implements Document, Serializable
new DefaultDocumentEvent(offset, length,
DocumentEvent.EventType.REMOVE);
- // Here we set up the parameters for an ElementChange, if one
- // needs to be added to the DocumentEvent later
- Element root = getDefaultRootElement();
- int start = root.getElementIndex(offset);
- int end = root.getElementIndex(offset + length);
-
- Element[] removed = new Element[end - start + 1];
- for (int i = start; i <= end; i++)
- removed[i - start] = root.getElement(i);
-
removeUpdate(event);
- Element[] added = new Element[1];
- added[0] = root.getElement(start);
boolean shouldFire = content.getString(offset, length).length() != 0;
writeLock();
@@ -694,17 +683,6 @@ public abstract class AbstractDocument implements Document, Serializable
postRemoveUpdate(event);
- GapContent.UndoRemove changes = null;
- if (content instanceof GapContent)
- changes = (GapContent.UndoRemove) temp;
-
- if (changes != null && !(start == end))
- {
- // We need to add an ElementChange to our DocumentEvent
- ElementEdit edit = new ElementEdit (root, start, removed, added);
- event.addEdit(edit);
- }
-
if (shouldFire)
fireRemoveUpdate(event);
}
@@ -1832,6 +1810,12 @@ public abstract class AbstractDocument implements Document, Serializable
Hashtable changes;
/**
+ * Indicates if this event has been modified or not. This is used to
+ * determine if this event is thrown.
+ */
+ boolean modified;
+
+ /**
* Creates a new <code>DefaultDocumentEvent</code>.
*
* @param offset the starting offset of the change
@@ -1845,6 +1829,7 @@ public abstract class AbstractDocument implements Document, Serializable
this.length = length;
this.type = type;
changes = new Hashtable();
+ modified = false;
}
/**
@@ -1859,6 +1844,7 @@ public abstract class AbstractDocument implements Document, Serializable
// XXX - Fully qualify ElementChange to work around gcj bug #2499.
if (edit instanceof DocumentEvent.ElementChange)
{
+ modified = true;
DocumentEvent.ElementChange elEdit =
(DocumentEvent.ElementChange) edit;
changes.put(elEdit.getElement(), elEdit);
@@ -2143,7 +2129,10 @@ public abstract class AbstractDocument implements Document, Serializable
*/
public String getName()
{
- return ContentElementName;
+ String name = super.getName();
+ if (name == null)
+ name = ContentElementName;
+ return name;
}
/**
diff --git a/javax/swing/text/BoxView.java b/javax/swing/text/BoxView.java
index b57df732c..5c9587dfe 100644
--- a/javax/swing/text/BoxView.java
+++ b/javax/swing/text/BoxView.java
@@ -307,7 +307,8 @@ public class BoxView
{
copy.setBounds(inside);
childAllocation(i, copy);
- if (!copy.isEmpty())
+ if (!copy.isEmpty()
+ && g.hitClip(copy.x, copy.y, copy.width, copy.height))
paintChild(g, copy, i);
}
}
@@ -475,7 +476,6 @@ public class BoxView
protected View getViewAtPoint(int x, int y, Rectangle r)
{
View result = null;
-
int count = getViewCount();
Rectangle copy = new Rectangle(r);
@@ -489,7 +489,9 @@ public class BoxView
break;
}
}
-
+
+ if (result == null && count > 0)
+ return getView(count - 1);
return result;
}
@@ -497,10 +499,12 @@ public class BoxView
* Computes the allocation for a child <code>View</code>. The parameter
* <code>a</code> stores the allocation of this <code>CompositeView</code>
* and is then adjusted to hold the allocation of the child view.
- *
- * @param index the index of the child <code>View</code>
- * @param a the allocation of this <code>CompositeView</code> before the
- * call, the allocation of the child on exit
+ *
+ * @param index
+ * the index of the child <code>View</code>
+ * @param a
+ * the allocation of this <code>CompositeView</code> before the
+ * call, the allocation of the child on exit
*/
protected void childAllocation(int index, Rectangle a)
{
@@ -736,4 +740,22 @@ public class BoxView
yLayoutValid = false;
super.preferenceChanged(child, width, height);
}
+
+ /**
+ * Maps the document model position <code>pos</code> to a Shape
+ * in the view coordinate space. This method overrides CompositeView's
+ * method to make sure the children are allocated properly before
+ * calling the super's behaviour.
+ */
+ public Shape modelToView(int pos, Shape a, Position.Bias bias)
+ throws BadLocationException
+ {
+ // Make sure everything is allocated properly and then call super
+ if (!isAllocationValid())
+ {
+ Rectangle bounds = a.getBounds();
+ setSize(bounds.width, bounds.height);
+ }
+ return super.modelToView(pos, a, bias);
+ }
}
diff --git a/javax/swing/text/ComponentView.java b/javax/swing/text/ComponentView.java
index 366dc1c38..2846f8b53 100644
--- a/javax/swing/text/ComponentView.java
+++ b/javax/swing/text/ComponentView.java
@@ -38,9 +38,14 @@ exception statement from your version. */
package javax.swing.text;
import java.awt.Component;
+import java.awt.Container;
import java.awt.Graphics;
+import java.awt.Rectangle;
import java.awt.Shape;
+import javax.swing.SwingConstants;
+import javax.swing.SwingUtilities;
+
/**
* A {@link View} implementation that is able to render arbitrary
* {@link Component}s. This uses the attribute
@@ -50,12 +55,17 @@ import java.awt.Shape;
* this <code>ComponentView</code>, so this view must not be shared between
* multiple <code>JTextComponent</code>s.
*
+ * @author Roman Kennke (kennke@aicas.com)
* @author original author unknown
- * @author Roman Kennke (roman@kennke.org)
*/
-// FIXME: This class is a complete stub and needs to be implemented properly.
public class ComponentView extends View
{
+
+ /**
+ * The component that is displayed by this view.
+ */
+ private Component comp;
+
/**
* Creates a new instance of <code>ComponentView</code> for the specified
* <code>Element</code>.
@@ -75,7 +85,7 @@ public class ComponentView extends View
*
* @return the component that is rendered
*/
- protected Component createComponent()
+ protected Component createComponent()
{
return StyleConstants.getComponent(getElement().getAttributes());
}
@@ -89,7 +99,14 @@ public class ComponentView extends View
*/
public float getAlignment(int axis)
{
- return 0;
+ float align;
+ if (axis == X_AXIS)
+ align = getComponent().getAlignmentX();
+ else if (axis == Y_AXIS)
+ align = getComponent().getAlignmentY();
+ else
+ throw new IllegalArgumentException();
+ return align;
}
/**
@@ -101,7 +118,9 @@ public class ComponentView extends View
*/
public final Component getComponent()
{
- return null;
+ if (comp == null)
+ comp = createComponent();
+ return comp;
}
/**
@@ -116,49 +135,115 @@ public class ComponentView extends View
*/
public float getMaximumSpan(int axis)
{
- return 0;
+ float span;
+ if (axis == X_AXIS)
+ span = getComponent().getMaximumSize().width;
+ else if (axis == Y_AXIS)
+ span = getComponent().getMaximumSize().height;
+ else
+ throw new IllegalArgumentException();
+ return span;
}
public float getMinimumSpan(int axis)
{
- // TODO: Implement this properly.
- return 0;
+ float span;
+ if (axis == X_AXIS)
+ span = getComponent().getMinimumSize().width;
+ else if (axis == Y_AXIS)
+ span = getComponent().getMinimumSize().height;
+ else
+ throw new IllegalArgumentException();
+ return span;
}
public float getPreferredSpan(int axis)
{
- // TODO: Implement this properly.
- return 0;
+ float span;
+ if (axis == X_AXIS)
+ span = getComponent().getPreferredSize().width;
+ else if (axis == Y_AXIS)
+ span = getComponent().getPreferredSize().height;
+ else
+ throw new IllegalArgumentException();
+ return span;
}
public Shape modelToView(int pos, Shape a, Position.Bias b)
throws BadLocationException
{
- // TODO: Implement this properly.
- return null;
+ Element el = getElement();
+ if (pos < el.getStartOffset() || pos >= el.getEndOffset())
+ throw new BadLocationException("Illegal offset for this view", pos);
+ Rectangle r = a.getBounds();
+ Component c = getComponent();
+ return new Rectangle(r.x, r.y, c.getWidth(), c.getHeight());
}
-
+
+ /**
+ * The real painting behavour is performed by normal component painting,
+ * triggered by the text component that hosts this view. This method does
+ * not paint by itself. However, it sets the size of the component according
+ * to the allocation that is passed here.
+ *
+ * @param g the graphics context
+ * @param a the allocation of the child
+ */
public void paint(Graphics g, Shape a)
{
- // TODO: Implement this properly.
+ Rectangle r = a.getBounds();
+ getComponent().setBounds(r.x, r.y, r.width, r.height);
}
-
- public void setParent(View p)
+
+ /**
+ * This sets up the component when the view is added to its parent, or
+ * cleans up the view when it is removed from its parent.
+ *
+ * When this view is added to a parent view, the component of this view
+ * is added to the container that hosts this view. When <code>p</code> is
+ * <code>null</code>, then the view is removed from it's parent and we have
+ * to also remove the component from it's parent container.
+ *
+ * @param p the parent view or <code>null</code> if this view is removed
+ * from it's parent
+ */
+ public void setParent(final View p)
{
- // TODO: Implement this properly.
+ if (SwingUtilities.isEventDispatchThread())
+ setParentImpl(p);
+ else
+ SwingUtilities.invokeLater
+ (new Runnable()
+ {
+ public void run()
+ {
+ setParentImpl(p);
+ }
+ });
}
-
- public void setSize(float width, float height)
+
+ /**
+ * The implementation of {@link #setParent}. This is package private to
+ * avoid a synthetic accessor method.
+ *
+ * @param p the parent view to set
+ */
+ void setParentImpl(View p)
{
- // TODO: Implement this properly.
+ if (p != null)
+ {
+ Component c = getComponent();
+ p.getContainer().add(c);
+ }
+ else
+ {
+ Component c = getComponent();
+ Container parent = c.getParent();
+ parent.remove(c);
+ comp = null;
+ }
}
- public int viewToModel(float x, float y, Shape a, Position.Bias[] bias)
- {
- // TODO: Implement this properly.
- return 0;
- }
-
/**
* Maps coordinates from the <code>View</code>'s space into a position
* in the document model.
@@ -171,9 +256,12 @@ public class ComponentView extends View
* @return the position in the document that corresponds to the screen
* coordinates <code>x, y</code>
*/
- public int viewToModel(float x, float y, Shape a, Position.Bias b)
+ public int viewToModel(float x, float y, Shape a, Position.Bias[] b)
{
- // FIXME: Implement this properly.
- return 0;
+ // The element should only have one character position and it is clear
+ // that this position is the position that best matches the given screen
+ // coordinates, simply because this view has only this one position.
+ Element el = getElement();
+ return el.getStartOffset();
}
}
diff --git a/javax/swing/text/CompositeView.java b/javax/swing/text/CompositeView.java
index 6d8ca912f..cd6645215 100644
--- a/javax/swing/text/CompositeView.java
+++ b/javax/swing/text/CompositeView.java
@@ -221,20 +221,17 @@ public abstract class CompositeView
if (childIndex != -1)
{
View child = getView(childIndex);
- Shape result = child.modelToView(pos, a, bias);
+ Rectangle r = a.getBounds();
+ childAllocation(childIndex, r);
+ Shape result = child.modelToView(pos, r, bias);
if (result == null)
throw new AssertionError("" + child.getClass().getName()
+ ".modelToView() must not return null");
return result;
}
else
- {
- // FIXME: Handle the case when we have no child view for the given
- // position.
- throw new AssertionError("No child views found where child views are "
- + "expected. pos = " + pos + ", bias = "
- + bias);
- }
+ throw new BadLocationException("No child view for the specified location",
+ pos);
}
/**
@@ -267,50 +264,56 @@ public abstract class CompositeView
* Maps coordinates from the <code>View</code>'s space into a position
* in the document model.
*
- * @param x the x coordinate in the view space
- * @param y the y coordinate in the view space
+ * @param x the x coordinate in the view space, x >= 0
+ * @param y the y coordinate in the view space, y >= 0
* @param a the allocation of this <code>View</code>
* @param b the bias to use
*
* @return the position in the document that corresponds to the screen
- * coordinates <code>x, y</code>
+ * coordinates <code>x, y</code> >= 0
*/
public int viewToModel(float x, float y, Shape a, Position.Bias[] b)
{
- Rectangle r = getInsideAllocation(a);
- View view = getViewAtPoint((int) x, (int) y, r);
- return view.viewToModel(x, y, a, b);
+ if (x >= 0 && y >= 0)
+ {
+ Rectangle r = getInsideAllocation(a);
+ View view = getViewAtPoint((int) x, (int) y, r);
+ return view.viewToModel(x, y, a, b);
+ }
+ return 0;
}
/**
* Returns the next model location that is visible in eiter north / south
- * direction or east / west direction. This is used to determine the
- * placement of the caret when navigating around the document with
- * the arrow keys.
- *
- * This is a convenience method for
- * {@link #getNextNorthSouthVisualPositionFrom} and
- * {@link #getNextEastWestVisualPositionFrom}.
- *
- * @param pos the model position to start search from
- * @param b the bias for <code>pos</code>
- * @param a the allocated region for this view
- * @param direction the direction from the current position, can be one of
- * the following:
- * <ul>
- * <li>{@link SwingConstants#WEST}</li>
- * <li>{@link SwingConstants#EAST}</li>
- * <li>{@link SwingConstants#NORTH}</li>
- * <li>{@link SwingConstants#SOUTH}</li>
- * </ul>
- * @param biasRet the bias of the return value gets stored here
- *
+ * direction or east / west direction. This is used to determine the placement
+ * of the caret when navigating around the document with the arrow keys. This
+ * is a convenience method for {@link #getNextNorthSouthVisualPositionFrom}
+ * and {@link #getNextEastWestVisualPositionFrom}.
+ *
+ * @param pos
+ * the model position to start search from
+ * @param b
+ * the bias for <code>pos</code>
+ * @param a
+ * the allocated region for this view
+ * @param direction
+ * the direction from the current position, can be one of the
+ * following:
+ * <ul>
+ * <li>{@link SwingConstants#WEST}</li>
+ * <li>{@link SwingConstants#EAST}</li>
+ * <li>{@link SwingConstants#NORTH}</li>
+ * <li>{@link SwingConstants#SOUTH}</li>
+ * </ul>
+ * @param biasRet
+ * the bias of the return value gets stored here
* @return the position inside the model that represents the next visual
* location
- *
- * @throws BadLocationException if <code>pos</code> is not a valid location
- * inside the document model
- * @throws IllegalArgumentException if <code>direction</code> is invalid
+ * @throws BadLocationException
+ * if <code>pos</code> is not a valid location inside the document
+ * model
+ * @throws IllegalArgumentException
+ * if <code>direction</code> is invalid
*/
public int getNextVisualPositionFrom(int pos, Position.Bias b, Shape a,
int direction, Position.Bias[] biasRet)
diff --git a/javax/swing/text/DefaultCaret.java b/javax/swing/text/DefaultCaret.java
index e5d28d0b8..de512c37f 100644
--- a/javax/swing/text/DefaultCaret.java
+++ b/javax/swing/text/DefaultCaret.java
@@ -40,6 +40,8 @@ package javax.swing.text;
import java.awt.Graphics;
import java.awt.Point;
import java.awt.Rectangle;
+import java.awt.event.ActionEvent;
+import java.awt.event.ActionListener;
import java.awt.event.FocusEvent;
import java.awt.event.FocusListener;
import java.awt.event.MouseEvent;
@@ -49,7 +51,9 @@ import java.beans.PropertyChangeEvent;
import java.beans.PropertyChangeListener;
import java.util.EventListener;
+import javax.swing.JComponent;
import javax.swing.SwingUtilities;
+import javax.swing.Timer;
import javax.swing.event.ChangeEvent;
import javax.swing.event.ChangeListener;
import javax.swing.event.DocumentEvent;
@@ -65,6 +69,41 @@ import javax.swing.event.EventListenerList;
public class DefaultCaret extends Rectangle
implements Caret, FocusListener, MouseListener, MouseMotionListener
{
+
+ /**
+ * Controls the blinking of the caret.
+ *
+ * @author Roman Kennke (kennke@aicas.com)
+ * @author Audrius Meskauskas (AudriusA@Bioinformatics.org)
+ */
+ private class BlinkTimerListener implements ActionListener
+ {
+ /**
+ * Forces the next event to be ignored. The next event should be ignored
+ * if we force the caret to appear. We do not know how long will it take
+ * to fire the comming event; this may be near immediately. Better to leave
+ * the caret visible one iteration longer.
+ */
+ boolean ignoreNextEvent;
+
+ /**
+ * Receives notification when the blink timer fires and updates the visible
+ * state of the caret.
+ *
+ * @param event the action event
+ */
+ public void actionPerformed(ActionEvent event)
+ {
+ if (ignoreNextEvent)
+ ignoreNextEvent = false;
+ else
+ {
+ visible = !visible;
+ repaint();
+ }
+ }
+ }
+
/**
* Listens for changes in the text component's document and updates the
* caret accordingly.
@@ -238,15 +277,28 @@ public class DefaultCaret extends Rectangle
private Point magicCaretPosition = null;
/**
- * Indicates if this <code>Caret</code> is currently visible or not.
+ * Indicates if this <code>Caret</code> is currently visible or not. This is
+ * package private to avoid an accessor method.
*/
- private boolean visible = true;
+ boolean visible = false;
/**
* The current highlight entry.
*/
private Object highlightEntry;
+ private Timer blinkTimer;
+
+ private BlinkTimerListener blinkListener;
+
+ /**
+ * Creates a new <code>DefaultCaret</code> instance.
+ */
+ public DefaultCaret()
+ {
+ // Nothing to do here.
+ }
+
/**
* Sets the Caret update policy.
*
@@ -292,7 +344,7 @@ public class DefaultCaret extends Rectangle
*/
public void mouseDragged(MouseEvent event)
{
- // FIXME: Implement this properly.
+ moveCaret(event);
}
/**
@@ -322,7 +374,7 @@ public class DefaultCaret extends Rectangle
*/
public void mouseClicked(MouseEvent event)
{
- // FIXME: Implement this properly.
+ // TODO: Implement double- and triple-click behaviour here.
}
/**
@@ -344,7 +396,7 @@ public class DefaultCaret extends Rectangle
*/
public void mouseExited(MouseEvent event)
{
- // TODO: What to do here, if anything?
+ // Nothing to do here.
}
/**
@@ -357,10 +409,7 @@ public class DefaultCaret extends Rectangle
*/
public void mousePressed(MouseEvent event)
{
- // FIXME: Implement this properly.
- if (!(event.getButton() == MouseEvent.BUTTON1))
- return;
- setDot(textComponent.viewToModel(event.getPoint()));
+ positionCaret(event);
}
/**
@@ -381,17 +430,45 @@ public class DefaultCaret extends Rectangle
*/
public void focusGained(FocusEvent event)
{
- // TODO: Implement this properly.
+ setVisible(true);
+ updateTimerStatus();
}
/**
* Sets the caret to <code>invisible</code>.
- *
+ *
* @param event the <code>FocusEvent</code>
*/
public void focusLost(FocusEvent event)
{
- // TODO: Implement this properly.
+ if (event.isTemporary() == false)
+ {
+ setVisible(false);
+ // Stop the blinker, if running.
+ if (blinkTimer != null && blinkTimer.isRunning())
+ blinkTimer.stop();
+ }
+ }
+
+ /**
+ * Install (if not present) and start the timer, if the caret must blink. The
+ * caret does not blink if it is invisible, or the component is disabled or
+ * not editable.
+ */
+ private void updateTimerStatus()
+ {
+ if (textComponent.isEnabled() && textComponent.isEditable())
+ {
+ if (blinkTimer == null)
+ initBlinkTimer();
+ if (!blinkTimer.isRunning())
+ blinkTimer.start();
+ }
+ else
+ {
+ if (blinkTimer != null)
+ blinkTimer.stop();
+ }
}
/**
@@ -402,7 +479,8 @@ public class DefaultCaret extends Rectangle
*/
protected void moveCaret(MouseEvent event)
{
- // FIXME: Implement this properly.
+ int newDot = getComponent().viewToModel(event.getPoint());
+ moveDot(newDot);
}
/**
@@ -413,7 +491,8 @@ public class DefaultCaret extends Rectangle
*/
protected void positionCaret(MouseEvent event)
{
- // FIXME: Implement this properly.
+ int newDot = getComponent().viewToModel(event.getPoint());
+ setDot(newDot);
}
/**
@@ -433,6 +512,11 @@ public class DefaultCaret extends Rectangle
textComponent.removePropertyChangeListener(propertyChangeListener);
propertyChangeListener = null;
textComponent = null;
+
+ // Deinstall blink timer if present.
+ if (blinkTimer != null)
+ blinkTimer.stop();
+ blinkTimer = null;
}
/**
@@ -452,6 +536,7 @@ public class DefaultCaret extends Rectangle
textComponent.addPropertyChangeListener(propertyChangeListener);
documentListener = new DocumentHandler();
textComponent.getDocument().addDocumentListener(documentListener);
+
repaint();
}
@@ -559,7 +644,7 @@ public class DefaultCaret extends Rectangle
*/
protected final void repaint()
{
- textComponent.repaint(this);
+ getComponent().repaint(x, y, width, height);
}
/**
@@ -570,7 +655,8 @@ public class DefaultCaret extends Rectangle
*/
public void paint(Graphics g)
{
- if (textComponent == null)
+ JTextComponent comp = getComponent();
+ if (comp == null)
return;
int dot = getDot();
@@ -578,25 +664,33 @@ public class DefaultCaret extends Rectangle
try
{
- rect = textComponent.modelToView(dot);
+ rect = textComponent.modelToView(dot);
}
catch (BadLocationException e)
{
- // This should never happen as dot should be always valid.
- return;
+ assert false : "Unexpected bad caret location: " + dot;
+ return;
}
if (rect == null)
return;
-
- // First we need to delete the old caret.
- // FIXME: Implement deleting of old caret.
-
+
+ // Check if paint has possibly been called directly, without a previous
+ // call to damage(). In this case we need to do some cleanup first.
+ if ((x != rect.x) || (y != rect.y))
+ {
+ repaint(); // Erase previous location of caret.
+ x = rect.x;
+ y = rect.y;
+ width = 1;
+ height = rect.height;
+ }
+
// Now draw the caret on the new position if visible.
if (visible)
{
- g.setColor(textComponent.getCaretColor());
- g.drawLine(rect.x, rect.y, rect.x, rect.y + rect.height);
+ g.setColor(textComponent.getCaretColor());
+ g.drawLine(rect.x, rect.y, rect.x, rect.y + rect.height);
}
}
@@ -687,6 +781,8 @@ public class DefaultCaret extends Rectangle
*/
public void setBlinkRate(int rate)
{
+ if (blinkTimer != null)
+ blinkTimer.setDelay(rate);
blinkRate = rate;
}
@@ -712,27 +808,71 @@ public class DefaultCaret extends Rectangle
*/
public void moveDot(int dot)
{
- this.dot = dot;
- handleHighlight();
- repaint();
+ if (dot >= 0)
+ {
+ this.dot = dot;
+ handleHighlight();
+ adjustVisibility(this);
+ appear();
+ }
}
/**
* Sets the current position of this <code>Caret</code> within the
- * <code>Document</code>. This also sets the <code>mark</code> to the
- * new location.
- *
- * @param dot the new position to be set
- *
+ * <code>Document</code>. This also sets the <code>mark</code> to the new
+ * location.
+ *
+ * @param dot
+ * the new position to be set
* @see #moveDot(int)
*/
public void setDot(int dot)
{
- this.dot = dot;
- this.mark = dot;
- handleHighlight();
- repaint();
+ if (dot >= 0)
+ {
+ this.mark = dot;
+ this.dot = dot;
+ handleHighlight();
+ adjustVisibility(this);
+ appear();
+ }
}
+
+ /**
+ * Show the caret (may be hidden due blinking) and adjust the timer not to
+ * hide it (possibly immediately).
+ *
+ * @author Audrius Meskauskas (AudriusA@Bioinformatics.org)
+ */
+ void appear()
+ {
+ // All machinery is only required if the carret is blinking.
+ if (blinkListener != null)
+ {
+ blinkListener.ignoreNextEvent = true;
+
+ // If the caret is visible, erase the current position by repainting
+ // over.
+ if (visible)
+ repaint();
+
+ // Draw the caret in the new position.
+ visible = true;
+
+ Rectangle area = null;
+ try
+ {
+ area = getComponent().modelToView(getDot());
+ }
+ catch (BadLocationException ex)
+ {
+ assert false : "Unexpected bad caret location: " + getDot();
+ }
+ if (area != null)
+ damage(area);
+ }
+ repaint();
+ }
/**
* Returns <code>true</code> if this <code>Caret</code> is currently visible,
@@ -757,7 +897,18 @@ public class DefaultCaret extends Rectangle
if (v != visible)
{
visible = v;
- repaint();
+ updateTimerStatus();
+ Rectangle area = null;
+ try
+ {
+ area = getComponent().modelToView(getDot());
+ }
+ catch (BadLocationException ex)
+ {
+ assert false: "Unexpected bad caret location: " + getDot();
+ }
+ if (area != null)
+ damage(area);
}
}
@@ -772,4 +923,47 @@ public class DefaultCaret extends Rectangle
{
return DefaultHighlighter.DefaultPainter;
}
+
+ /**
+ * Updates the carets rectangle properties to the specified rectangle and
+ * repaints the caret.
+ *
+ * @param r the rectangle to set as the caret rectangle
+ */
+ protected void damage(Rectangle r)
+ {
+ if (r == null)
+ return;
+ x = r.x;
+ y = r.y;
+ width = 1;
+ // height is normally set in paint and we leave it untouched. However, we
+ // must set a valid value here, since otherwise the painting mechanism
+ // sets a zero clip and never calls paint.
+ if (height <= 0)
+ height = getComponent().getHeight();
+ repaint();
+ }
+
+ /**
+ * Adjusts the text component so that the caret is visible. This default
+ * implementation simply calls
+ * {@link JComponent#scrollRectToVisible(Rectangle)} on the text component.
+ * Subclasses may wish to change this.
+ */
+ protected void adjustVisibility(Rectangle rect)
+ {
+ getComponent().scrollRectToVisible(rect);
+ }
+
+ /**
+ * Initializes the blink timer.
+ */
+ private void initBlinkTimer()
+ {
+ // Setup the blink timer.
+ blinkListener = new BlinkTimerListener();
+ blinkTimer = new Timer(getBlinkRate(), blinkListener);
+ blinkTimer.setRepeats(true);
+ }
}
diff --git a/javax/swing/text/DefaultEditorKit.java b/javax/swing/text/DefaultEditorKit.java
index 3b3fc1f72..fa8c050b0 100644
--- a/javax/swing/text/DefaultEditorKit.java
+++ b/javax/swing/text/DefaultEditorKit.java
@@ -112,8 +112,7 @@ public class DefaultEditorKit extends EditorKit
*/
public void actionPerformed(ActionEvent event)
{
- // FIXME: Implement me. Tookit.getSystemClipboard should be used
- // for that.
+ getTextComponent(event).copy();
}
}
@@ -144,8 +143,7 @@ public class DefaultEditorKit extends EditorKit
*/
public void actionPerformed(ActionEvent event)
{
- // FIXME: Implement me. Tookit.getSystemClipboard should be used
- // for that.
+ getTextComponent(event).cut();
}
}
@@ -174,8 +172,7 @@ public class DefaultEditorKit extends EditorKit
*/
public void actionPerformed(ActionEvent event)
{
- // FIXME: Implement me. Tookit.getSystemClipboard should be used
- // for that.
+ getTextComponent(event).paste();
}
}
@@ -216,19 +213,9 @@ public class DefaultEditorKit extends EditorKit
return;
JTextComponent t = getTextComponent(event);
- if (t != null)
- {
- try
- {
- t.getDocument().insertString(t.getCaret().getDot(),
- event.getActionCommand(), null);
- }
- catch (BadLocationException be)
- {
- // FIXME: we're not authorized to throw this.. swallow it?
- }
- }
- }
+ if (t != null && t.isEnabled() && t.isEditable())
+ t.replaceSelection(event.getActionCommand());
+ }
}
/**
@@ -309,7 +296,8 @@ public class DefaultEditorKit extends EditorKit
*/
public void actionPerformed(ActionEvent event)
{
- // FIXME: Implement this.
+ JTextComponent t = getTextComponent(event);
+ t.replaceSelection("\t");
}
}
diff --git a/javax/swing/text/DefaultStyledDocument.java b/javax/swing/text/DefaultStyledDocument.java
index 648b0bd4d..bdb198efa 100644
--- a/javax/swing/text/DefaultStyledDocument.java
+++ b/javax/swing/text/DefaultStyledDocument.java
@@ -41,9 +41,15 @@ package javax.swing.text;
import java.awt.Color;
import java.awt.Font;
import java.io.Serializable;
+import java.util.Enumeration;
+import java.util.Stack;
import java.util.Vector;
+import javax.swing.event.ChangeEvent;
+import javax.swing.event.ChangeListener;
import javax.swing.event.DocumentEvent;
+import javax.swing.undo.AbstractUndoableEdit;
+import javax.swing.undo.UndoableEdit;
/**
* The default implementation of {@link StyledDocument}.
@@ -61,6 +67,87 @@ public class DefaultStyledDocument extends AbstractDocument
implements StyledDocument
{
/**
+ * An {@link UndoableEdit} that can undo attribute changes to an element.
+ *
+ * @author Roman Kennke (kennke@aicas.com)
+ */
+ public static class AttributeUndoableEdit
+ extends AbstractUndoableEdit
+ {
+ /**
+ * A copy of the old attributes.
+ */
+ protected AttributeSet copy;
+
+ /**
+ * The new attributes.
+ */
+ protected AttributeSet newAttributes;
+
+ /**
+ * If the new attributes replaced the old attributes or if they only were
+ * added to them.
+ */
+ protected boolean isReplacing;
+
+ /**
+ * The element that has changed.
+ */
+ protected Element element;
+
+ /**
+ * Creates a new <code>AttributeUndoableEdit</code>.
+ *
+ * @param el the element that changes attributes
+ * @param newAtts the new attributes
+ * @param replacing if the new attributes replace the old or only append to
+ * them
+ */
+ public AttributeUndoableEdit(Element el, AttributeSet newAtts,
+ boolean replacing)
+ {
+ element = el;
+ newAttributes = newAtts;
+ isReplacing = replacing;
+ copy = el.getAttributes().copyAttributes();
+ }
+
+ /**
+ * Undos the attribute change. The <code>copy</code> field is set as
+ * attributes on <code>element</code>.
+ */
+ public void undo()
+ {
+ super.undo();
+ AttributeSet atts = element.getAttributes();
+ if (atts instanceof MutableAttributeSet)
+ {
+ MutableAttributeSet mutable = (MutableAttributeSet) atts;
+ mutable.removeAttributes(atts);
+ mutable.addAttributes(copy);
+ }
+ }
+
+ /**
+ * Redos an attribute change. This adds <code>newAttributes</code> to the
+ * <code>element</code>'s attribute set, possibly clearing all attributes
+ * if <code>isReplacing</code> is true.
+ */
+ public void redo()
+ {
+ super.undo();
+ AttributeSet atts = element.getAttributes();
+ if (atts instanceof MutableAttributeSet)
+ {
+ MutableAttributeSet mutable = (MutableAttributeSet) atts;
+ if (isReplacing)
+ mutable.removeAttributes(atts);
+ mutable.addAttributes(newAttributes);
+ }
+ }
+ }
+
+ /**
* Carries specification information for new {@link Element}s that should
* be created in {@link ElementBuffer}. This allows the parsing process
* to be decoupled from the <code>Element</code> creation process.
@@ -343,6 +430,26 @@ public class DefaultStyledDocument extends AbstractDocument
private int length;
/**
+ * The number of inserted end tags. This is a counter which always gets
+ * incremented when an end tag is inserted. This is evaluated before
+ * content insertion to go up the element stack.
+ */
+ private int numEndTags;
+
+ /**
+ * The number of inserted start tags. This is a counter which always gets
+ * incremented when an end tag is inserted. This is evaluated before
+ * content insertion to go up the element stack.
+ */
+ private int numStartTags;
+
+ /**
+ * The current position in the element tree. This is used for bulk inserts
+ * using ElementSpecs.
+ */
+ private Stack elementStack;
+
+ /**
* Holds fractured elements during insertion of end and start tags.
* Inserting an end tag may lead to fracturing of the current paragraph
* element. The elements that have been cut off may be added to the
@@ -364,6 +471,7 @@ public class DefaultStyledDocument extends AbstractDocument
public ElementBuffer(Element root)
{
this.root = root;
+ elementStack = new Stack();
}
/**
@@ -407,11 +515,50 @@ public class DefaultStyledDocument extends AbstractDocument
{
// Split up the element at the start offset if necessary.
Element el = getCharacterElement(offset);
- split(el, offset);
+ Element[] res = split(el, offset, 0);
+ BranchElement par = (BranchElement) el.getParentElement();
+ if (res[1] != null)
+ {
+ int index = par.getElementIndex(offset);
+ Element[] removed;
+ Element[] added;
+ if (res[0] == null)
+ {
+ removed = new Element[0];
+ added = new Element[]{ res[1] };
+ index++;
+ }
+ else
+ {
+ removed = new Element[]{ el };
+ added = new Element[]{ res[0], res[1] };
+ }
+ par.replace(index, removed.length, added);
+ addEdit(par, index, removed, added);
+ }
int endOffset = offset + length;
el = getCharacterElement(endOffset);
- split(el, endOffset);
+ res = split(el, endOffset, 0);
+ par = (BranchElement) el.getParentElement();
+ if (res[1] != null)
+ {
+ int index = par.getElementIndex(offset);
+ Element[] removed;
+ Element[] added;
+ if (res[1] == null)
+ {
+ removed = new Element[0];
+ added = new Element[]{ res[1] };
+ }
+ else
+ {
+ removed = new Element[]{ el };
+ added = new Element[]{ res[0], res[1] };
+ }
+ par.replace(index, removed.length, added);
+ addEdit(par, index, removed, added);
+ }
}
/**
@@ -419,42 +566,96 @@ public class DefaultStyledDocument extends AbstractDocument
*
* @param el the Element to possibly split
* @param offset the offset at which to possibly split
+ * @param space the amount of space to create between the splitted parts
+ *
+ * @return An array of elements which represent the split result. This
+ * array has two elements, the two parts of the split. The first
+ * element might be null, which means that the element which should
+ * be splitted can remain in place. The second element might also
+ * be null, which means that the offset is already at an element
+ * boundary and the element doesn't need to be splitted.
+ *
*/
- void split(Element el, int offset)
+ private Element[] split(Element el, int offset, int space)
{
- if (el instanceof AbstractElement)
- {
- AbstractElement ael = (AbstractElement) el;
- int startOffset = ael.getStartOffset();
- int endOffset = ael.getEndOffset();
- int len = endOffset - startOffset;
- if (startOffset != offset && endOffset != offset)
- {
- Element paragraph = ael.getParentElement();
- if (paragraph instanceof BranchElement)
- {
- BranchElement par = (BranchElement) paragraph;
- Element child1 = createLeafElement(par, ael, startOffset,
- offset);
- Element child2 = createLeafElement(par, ael, offset,
- endOffset);
- int index = par.getElementIndex(startOffset);
- Element[] add = new Element[]{ child1, child2 };
- par.replace(index, 1, add);
- documentEvent.addEdit(new ElementEdit(par, index,
- new Element[]{ el },
- add));
- }
+ // If we are at an element boundary, then return an empty array.
+ if ((offset == el.getStartOffset() || offset == el.getEndOffset())
+ && space == 0 && el.isLeaf())
+ return new Element[2];
+
+ // If the element is an instance of BranchElement, then we recursivly
+ // call this method to perform the split.
+ Element[] res = new Element[2];
+ if (el instanceof BranchElement)
+ {
+ int index = el.getElementIndex(offset);
+ Element child = el.getElement(index);
+ Element[] result = split(child, offset, space);
+ Element[] removed;
+ Element[] added;
+ Element[] newAdded;
+
+ int count = el.getElementCount();
+ if (!(result[1] == null))
+ {
+ // This is the case when we can keep the first element.
+ if (result[0] == null)
+ {
+ removed = new Element[count - index - 1];
+ newAdded = new Element[count - index - 1];
+ added = new Element[]{};
+ }
+ // This is the case when we may not keep the first element.
else
- throw new AssertionError("paragraph elements are expected to "
- + "be instances of "
- + "javax.swing.text.AbstractDocument.BranchElement");
- }
- }
- else
- throw new AssertionError("content elements are expected to be "
- + "instances of "
- + "javax.swing.text.AbstractDocument.AbstractElement");
+ {
+ removed = new Element[count - index];
+ newAdded = new Element[count - index];
+ added = new Element[]{result[0]};
+ }
+ newAdded[0] = result[1];
+ for (int i = index; i < count; i++)
+ {
+ Element el2 = el.getElement(i);
+ int ind = i - count + removed.length;
+ removed[ind] = el2;
+ if (ind != 0)
+ newAdded[ind] = el2;
+ }
+
+ ((BranchElement) el).replace(index, removed.length, added);
+ addEdit(el, index, removed, added);
+ BranchElement newPar =
+ (BranchElement) createBranchElement(el.getParentElement(),
+ el.getAttributes());
+ newPar.replace(0, 0, newAdded);
+ res = new Element[]{ null, newPar };
+ }
+ else
+ {
+ removed = new Element[count - index];
+ for (int i = index; i < count; ++i)
+ removed[i - index] = el.getElement(i);
+ added = new Element[0];
+ ((BranchElement) el).replace(index, removed.length,
+ added);
+ addEdit(el, index, removed, added);
+ BranchElement newPar =
+ (BranchElement) createBranchElement(el.getParentElement(),
+ el.getAttributes());
+ newPar.replace(0, 0, removed);
+ res = new Element[]{ null, newPar };
+ }
+ }
+ else if (el instanceof LeafElement)
+ {
+ BranchElement par = (BranchElement) el.getParentElement();
+ Element el1 = createLeafElement(par, el.getAttributes(),
+ el.getStartOffset(), offset);
+ Element el2 = createLeafElement(par, el.getAttributes(),
+ offset + space, el.getEndOffset());
+ res = new Element[]{ el1, el2 };
+ }
+ return res;
}
/**
@@ -477,6 +678,12 @@ public class DefaultStyledDocument extends AbstractDocument
this.offset = offset;
this.length = length;
documentEvent = ev;
+ // Push the root and the paragraph at offset onto the element stack.
+ elementStack.clear();
+ elementStack.push(root);
+ elementStack.push(root.getElement(root.getElementIndex(offset)));
+ numEndTags = 0;
+ numStartTags = 0;
insertUpdate(data);
}
@@ -495,93 +702,102 @@ public class DefaultStyledDocument extends AbstractDocument
switch (data[i].getType())
{
case ElementSpec.StartTagType:
- insertStartTag(data[i]);
+ numStartTags++;
break;
case ElementSpec.EndTagType:
- insertEndTag(data[i]);
+ numEndTags++;
break;
default:
insertContentTag(data[i]);
break;
}
}
+ endEdit();
}
/**
- * Insert a new paragraph after the paragraph at the current position.
- *
- * @param tag the element spec that describes the element to be inserted
+ * Finishes an insertion by possibly evaluating the outstanding start and
+ * end tags. However, this is only performed if the event has received any
+ * modifications.
*/
- void insertStartTag(ElementSpec tag)
+ private void endEdit()
{
- BranchElement root = (BranchElement) getDefaultRootElement();
- int index = root.getElementIndex(offset);
- if (index == -1)
- index = 0;
-
- BranchElement newParagraph =
- (BranchElement) createBranchElement(root, tag.getAttributes());
- newParagraph.setResolveParent(getStyle(StyleContext.DEFAULT_STYLE));
-
- // Add new paragraph into document structure.
- Element[] added = new Element[]{newParagraph};
- root.replace(index + 1, 0, added);
- ElementEdit edit = new ElementEdit(root, index + 1, new Element[0],
- added);
- documentEvent.addEdit(edit);
-
- // Maybe add fractured elements.
- if (tag.getDirection() == ElementSpec.JoinFractureDirection)
- {
- Element[] newFracture = new Element[fracture.length];
- for (int i = 0; i < fracture.length; i++)
- {
- Element oldLeaf = fracture[i];
- Element newLeaf = createLeafElement(newParagraph,
- oldLeaf.getAttributes(),
- oldLeaf.getStartOffset(),
- oldLeaf.getEndOffset());
- newFracture[i] = newLeaf;
- }
- newParagraph.replace(0, 0, newFracture);
- edit = new ElementEdit(newParagraph, 0, new Element[0],
- fracture);
- documentEvent.addEdit(edit);
- fracture = new Element[0];
- }
+ if (documentEvent.modified)
+ prepareContentInsertion();
}
/**
- * Inserts an end tag into the document structure. This cuts of the
- * current paragraph element, possibly fracturing it's child elements.
- * The fractured elements are saved so that they can be joined later
- * with a new paragraph element.
+ * Evaluates the number of inserted end tags and performs the corresponding
+ * structural changes.
*/
- void insertEndTag(ElementSpec tag)
+ private void prepareContentInsertion()
{
- BranchElement root = (BranchElement) getDefaultRootElement();
- int parIndex = root.getElementIndex(offset);
- BranchElement paragraph = (BranchElement) root.getElement(parIndex);
-
- int index = paragraph.getElementIndex(offset);
- LeafElement content = (LeafElement) paragraph.getElement(index);
- // We might have to split the element at offset.
- split(content, offset);
- index = paragraph.getElementIndex(offset);
-
- int count = paragraph.getElementCount();
- // Store fractured elements.
- fracture = new Element[count - index];
- for (int i = index; i < count; ++i)
- fracture[i - index] = paragraph.getElement(i);
-
- // Delete fractured elements.
- paragraph.replace(index, count - index, new Element[0]);
-
- // Add this action to the document event.
- ElementEdit edit = new ElementEdit(paragraph, index, fracture,
- new Element[0]);
- documentEvent.addEdit(edit);
+ while (numEndTags > 0)
+ {
+ elementStack.pop();
+ numEndTags--;
+ }
+
+ while (numStartTags > 0)
+ {
+ Element current = (Element) elementStack.peek();
+ Element newParagraph =
+ insertParagraph((BranchElement) current, offset);
+ elementStack.push(newParagraph);
+ numStartTags--;
+ }
+ }
+
+ private Element insertParagraph(BranchElement par, int offset)
+ {
+ Element current = par.getElement(par.getElementIndex(offset));
+ Element[] res = split(current, offset, 0);
+ int index = par.getElementIndex(offset);
+ Element ret;
+ if (res[1] != null)
+ {
+ Element[] removed;
+ Element[] added;
+ if (res[0] == null)
+ {
+ removed = new Element[0];
+ if (res[1] instanceof BranchElement)
+ {
+ added = new Element[]{ res[1] };
+ ret = res[1];
+ }
+ else
+ {
+ ret = createBranchElement(par, null);
+ added = new Element[]{ ret, res[1] };
+ }
+ index++;
+ }
+ else
+ {
+ removed = new Element[]{ current };
+ if (res[1] instanceof BranchElement)
+ {
+ ret = res[1];
+ added = new Element[]{ res[0], res[1] };
+ }
+ else
+ {
+ ret = createBranchElement(par, null);
+ added = new Element[]{ res[0], ret, res[1] };
+ }
+ }
+ par.replace(index, removed.length, added);
+ addEdit(par, index, removed, added);
+ }
+ else
+ {
+ ret = createBranchElement(par, null);
+ Element[] added = new Element[]{ ret };
+ par.replace(index, 0, added);
+ addEdit(par, index, new Element[0], added);
+ }
+ return ret;
}
/**
@@ -589,102 +805,190 @@ public class DefaultStyledDocument extends AbstractDocument
*
* @param tag the element spec
*/
- void insertContentTag(ElementSpec tag)
+ private void insertContentTag(ElementSpec tag)
{
+ prepareContentInsertion();
int len = tag.getLength();
int dir = tag.getDirection();
if (dir == ElementSpec.JoinPreviousDirection)
{
- Element prev = getCharacterElement(offset);
- BranchElement prevParent = (BranchElement) prev.getParentElement();
- Element join = createLeafElement(prevParent, tag.getAttributes(),
- prev.getStartOffset(),
- Math.max(prev.getEndOffset(),
- offset + len));
- int ind = prevParent.getElementIndex(offset);
- if (ind == -1)
- ind = 0;
- Element[] add = new Element[]{join};
- prevParent.replace(ind, 1, add);
-
- // Add this action to the document event.
- ElementEdit edit = new ElementEdit(prevParent, ind,
- new Element[]{prev}, add);
- documentEvent.addEdit(edit);
+ // The mauve tests to this class show that a JoinPrevious insertion
+ // does not add any edits to the document event. To me this means
+ // that nothing is done here. The previous element naturally should
+ // expand so that it covers the new characters.
}
else if (dir == ElementSpec.JoinNextDirection)
{
- Element next = getCharacterElement(offset + len);
- BranchElement nextParent = (BranchElement) next.getParentElement();
- Element join = createLeafElement(nextParent, tag.getAttributes(),
- offset,
- next.getEndOffset());
- int ind = nextParent.getElementIndex(offset + len);
- if (ind == -1)
- ind = 0;
- Element[] add = new Element[]{join};
- nextParent.replace(ind, 1, add);
+ BranchElement paragraph = (BranchElement) elementStack.peek();
+ int currentIndex = paragraph.getElementIndex(offset);
+ Element current = paragraph.getElement(currentIndex);
+ Element next = paragraph.getElement(currentIndex + 1);
+
+ Element newEl1 = createLeafElement(paragraph,
+ current.getAttributes(),
+ current.getStartOffset(),
+ offset);
+ Element newEl2 = createLeafElement(paragraph,
+ current.getAttributes(),
+ offset,
+ next.getEndOffset());
+
+ Element[] add = new Element[] {newEl1, newEl2};
+ Element[] remove = new Element[] {current, next};
+ paragraph.replace(currentIndex, 2, add);
// Add this action to the document event.
- ElementEdit edit = new ElementEdit(nextParent, ind,
- new Element[]{next}, add);
- documentEvent.addEdit(edit);
+ addEdit(paragraph, currentIndex, remove, add);
}
else
{
- BranchElement par = (BranchElement) getParagraphElement(offset);
+ BranchElement paragraph = (BranchElement) elementStack.peek();
+ int index = paragraph.getElementIndex(offset);
+ Element current = paragraph.getElement(index);
+
+ Element[] added;
+ Element[] removed;
+ Element[] splitRes = split(current, offset, length);
+ // Special case for when offset == startOffset or offset == endOffset.
+ if (splitRes[0] == null)
+ {
+ added = new Element[2];
+ added[0] = createLeafElement(paragraph, tag.getAttributes(),
+ offset, offset + length);
+ added[1] = splitRes[1];
+ removed = new Element[0];
+ index++;
+ }
+ else if (current.getStartOffset() == offset)
+ {
+ added = new Element[2];
+ added[0] = createLeafElement(paragraph, tag.getAttributes(),
+ offset, offset + length);
+ added[1] = splitRes[1];
+ removed = new Element[] { current };
+ }
+ else if (current.getEndOffset() - length == offset)
+ {
+ added = new Element[2];
+ added[0] = splitRes[0];
+ added[1] = createLeafElement(paragraph, tag.getAttributes(),
+ offset, offset + length);
+ removed = new Element[] { current };
+ }
+ else
+ {
+ added = new Element[3];
+ added[0] = splitRes[0];
+ added[1] = createLeafElement(paragraph, tag.getAttributes(),
+ offset, offset + length);
+ added[2] = splitRes[1];
+ removed = new Element[] { current };
+ }
+ paragraph.replace(index, removed.length, added);
+ addEdit(paragraph, index, removed, added);
+ }
+ offset += len;
+ }
+
+ /**
+ * Creates a copy of the element <code>clonee</code> that has the parent
+ * <code>parent</code>.
+ * @param parent the parent of the newly created Element
+ * @param clonee the Element to clone
+ * @return the cloned Element
+ */
+ public Element clone (Element parent, Element clonee)
+ {
+ // If the Element we want to clone is a leaf, then simply copy it
+ if (clonee.isLeaf())
+ return createLeafElement(parent, clonee.getAttributes(),
+ clonee.getStartOffset(), clonee.getEndOffset());
+
+ // Otherwise create a new BranchElement with the desired parent and
+ // the clonee's attributes
+ BranchElement result = (BranchElement) createBranchElement(parent, clonee.getAttributes());
+
+ // And clone all the of clonee's children
+ Element[] children = new Element[clonee.getElementCount()];
+ for (int i = 0; i < children.length; i++)
+ children[i] = clone(result, clonee.getElement(i));
+
+ // Make the cloned children the children of the BranchElement
+ result.replace(0, 0, children);
+ return result;
+ }
- int ind = par.getElementIndex(offset);
+ /**
+ * Adds an ElementChange for a given element modification to the document
+ * event. If there already is an ElementChange registered for this element,
+ * this method tries to merge the ElementChanges together. However, this
+ * is only possible if the indices of the new and old ElementChange are
+ * equal.
+ *
+ * @param e the element
+ * @param i the index of the change
+ * @param removed the removed elements, or <code>null</code>
+ * @param added the added elements, or <code>null</code>
+ */
+ private void addEdit(Element e, int i, Element[] removed, Element[] added)
+ {
+ // Perform sanity check first.
+ DocumentEvent.ElementChange ec = documentEvent.getChange(e);
- // Make room for the element.
- // Cut previous element.
- Element prev = par.getElement(ind);
- if (prev != null && prev.getStartOffset() < offset)
+ // Merge the existing stuff with the new stuff.
+ Element[] oldAdded = ec == null ? null: ec.getChildrenAdded();
+ Element[] newAdded;
+ if (oldAdded != null && added != null)
+ {
+ if (ec.getIndex() <= i)
{
- Element cutPrev = createLeafElement(par, prev.getAttributes(),
- prev.getStartOffset(),
- offset);
- Element[] remove = new Element[]{prev};
- Element[] add = new Element[]{cutPrev};
- if (prev.getEndOffset() > offset + len)
- {
- Element rem = createLeafElement(par, prev.getAttributes(),
- offset + len,
- prev.getEndOffset());
- add = new Element[]{cutPrev, rem};
- }
-
- par.replace(ind, 1, add);
- documentEvent.addEdit(new ElementEdit(par, ind, remove, add));
- ind++;
+ int index = i - ec.getIndex();
+ // Merge adds together.
+ newAdded = new Element[oldAdded.length + added.length];
+ System.arraycopy(oldAdded, 0, newAdded, 0, index);
+ System.arraycopy(added, 0, newAdded, index, added.length);
+ System.arraycopy(oldAdded, index, newAdded, index + added.length,
+ oldAdded.length - index);
+ i = ec.getIndex();
}
- // ind now points to the next element.
+ else
+ throw new AssertionError("Not yet implemented case.");
+ }
+ else if (added != null)
+ newAdded = added;
+ else if (oldAdded != null)
+ newAdded = oldAdded;
+ else
+ newAdded = new Element[0];
- // Cut next element if necessary.
- Element next = par.getElement(ind);
- if (next != null && next.getStartOffset() < offset + len)
+ Element[] oldRemoved = ec == null ? null: ec.getChildrenRemoved();
+ Element[] newRemoved;
+ if (oldRemoved != null && removed != null)
+ {
+ if (ec.getIndex() <= i)
{
- Element cutNext = createLeafElement(par, next.getAttributes(),
- offset + len,
- next.getEndOffset());
- Element[] remove = new Element[]{next};
- Element[] add = new Element[]{cutNext};
- par.replace(ind, 1, add);
- documentEvent.addEdit(new ElementEdit(par, ind, remove,
- add));
+ int index = i - ec.getIndex();
+ // Merge removes together.
+ newRemoved = new Element[oldRemoved.length + removed.length];
+ System.arraycopy(oldAdded, 0, newRemoved, 0, index);
+ System.arraycopy(removed, 0, newRemoved, index, removed.length);
+ System.arraycopy(oldRemoved, index, newRemoved,
+ index + removed.length,
+ oldRemoved.length - index);
+ i = ec.getIndex();
}
-
- // Insert new element.
- Element newEl = createLeafElement(par, tag.getAttributes(),
- offset, offset + len);
- Element[] added = new Element[]{newEl};
- par.replace(ind, 0, added);
- // Add this action to the document event.
- ElementEdit edit = new ElementEdit(par, ind, new Element[0],
- added);
- documentEvent.addEdit(edit);
+ else
+ throw new AssertionError("Not yet implemented case.");
}
- offset += len;
+ else if (removed != null)
+ newRemoved = removed;
+ else if (oldRemoved != null)
+ newRemoved = oldRemoved;
+ else
+ newRemoved = new Element[0];
+
+ // Replace the existing edit for the element with the merged.
+ documentEvent.addEdit(new ElementEdit(e, i, newRemoved, newAdded));
}
}
@@ -714,6 +1018,29 @@ public class DefaultStyledDocument extends AbstractDocument
}
}
+ /**
+ * Receives notification when any of the document's style changes and calls
+ * {@link DefaultStyledDocument#styleChanged(Style)}.
+ *
+ * @author Roman Kennke (kennke@aicas.com)
+ */
+ private class StyleChangeListener
+ implements ChangeListener
+ {
+
+ /**
+ * Receives notification when any of the document's style changes and calls
+ * {@link DefaultStyledDocument#styleChanged(Style)}.
+ *
+ * @param event the change event
+ */
+ public void stateChanged(ChangeEvent event)
+ {
+ Style style = (Style) event.getSource();
+ styleChanged(style);
+ }
+ }
+
/** The serialization UID (compatible with JDK1.5). */
private static final long serialVersionUID = 940485415728614849L;
@@ -729,6 +1056,11 @@ public class DefaultStyledDocument extends AbstractDocument
protected DefaultStyledDocument.ElementBuffer buffer;
/**
+ * Listens for changes on this document's styles and notifies styleChanged().
+ */
+ private StyleChangeListener styleChangeListener;
+
+ /**
* Creates a new <code>DefaultStyledDocument</code>.
*/
public DefaultStyledDocument()
@@ -781,7 +1113,14 @@ public class DefaultStyledDocument extends AbstractDocument
public Style addStyle(String nm, Style parent)
{
StyleContext context = (StyleContext) getAttributeContext();
- return context.addStyle(nm, parent);
+ Style newStyle = context.addStyle(nm, parent);
+
+ // Register change listener.
+ if (styleChangeListener == null)
+ styleChangeListener = new StyleChangeListener();
+ newStyle.addChangeListener(styleChangeListener);
+
+ return newStyle;
}
/**
@@ -825,10 +1164,10 @@ public class DefaultStyledDocument extends AbstractDocument
{
Element element = getDefaultRootElement();
- while (! element.isLeaf())
+ while (!element.isLeaf())
{
- int index = element.getElementIndex(position);
- element = element.getElement(index);
+ int index = element.getElementIndex(position);
+ element = element.getElement(index);
}
return element;
@@ -976,34 +1315,34 @@ public class DefaultStyledDocument extends AbstractDocument
int paragraphCount = root.getElementCount();
for (int pindex = 0; pindex < paragraphCount; pindex++)
{
- Element paragraph = root.getElement(pindex);
- // Skip paragraphs that lie outside the interval.
- if ((paragraph.getStartOffset() > offset + length)
- || (paragraph.getEndOffset() < offset))
- continue;
-
- // Visit content elements within this paragraph
- int contentCount = paragraph.getElementCount();
- for (int cindex = 0; cindex < contentCount; cindex++)
- {
- Element content = paragraph.getElement(cindex);
- // Skip content that lies outside the interval.
- if ((content.getStartOffset() > offset + length)
- || (content.getEndOffset() < offset))
- continue;
-
- if (content instanceof AbstractElement)
- {
- AbstractElement el = (AbstractElement) content;
- if (replace)
- el.removeAttributes(el);
- el.addAttributes(attributes);
- }
- else
- throw new AssertionError("content elements are expected to be"
- + "instances of "
+ Element paragraph = root.getElement(pindex);
+ // Skip paragraphs that lie outside the interval.
+ if ((paragraph.getStartOffset() > offset + length)
+ || (paragraph.getEndOffset() < offset))
+ continue;
+
+ // Visit content elements within this paragraph
+ int contentCount = paragraph.getElementCount();
+ for (int cindex = 0; cindex < contentCount; cindex++)
+ {
+ Element content = paragraph.getElement(cindex);
+ // Skip content that lies outside the interval.
+ if ((content.getStartOffset() > offset + length)
+ || (content.getEndOffset() < offset))
+ continue;
+
+ if (content instanceof AbstractElement)
+ {
+ AbstractElement el = (AbstractElement) content;
+ if (replace)
+ el.removeAttributes(el);
+ el.addAttributes(attributes);
+ }
+ else
+ throw new AssertionError("content elements are expected to be"
+ + "instances of "
+ "javax.swing.text.AbstractDocument.AbstractElement");
- }
+ }
}
fireChangedUpdate(ev);
@@ -1074,8 +1413,8 @@ public class DefaultStyledDocument extends AbstractDocument
catch (BadLocationException ex)
{
AssertionError ae = new AssertionError("Unexpected bad location");
- ae.initCause(ex);
- throw ae;
+ ae.initCause(ex);
+ throw ae;
}
int len = 0;
@@ -1144,5 +1483,94 @@ public class DefaultStyledDocument extends AbstractDocument
(ElementSpec[]) specs.toArray(new ElementSpec[specs.size()]);
buffer.insert(offset, length, elSpecs, ev);
- }
+ }
+
+ /**
+ * Returns an enumeration of all style names.
+ *
+ * @return an enumeration of all style names
+ */
+ public Enumeration getStyleNames()
+ {
+ StyleContext context = (StyleContext) getAttributeContext();
+ return context.getStyleNames();
+ }
+
+ /**
+ * Called when any of this document's styles changes.
+ *
+ * @param style the style that changed
+ */
+ protected void styleChanged(Style style)
+ {
+ // Nothing to do here. This is intended to be overridden by subclasses.
+ }
+
+ /**
+ * Inserts a bulk of structured content at once.
+ *
+ * @param offset the offset at which the content should be inserted
+ * @param data the actual content spec to be inserted
+ */
+ protected void insert(int offset, ElementSpec[] data)
+ throws BadLocationException
+ {
+ writeLock();
+ // First we insert the content.
+ int index = offset;
+ for (int i = 0; i < data.length; i++)
+ {
+ ElementSpec spec = data[i];
+ if (spec.getArray() != null && spec.getLength() > 0)
+ {
+ String insertString = new String(spec.getArray(), spec.getOffset(),
+ spec.getLength());
+ content.insertString(index, insertString);
+ }
+ index += spec.getLength();
+ }
+ // Update the view structure.
+ DefaultDocumentEvent ev = new DefaultDocumentEvent(offset, index - offset,
+ DocumentEvent.EventType.INSERT);
+ for (int i = 0; i < data.length; i++)
+ {
+ ElementSpec spec = data[i];
+ AttributeSet atts = spec.getAttributes();
+ if (atts != null)
+ insertUpdate(ev, atts);
+ }
+
+ // Finally we must update the document structure and fire the insert update
+ // event.
+ buffer.insert(offset, index - offset, data, ev);
+ if (ev.modified)
+ fireInsertUpdate(ev);
+ writeUnlock();
+ }
+
+ /**
+ * Initializes the <code>DefaultStyledDocument</code> with the specified
+ * data.
+ *
+ * @param data the specification of the content with which the document is
+ * initialized
+ */
+ protected void create(ElementSpec[] data)
+ {
+ try
+ {
+ // Clear content.
+ content.remove(0, content.length());
+ // Clear buffer and root element.
+ buffer = new ElementBuffer(createDefaultRoot());
+ // Insert the data.
+ insert(0, data);
+ }
+ catch (BadLocationException ex)
+ {
+ AssertionError err = new AssertionError("Unexpected bad location");
+ err.initCause(ex);
+ throw err;
+ }
+ }
}
diff --git a/javax/swing/text/DefaultTextUI.java b/javax/swing/text/DefaultTextUI.java
new file mode 100644
index 000000000..e7ff01845
--- /dev/null
+++ b/javax/swing/text/DefaultTextUI.java
@@ -0,0 +1,61 @@
+/* DefaultTextUI.java -- Deprecated base UI for text components
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.swing.text;
+
+import javax.swing.plaf.basic.BasicTextUI;
+
+/**
+ * This class is deprecated and should not be used anymore. The base UI for
+ * all text components is now {@link BasicTextUI}.
+ *
+ * @author Roman Kennke (kennke@aicas.com)
+ */
+public abstract class DefaultTextUI extends BasicTextUI
+{
+ /**
+ * This class is deprecated and should not be used anymore. The base UI for
+ * all text components is now {@link BasicTextUI}.
+ *
+ * @deprecated use {@link BasicTextUI} instead
+ */
+ public DefaultTextUI()
+ {
+ // Nothing to do here.
+ }
+}
diff --git a/javax/swing/text/FieldView.java b/javax/swing/text/FieldView.java
index d8a3568e5..249641844 100644
--- a/javax/swing/text/FieldView.java
+++ b/javax/swing/text/FieldView.java
@@ -125,16 +125,18 @@ public class FieldView extends PlainView
try
{
- text = elem.getDocument().getText(elem.getStartOffset(),
- elem.getEndOffset());
+ text = elem.getDocument().getText(elem.getStartOffset(),
+ elem.getEndOffset());
}
catch (BadLocationException e)
{
- // This should never happen.
- text = "";
+ // Should never happen
+ AssertionError ae = new AssertionError();
+ ae.initCause(e);
+ throw ae;
}
-
- return fm.stringWidth(text) + 30;
+
+ return fm.stringWidth(text);
}
public int getResizeWeight(int axis)
diff --git a/javax/swing/text/FlowView.java b/javax/swing/text/FlowView.java
index 5f23ba987..6d4b9cd31 100644
--- a/javax/swing/text/FlowView.java
+++ b/javax/swing/text/FlowView.java
@@ -45,6 +45,7 @@ import java.awt.Shape;
import java.util.Iterator;
import java.util.Vector;
+import javax.swing.SwingConstants;
import javax.swing.event.DocumentEvent;
/**
@@ -569,6 +570,9 @@ public abstract class FlowView extends BoxView
*/
public void insertUpdate(DocumentEvent changes, Shape a, ViewFactory vf)
{
+ // First we must send the insertUpdate to the logical view so it can
+ // be updated accordingly.
+ layoutPool.insertUpdate(changes, a, vf);
strategy.insertUpdate(this, changes, getInsideAllocation(a));
}
diff --git a/javax/swing/text/GapContent.java b/javax/swing/text/GapContent.java
index 439365e59..1e62a4695 100644
--- a/javax/swing/text/GapContent.java
+++ b/javax/swing/text/GapContent.java
@@ -100,15 +100,15 @@ public class GapContent
public int compareTo(Object o)
{
if (o instanceof Integer)
- {
- int otherMark = ((Integer) o).intValue();
- return mark - otherMark;
- }
+ {
+ int otherMark = ((Integer) o).intValue();
+ return mark - otherMark;
+ }
else
- {
- GapContentPosition other = (GapContentPosition) o;
- return mark - other.mark;
- }
+ {
+ GapContentPosition other = (GapContentPosition) o;
+ return mark - other.mark;
+ }
}
/**
@@ -644,6 +644,13 @@ public class GapContent
new GapContentPosition(offset));
if (index1 < 0)
index1 = -(index1 + 1);
+
+ // Search the first index with the specified offset. The binarySearch does
+ // not necessarily find the first one.
+ while (index1 > 0
+ && ((GapContentPosition) positions.get(index1 - 1)).mark == offset)
+ index1--;
+
for (ListIterator i = positions.listIterator(index1); i.hasNext();)
{
GapContentPosition p = (GapContentPosition) i.next();
@@ -672,6 +679,13 @@ public class GapContent
new GapContentPosition(offset));
if (index1 < 0)
index1 = -(index1 + 1);
+
+ // Search the first index with the specified offset. The binarySearch does
+ // not necessarily find the first one.
+ while (index1 > 0
+ && ((GapContentPosition) positions.get(index1 - 1)).mark == offset)
+ index1--;
+
for (ListIterator i = positions.listIterator(index1); i.hasNext();)
{
GapContentPosition p = (GapContentPosition) i.next();
@@ -700,6 +714,12 @@ public class GapContent
new GapContentPosition(offset));
if (index1 < 0)
index1 = -(index1 + 1);
+
+ // Search the first index with the specified offset. The binarySearch does
+ // not necessarily find the first one.
+ while (index1 > 0
+ && ((GapContentPosition) positions.get(index1 - 1)).mark == offset)
+ index1--;
for (ListIterator i = positions.listIterator(index1); i.hasNext();)
{
GapContentPosition p = (GapContentPosition) i.next();
diff --git a/javax/swing/text/GlyphView.java b/javax/swing/text/GlyphView.java
index b516d20e4..47deb50d0 100644
--- a/javax/swing/text/GlyphView.java
+++ b/javax/swing/text/GlyphView.java
@@ -457,9 +457,6 @@ public class GlyphView extends View implements TabableView, Cloneable
Bias[] biasRet)
{
Rectangle b = a.getBounds();
- assert b.contains(x, y) : "The coordinates are expected to be within the "
- + "view's bounds: x=" + x + ", y=" + y
- + "a=" + a;
int pos = getBoundedPosition(v, v.getStartOffset(), b.x, x - b.x);
return pos;
}
diff --git a/javax/swing/text/IconView.java b/javax/swing/text/IconView.java
index c7e22b6c3..af2581a88 100644
--- a/javax/swing/text/IconView.java
+++ b/javax/swing/text/IconView.java
@@ -39,9 +39,25 @@ exception statement from your version. */
package javax.swing.text;
import java.awt.Graphics;
+import java.awt.Rectangle;
import java.awt.Shape;
-// TODO: Implement this class.
+import javax.swing.Icon;
+import javax.swing.JTextPane;
+import javax.swing.SwingConstants;
+
+/**
+ * A View that can render an icon. This view is created by the
+ * {@link StyledEditorKit}'s view factory for all elements that have name
+ * {@link StyleConstants#IconElementName}. This is usually created by
+ * inserting an icon into <code>JTextPane</code> using
+ * {@link JTextPane#insertIcon(Icon)}
+ *
+ * The icon is determined using the attribute
+ * {@link StyleConstants#IconAttribute}, which's value must be an {@link Icon}.
+ *
+ * @author Roman Kennke (kennke@aicas.com)
+ */
public class IconView
extends View
{
@@ -65,7 +81,9 @@ public class IconView
*/
public void paint(Graphics g, Shape a)
{
- // TODO: Implement me.
+ Icon icon = StyleConstants.getIcon(getElement().getAttributes());
+ Rectangle b = a.getBounds();
+ icon.paintIcon(getContainer(), g, b.x, b.y);
}
/**
@@ -78,8 +96,15 @@ public class IconView
*/
public float getPreferredSpan(int axis)
{
- // TODO: Implement me.
- return 0F;
+ Icon icon = StyleConstants.getIcon(getElement().getAttributes());
+ float span;
+ if (axis == X_AXIS)
+ span = icon.getIconWidth();
+ else if (axis == Y_AXIS)
+ span = icon.getIconHeight();
+ else
+ throw new IllegalArgumentException();
+ return span;
}
/**
@@ -104,8 +129,12 @@ public class IconView
public Shape modelToView(int pos, Shape a, Position.Bias b)
throws BadLocationException
{
- // Implement me.
- return null;
+ Element el = getElement();
+ if (pos < el.getStartOffset() || pos >= el.getEndOffset())
+ throw new BadLocationException("Illegal offset for this view", pos);
+ Rectangle r = a.getBounds();
+ Icon icon = StyleConstants.getIcon(el.getAttributes());
+ return new Rectangle(r.x, r.y, icon.getIconWidth(), icon.getIconHeight());
}
/**
@@ -122,7 +151,11 @@ public class IconView
*/
public int viewToModel(float x, float y, Shape a, Position.Bias[] b)
{
- // FIXME: not implemented
- return 0;
+ // The element should only have one character position and it is clear
+ // that this position is the position that best matches the given screen
+ // coordinates, simply because this view has only this one position.
+ Element el = getElement();
+ return el.getStartOffset();
}
+
}
diff --git a/javax/swing/text/InternationalFormatter.java b/javax/swing/text/InternationalFormatter.java
index 86300a70d..a7ed18166 100644
--- a/javax/swing/text/InternationalFormatter.java
+++ b/javax/swing/text/InternationalFormatter.java
@@ -78,6 +78,8 @@ public class InternationalFormatter
minimum = null;
maximum = null;
format = null;
+ setCommitsOnValidEdit(false);
+ setOverwriteMode(false);
}
/**
diff --git a/javax/swing/text/JTextComponent.java b/javax/swing/text/JTextComponent.java
index be68cd5d7..87f884986 100644
--- a/javax/swing/text/JTextComponent.java
+++ b/javax/swing/text/JTextComponent.java
@@ -50,7 +50,6 @@ import java.awt.datatransfer.StringSelection;
import java.awt.datatransfer.Transferable;
import java.awt.datatransfer.UnsupportedFlavorException;
import java.awt.event.ActionEvent;
-import java.awt.event.ActionListener;
import java.awt.event.InputMethodListener;
import java.awt.event.KeyEvent;
import java.awt.event.MouseEvent;
@@ -73,7 +72,6 @@ import javax.swing.JViewport;
import javax.swing.KeyStroke;
import javax.swing.Scrollable;
import javax.swing.SwingConstants;
-import javax.swing.Timer;
import javax.swing.TransferHandler;
import javax.swing.UIManager;
import javax.swing.event.CaretEvent;
@@ -304,48 +302,6 @@ public abstract class JTextComponent extends JComponent
}
/**
- * The timer that lets the caret blink.
- */
- private class CaretBlinkTimer extends Timer implements ActionListener
- {
- /**
- * Creates a new CaretBlinkTimer object with a default delay of 1 second.
- */
- public CaretBlinkTimer()
- {
- super(1000, null);
- addActionListener(this);
- }
-
- /**
- * Lets the caret blink.
- */
- public void actionPerformed(ActionEvent ev)
- {
- Caret c = caret;
- if (c != null)
- c.setVisible(!c.isVisible());
- }
-
- /**
- * Updates the blink delay according to the current caret.
- */
- public void update()
- {
- stop();
- Caret c = caret;
- if (c != null)
- {
- setDelay(c.getBlinkRate());
- if (editable)
- start();
- else
- c.setVisible(false);
- }
- }
- }
-
- /**
* According to <a
* href="http://java.sun.com/products/jfc/tsc/special_report/kestrel/keybindings.html">this
* report</a>, a pair of private classes wraps a {@link
@@ -701,8 +657,6 @@ public abstract class JTextComponent extends JComponent
private char focusAccelerator = '\0';
private NavigationFilter navigationFilter;
- private CaretBlinkTimer caretBlinkTimer;
-
/**
* Get a Keymap from the global keymap table, by name.
*
@@ -910,7 +864,7 @@ public abstract class JTextComponent extends JComponent
Hashtable acts = new Hashtable(actions.length);
for (int i = 0; i < actions.length; ++i)
acts.put(actions[i].getValue(Action.NAME), actions[i]);
- for (int i = 0; i < bindings.length; ++i)
+ for (int i = 0; i < bindings.length; ++i)
if (acts.containsKey(bindings[i].actionName))
map.addActionForKeyStroke(bindings[i].key, (Action) acts.get(bindings[i].actionName));
}
@@ -960,8 +914,6 @@ public abstract class JTextComponent extends JComponent
creatingKeymap = true;
}
- caretBlinkTimer = new CaretBlinkTimer();
-
setFocusable(true);
setEditable(true);
enableEvents(AWTEvent.KEY_EVENT_MASK);
@@ -969,17 +921,33 @@ public abstract class JTextComponent extends JComponent
// need to do this after updateUI()
if (creatingKeymap)
- loadKeymap(defkeymap,
- new KeyBinding[] {
- new KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_LEFT, 0),
- DefaultEditorKit.backwardAction),
- new KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_RIGHT, 0),
- DefaultEditorKit.forwardAction),
- new KeyBinding(KeyStroke.getKeyStroke("typed \b"),
- DefaultEditorKit.deletePrevCharAction),
- new KeyBinding(KeyStroke.getKeyStroke("typed \u007f"),
- DefaultEditorKit.deleteNextCharAction)
- },
+ loadKeymap(
+ defkeymap,
+ new KeyBinding[] {
+ new KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_LEFT, 0),
+ DefaultEditorKit.backwardAction),
+ new KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_RIGHT, 0),
+ DefaultEditorKit.forwardAction),
+ new KeyBinding(KeyStroke.getKeyStroke("typed \b"),
+ DefaultEditorKit.deletePrevCharAction),
+ new KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_X,
+ KeyEvent.CTRL_DOWN_MASK),
+ DefaultEditorKit.cutAction),
+ new KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_C,
+ KeyEvent.CTRL_DOWN_MASK),
+ DefaultEditorKit.copyAction),
+ new KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_V,
+ KeyEvent.CTRL_DOWN_MASK),
+ DefaultEditorKit.pasteAction),
+ new KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_LEFT,
+ KeyEvent.SHIFT_DOWN_MASK),
+ DefaultEditorKit.selectionBackwardAction),
+ new KeyBinding(KeyStroke.getKeyStroke(KeyEvent.VK_RIGHT,
+ KeyEvent.SHIFT_DOWN_MASK),
+ DefaultEditorKit.selectionForwardAction),
+ new KeyBinding(KeyStroke.getKeyStroke("typed \u007f"),
+ DefaultEditorKit.deleteNextCharAction)
+ },
getActions());
}
@@ -1200,14 +1168,6 @@ public abstract class JTextComponent extends JComponent
if (editable == newValue)
return;
- if (newValue == true)
- caretBlinkTimer.start();
- else
- {
- caretBlinkTimer.stop();
- caret.setVisible(false);
- }
-
boolean oldValue = editable;
editable = newValue;
firePropertyChange("editable", oldValue, newValue);
@@ -1236,8 +1196,6 @@ public abstract class JTextComponent extends JComponent
Caret oldCaret = caret;
caret = newCaret;
- caretBlinkTimer.update();
-
if (caret != null)
caret.install(this);
@@ -1405,7 +1363,7 @@ public abstract class JTextComponent extends JComponent
start = Math.max(start, 0);
start = Math.min(start, length);
- end = Math.max(end, 0);
+ end = Math.max(end, start);
end = Math.min(end, length);
setCaretPosition(start);
diff --git a/javax/swing/text/MaskFormatter.java b/javax/swing/text/MaskFormatter.java
new file mode 100644
index 000000000..d12b9ea29
--- /dev/null
+++ b/javax/swing/text/MaskFormatter.java
@@ -0,0 +1,583 @@
+/* MaskFormatter.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.swing.text;
+
+import java.text.ParseException;
+
+import javax.swing.JFormattedTextField;
+
+/**
+ * @author Anthony Balkissoon abalkiss at redhat dot com
+ *
+ */
+public class MaskFormatter extends DefaultFormatter
+{
+ // The declaration of the valid mask characters
+ private static final char NUM_CHAR = '#';
+ private static final char ESCAPE_CHAR = '\'';
+ private static final char UPPERCASE_CHAR = 'U';
+ private static final char LOWERCASE_CHAR = 'L';
+ private static final char ALPHANUM_CHAR = 'A';
+ private static final char LETTER_CHAR = '?';
+ private static final char ANYTHING_CHAR = '*';
+ private static final char HEX_CHAR = 'H';
+
+ /** The mask for this MaskFormatter **/
+ private String mask;
+
+ /**
+ * A String made up of the characters that are not valid for input for
+ * this MaskFormatter.
+ */
+ private String invalidChars;
+
+ /**
+ * A String made up of the characters that are valid for input for
+ * this MaskFormatter.
+ */
+ private String validChars;
+
+ /** A String used in place of missing chracters if the value does not
+ * completely fill in the spaces in the mask.
+ */
+ private String placeHolder;
+
+ /** A character used in place of missing characters if the value does
+ * not completely fill in the spaces in the mask.
+ */
+ private char placeHolderChar = ' ';
+
+ /**
+ * Whether or not stringToValue should return literal characters in the mask.
+ */
+ private boolean valueContainsLiteralCharacters = true;
+
+ /** A String used for easy access to valid HEX characters **/
+ private static String hexString = "0123456789abcdefABCDEF";
+
+ /** An int to hold the length of the mask, accounting for escaped characters **/
+ int maskLength = 0;
+
+ public MaskFormatter ()
+ {
+ // Override super's default behaviour, in MaskFormatter the default
+ // is not to allow invalid values
+ setAllowsInvalid(false);
+ }
+
+ /**
+ * Creates a MaskFormatter with the specified mask.
+ * @specnote doesn't actually throw a ParseException although it
+ * is declared to do so
+ * @param mask
+ * @throws java.text.ParseException
+ */
+ public MaskFormatter (String mask) throws java.text.ParseException
+ {
+ // Override super's default behaviour, in MaskFormatter the default
+ // is not to allow invalid values
+ setAllowsInvalid(false);
+ setMask (mask);
+ }
+
+ /**
+ * Returns the mask used in this MaskFormatter.
+ * @return the mask used in this MaskFormatter.
+ */
+ public String getMask()
+ {
+ return mask;
+ }
+
+ /**
+ * Returns a String containing the characters that are not valid for input
+ * for this MaskFormatter.
+ * @return a String containing the invalid characters.
+ */
+ public String getInvalidCharacters()
+ {
+ return invalidChars;
+ }
+
+ /**
+ * Sets characters that are not valid for input. If
+ * <code>invalidCharacters</code> is non-null then no characters contained
+ * in it will be allowed to be input.
+ *
+ * @param invalidCharacters the String specifying invalid characters.
+ */
+ public void setInvalidCharacters (String invalidCharacters)
+ {
+ this.invalidChars = invalidCharacters;
+ }
+
+ /**
+ * Returns a String containing the characters that are valid for input
+ * for this MaskFormatter.
+ * @return a String containing the valid characters.
+ */
+ public String getValidCharacters()
+ {
+ return validChars;
+ }
+
+ /**
+ * Sets characters that are valid for input. If
+ * <code>validCharacters</code> is non-null then no characters that are
+ * not contained in it will be allowed to be input.
+ *
+ * @param validCharacters the String specifying valid characters.
+ */
+ public void setValidCharacters (String validCharacters)
+ {
+ this.validChars = validCharacters;
+ }
+
+ /**
+ * Returns the place holder String that is used in place of missing
+ * characters when the value doesn't completely fill in the spaces
+ * in the mask.
+ * @return the place holder String.
+ */
+ public String getPlaceholder()
+ {
+ return placeHolder;
+ }
+
+ /**
+ * Sets the string to use if the value does not completely fill in the mask.
+ * If this is null, the place holder character will be used instead.
+ * @param placeholder the String to use if the value doesn't completely
+ * fill in the mask.
+ */
+ public void setPlaceholder (String placeholder)
+ {
+ this.placeHolder = placeholder;
+ }
+
+ /**
+ * Returns the character used in place of missing characters when the
+ * value doesn't completely fill the mask.
+ * @return the place holder character
+ */
+ public char getPlaceholderCharacter()
+ {
+ return placeHolderChar;
+ }
+
+ /**
+ * Sets the char to use if the value does not completely fill in the mask.
+ * This is only used if the place holder String has not been set or does
+ * not completely fill in the mask.
+ * @param placeholder the char to use if the value doesn't completely
+ * fill in the mask.
+ */
+ public void setPlaceholderCharacter (char placeholder)
+ {
+ this.placeHolderChar = placeholder;
+ }
+
+ /**
+ * Returns true if stringToValue should return the literal
+ * characters in the mask.
+ * @return true if stringToValue should return the literal
+ * characters in the mask
+ */
+ public boolean getValueContainsLiteralCharacters()
+ {
+ return valueContainsLiteralCharacters;
+ }
+
+ /**
+ * Determines whether stringToValue will return literal characters or not.
+ * @param containsLiteralChars if true, stringToValue will return the
+ * literal characters in the mask, otherwise it will not.
+ */
+ public void setValueContainsLiteralCharacters (boolean containsLiteralChars)
+ {
+ this.valueContainsLiteralCharacters = containsLiteralChars;
+ }
+
+ /**
+ * Sets the mask for this MaskFormatter.
+ * @specnote doesn't actually throw a ParseException even though it is
+ * declared to do so
+ * @param mask the new mask for this MaskFormatter
+ * @throws ParseException if <code>mask</code> is not valid.
+ */
+ public void setMask (String mask) throws ParseException
+ {
+ this.mask = mask;
+
+ // Update the cached maskLength.
+ int end = mask.length() - 1;
+ maskLength = 0;
+ for (int i = 0; i <= end; i++)
+ {
+ // Handle escape characters properly - they don't add to the maskLength
+ // but 2 escape characters in a row is really one escape character and
+ // one literal single quote, so that does add 1 to the maskLength.
+ if (mask.charAt(i) == '\'')
+ {
+ // Escape characters at the end of the mask don't do anything.
+ if (i != end)
+ maskLength++;
+ i++;
+ }
+ else
+ maskLength++;
+ }
+ }
+
+ /**
+ * Installs this MaskFormatter on the JFormattedTextField.
+ * Invokes valueToString to convert the current value from the
+ * JFormattedTextField to a String, then installs the Actions from
+ * getActions, the DocumentFilter from getDocumentFilter, and the
+ * NavigationFilter from getNavigationFilter.
+ *
+ * If valueToString throws a ParseException, this method sets the text
+ * to an empty String and marks the JFormattedTextField as invalid.
+ */
+ public void install (JFormattedTextField ftf)
+ {
+ super.install(ftf);
+ if (ftf != null)
+ {
+ try
+ {
+ valueToString(ftf.getValue());
+ }
+ catch (ParseException pe)
+ {
+ // Set the text to an empty String and mark the JFormattedTextField
+ // as invalid.
+ ftf.setText("");
+ setEditValid(false);
+ }
+ }
+ }
+
+ /**
+ * Parses the text using the mask, valid characters, and invalid characters
+ * to determine the appropriate Object to return. This strips the literal
+ * characters if necessary and invokes super.stringToValue. If the paramter
+ * is invalid for the current mask and valid/invalid character sets this
+ * method will throw a ParseException.
+ *
+ * @param value the String to parse
+ * @throws ParseException if value doesn't match the mask and valid/invalid
+ * character sets
+ */
+ public Object stringToValue (String value) throws ParseException
+ {
+ int vLength = value.length();
+
+ // For value to be a valid it must be the same length as the mask
+ // note this doesn't take into account symbols that occupy more than
+ // one character, this is something we may possibly need to fix.
+ if (maskLength != vLength)
+ throw new ParseException ("stringToValue passed invalid value", vLength);
+
+ // Check if the value is valid according to the mask and valid/invalid
+ // sets.
+ try
+ {
+ convertValue(value, false);
+ }
+ catch (ParseException pe)
+ {
+ throw new ParseException("stringToValue passed invalid value",
+ pe.getErrorOffset());
+ }
+
+ if (!getValueContainsLiteralCharacters())
+ value = stripLiterals(value);
+ return super.stringToValue(value);
+ }
+
+ /**
+ * Strips the literal characters from the given String.
+ * @param value the String to strip
+ * @return the stripped String
+ */
+ String stripLiterals(String value)
+ {
+ StringBuffer result = new StringBuffer();
+ for (int i = 0; i < value.length(); i++)
+ {
+ // Only append the characters that don't correspond to literal
+ // characters in the mask.
+ switch (mask.charAt(i))
+ {
+ case NUM_CHAR:
+ case UPPERCASE_CHAR:
+ case LOWERCASE_CHAR:
+ case ALPHANUM_CHAR:
+ case LETTER_CHAR:
+ case HEX_CHAR:
+ case ANYTHING_CHAR:
+ result.append(value.charAt(i));
+ break;
+ default:
+ }
+ }
+ return result.toString();
+ }
+
+ /**
+ * Returns a String representation of the Object value based on the mask.
+ *
+ * @param value the value to convert
+ * @throws ParseException if value is invalid for this mask and valid/invalid
+ * character sets
+ */
+ public String valueToString (Object value) throws ParseException
+ {
+ String result = super.valueToString(value);
+ int rLength = result.length();
+
+ // If value is longer than the mask, truncate it. Note we may need to
+ // account for symbols that are more than one character long.
+ if (rLength > maskLength)
+ result = result.substring(0, maskLength);
+
+ // Verify the validity and convert to upper/lowercase as needed.
+ result = convertValue(result, true);
+ if (rLength < maskLength)
+ return pad(result, rLength);
+ return result;
+ }
+
+ /**
+ * This method takes in a String and runs it through the mask to make
+ * sure that it is valid. If <code>convert</code> is true, it also
+ * converts letters to upper/lowercase as required by the mask.
+ * @param value the String to convert
+ * @param convert true if we should convert letters to upper/lowercase
+ * @return the converted String
+ * @throws ParseException if the given String isn't valid for the mask
+ */
+ String convertValue(String value, boolean convert) throws ParseException
+ {
+ StringBuffer result = new StringBuffer(value);
+ char markChar;
+ char resultChar;
+ boolean literal;
+
+ // this boolean is specifically to avoid calling the isCharValid method
+ // when neither invalidChars or validChars has been set
+ boolean checkCharSets = (invalidChars != null || validChars != null);
+
+ for (int i = 0, j = 0; i < value.length(); i++, j++)
+ {
+ literal = false;
+ resultChar = result.charAt(i);
+ // This switch block on the mask character checks that the character
+ // within <code>value</code> at that point is valid according to the
+ // mask and also converts to upper/lowercase as needed.
+ switch (mask.charAt(j))
+ {
+ case NUM_CHAR:
+ if (!Character.isDigit(resultChar))
+ throw new ParseException("Number expected", i);
+ break;
+ case UPPERCASE_CHAR:
+ if (!Character.isLetter(resultChar))
+ throw new ParseException("Letter expected", i);
+ if (convert)
+ result.setCharAt(i, Character.toUpperCase(resultChar));
+ break;
+ case LOWERCASE_CHAR:
+ if (!Character.isLetter(resultChar))
+ throw new ParseException("Letter expected", i);
+ if (convert)
+ result.setCharAt(i, Character.toLowerCase(resultChar));
+ break;
+ case ALPHANUM_CHAR:
+ if (!Character.isLetterOrDigit(resultChar))
+ throw new ParseException("Letter or number expected", i);
+ break;
+ case LETTER_CHAR:
+ if (!Character.isLetter(resultChar))
+ throw new ParseException("Letter expected", i);
+ break;
+ case HEX_CHAR:
+ if (hexString.indexOf(resultChar) == -1)
+ throw new ParseException("Hexadecimal character expected", i);
+ break;
+ case ANYTHING_CHAR:
+ break;
+ case ESCAPE_CHAR:
+ // Escape character, check the next character to make sure that
+ // the literals match
+ j++;
+ literal = true;
+ if (resultChar != mask.charAt(j))
+ throw new ParseException ("Invalid character: "+resultChar, i);
+ break;
+ default:
+ literal = true;
+ if (!getValueContainsLiteralCharacters() && convert)
+ throw new ParseException ("Invalid character: "+resultChar, i);
+ else if (resultChar != mask.charAt(j))
+ throw new ParseException ("Invalid character: "+resultChar, i);
+ }
+ // If necessary, check if the character is valid.
+ if (!literal && checkCharSets && !isCharValid(resultChar))
+ throw new ParseException("invalid character: "+resultChar, i);
+
+ }
+ return result.toString();
+ }
+
+ /**
+ * Convenience method used by many other methods to check if a character is
+ * valid according to the mask, the validChars, and the invalidChars. To
+ * be valid a character must:
+ * 1. be allowed by the mask
+ * 2. be present in any non-null validChars String
+ * 3. not be present in any non-null invalidChars String
+ * @param testChar the character to test
+ * @return true if the character is valid
+ */
+ boolean isCharValid(char testChar)
+ {
+ char lower = Character.toLowerCase(testChar);
+ char upper = Character.toUpperCase(testChar);
+ // If validChars isn't null, the character must appear in it.
+ if (validChars != null)
+ if (validChars.indexOf(lower) == -1 && validChars.indexOf(upper) == -1)
+ return false;
+ // If invalidChars isn't null, the character must not appear in it.
+ if (invalidChars != null)
+ if (invalidChars.indexOf(lower) != -1
+ || invalidChars.indexOf(upper) != -1)
+ return false;
+ return true;
+ }
+
+ /**
+ * Pads the value with literals, the placeholder String and/or placeholder
+ * character as appropriate.
+ * @param value the value to pad
+ * @param currLength the current length of the value
+ * @return the padded String
+ */
+ String pad (String value, int currLength)
+ {
+ StringBuffer result = new StringBuffer(value);
+ int index = currLength;
+ while (result.length() < maskLength)
+ {
+ // The character used to pad may be a literal, a character from the
+ // place holder string, or the place holder character. getPadCharAt
+ // will find the proper one for us.
+ result.append (getPadCharAt(index));
+ index++;
+ }
+ return result.toString();
+ }
+
+ /**
+ * Returns the character with which to pad the value at the given index
+ * position. If the mask has a literal at this position, this is returned
+ * otherwise if the place holder string is initialized and is longer than
+ * <code>i</code> characters then the character at position <code>i</code>
+ * from this String is returned. Else, the place holder character is
+ * returned.
+ * @param i the index at which we want to pad the value
+ * @return the character with which we should pad the value
+ */
+ char getPadCharAt(int i)
+ {
+ boolean escaped = false;
+ int target = i;
+ char maskChar;
+ int holderLength = placeHolder == null ? -1 : placeHolder.length();
+ // We must iterate through the mask from the beginning, because the given
+ // index doesn't account for escaped characters. For example, with the
+ // mask "1A'A''A1" index 2 refers to the literalized A, not to the
+ // single quotation.
+ for (int n = 0; n < mask.length(); n++)
+ {
+ maskChar = mask.charAt(n);
+ if (maskChar == ESCAPE_CHAR && !escaped)
+ {
+ target++;
+ escaped = true;
+ }
+ else if (escaped == true)
+ {
+ // Check if target == n which means we've come to the character
+ // we want to return and since it is a literal (because escaped
+ // is true), we return it.
+ if (target == n)
+ return maskChar;
+ escaped = false;
+ }
+ if (target == n)
+ {
+ // We've come to the character we want to return. It wasn't
+ // escaped so if it isn't a literal we should return either
+ // the character from place holder string or the place holder
+ // character, depending on whether or not the place holder
+ // string is long enough.
+ switch (maskChar)
+ {
+ case NUM_CHAR:
+ case UPPERCASE_CHAR:
+ case LOWERCASE_CHAR:
+ case ALPHANUM_CHAR:
+ case LETTER_CHAR:
+ case HEX_CHAR:
+ case ANYTHING_CHAR:
+ if (holderLength > i)
+ return placeHolder.charAt(i);
+ else
+ return placeHolderChar;
+ default:
+ return maskChar;
+ }
+ }
+ }
+ // This shouldn't happen
+ throw new AssertionError("MaskFormatter.getMaskCharAt failed");
+ }
+}
diff --git a/javax/swing/text/NumberFormatter.java b/javax/swing/text/NumberFormatter.java
new file mode 100644
index 000000000..a858ff496
--- /dev/null
+++ b/javax/swing/text/NumberFormatter.java
@@ -0,0 +1,86 @@
+/* NumberFormatter.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package javax.swing.text;
+
+import java.text.Format;
+import java.text.NumberFormat;
+
+/**
+ * <code>NumberFormatter</code> is an {@link InternationalFormatter}
+ * that implements value to string and string to value conversion via
+ * an instance of {@link NumberFormat}.
+ *
+ * @author Anthony Balkissoon abalkiss at redhat dot com
+ * @since 1.4
+ */
+public class NumberFormatter extends InternationalFormatter
+{
+
+ /**
+ * Creates a NumberFormatter with the default NumberFormat from
+ * NumberFormat.getNumberInstance().
+ */
+ public NumberFormatter ()
+ {
+ this (NumberFormat.getNumberInstance());
+ }
+
+ /**
+ * Creates a NumberFormatter with the specified NumberFormat.
+ * @param format the NumberFormat to use for this NumberFormatter.
+ */
+ public NumberFormatter (NumberFormat format)
+ {
+ super(format);
+ setFormat(format);
+ }
+
+ /**
+ * Sets the NumberFormat that this NumberFormatter will use to determine
+ * legal values for editing and displaying.
+ *
+ * @param format the Format to use to determine legal values.
+ */
+ public void setFormat (Format format)
+ {
+ // TODO: This should be different from the super implementation
+ // but I don't yet know how.
+ super.setFormat(format);
+ }
+}
diff --git a/javax/swing/text/ParagraphView.java b/javax/swing/text/ParagraphView.java
index 6fb121f94..c48645031 100644
--- a/javax/swing/text/ParagraphView.java
+++ b/javax/swing/text/ParagraphView.java
@@ -38,6 +38,10 @@ exception statement from your version. */
package javax.swing.text;
+import java.awt.Shape;
+
+import javax.swing.event.DocumentEvent;
+
/**
* A {@link FlowView} that flows it's children horizontally and boxes the rows
* vertically.
@@ -67,6 +71,26 @@ public class ParagraphView extends FlowView implements TabExpander
}
/**
+ * The indentation of the first line of the paragraph.
+ */
+ protected int firstLineIndent;
+
+ /**
+ * The justification of the paragraph.
+ */
+ private int justification;
+
+ /**
+ * The line spacing of this paragraph.
+ */
+ private float lineSpacing;
+
+ /**
+ * The TabSet of this paragraph.
+ */
+ private TabSet tabSet;
+
+ /**
* Creates a new <code>ParagraphView</code> for the given
* <code>Element</code>.
*
@@ -116,4 +140,93 @@ public class ParagraphView extends FlowView implements TabExpander
else
return 0.0F;
}
+
+ /**
+ * Receives notification when some attributes of the displayed element
+ * changes. This triggers a refresh of the cached attributes of this
+ * paragraph.
+ *
+ * @param ev the document event
+ * @param a the allocation of this view
+ * @param fv the view factory to use for creating new child views
+ */
+ public void changedUpdate(DocumentEvent ev, Shape a, ViewFactory fv)
+ {
+ setPropertiesFromAttributes();
+ }
+
+ /**
+ * Fetches the cached properties from the element's attributes.
+ */
+ protected void setPropertiesFromAttributes()
+ {
+ Element el = getElement();
+ AttributeSet atts = el.getAttributes();
+ setFirstLineIndent(StyleConstants.getFirstLineIndent(atts));
+ setLineSpacing(StyleConstants.getLineSpacing(atts));
+ setJustification(StyleConstants.getAlignment(atts));
+ tabSet = StyleConstants.getTabSet(atts);
+ }
+
+ /**
+ * Sets the indentation of the first line of the paragraph.
+ *
+ * @param i the indentation to set
+ */
+ protected void setFirstLineIndent(float i)
+ {
+ firstLineIndent = (int) i;
+ }
+
+ /**
+ * Sets the justification of the paragraph.
+ *
+ * @param j the justification to set
+ */
+ protected void setJustification(int j)
+ {
+ justification = j;
+ }
+
+ /**
+ * Sets the line spacing for this paragraph.
+ *
+ * @param s the line spacing to set
+ */
+ protected void setLineSpacing(float s)
+ {
+ lineSpacing = s;
+ }
+
+ /**
+ * Returns the i-th view from the logical views, before breaking into rows.
+ *
+ * @param i the index of the logical view to return
+ *
+ * @return the i-th view from the logical views, before breaking into rows
+ */
+ protected View getLayoutView(int i)
+ {
+ return layoutPool.getView(i);
+ }
+
+ /**
+ * Returns the number of logical child views.
+ *
+ * @return the number of logical child views
+ */
+ protected int getLayoutViewCount()
+ {
+ return layoutPool.getViewCount();
+ }
+
+ /**
+ * Returns the TabSet used by this ParagraphView.
+ *
+ * @return the TabSet used by this ParagraphView
+ */
+ protected TabSet getTabSet()
+ {
+ return tabSet;
+ }
}
diff --git a/javax/swing/text/PasswordView.java b/javax/swing/text/PasswordView.java
index c3aa66cbe..e54331c5a 100644
--- a/javax/swing/text/PasswordView.java
+++ b/javax/swing/text/PasswordView.java
@@ -41,6 +41,7 @@ package javax.swing.text;
import java.awt.Color;
import java.awt.FontMetrics;
import java.awt.Graphics;
+import java.awt.Rectangle;
import java.awt.Shape;
import javax.swing.JPasswordField;
@@ -211,7 +212,10 @@ public class PasswordView
/**
* Provides a mapping from the document model coordinate space to the
* coordinate space of the view mapped to it.
- *
+ *
+ * This method is overridden to provide a correct mapping with respect to the
+ * echo char and not to the real content.
+ *
* @param pos - the position to convert >= 0
* @param a - the allocated region to render into
* @param b - typesafe enumeration to indicate bias to a position in the model.
@@ -222,7 +226,35 @@ public class PasswordView
public Shape modelToView(int pos, Shape a, Position.Bias b)
throws BadLocationException
{
- return super.modelToView(pos, a, b);
+ Shape newAlloc = adjustAllocation(a);
+
+ // Ensure metrics are up-to-date.
+ updateMetrics();
+
+ // Get rectangle of the line containing position.
+ int lineIndex = getElement().getElementIndex(pos);
+ Rectangle rect = lineToRect(newAlloc, lineIndex);
+
+ // Get the rectangle for position.
+ Element line = getElement().getElement(lineIndex);
+ int lineStart = line.getStartOffset();
+ Segment segment = getLineBuffer();
+ segment.array = new char[pos - lineStart];
+ char echoChar = getEchoChar();
+ for (int i = 0; i < segment.array.length; ++i)
+ segment.array[i] = echoChar;
+ segment.offset = 0;
+ segment.count = segment.array.length;
+
+ int xoffset = Utilities.getTabbedTextWidth(segment, metrics, rect.x,
+ this, lineStart);
+
+ // Calc the real rectangle.
+ rect.x += xoffset;
+ rect.width = 1;
+ rect.height = metrics.getHeight();
+
+ return rect;
}
/**
@@ -239,6 +271,8 @@ public class PasswordView
*/
public int viewToModel(float fx, float fy, Shape a, Position.Bias[] bias)
{
+ // FIXME: This only provides a view->model mapping for the real text
+ // content and does not respect the echo char.
return super.viewToModel(fx, fy, a, bias);
}
}
diff --git a/javax/swing/text/PlainDocument.java b/javax/swing/text/PlainDocument.java
index 9e600c4c9..0c00a06ff 100644
--- a/javax/swing/text/PlainDocument.java
+++ b/javax/swing/text/PlainDocument.java
@@ -105,10 +105,65 @@ public class PlainDocument extends AbstractDocument
return root;
}
- protected void insertUpdate(DefaultDocumentEvent event, AttributeSet attributes)
+ protected void insertUpdate(DefaultDocumentEvent event,
+ AttributeSet attributes)
{
- reindex();
+ int offset = event.getOffset();
+ int end = offset + event.getLength();
+ int elementIndex = rootElement.getElementIndex(offset);
+ Element firstElement = rootElement.getElement(elementIndex);
+
+ // added and removed are Element arrays used to add an ElementEdit
+ // to the DocumentEvent if there were entire lines added or removed.
+ Element[] removed = new Element[1];
+ Element[] added;
+ try
+ {
+ String str = content.getString(0, content.length());
+ ArrayList elts = new ArrayList();
+ // Determine how many NEW lines were added by finding the newline
+ // characters within the newly inserted text
+ int j = firstElement.getStartOffset();
+ int i = str.indexOf('\n', offset);
+ while (i != -1 && i <= end)
+ {
+ // For each new line, create a new element
+ elts.add(createLeafElement(rootElement, SimpleAttributeSet.EMPTY,
+ j, i + 1));
+ j = i + 1;
+ if (j >= str.length())
+ break;
+ i = str.indexOf('\n', j);
+ }
+ // If there were new lines added we have to add an ElementEdit to
+ // the DocumentEvent and we have to call rootElement.replace to
+ // insert the new lines
+ if (elts.size() != 0)
+ {
+ // Set up the ElementEdit by filling the added and removed
+ // arrays with the proper Elements
+ added = new Element[elts.size()];
+ for (int k = 0; k < elts.size(); ++k)
+ added[k] = (Element) elts.get(k);
+ removed[0] = firstElement;
+
+ // Now create and add the ElementEdit
+ ElementEdit e = new ElementEdit(rootElement, elementIndex, removed,
+ added);
+ event.addEdit(e);
+
+ // And call replace to actually make the changes
+ ((BranchElement) rootElement).replace(elementIndex, 1, added);
+ }
+ }
+ catch (BadLocationException e)
+ {
+ // This shouldn't happen so we throw an AssertionError
+ AssertionError ae = new AssertionError();
+ ae.initCause(e);
+ throw ae;
+ }
super.insertUpdate(event, attributes);
}
@@ -116,24 +171,37 @@ public class PlainDocument extends AbstractDocument
{
super.removeUpdate(event);
+ // added and removed are Element arrays used to add an ElementEdit
+ // to the DocumentEvent if there were entire lines added or removed
+ // from the Document
+ Element[] added = new Element[1];
+ Element[] removed;
int p0 = event.getOffset();
- int len = event.getLength();
- int p1 = len + p0;
// check if we must collapse some elements
int i1 = rootElement.getElementIndex(p0);
- int i2 = rootElement.getElementIndex(p1);
+ int i2 = rootElement.getElementIndex(p0 + event.getLength());
if (i1 != i2)
{
- Element el1 = rootElement.getElement(i1);
- Element el2 = rootElement.getElement(i2);
- int start = el1.getStartOffset();
- int end = el2.getEndOffset();
- // collapse elements if the removal spans more than 1 line
- Element newEl = createLeafElement(rootElement,
+ // If there were lines removed then we have to add an ElementEdit
+ // to the DocumentEvent so we set it up now by filling the Element
+ // arrays "removed" and "added" appropriately
+ removed = new Element [i2 - i1 + 1];
+ for (int i = i1; i <= i2; i++)
+ removed[i-i1] = rootElement.getElement(i);
+
+ int start = rootElement.getElement(i1).getStartOffset();
+ int end = rootElement.getElement(i2).getEndOffset();
+ added[0] = createLeafElement(rootElement,
SimpleAttributeSet.EMPTY,
start, end);
- rootElement.replace(i1, i2 - i1 + 1, new Element[]{ newEl });
+
+ // Now create and add the ElementEdit
+ ElementEdit e = new ElementEdit(rootElement, i1, removed, added);
+ event.addEdit(e);
+
+ // collapse elements if the removal spans more than 1 line
+ rootElement.replace(i1, i2 - i1 + 1, added);
}
}
@@ -167,7 +235,7 @@ public class PlainDocument extends AbstractDocument
throws BadLocationException
{
String string = str;
- if (Boolean.TRUE.equals(getProperty("filterNewlines")))
+ if (str != null && Boolean.TRUE.equals(getProperty("filterNewlines")))
string = str.replaceAll("\n", " ");
super.insertString(offs, string, atts);
}
diff --git a/javax/swing/text/PlainView.java b/javax/swing/text/PlainView.java
index 07351ade9..a318ee71a 100644
--- a/javax/swing/text/PlainView.java
+++ b/javax/swing/text/PlainView.java
@@ -46,6 +46,7 @@ import java.awt.Graphics;
import java.awt.Rectangle;
import java.awt.Shape;
+import javax.swing.SwingConstants;
import javax.swing.event.DocumentEvent;
import javax.swing.event.DocumentEvent.ElementChange;
@@ -184,7 +185,6 @@ public class PlainView extends View implements TabExpander
JTextComponent textComponent = (JTextComponent) getContainer();
- g.setFont(textComponent.getFont());
selectedColor = textComponent.getSelectedTextColor();
unselectedColor = textComponent.getForeground();
disabledColor = textComponent.getDisabledTextColor();
@@ -325,19 +325,19 @@ public class PlainView extends View implements TabExpander
Element line = root.getElement(lineClicked);
Segment s = getLineBuffer();
-
int start = line.getStartOffset();
- int end = line.getEndOffset();
+ // We don't want the \n at the end of the line.
+ int end = line.getEndOffset() - 1;
try
- {
- doc.getText(start, end - start, s);
- }
+ {
+ doc.getText(start, end - start, s);
+ }
catch (BadLocationException ble)
- {
- AssertionError ae = new AssertionError("Unexpected bad location");
- ae.initCause(ble);
- throw ae;
- }
+ {
+ AssertionError ae = new AssertionError("Unexpected bad location");
+ ae.initCause(ble);
+ throw ae;
+ }
int pos = Utilities.getTabbedTextOffset(s, metrics, rec.x, (int)x, this, start);
return Math.max (0, pos);
@@ -512,7 +512,8 @@ public class PlainView extends View implements TabExpander
else
{
Rectangle repaintRec = rec0.union(rec1);
- host.repaint();
+ host.repaint(repaintRec.x, repaintRec.y, repaintRec.width,
+ repaintRec.height);
}
}
diff --git a/javax/swing/text/StyleConstants.java b/javax/swing/text/StyleConstants.java
index 7d8f9bb63..598eaf621 100644
--- a/javax/swing/text/StyleConstants.java
+++ b/javax/swing/text/StyleConstants.java
@@ -54,11 +54,13 @@ public class StyleConstants
public static final Object BidiLevel = CharacterConstants.BidiLevel;
public static final Object Bold = CharacterConstants.Bold;
public static final Object ComponentAttribute = CharacterConstants.ComponentAttribute;
- public static final Object FontFamily = CharacterConstants.Family;
+ public static final Object Family = CharacterConstants.Family;
+ public static final Object FontFamily = CharacterConstants.Family;
public static final Object FontSize = CharacterConstants.Size;
public static final Object Foreground = CharacterConstants.Foreground;
public static final Object IconAttribute = CharacterConstants.IconAttribute;
public static final Object Italic = CharacterConstants.Italic;
+ public static final Object Size = CharacterConstants.Size;
public static final Object StrikeThrough = CharacterConstants.StrikeThrough;
public static final Object Subscript = CharacterConstants.Subscript;
public static final Object Superscript = CharacterConstants.Superscript;
diff --git a/javax/swing/text/Utilities.java b/javax/swing/text/Utilities.java
index cdbe9f98e..1adc8ff87 100644
--- a/javax/swing/text/Utilities.java
+++ b/javax/swing/text/Utilities.java
@@ -40,8 +40,13 @@ package javax.swing.text;
import java.awt.FontMetrics;
import java.awt.Graphics;
+import java.awt.Point;
+import java.awt.Rectangle;
import java.text.BreakIterator;
+import javax.swing.SwingConstants;
+import javax.swing.SwingUtilities;
+
/**
* A set of utilities to deal with text. This is used by several other classes
* inside this package.
@@ -522,4 +527,85 @@ public class Utilities
// just break it on the character boundary
return mark;
}
+
+ /**
+ * Returns the paragraph element in the text component <code>c</code> at
+ * the specified location <code>offset</code>.
+ *
+ * @param c the text component
+ * @param offset the offset of the paragraph element to return
+ *
+ * @return the paragraph element at <code>offset</code>
+ */
+ public static final Element getParagraphElement(JTextComponent c, int offset)
+ {
+ Document doc = c.getDocument();
+ Element par = null;
+ if (doc instanceof StyledDocument)
+ {
+ StyledDocument styledDoc = (StyledDocument) doc;
+ par = styledDoc.getParagraphElement(offset);
+ }
+ else
+ {
+ Element root = c.getDocument().getDefaultRootElement();
+ int parIndex = root.getElementIndex(offset);
+ par = root.getElement(parIndex);
+ }
+ return par;
+ }
+
+ /**
+ * Returns the document position that is closest above to the specified x
+ * coordinate in the row containing <code>offset</code>.
+ *
+ * @param c the text component
+ * @param offset the offset
+ * @param x the x coordinate
+ *
+ * @return the document position that is closest above to the specified x
+ * coordinate in the row containing <code>offset</code>
+ *
+ * @throws BadLocationException if <code>offset</code> is not a valid offset
+ */
+ public static final int getPositionAbove(JTextComponent c, int offset, int x)
+ throws BadLocationException
+ {
+ View rootView = c.getUI().getRootView(c);
+ Rectangle r = c.modelToView(offset);
+ int offs = c.viewToModel(new Point(x, r.y));
+ int pos = rootView.getNextVisualPositionFrom(offs,
+ Position.Bias.Forward,
+ SwingUtilities.calculateInnerArea(c, null),
+ SwingConstants.NORTH,
+ new Position.Bias[1]);
+ return pos;
+ }
+
+ /**
+ * Returns the document position that is closest below to the specified x
+ * coordinate in the row containing <code>offset</code>.
+ *
+ * @param c the text component
+ * @param offset the offset
+ * @param x the x coordinate
+ *
+ * @return the document position that is closest above to the specified x
+ * coordinate in the row containing <code>offset</code>
+ *
+ * @throws BadLocationException if <code>offset</code> is not a valid offset
+ */
+ public static final int getPositionBelow(JTextComponent c, int offset, int x)
+ throws BadLocationException
+ {
+ View rootView = c.getUI().getRootView(c);
+ Rectangle r = c.modelToView(offset);
+ int offs = c.viewToModel(new Point(x, r.y));
+ int pos = rootView.getNextVisualPositionFrom(offs,
+ Position.Bias.Forward,
+ SwingUtilities.calculateInnerArea(c, null),
+ SwingConstants.SOUTH,
+ new Position.Bias[1]);
+ return pos;
+ }
}
diff --git a/javax/swing/text/View.java b/javax/swing/text/View.java
index 7b3039cfb..2de85446f 100644
--- a/javax/swing/text/View.java
+++ b/javax/swing/text/View.java
@@ -594,4 +594,52 @@ public abstract class View implements SwingConstants
for (int i = 0; i < count; ++i)
getView(i).dump(indent + 1);
}
+
+ /**
+ * Returns the document position that is (visually) nearest to the given
+ * document position <code>pos</code> in the given direction <code>d</code>.
+ *
+ * @param pos the document position
+ * @param b the bias for <code>pos</code>
+ * @param a the allocation for this view
+ * @param d the direction, must be either {@link SwingConstants#NORTH},
+ * {@link SwingConstants#SOUTH}, {@link SwingConstants#WEST} or
+ * {@link SwingConstants#EAST}
+ * @param biasRet an array of {@link Position.Bias} that can hold at least
+ * one element, which is filled with the bias of the return position
+ * on method exit
+ *
+ * @return the document position that is (visually) nearest to the given
+ * document position <code>pos</code> in the given direction
+ * <code>d</code>
+ *
+ * @throws BadLocationException if <code>pos</code> is not a valid offset in
+ * the document model
+ * @throws IllegalArgumentException if <code>d</code> is not a valid direction
+ */
+ public int getNextVisualPositionFrom(int pos, Position.Bias b,
+ Shape a, int d,
+ Position.Bias[] biasRet)
+ throws BadLocationException
+ {
+ int ret = pos;
+ switch (d)
+ {
+ case WEST:
+ ret = pos - 1;
+ break;
+ case EAST:
+ ret = pos + 1;
+ break;
+ case NORTH:
+ // TODO: Implement this
+ break;
+ case SOUTH:
+ // TODO: Implement this
+ break;
+ default:
+ throw new IllegalArgumentException("Illegal value for d");
+ }
+ return ret;
+ }
}
diff --git a/javax/swing/text/WrappedPlainView.java b/javax/swing/text/WrappedPlainView.java
index 5b70c9df2..baba343c5 100644
--- a/javax/swing/text/WrappedPlainView.java
+++ b/javax/swing/text/WrappedPlainView.java
@@ -45,11 +45,12 @@ import java.awt.Graphics;
import java.awt.Rectangle;
import java.awt.Shape;
+import javax.swing.SwingConstants;
import javax.swing.event.DocumentEvent;
import javax.swing.text.Position.Bias;
/**
- * @author abalkiss
+ * @author Anthony Balkissoon abalkiss at redhat dot com
*
*/
public class WrappedPlainView extends BoxView implements TabExpander
@@ -72,6 +73,12 @@ public class WrappedPlainView extends BoxView implements TabExpander
/** A ViewFactory that creates WrappedLines **/
ViewFactory viewFactory = new WrappedLineCreator();
+ /** The start of the selected text **/
+ int selectionStart;
+
+ /** The end of the selected text **/
+ int selectionEnd;
+
/**
* The instance returned by {@link #getLineBuffer()}.
*/
@@ -143,7 +150,44 @@ public class WrappedPlainView extends BoxView implements TabExpander
{
try
{
- drawUnselectedText(g, x, y, p0, p1);
+ // We have to draw both selected and unselected text. There are
+ // several cases:
+ // - entire range is unselected
+ // - entire range is selected
+ // - start of range is selected, end of range is unselected
+ // - start of range is unselected, end of range is selected
+ // - middle of range is selected, start and end of range is unselected
+
+ // entire range unselected:
+ if ((selectionStart == selectionEnd) ||
+ (p0 > selectionEnd || p1 < selectionStart))
+ drawUnselectedText(g, x, y, p0, p1);
+
+ // entire range selected
+ else if (p0 >= selectionStart && p1 <= selectionEnd)
+ drawSelectedText(g, x, y, p0, p1);
+
+ // start of range selected, end of range unselected
+ else if (p0 >= selectionStart)
+ {
+ x = drawSelectedText(g, x, y, p0, selectionEnd);
+ drawUnselectedText(g, x, y, selectionEnd, p1);
+ }
+
+ // start of range unselected, end of range selected
+ else if (selectionStart > p0 && selectionEnd > p1)
+ {
+ x = drawUnselectedText(g, x, y, p0, selectionStart);
+ drawSelectedText(g, x, y, selectionStart, p1);
+ }
+
+ // middle of range selected
+ else if (selectionStart > p0)
+ {
+ x = drawUnselectedText(g, x, y, p0, selectionStart);
+ x = drawSelectedText(g, x, y, selectionStart, selectionEnd);
+ drawUnselectedText(g, x, y, selectionEnd, p1);
+ }
}
catch (BadLocationException ble)
{
@@ -169,7 +213,7 @@ public class WrappedPlainView extends BoxView implements TabExpander
g.setColor(selectedColor);
Segment segment = getLineBuffer();
getDocument().getText(p0, p1 - p0, segment);
- return Utilities.drawTabbedText(segment, x, y, g, this, 0);
+ return Utilities.drawTabbedText(segment, x, y, g, this, p0);
}
/**
@@ -184,7 +228,7 @@ public class WrappedPlainView extends BoxView implements TabExpander
*/
protected int drawUnselectedText(Graphics g, int x, int y, int p0, int p1)
throws BadLocationException
- {
+ {
JTextComponent textComponent = (JTextComponent) getContainer();
if (textComponent.isEnabled())
g.setColor(unselectedColor);
@@ -193,7 +237,7 @@ public class WrappedPlainView extends BoxView implements TabExpander
Segment segment = getLineBuffer();
getDocument().getText(p0, p1 - p0, segment);
- return Utilities.drawTabbedText(segment, x, y, g, this, segment.offset);
+ return Utilities.drawTabbedText(segment, x, y, g, this, p0);
}
/**
@@ -267,6 +311,26 @@ public class WrappedPlainView extends BoxView implements TabExpander
}
/**
+ * Determines the minimum span along the given axis. Implemented to
+ * cache the font metrics and then call the super classes method.
+ */
+ public float getMinimumSpan (int axis)
+ {
+ updateMetrics();
+ return super.getMinimumSpan(axis);
+ }
+
+ /**
+ * Determines the maximum span along the given axis. Implemented to
+ * cache the font metrics and then call the super classes method.
+ */
+ public float getMaximumSpan (int axis)
+ {
+ updateMetrics();
+ return super.getMaximumSpan(axis);
+ }
+
+ /**
* Called when something was inserted. Overridden so that
* the view factory creates WrappedLine views.
*/
@@ -319,6 +383,9 @@ public class WrappedPlainView extends BoxView implements TabExpander
*/
public void paint(Graphics g, Shape a)
{
+ JTextComponent comp = (JTextComponent)getContainer();
+ selectionStart = comp.getSelectionStart();
+ selectionEnd = comp.getSelectionEnd();
updateMetrics();
super.paint(g, a);
}
@@ -330,6 +397,8 @@ public class WrappedPlainView extends BoxView implements TabExpander
public void setSize (float width, float height)
{
updateMetrics();
+ if (width != getWidth())
+ preferenceChanged(null, true, true);
super.setSize(width, height);
}
@@ -359,6 +428,10 @@ public class WrappedPlainView extends BoxView implements TabExpander
unselectedColor = textComponent.getForeground();
disabledColor = textComponent.getDisabledTextColor();
+ // FIXME: this is a hack, for some reason textComponent.getSelectedColor
+ // was returning black, which is not visible against a black background
+ selectedColor = Color.WHITE;
+
Rectangle rect = s.getBounds();
int lineHeight = metrics.getHeight();
@@ -384,11 +457,11 @@ public class WrappedPlainView extends BoxView implements TabExpander
*/
int determineNumLines()
{
+ numLines = 0;
int end = getEndOffset();
if (end == 0)
return 0;
-
- numLines = 0;
+
int breakPoint;
for (int i = getStartOffset(); i < end;)
{
@@ -434,7 +507,8 @@ public class WrappedPlainView extends BoxView implements TabExpander
* in model space
* @throws BadLocationException if the given model position is invalid
*/
- public Shape modelToView(int pos, Shape a, Bias b) throws BadLocationException
+ public Shape modelToView(int pos, Shape a, Bias b)
+ throws BadLocationException
{
Segment s = getLineBuffer();
int lineHeight = metrics.getHeight();
@@ -467,7 +541,9 @@ public class WrappedPlainView extends BoxView implements TabExpander
{
// Shouldn't happen
}
- rect.x += Utilities.getTabbedTextWidth(s, metrics, rect.x, WrappedPlainView.this, currLineStart);
+ rect.x += Utilities.getTabbedTextWidth(s, metrics, rect.x,
+ WrappedPlainView.this,
+ currLineStart);
return rect;
}
// Increment rect.y so we're checking the next logical line
@@ -544,5 +620,51 @@ public class WrappedPlainView extends BoxView implements TabExpander
currLineStart = currLineEnd;
}
}
+
+ /**
+ * This method is called from insertUpdate and removeUpdate.
+ * If the number of lines in the document has changed, just repaint
+ * the whole thing (note, could improve performance by not repainting
+ * anything above the changes). If the number of lines hasn't changed,
+ * just repaint the given Rectangle.
+ * @param a the Rectangle to repaint if the number of lines hasn't changed
+ */
+ void updateDamage (Rectangle a)
+ {
+ int newNumLines = determineNumLines();
+ if (numLines != newNumLines)
+ {
+ numLines = newNumLines;
+ getContainer().repaint();
+ }
+ else
+ getContainer().repaint(a.x, a.y, a.width, a.height);
+ }
+
+ /**
+ * This method is called when something is inserted into the Document
+ * that this View is displaying.
+ *
+ * @param changes the DocumentEvent for the changes.
+ * @param a the allocation of the View
+ * @param f the ViewFactory used to rebuild
+ */
+ public void insertUpdate (DocumentEvent changes, Shape a, ViewFactory f)
+ {
+ updateDamage((Rectangle)a);
+ }
+
+ /**
+ * This method is called when something is removed from the Document
+ * that this View is displaying.
+ *
+ * @param changes the DocumentEvent for the changes.
+ * @param a the allocation of the View
+ * @param f the ViewFactory used to rebuild
+ */
+ public void removeUpdate (DocumentEvent changes, Shape a, ViewFactory f)
+ {
+ updateDamage((Rectangle)a);
+ }
}
}
diff --git a/javax/swing/tree/DefaultTreeCellEditor.java b/javax/swing/tree/DefaultTreeCellEditor.java
index 2891a778e..ae8b99c2f 100644
--- a/javax/swing/tree/DefaultTreeCellEditor.java
+++ b/javax/swing/tree/DefaultTreeCellEditor.java
@@ -339,9 +339,8 @@ public class DefaultTreeCellEditor
lastPath = tree.getLeadSelectionPath();
tree.addTreeSelectionListener(this);
editingContainer = createContainer();
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
- setFont(defaults.getFont("Tree.font"));
- setBorderSelectionColor(defaults.getColor("Tree.selectionBorderColor"));
+ setFont(UIManager.getFont("Tree.font"));
+ setBorderSelectionColor(UIManager.getColor("Tree.selectionBorderColor"));
editingIcon = renderer.getIcon();
timer = new javax.swing.Timer(1200, this);
}
@@ -735,9 +734,8 @@ public class DefaultTreeCellEditor
*/
protected TreeCellEditor createTreeCellEditor()
{
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
realEditor = new DefaultCellEditor(new DefaultTreeCellEditor.DefaultTextField(
- defaults.getBorder("Tree.selectionBorder")));
+ UIManager.getBorder("Tree.selectionBorder")));
return realEditor;
}
}
diff --git a/javax/swing/tree/DefaultTreeCellRenderer.java b/javax/swing/tree/DefaultTreeCellRenderer.java
index 4a353b301..df70ba7fb 100644
--- a/javax/swing/tree/DefaultTreeCellRenderer.java
+++ b/javax/swing/tree/DefaultTreeCellRenderer.java
@@ -51,7 +51,6 @@ import javax.swing.border.Border;
import javax.swing.Icon;
import javax.swing.JLabel;
import javax.swing.JTree;
-import javax.swing.UIDefaults;
import javax.swing.UIManager;
import javax.swing.SwingUtilities;
import javax.swing.plaf.UIResource;
@@ -133,17 +132,15 @@ public class DefaultTreeCellRenderer
*/
public DefaultTreeCellRenderer()
{
- UIDefaults defaults = UIManager.getLookAndFeelDefaults();
-
setLeafIcon(getDefaultLeafIcon());
setOpenIcon(getDefaultOpenIcon());
setClosedIcon(getDefaultClosedIcon());
- setTextNonSelectionColor(defaults.getColor("Tree.textForeground"));
- setTextSelectionColor(defaults.getColor("Tree.selectionForeground"));
- setBackgroundNonSelectionColor(defaults.getColor("Tree.nonSelectionBackground"));
- setBackgroundSelectionColor(defaults.getColor("Tree.selectionBackground"));
- setBorderSelectionColor(defaults.getColor("Tree.selectionBorderColor"));
+ setTextNonSelectionColor(UIManager.getColor("Tree.textForeground"));
+ setTextSelectionColor(UIManager.getColor("Tree.selectionForeground"));
+ setBackgroundNonSelectionColor(UIManager.getColor("Tree.nonSelectionBackground"));
+ setBackgroundSelectionColor(UIManager.getColor("Tree.selectionBackground"));
+ setBorderSelectionColor(UIManager.getColor("Tree.selectionBorderColor"));
}
// -------------------------------------------------------------
@@ -157,7 +154,7 @@ public class DefaultTreeCellRenderer
*/
public Icon getDefaultOpenIcon()
{
- return UIManager.getLookAndFeelDefaults().getIcon("Tree.openIcon");
+ return UIManager.getIcon("Tree.openIcon");
}
/**
@@ -167,7 +164,7 @@ public class DefaultTreeCellRenderer
*/
public Icon getDefaultClosedIcon()
{
- return UIManager.getLookAndFeelDefaults().getIcon("Tree.closedIcon");
+ return UIManager.getIcon("Tree.closedIcon");
}
/**
@@ -177,7 +174,7 @@ public class DefaultTreeCellRenderer
*/
public Icon getDefaultLeafIcon()
{
- return UIManager.getLookAndFeelDefaults().getIcon("Tree.leafIcon");
+ return UIManager.getIcon("Tree.leafIcon");
}
/**
@@ -412,15 +409,14 @@ public class DefaultTreeCellRenderer
setOpaque(false);
setVerticalAlignment(TOP);
setEnabled(true);
- super.setFont(UIManager.getLookAndFeelDefaults().getFont("Tree.font"));
+ super.setFont(UIManager.getFont("Tree.font"));
if (selected)
{
super.setBackground(getBackgroundSelectionColor());
setForeground(getTextSelectionColor());
- if (tree.getLeadSelectionPath() == null ||
- (tree.getLeadSelectionPath().getLastPathComponent()).equals(val))
+ if (hasFocus)
setBorderSelectionColor(UIManager.getLookAndFeelDefaults().
getColor("Tree.selectionBorderColor"));
else
@@ -460,8 +456,7 @@ public class DefaultTreeCellRenderer
Rectangle tr = new Rectangle();
Insets insets = new Insets(0, 0, 0, 0);
- Border border = UIManager.getLookAndFeelDefaults().getBorder(
- "Tree.selectionBorder");
+ Border border = UIManager.getBorder("Tree.selectionBorder");
if (border != null)
insets = border.getBorderInsets(this);
diff --git a/lib/.cvsignore b/lib/.cvsignore
index 5bda1237a..beb0f009b 100644
--- a/lib/.cvsignore
+++ b/lib/.cvsignore
@@ -32,3 +32,4 @@ org
META-INF
Makefile.deps
lists
+copy-vmresources.sh
diff --git a/native/jni/gtk-peer/Makefile.am b/native/jni/gtk-peer/Makefile.am
index bb947424c..46ea172f3 100644
--- a/native/jni/gtk-peer/Makefile.am
+++ b/native/jni/gtk-peer/Makefile.am
@@ -55,11 +55,11 @@ libgtkpeer_la_LIBADD = $(top_builddir)/native/jni/classpath/native_state.lo \
$(top_builddir)/native/jni/classpath/jcl.lo
AM_LDFLAGS = @CLASSPATH_MODULE@ @GTK_LIBS@ @CAIRO_LIBS@ @PANGOFT2_LIBS@ \
- @FREETYPE2_LIBS@ @X_PRE_LIBS@ @X_LIBS@ @X_EXTRA_LIBS@ -lX11 -lXtst
+ @X_PRE_LIBS@ @X_LIBS@ @X_EXTRA_LIBS@ -lX11 -lXtst
AM_CPPFLAGS = @CLASSPATH_INCLUDES@
# Just the WARNING_CFLAGS. We cannot use the strict flags since the gtk
# headers contain broken prototypes (by design, see gtkitemfactory.h).
AM_CFLAGS = @WARNING_CFLAGS@ @ERROR_CFLAGS@ \
- @GTK_CFLAGS@ @CAIRO_CFLAGS@ @PANGOFT2_CFLAGS@ @FREETYPE2_CFLAGS@ \
+ @GTK_CFLAGS@ @CAIRO_CFLAGS@ @PANGOFT2_CFLAGS@ \
@X_CFLAGS@
diff --git a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkFontPeer.c b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkFontPeer.c
index ce65a1994..30f2d5e24 100644
--- a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkFontPeer.c
+++ b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkFontPeer.c
@@ -65,6 +65,9 @@ Java_gnu_java_awt_peer_gtk_GdkFontPeer_initStaticState
glyphVector_class = (*env)->FindClass
(env, "gnu/java/awt/peer/gtk/GdkGlyphVector");
+ glyphVector_class = (*env)->NewGlobalRef
+ (env, glyphVector_class);
+
glyphVector_ctor = (*env)->GetMethodID
(env, glyphVector_class, "<init>",
"([D[ILjava/awt/Font;Ljava/awt/font/FontRenderContext;)V");
@@ -288,6 +291,10 @@ Java_gnu_java_awt_peer_gtk_GdkFontPeer_getTextMetrics
const char *cstr = NULL;
jdouble *native_metrics = NULL;
PangoRectangle log;
+ PangoRectangle log2;
+ int line_count = 0;
+ int i = 0;
+ int width = 0;
gdk_threads_enter();
@@ -296,9 +303,17 @@ Java_gnu_java_awt_peer_gtk_GdkFontPeer_getTextMetrics
cstr = (*env)->GetStringUTFChars (env, str, NULL);
g_assert(cstr != NULL);
-
+
pango_layout_set_text (pfont->layout, cstr, -1);
pango_layout_get_extents (pfont->layout, NULL, &log);
+
+ line_count = pango_layout_get_line_count (pfont->layout);
+ for (i = 0; i < line_count; i++)
+ {
+ pango_layout_line_get_extents (pango_layout_get_line (pfont->layout, i),
+ NULL, &log2);
+ width += log2.width;
+ }
(*env)->ReleaseStringUTFChars (env, str, cstr);
pango_layout_set_text (pfont->layout, "", -1);
@@ -312,12 +327,12 @@ Java_gnu_java_awt_peer_gtk_GdkFontPeer_getTextMetrics
native_metrics[TEXT_METRICS_Y_BEARING]
= PANGO_PIXELS( ((double)log.y) );
- native_metrics[TEXT_METRICS_WIDTH]
- = PANGO_PIXELS( ((double)log.width) );
-
native_metrics[TEXT_METRICS_HEIGHT]
= PANGO_PIXELS( ((double)log.height) );
+ native_metrics[TEXT_METRICS_WIDTH]
+ = PANGO_PIXELS( ((double)width) );
+
native_metrics[TEXT_METRICS_X_ADVANCE]
= PANGO_PIXELS( ((double) (log.x + log.width)) );
diff --git a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkGraphics.c b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkGraphics.c
index 4aca1cf57..244c27e6b 100644
--- a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkGraphics.c
+++ b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkGraphics.c
@@ -291,6 +291,11 @@ Java_gnu_java_awt_peer_gtk_GdkGraphics_drawString
struct peerfont *pfont = NULL;
struct graphics *g = NULL;
const char *cstr = NULL;
+ const char *sTmp = NULL;
+ char *tmp = NULL;
+ char *p = NULL;
+ int count = 0;
+ int charSize = 0;
int baseline_y = 0;
PangoLayoutIter *iter = NULL;
@@ -303,9 +308,29 @@ Java_gnu_java_awt_peer_gtk_GdkGraphics_drawString
g_assert (pfont != NULL);
cstr = (*env)->GetStringUTFChars (env, str, NULL);
+ g_assert (cstr != NULL);
+
+ charSize = sizeof(char);
+ p = malloc((strlen(cstr) + 1) * charSize);
+ g_assert (p != NULL);
+
+ tmp = p;
+ sTmp = cstr;
+ for (; *sTmp != '\0'; sTmp++)
+ if (((unsigned char) *sTmp) >= ' ')
+ {
+ *p = *sTmp;
+ count++;
+ p++;
+ }
+ *p = '\0';
+
+ p = realloc(tmp, (count + 1) * charSize);
+ g_assert (p != NULL);
+ pango_layout_set_text (pfont->layout, p, -1);
+ free(p);
pango_layout_set_font_description (pfont->layout, pfont->desc);
- pango_layout_set_text (pfont->layout, cstr, -1);
iter = pango_layout_get_iter (pfont->layout);
baseline_y = pango_layout_iter_get_baseline (iter);
@@ -317,7 +342,7 @@ Java_gnu_java_awt_peer_gtk_GdkGraphics_drawString
pango_layout_iter_free (iter);
pango_layout_set_text (pfont->layout, "", -1);
-
+
gdk_flush ();
(*env)->ReleaseStringUTFChars (env, str, cstr);
diff --git a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkGraphics2D.c b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkGraphics2D.c
index 17effd88f..092e997a3 100644
--- a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkGraphics2D.c
+++ b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkGraphics2D.c
@@ -565,6 +565,13 @@ Java_gnu_java_awt_peer_gtk_GdkGraphics2D_gdkDrawDrawable
/* gdk_flush(); */
+ if (!GDK_IS_DRAWABLE (src->drawable) ||
+ !GDK_IS_DRAWABLE (dst->drawable))
+ {
+ gdk_threads_leave ();
+ return;
+ }
+
gdk_drawable_get_size (src->drawable, &s_width, &s_height);
gdk_drawable_get_size (dst->drawable, &d_width, &d_height);
width = min (s_width, d_width);
@@ -780,12 +787,13 @@ Java_gnu_java_awt_peer_gtk_GdkGraphics2D_setGradientUnlocked
if (peer_is_disposed(env, obj))
return;
- if (gr->debug) printf ("setGradient (%f,%f) -> (%f,%f); (%d,%d,%d,%d) -> (%d,%d,%d,%d)\n",
- x1, y1,
- x2, y2,
- r1, g1, b1, a1,
- r2, g2, b2, a2);
-
+ if (gr->debug)
+ printf ("setGradientUnlocked (%f,%f) -> (%f,%f); (%d,%d,%d,%d) -> (%d,%d,%d,%d)\n",
+ x1, y1,
+ x2, y2,
+ r1, g1, b1, a1,
+ r2, g2, b2, a2);
+
if (cyclic)
surf = cairo_surface_create_similar (gr->surface, CAIRO_FORMAT_ARGB32, 3, 2);
else
@@ -906,8 +914,9 @@ Java_gnu_java_awt_peer_gtk_GdkGraphics2D_setTexturePixelsUnlocked
gr = (struct graphics2d *) NSA_GET_G2D_PTR (env, obj);
g_assert (gr != NULL);
- if (gr->debug) printf ("setTexturePixels (%d pixels, %dx%d, stride: %d)\n",
- (*env)->GetArrayLength (env, jarr), w, h, stride);
+ if (gr->debug)
+ printf ("setTexturePixelsUnlocked (%d pixels, %dx%d, stride: %d)\n",
+ (*env)->GetArrayLength (env, jarr), w, h, stride);
if (gr->pattern)
cairo_pattern_destroy (gr->pattern);
@@ -960,8 +969,9 @@ Java_gnu_java_awt_peer_gtk_GdkGraphics2D_drawPixels
gr = (struct graphics2d *) NSA_GET_G2D_PTR (env, obj);
g_assert (gr != NULL);
- if (gr->debug) printf ("drawPixels (%d pixels, %dx%d, stride: %d)\n",
- (*env)->GetArrayLength (env, java_pixels), w, h, stride);
+ if (gr->debug)
+ printf ("drawPixels (%d pixels, %dx%d, stride: %d)\n",
+ (*env)->GetArrayLength (env, java_pixels), w, h, stride);
native_pixels = (*env)->GetIntArrayElements (env, java_pixels, NULL);
native_matrix = (*env)->GetDoubleArrayElements (env, java_matrix, NULL);
@@ -1081,10 +1091,11 @@ Java_gnu_java_awt_peer_gtk_GdkGraphics2D_cairoSetMatrixUnlocked
g_assert (native_matrix != NULL);
g_assert ((*env)->GetArrayLength (env, java_matrix) == 6);
- if (gr->debug) printf ("cairo_set_matrix [ %f, %f, %f, %f, %f, %f ]\n",
- native_matrix[0], native_matrix[1],
- native_matrix[2], native_matrix[3],
- native_matrix[4], native_matrix[5]);
+ if (gr->debug)
+ printf ("cairo_matrix_init [ %f, %f, %f, %f, %f, %f ]\n",
+ native_matrix[0], native_matrix[1],
+ native_matrix[2], native_matrix[3],
+ native_matrix[4], native_matrix[5]);
{
cairo_matrix_t mat;
@@ -1272,7 +1283,7 @@ Java_gnu_java_awt_peer_gtk_GdkGraphics2D_cairoDrawGlyphVector
(*env)->ReleaseFloatArrayElements (env, java_positions, native_positions, 0);
(*env)->ReleaseIntArrayElements (env, java_codes, native_codes, 0);
- begin_drawing_operation (env, gr);
+ begin_drawing_operation (env, gr);
cairo_show_glyphs (gr->cr, glyphs, n);
end_drawing_operation (env, gr);
@@ -1440,7 +1451,8 @@ Java_gnu_java_awt_peer_gtk_GdkGraphics2D_cairoSetRGBAColorUnlocked
draw to a PixBuf, you must exchange the R and B components of your
color. */
- if (gr->debug) printf ("cairo_set_source_rgb (%f, %f, %f)\n", r, g, b);
+ if (gr->debug)
+ printf ("cairo_set_source_rgba (%f, %f, %f, %f)\n", r, g, b, a);
if (gr->drawbuf)
cairo_set_source_rgba (gr->cr, b, g, r, a);
@@ -1731,7 +1743,9 @@ Java_gnu_java_awt_peer_gtk_GdkGraphics2D_cairoCurveTo
gr = (struct graphics2d *) NSA_GET_G2D_PTR (env, obj);
g_assert (gr != NULL);
- if (gr->debug) printf ("cairo_curve_to (%f, %f), (%f, %f), (%f, %f)\n", x1, y1, x2, y2, x3, y3);
+ if (gr->debug)
+ printf ("cairo_curve_to (%f, %f), (%f, %f), (%f, %f)\n",
+ x1, y1, x2, y2, x3, y3);
cairo_curve_to (gr->cr, x1, y1, x2, y2, x3, y3);
gdk_threads_leave();
@@ -1797,7 +1811,9 @@ Java_gnu_java_awt_peer_gtk_GdkGraphics2D_cairoRelCurveTo
gr = (struct graphics2d *) NSA_GET_G2D_PTR (env, obj);
g_assert (gr != NULL);
- if (gr->debug) printf ("cairo_rel_curve_to (%f, %f), (%f, %f), (%f, %f)\n", dx1, dy1, dx2, dy2, dx3, dy3);
+ if (gr->debug)
+ printf ("cairo_rel_curve_to (%f, %f), (%f, %f), (%f, %f)\n",
+ dx1, dy1, dx2, dy2, dx3, dy3);
cairo_rel_curve_to (gr->cr, dx1, dy1, dx2, dy2, dx3, dy3);
gdk_threads_leave();
@@ -1825,7 +1841,8 @@ Java_gnu_java_awt_peer_gtk_GdkGraphics2D_cairoRectangle
return;
}
- if (gr->debug) printf ("cairo_rectangle (%f, %f) (%f, %f)\n", x, y, width, height);
+ if (gr->debug)
+ printf ("cairo_rectangle (%f, %f) (%f, %f)\n", x, y, width, height);
cairo_rectangle (gr->cr, x, y, width, height);
gdk_threads_leave();
@@ -1955,7 +1972,7 @@ Java_gnu_java_awt_peer_gtk_GdkGraphics2D_cairoSurfaceSetFilterUnlocked
gr = (struct graphics2d *) NSA_GET_G2D_PTR (env, obj);
g_assert (gr != NULL);
- if (gr->debug) printf ("cairo_surface_set_filter %d\n", filter);
+ if (gr->debug) printf ("cairo_pattern_set_filter %d\n", filter);
switch ((enum java_awt_rendering_hints_filter) filter)
{
case java_awt_rendering_hints_VALUE_INTERPOLATION_NEAREST_NEIGHBOR:
diff --git a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkGraphicsEnvironment.c b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkGraphicsEnvironment.c
index 0467c3c7a..7662800f0 100644
--- a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkGraphicsEnvironment.c
+++ b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkGraphicsEnvironment.c
@@ -71,6 +71,7 @@ Java_gnu_java_awt_peer_gtk_GdkGraphicsEnvironment_nativeGetFontFamilies
const char *name_tmp = pango_font_family_get_name (families[idx]);
jstring name = (*env)->NewStringUTF (env, name_tmp);
(*env)->SetObjectArrayElement (env, family_name, idx, name);
+ (*env)->DeleteLocalRef(env, name);
}
g_free (families);
diff --git a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkPixbufDecoder.c b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkPixbufDecoder.c
index 74103b5da..4d6169b85 100644
--- a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkPixbufDecoder.c
+++ b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GdkPixbufDecoder.c
@@ -270,6 +270,8 @@ query_formats (JNIEnv *env, jclass clazz)
(*env)->DeleteLocalRef(env, string);
++ch;
}
+
+ (*env)->DeleteLocalRef(env, jformat);
}
g_slist_free(formats);
@@ -376,6 +378,7 @@ save_to_stream(const gchar *buf,
(*(ssr->env))->ReleaseByteArrayElements ((ssr->env), jbuf, cbuf, 0);
(*(ssr->env))->CallVoidMethod ((ssr->env), *(ssr->stream),
dataOutputWriteID, jbuf);
+ (*(ssr->env))->DeleteLocalRef((ssr->env), jbuf);
gdk_threads_enter ();
diff --git a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkChoicePeer.c b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkChoicePeer.c
index c5bf5a353..e9a0f693e 100644
--- a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkChoicePeer.c
+++ b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkChoicePeer.c
@@ -121,6 +121,7 @@ Java_gnu_java_awt_peer_gtk_GtkChoicePeer_append
gtk_combo_box_append_text (GTK_COMBO_BOX (ptr), label);
(*env)->ReleaseStringUTFChars (env, item, label);
+ (*env)->DeleteLocalRef(env, item);
}
gdk_threads_leave ();
diff --git a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkClipboard.c b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkClipboard.c
index f10a80d58..3b62dc335 100644
--- a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkClipboard.c
+++ b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkClipboard.c
@@ -53,7 +53,7 @@ jstring cp_gtk_imageTarget;
jstring cp_gtk_filesTarget;
/* Simple id to keep track of the selection we are currently managing. */
-static int current_selection = 0;
+static gint current_selection = 0;
/* Whether we "own" the clipboard. And may clear it. */
static int owner = 0;
@@ -261,7 +261,7 @@ static void
clipboard_clear_func (GtkClipboard *clipboard __attribute__((unused)),
gpointer user_data)
{
- if (owner && (int) user_data == current_selection)
+ if (owner && GPOINTER_TO_INT(user_data) == current_selection)
{
JNIEnv *env = cp_gtk_gdk_env();
owner = 0;
@@ -351,7 +351,7 @@ Java_gnu_java_awt_peer_gtk_GtkClipboard_advertiseContent
if (gtk_clipboard_set_with_data (cp_gtk_clipboard, targets, n,
clipboard_get_func,
clipboard_clear_func,
- (gpointer) current_selection))
+ GINT_TO_POINTER(current_selection)))
{
owner = 1;
if (gtk_clipboard_instance == NULL)
diff --git a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkComponentPeer.c b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkComponentPeer.c
index 85ce2ae65..6de7b61b8 100644
--- a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkComponentPeer.c
+++ b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkComponentPeer.c
@@ -454,7 +454,7 @@ Java_gnu_java_awt_peer_gtk_GtkComponentPeer_gtkWidgetDispatchKeyEvent
* Find the origin of a widget's window.
*/
JNIEXPORT void JNICALL
-Java_gnu_java_awt_peer_gtk_GtkComponentPeer_gtkWidgetGetLocationOnScreen
+Java_gnu_java_awt_peer_gtk_GtkComponentPeer_gtkWindowGetLocationOnScreen
(JNIEnv * env, jobject obj, jintArray jpoint)
{
void *ptr;
@@ -467,11 +467,34 @@ Java_gnu_java_awt_peer_gtk_GtkComponentPeer_gtkWidgetGetLocationOnScreen
gdk_window_get_root_origin (GTK_WIDGET (ptr)->window, point, point+1);
- if (!GTK_IS_CONTAINER (ptr))
- {
- *point += GTK_WIDGET(ptr)->allocation.x;
- *(point+1) += GTK_WIDGET(ptr)->allocation.y;
- }
+ (*env)->ReleaseIntArrayElements(env, jpoint, point, 0);
+
+ gdk_threads_leave ();
+}
+
+/*
+ * Find the origin of a widget
+ */
+JNIEXPORT void JNICALL
+Java_gnu_java_awt_peer_gtk_GtkComponentPeer_gtkWidgetGetLocationOnScreen
+ (JNIEnv * env, jobject obj, jintArray jpoint)
+{
+ void *ptr;
+ jint *point;
+ GtkWidget *widget;
+
+ gdk_threads_enter ();
+
+ ptr = NSA_GET_PTR (env, obj);
+ point = (*env)->GetIntArrayElements (env, jpoint, 0);
+
+ widget = GTK_WIDGET(ptr);
+ while(gtk_widget_get_parent(widget) != NULL)
+ widget = gtk_widget_get_parent(widget);
+ gdk_window_get_position (GTK_WIDGET(widget)->window, point, point+1);
+
+ *point += GTK_WIDGET(ptr)->allocation.x;
+ *(point+1) += GTK_WIDGET(ptr)->allocation.y;
(*env)->ReleaseIntArrayElements(env, jpoint, point, 0);
diff --git a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkListPeer.c b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkListPeer.c
index fc89ab71c..6da42cec6 100644
--- a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkListPeer.c
+++ b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkListPeer.c
@@ -239,6 +239,7 @@ Java_gnu_java_awt_peer_gtk_GtkListPeer_append
COLUMN_STRING, text,
-1);
(*env)->ReleaseStringUTFChars (env, item, text);
+ (*env)->DeleteLocalRef(env, item);
}
gdk_threads_leave ();
diff --git a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkSelection.c b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkSelection.c
index f744e90ad..3244d2364 100644
--- a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkSelection.c
+++ b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkSelection.c
@@ -130,6 +130,7 @@ clipboard_targets_received (GtkClipboard *clipboard
break;
(*env)->SetObjectArrayElement (env, strings, i++,
string);
+ (*env)->DeleteLocalRef (env, string);
}
}
}
@@ -201,6 +202,10 @@ clipboard_text_received (GtkClipboard *clipboard
textAvailableID,
string);
(*env)->DeleteGlobalRef (env, selection_obj);
+
+ if (string != NULL)
+ (*env)->DeleteLocalRef (env, string);
+
}
JNIEXPORT void JNICALL
@@ -324,6 +329,7 @@ clipboard_uris_received (GtkClipboard *clipboard
if (string == NULL)
break;
(*env)->SetObjectArrayElement (env, strings, i, string);
+ (*env)->DeleteLocalRef (env, string);
}
}
g_strfreev (uris);
diff --git a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkToolkit.c b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkToolkit.c
index 59b56cf35..b14330e5f 100644
--- a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkToolkit.c
+++ b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkToolkit.c
@@ -135,6 +135,8 @@ Java_gnu_java_awt_peer_gtk_GtkToolkit_gtkInit (JNIEnv *env,
gtkgenericpeer = (*env)->FindClass(env, "gnu/java/awt/peer/gtk/GtkGenericPeer");
+ gtkgenericpeer = (*env)->NewGlobalRef(env, gtkgenericpeer);
+
printCurrentThreadID = (*env)->GetStaticMethodID (env, gtkgenericpeer,
"printCurrentThread", "()V");
diff --git a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkWindowPeer.c b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkWindowPeer.c
index d79bbecba..ac8f6a8ff 100644
--- a/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkWindowPeer.c
+++ b/native/jni/gtk-peer/gnu_java_awt_peer_gtk_GtkWindowPeer.c
@@ -1204,8 +1204,8 @@ Java_gnu_java_awt_peer_gtk_GtkWindowPeer_gtkWindowSetResizable
gdk_threads_enter ();
ptr = NSA_GET_PTR (env, obj);
-
gtk_window_set_resizable (GTK_WINDOW (ptr), resizable);
+ g_object_set (G_OBJECT (ptr), "allow-shrink", resizable, NULL);
gdk_threads_leave ();
}
diff --git a/native/jni/java-io/Makefile.am b/native/jni/java-io/Makefile.am
index efa7d5688..35afaae50 100644
--- a/native/jni/java-io/Makefile.am
+++ b/native/jni/java-io/Makefile.am
@@ -1,8 +1,6 @@
nativelib_LTLIBRARIES = libjavaio.la
-libjavaio_la_SOURCES = javaio.h \
- javaio.c \
- java_io_VMFile.c \
+libjavaio_la_SOURCES = java_io_VMFile.c \
java_io_VMObjectInputStream.c \
java_io_VMObjectStreamClass.c
diff --git a/native/jni/java-io/java_io_VMFile.c b/native/jni/java-io/java_io_VMFile.c
index b32c29477..354df04ed 100644
--- a/native/jni/java-io/java_io_VMFile.c
+++ b/native/jni/java-io/java_io_VMFile.c
@@ -50,8 +50,6 @@ exception statement from your version. */
#endif
#include "target_native_math_int.h"
-#include "javaio.h"
-
#include "java_io_VMFile.h"
/*************************************************************************/
diff --git a/native/jni/java-io/javaio.c b/native/jni/java-io/javaio.c
deleted file mode 100644
index 6dc3de8f0..000000000
--- a/native/jni/java-io/javaio.c
+++ /dev/null
@@ -1,363 +0,0 @@
-/* javaio.c - Common java.io native functions
- Copyright (C) 1998, 2002, 2004 Free Software Foundation, Inc.
-
-This file is part of GNU Classpath.
-
-GNU Classpath is free software; you can redistribute it and/or modify
-it under the terms of the GNU General Public License as published by
-the Free Software Foundation; either version 2, or (at your option)
-any later version.
-
-GNU Classpath is distributed in the hope that it will be useful, but
-WITHOUT ANY WARRANTY; without even the implied warranty of
-MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
-General Public License for more details.
-
-You should have received a copy of the GNU General Public License
-along with GNU Classpath; see the file COPYING. If not, write to the
-Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
-02110-1301 USA.
-
-Linking this library statically or dynamically with other modules is
-making a combined work based on this library. Thus, the terms and
-conditions of the GNU General Public License cover the whole
-combination.
-
-As a special exception, the copyright holders of this library give you
-permission to link this library with independent modules to produce an
-executable, regardless of the license terms of these independent
-modules, and to copy and distribute the resulting executable under
-terms of your choice, provided that you also meet, for each linked
-independent module, the terms and conditions of the license of that
-module. An independent module is a module which is not derived from
-or based on this library. If you modify this library, you may extend
-this exception to your version of the library, but you are not
-obligated to do so. If you do not wish to do so, delete this
-exception statement from your version. */
-
-/* do not move; needed here because of some macro definitions */
-#include <config.h>
-
-#include <stdio.h>
-#include <stdlib.h>
-
-#include <jni.h>
-#include <jcl.h>
-
-#include "target_native.h"
-#ifndef WITHOUT_FILESYSTEM
-#include "target_native_file.h"
-#endif
-#include "target_native_math_int.h"
-
-#include "javaio.h"
-
-/*
- * Function to open a file
- */
-
-jint
-_javaio_open_read (JNIEnv * env, jstring name)
-{
-#ifndef WITHOUT_FILESYSTEM
- const char *filename;
- int fd;
- int result;
-
- filename = JCL_jstring_to_cstring (env, name);
- if (filename == NULL)
- return (-1);
-
- TARGET_NATIVE_FILE_OPEN_READ (filename, fd, result);
- (*env)->ReleaseStringUTFChars (env, name, filename);
- if (result != TARGET_NATIVE_OK)
- {
- if (TARGET_NATIVE_LAST_ERROR () == TARGET_NATIVE_ERROR_NO_SUCH_FILE)
- JCL_ThrowException (env,
- "java/io/FileNotFoundException",
- TARGET_NATIVE_LAST_ERROR_STRING ());
- else
- JCL_ThrowException (env,
- "java/io/IOException",
- TARGET_NATIVE_LAST_ERROR_STRING ());
- }
-
- JCL_free_cstring (env, name, filename);
- return (fd);
-#else /* not WITHOUT_FILESYSTEM */
- return (-1);
-#endif /* not WITHOUT_FILESYSTEM */
-}
-
-/*
- * Function to open a file for reading/writing
- */
-
-jint
-_javaio_open_readwrite (JNIEnv * env, jstring name)
-{
-#ifndef WITHOUT_FILESYSTEM
- const char *filename;
- int fd;
- int result;
-
- filename = JCL_jstring_to_cstring (env, name);
- if (filename == NULL)
- return (-1);
-
- TARGET_NATIVE_FILE_OPEN_READWRITE (filename, fd, result);
- (*env)->ReleaseStringUTFChars (env, name, filename);
- if (result != TARGET_NATIVE_OK)
- {
- if (TARGET_NATIVE_LAST_ERROR () == TARGET_NATIVE_ERROR_NO_SUCH_FILE)
- JCL_ThrowException (env,
- "java/io/FileNotFoundException",
- TARGET_NATIVE_LAST_ERROR_STRING ());
- else
- JCL_ThrowException (env,
- "java/io/IOException",
- TARGET_NATIVE_LAST_ERROR_STRING ());
- }
-
- JCL_free_cstring (env, name, filename);
- return (fd);
-#else /* not WITHOUT_FILESYSTEM */
- return (-1);
-#endif /* not WITHOUT_FILESYSTEM */
-}
-
-/*************************************************************************/
-
-/*
- * Function to close a file
- */
-
-void
-_javaio_close (JNIEnv * env, jint fd)
-{
-#ifndef WITHOUT_FILESYSTEM
- int result;
-
- if (fd != -1)
- {
- TARGET_NATIVE_FILE_CLOSE (fd, result);
- if (result != TARGET_NATIVE_OK)
- JCL_ThrowException (env,
- "java/io/IOException",
- TARGET_NATIVE_LAST_ERROR_STRING ());
- }
-#else /* not WITHOUT_FILESYSTEM */
-#endif /* not WITHOUT_FILESYSTEM */
-}
-
-/*************************************************************************/
-
-/*
- * Skips bytes in a file
- */
-
-jlong
-_javaio_skip_bytes (JNIEnv * env, jint fd, jlong num_bytes)
-{
-#ifndef WITHOUT_FILESYSTEM
- jlong current_offset, new_offset;
- int result;
-
- TARGET_NATIVE_FILE_SEEK_CURRENT (fd, TARGET_NATIVE_MATH_INT_INT64_CONST_0,
- current_offset, result);
- if (result != TARGET_NATIVE_OK)
- JCL_ThrowException (env,
- "java/io/IOException",
- TARGET_NATIVE_LAST_ERROR_STRING ());
-
- TARGET_NATIVE_FILE_SEEK_CURRENT (fd, num_bytes, new_offset, result);
- if (result != TARGET_NATIVE_OK)
- JCL_ThrowException (env,
- "java/io/IOException",
- TARGET_NATIVE_LAST_ERROR_STRING ());
-
- return (TARGET_NATIVE_MATH_INT_INT64_SUB (new_offset, current_offset));
-#else /* not WITHOUT_FILESYSTEM */
- return (TARGET_NATIVE_MATH_INT_INT64_CONST_0);
-#endif /* not WITHOUT_FILESYSTEM */
-}
-
-/*************************************************************************/
-
-/*
- * Gets the size of the file
- */
-
-jlong
-_javaio_get_file_length (JNIEnv * env, jint fd)
-{
-#ifndef WITHOUT_FILESYSTEM
- jlong length;
- int result;
-
- TARGET_NATIVE_FILE_SIZE (fd, length, result);
- if (result != TARGET_NATIVE_OK)
- {
- JCL_ThrowException (env,
- "java/io/IOException",
- TARGET_NATIVE_LAST_ERROR_STRING ());
- return (TARGET_NATIVE_MATH_INT_INT64_CONST_MINUS_1);
- }
-
- return (length);
-#else /* not WITHOUT_FILESYSTEM */
- return (TARGET_NATIVE_MATH_INT_INT64_CONST_0);
-#endif /* not WITHOUT_FILESYSTEM */
-}
-
-/*************************************************************************/
-
-/*
- * Reads data from a file
- */
-
-jint
-_javaio_read (JNIEnv * env, jint fd, jarray buf, jint offset, jint len)
-{
-#ifndef WITHOUT_FILESYSTEM
- jbyte *bufptr;
- int bytesRead;
- int result;
-
- assert (offset >= 0);
- assert (len >= 0);
-
- if (len == 0)
- return 0; /* Nothing todo, and GetByteArrayElements() seems undefined. */
-
- bufptr = (*env)->GetByteArrayElements (env, buf, JNI_FALSE);
- if (bufptr == NULL)
- {
- JCL_ThrowException (env, "java/io/IOException",
- "Internal Error: get byte array fail");
- return (-1);
- }
-
- TARGET_NATIVE_FILE_READ (fd, (bufptr + offset), len, bytesRead, result);
- (*env)->ReleaseByteArrayElements (env, buf, bufptr, 0);
- if (result != TARGET_NATIVE_OK)
- JCL_ThrowException (env,
- "java/io/IOException",
- TARGET_NATIVE_LAST_ERROR_STRING ());
-
- if (bytesRead == 0)
- return (-1);
-
- return (bytesRead);
-#else /* not WITHOUT_FILESYSTEM */
- jbyte *bufptr;
- int bytesRead;
-
- assert (offset >= 0);
- assert (len >= 0);
-
- if ((fd == 0) || (fd == 1) || (fd == 2))
- {
- if (len == 0)
- return 0; /* Nothing todo, and GetByteArrayElements() seems undefined. */
-
- bufptr = (*env)->GetByteArrayElements (env, buf, JNI_FALSE);
- if (bufptr == NULL)
- {
- JCL_ThrowException (env, "java/io/IOException",
- "Internal Error: get byte array");
- return (-1);
- }
-
- TARGET_NATIVE_FILE_READ (fd, (bufptr + offset), len, bytesRead, result);
- (*env)->ReleaseByteArrayElements (env, buf, bufptr, 0);
- if (result != TARGET_NATIVE_OK)
- JCL_ThrowException (env,
- "java/io/IOException",
- TARGET_NATIVE_LAST_ERROR_STRING ());
-
- if (bytesRead == 0)
- return (-1);
-
- return (bytesRead);
- }
- else
- {
- return (-1);
- }
-#endif /* not WITHOUT_FILESYSTEM */
-}
-
-/*************************************************************************/
-
-/*
- * Writes data to a file
- */
-
-jint
-_javaio_write (JNIEnv * env, jint fd, jarray buf, jint offset, jint len)
-{
-#ifndef WITHOUT_FILESYSTEM
- jbyte *bufptr;
- int bytes_written;
- int result;
-
- if (len == 0)
- return 0; /* Nothing todo, and GetByteArrayElements() seems undefined. */
-
- bufptr = (*env)->GetByteArrayElements (env, buf, 0);
- if (bufptr == NULL)
- {
- JCL_ThrowException (env, "java/io/IOException",
- "Internal Error: get byte array");
- return (-1);
- }
-
- TARGET_NATIVE_FILE_WRITE (fd, (bufptr + offset), len, bytes_written,
- result);
- (*env)->ReleaseByteArrayElements (env, buf, bufptr, 0);
- if (result != TARGET_NATIVE_OK)
- JCL_ThrowException (env,
- "java/io/IOException",
- TARGET_NATIVE_LAST_ERROR_STRING ());
-
- if (bytes_written == 0)
- return (-1);
-
- return (bytes_written);
-#else /* not WITHOUT_FILESYSTEM */
- jbyte *bufptr;
- int bytesWritten;
-
- if ((fd == 0) || (fd == 1) || (fd == 2))
- {
- if (len == 0)
- return 0; /* Nothing todo, and GetByteArrayElements() seems undefined. */
-
- bufptr = (*env)->GetByteArrayElements (env, buf, 0);
- if (bufptr == NULL)
- {
- JCL_ThrowException (env, "java/io/IOException", "Internal Error");
- return (-1);
- }
-
- TARGET_NATIVE_FILE_WRITE (fd, (bufptr + offset), len, bytes_written,
- result);
- (*env)->ReleaseByteArrayElements (env, buf, bufptr, 0);
-
- if (bytes_written == -1)
- JCL_ThrowException (env,
- "java/io/IOException",
- TARGET_NATIVE_LAST_ERROR_STRING ());
-
- if (bytes_written == 0)
- return (-1);
-
- return (bytes_written);
- }
- else
- {
- return (-1);
- }
-#endif /* not WITHOUT_FILESYSTEM */
-}
diff --git a/native/jni/java-lang/java_lang_VMDouble.c b/native/jni/java-lang/java_lang_VMDouble.c
index 846df2e6a..076f42b86 100644
--- a/native/jni/java-lang/java_lang_VMDouble.c
+++ b/native/jni/java-lang/java_lang_VMDouble.c
@@ -71,6 +71,11 @@ Java_java_lang_VMDouble_initIDs (JNIEnv * env, jclass cls __attribute__ ((__unus
{
DBG ("unable to get class java.lang.Double\n") return;
}
+ clsDouble = (*env)->NewGlobalRef(env, clsDouble);
+ if (clsDouble == NULL)
+ {
+ DBG ("unable to register class java.lang.Double as global ref\n") return;
+ }
isNaNID = (*env)->GetStaticMethodID (env, clsDouble, "isNaN", "(D)Z");
if (isNaNID == NULL)
{
diff --git a/native/jni/java-nio/gnu_java_nio_charset_iconv_IconvDecoder.c b/native/jni/java-nio/gnu_java_nio_charset_iconv_IconvDecoder.c
index 2541e81ea..b82cd2d90 100644
--- a/native/jni/java-nio/gnu_java_nio_charset_iconv_IconvDecoder.c
+++ b/native/jni/java-nio/gnu_java_nio_charset_iconv_IconvDecoder.c
@@ -140,7 +140,7 @@ Java_gnu_java_nio_charset_iconv_IconvDecoder_decode (JNIEnv * env,
if (retval == (size_t) (-1))
{
- if (errno == EILSEQ || errno == EINVAL)
+ if (errno == EILSEQ)
retval = 1;
else
retval = 0;
diff --git a/native/jni/java-nio/java_nio.c b/native/jni/java-nio/java_nio.c
index a25f38a6d..bd6f97d3e 100644
--- a/native/jni/java-nio/java_nio.c
+++ b/native/jni/java-nio/java_nio.c
@@ -52,8 +52,6 @@ exception statement from your version. */
#include "java_nio_channels_FileChannelImpl.h"
-#include "javaio.h"
-
#define NIO_DEBUG(X) /* no debug */
//#define NIO_DEBUG(X) X
diff --git a/native/jni/midi-alsa/.cvsignore b/native/jni/midi-alsa/.cvsignore
index a71781585..483b27744 100644
--- a/native/jni/midi-alsa/.cvsignore
+++ b/native/jni/midi-alsa/.cvsignore
@@ -5,3 +5,5 @@
.libs
.depsMakefile
Makefile.in
+Makefile
+.deps
diff --git a/native/jni/midi-dssi/.cvsignore b/native/jni/midi-dssi/.cvsignore
index a71781585..ac18ca272 100644
--- a/native/jni/midi-dssi/.cvsignore
+++ b/native/jni/midi-dssi/.cvsignore
@@ -5,3 +5,5 @@
.libs
.depsMakefile
Makefile.in
+.deps
+Makefile
diff --git a/native/jni/midi-dssi/Makefile.am b/native/jni/midi-dssi/Makefile.am
index 58ee5c925..6b1ef0407 100644
--- a/native/jni/midi-dssi/Makefile.am
+++ b/native/jni/midi-dssi/Makefile.am
@@ -1,7 +1,8 @@
nativelib_LTLIBRARIES = libgjsmdssi.la
libgjsmdssi_la_SOURCES = gnu_javax_sound_midi_dssi_DSSIMidiDeviceProvider.c \
-gnu_javax_sound_midi_dssi_DSSISynthesizer.c
+ gnu_javax_sound_midi_dssi_DSSISynthesizer.c \
+ dssi_data.h
libgjsmdssi_la_LIBADD = $(top_builddir)/native/jni/classpath/jcl.lo -ljack
diff --git a/native/jni/qt-peer/qtmenupeer.cpp b/native/jni/qt-peer/qtmenupeer.cpp
index bf081e984..1ac17145c 100644
--- a/native/jni/qt-peer/qtmenupeer.cpp
+++ b/native/jni/qt-peer/qtmenupeer.cpp
@@ -125,6 +125,7 @@ public:
jclass menuCls = env->GetObjectClass( menuPeer );
jmethodID mid = env->GetMethodID(menuCls, "add", "(J)V");
+ env->DeleteLocalRef(menuCls);
env->CallVoidMethod( menuPeer, mid, (jlong)newAction );
env->DeleteGlobalRef( menuPeer );
diff --git a/native/jni/xmlj/xmlj_util.h b/native/jni/xmlj/xmlj_util.h
index 7bbe78b8e..72601ae9f 100644
--- a/native/jni/xmlj/xmlj_util.h
+++ b/native/jni/xmlj/xmlj_util.h
@@ -1,5 +1,5 @@
/* xmlj_util.h -
- Copyright (C) 2003, 2004 Free Software Foundation, Inc.
+ Copyright (C) 2003, 2004, 2005 Free Software Foundation, Inc.
This file is part of GNU Classpath.
@@ -38,10 +38,6 @@ exception statement from your version. */
#ifndef XMLJ_UTIL_H
#define XMLJ_UTIL_H
-#if defined __64BIT__ || defined __LP64 || defined _LP64 || defined __LP64__ || defined _ADDR64
-# define XMLJ_64BIT_POINTER 1
-#endif
-
#include <jni.h>
#include <libxml/xmlstring.h>
diff --git a/org/omg/CORBA/DATA_CONVERSION.java b/org/omg/CORBA/DATA_CONVERSION.java
index 3faacdcb2..7261aae46 100644
--- a/org/omg/CORBA/DATA_CONVERSION.java
+++ b/org/omg/CORBA/DATA_CONVERSION.java
@@ -44,6 +44,26 @@ import java.io.Serializable;
* Means that the ORB cannot convert between the marshalled and
* native data representation.
*
+ * In GNU Classpath, this exception may have the following minor codes:
+ *
+ * <table border="1">
+ * <tr>
+ * <td>Hex</td>
+ * <td>Dec</td>
+ * <td>Minor</td>
+ * <td>Name</td>
+ * <td>Case</td>
+ * </tr>
+ * <td>47430016</td>
+ * <td>1195573270</td>
+ * <td>22</td>
+ * <td>Missing_IOR</td>
+ * <td>The object URL is such that the IOR string must be read from some
+ * local or remote resource (file or network), but this resource is not
+ * reacheable.</td>
+ * </tr>
+ * </table>
+ *
* @author Audrius Meskauskas (AudriusA@Bioinformatics.org)
*/
public class DATA_CONVERSION
diff --git a/org/omg/CORBA/ORB.java b/org/omg/CORBA/ORB.java
index 667da2da8..98c758445 100644
--- a/org/omg/CORBA/ORB.java
+++ b/org/omg/CORBA/ORB.java
@@ -49,6 +49,7 @@ import gnu.CORBA.typecodes.RecordTypeCode;
import gnu.CORBA.typecodes.RecursiveTypeCode;
import org.omg.CORBA.ORBPackage.InconsistentTypeCode;
+import org.omg.PortableInterceptor.ObjectReferenceTemplate;
import java.applet.Applet;
@@ -97,6 +98,21 @@ import java.util.Properties;
* {@link #resolve_initial_references(String)}.</td>
* </tr>
* <tr>
+ * <td>org.omg.CORBA.ORBid</td>
+ * <td>Specifies the name (ORB Id) of this ORB. The ORB Id is later accessible
+ * by {@link ObjectReferenceTemplate#orb_id}. The default value includes the
+ * hashcode of the ORB instance that is normally different for each ORB.
+ * </td>
+ * </tr>
+ * <tr>
+ * <td>org.omg.CORBA.ServerId</td>
+ * <td>Specifies the name (Server Id) of this server. This property assigns
+ * value to the <i>static</i> field, ensuring that all ORB's on the same jre
+ * have the same Server Id. It is normally set as the system property. The
+ * server Id is later accessible as {@link ObjectReferenceTemplate#server_id}.
+ * </td>
+ * </tr>
+ * <tr>
* <td>gnu.CORBA.ListenerPort</td>
* <td>Specifies that this ORB should serve all its objects on a single port
* (for example, "1234") or on a specified port range (for example,
@@ -1025,6 +1041,12 @@ public abstract class ORB
* that runs on the given host at the given port. The ORB expects to find
* there the {@link org.omg.CosNaming.NamingContext} under the key
* "NameService.<br>
+ * 7. file://[file name] Read the object definition string from the
+ * file system<br>
+ * 8. http://[url] Read the object definition string from the provided
+ * url.<br>
+ * 9. ftp://[url] Read the object definition string from the provided
+ * url.<br>
*
* <p>The default port is always 2809. The default iiop version is 1.0
* that now may not always be supported, so we would recommend to specify
diff --git a/org/omg/PortableInterceptor/IORInfoOperations.java b/org/omg/PortableInterceptor/IORInfoOperations.java
index 58ef02fb0..fdeb2973b 100644
--- a/org/omg/PortableInterceptor/IORInfoOperations.java
+++ b/org/omg/PortableInterceptor/IORInfoOperations.java
@@ -73,7 +73,7 @@ public interface IORInfoOperations
void add_ior_component(TaggedComponent tagged_component);
/**
- * Get the server side policy for an IOR being constructed. The method returns
+ * Get the server side policy for an IOR being constructed. The method returns
* policies applying for POA where the object, represented by this IOR, is
* connected.
*
@@ -85,4 +85,54 @@ public interface IORInfoOperations
* @see org.omg.PortableServer.POAOperations#create_POA
*/
Policy get_effective_policy(int policy_type);
+
+ /**
+ * Get the adapter template that is associated with the object POA.
+ * The template is also a reference factory and can produce the new object
+ * references.
+ *
+ * @since 1.5
+ */
+ public ObjectReferenceTemplate adapter_template();
+
+ /**
+ * The current_factory is the factory, used by the adapter to create
+ * object references. This factory is initially the same as the
+ * adapter_template.
+ *
+ * @since 1.5
+ */
+ public ObjectReferenceFactory current_factory();
+
+ /**
+ * Set the current object reference factory, used to produce the new objects.
+ *
+ * The current factory can only be set during the call to the
+ * {@link IORInterceptor_3_0Operations#components_established(IORInfo)}.
+ *
+ * @since 1.5
+ */
+ public void current_factory(ObjectReferenceFactory factory);
+
+ /**
+ * Get the POA manager Id.
+ *
+ * @return Id that uniquely refers to the poa manager, used by this POA.
+ *
+ * @since 1.5
+ *
+ * @see IORInterceptor_3_0Operations#adapter_manager_state_changed
+ */
+ public int manager_id();
+
+ /**
+ * Get the state of the adapter manager.
+ *
+ * @since 1.5
+ *
+ * @return the state of the adapters to that the IOR being created belongs.
+ * One of the {@link HOLDING#value}, {@link DISCARDING#value},
+ * {@link INACTIVE#value} or {@link NON_EXISTENT#value}.
+ */
+ short state();
} \ No newline at end of file
diff --git a/org/omg/PortableInterceptor/IORInterceptorOperations.java b/org/omg/PortableInterceptor/IORInterceptorOperations.java
index 868fcab6c..746d139cf 100644
--- a/org/omg/PortableInterceptor/IORInterceptorOperations.java
+++ b/org/omg/PortableInterceptor/IORInterceptorOperations.java
@@ -47,12 +47,12 @@ package org.omg.PortableInterceptor;
public interface IORInterceptorOperations extends InterceptorOperations
{
/**
- * A server side ORB calls this method on all registered IORInterceptor's when
+ * A server side ORB calls this method on all registered IORInterceptor's when
* creating the object reference (IOR). The interceptors have the possibility
* to add additional tags to the IOR being created.
*
- * @param info the interface class providing methods to insert additional tags
- * into IOR being constructed. The same instan
+ * @param info the interface class providing methods to insert additional tags
+ * into IOR being constructed.
*/
public void establish_components(IORInfo info);
} \ No newline at end of file
diff --git a/org/omg/PortableInterceptor/IORInterceptor_3_0.java b/org/omg/PortableInterceptor/IORInterceptor_3_0.java
new file mode 100644
index 000000000..4b2093d40
--- /dev/null
+++ b/org/omg/PortableInterceptor/IORInterceptor_3_0.java
@@ -0,0 +1,59 @@
+/* IORInterceptor_3_0.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package org.omg.PortableInterceptor;
+
+import org.omg.CORBA.portable.IDLEntity;
+
+/**
+ * The IORInterceptor_3_0 adds to {@link Interceptor} functionality, available
+ * since CORBA 3.0. These new operations are defined separately in
+ * {@link IORInterceptor_3_0Operations}.
+ *
+ * IORInterceptor_3_0 is registered exactly in the same way as the
+ * {@link IORInterceptor}. The ORB calls the additional methods to all
+ * IOR interceptors that implement this extended interface.
+ *
+ * @since 1.5
+ *
+ * @author Audrius Meskauskas, Lithuania (AudriusA@Bioinformatics.org)
+ */
+public interface IORInterceptor_3_0
+ extends IORInterceptor_3_0Operations, IDLEntity, IORInterceptor
+{
+} \ No newline at end of file
diff --git a/org/omg/PortableInterceptor/IORInterceptor_3_0Helper.java b/org/omg/PortableInterceptor/IORInterceptor_3_0Helper.java
new file mode 100644
index 000000000..565242477
--- /dev/null
+++ b/org/omg/PortableInterceptor/IORInterceptor_3_0Helper.java
@@ -0,0 +1,195 @@
+/* IORInterceptor_3_0Helper.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package org.omg.PortableInterceptor;
+
+import gnu.CORBA.Minor;
+
+import org.omg.CORBA.Any;
+import org.omg.CORBA.BAD_OPERATION;
+import org.omg.CORBA.BAD_PARAM;
+import org.omg.CORBA.ORB;
+import org.omg.CORBA.TypeCode;
+import org.omg.CORBA.portable.Delegate;
+import org.omg.CORBA.portable.InputStream;
+import org.omg.CORBA.portable.ObjectImpl;
+import org.omg.CORBA.portable.OutputStream;
+
+/**
+ * The helper operations for the CORBA object {@link IORInterceptor_3_0}.
+ *
+ * @since 1.5
+ *
+ * @author Audrius Meskauskas, Lithuania (AudriusA@Bioinformatics.org)
+ */
+public abstract class IORInterceptor_3_0Helper
+{
+ /**
+ * The cached {@link IORInterceptor_3_0} typecode, computed once.
+ */
+ private static TypeCode typeCode;
+
+ /**
+ * Get the type code of the {@link IORInterceptor_3_0}.
+ */
+ public static TypeCode type()
+ {
+ if (typeCode == null)
+ typeCode = ORB.init().create_interface_tc(id(), "IORInterceptor_3_0");
+ return typeCode;
+ }
+
+ /**
+ * Insert the IORInterceptor_3_0 into the given Any.
+ *
+ * @param any the Any to insert into.
+ * @param that the IORInterceptor_3_0 to insert.
+ */
+ public static void insert(Any any, IORInterceptor_3_0 that)
+ {
+ any.insert_Streamable(new IORInterceptor_3_0Holder(that));
+ }
+
+ /**
+ * Extract the IORInterceptor_3_0 from given Any.
+ *
+ * @throws BAD_OPERATION if the passed Any does not contain
+ * IORInterceptor_3_0.
+ */
+ public static IORInterceptor_3_0 extract(Any any)
+ {
+ try
+ {
+ IORInterceptor_3_0Holder holder = (IORInterceptor_3_0Holder)
+ any.extract_Streamable();
+ return holder.value;
+ }
+ catch (ClassCastException cex)
+ {
+ BAD_OPERATION bad = new BAD_OPERATION("IORInterceptor_3_0 expected");
+ bad.minor = Minor.Any;
+ bad.initCause(cex);
+ throw bad;
+ }
+ }
+
+ /**
+ * Get the IORInterceptor_3_0 repository id.
+ *
+ * @return "IDL:omg.org/PortableInterceptor/IORInterceptor_3_0:1.0", always.
+ */
+ public static String id()
+ {
+ return "IDL:omg.org/PortableInterceptor/IORInterceptor_3_0:1.0";
+ }
+
+ /**
+ * Narrow the passed object into the IORInterceptor_3_0. If the object has a
+ * different java type, create an instance of the _IORInterceptor_3_0Stub,
+ * using the same delegate, as for the passed parameter. Hence, unlike java
+ * type cast, this method may return a different object, than has been passed.
+ *
+ * @param obj the object to narrow.
+ * @return narrowed instance.
+ * @throws BAD_PARAM if the passed object is not a IORInterceptor_3_0.
+ */
+ public static IORInterceptor_3_0 narrow(org.omg.CORBA.Object obj)
+ {
+ if (obj == null)
+ return null;
+ else if (obj instanceof IORInterceptor_3_0)
+ return (IORInterceptor_3_0) obj;
+ else if (!obj._is_a(id()))
+ throw new BAD_PARAM("Not a IORInterceptor_3_0");
+ else
+ {
+ Delegate delegate = ((ObjectImpl) obj)._get_delegate();
+ return new _IORInterceptor_3_0Stub(delegate);
+ }
+ }
+
+ /**
+ * Narrow the passed object into the IORInterceptor_3_0. No type-checking is
+ * performed to verify that the object actually supports the requested type.
+ * The {@link BAD_OPERATION} will be thrown if unsupported operations are
+ * invoked on the new returned reference, but no failure is expected at the
+ * time of the unchecked_narrow. For instance, the narrowing of the
+ * remote instance of the {@link IORInterceptor} will work as long as only the
+ * methods, inherited from this parent, are invoked.
+ *
+ *
+ * @param obj the object to narrow.
+ * @return narrowed instance.
+ * @throws BAD_PARAM if the passed object is not a IORInterceptor_3_0.
+ */
+ public static IORInterceptor_3_0 unchecked_narrow(org.omg.CORBA.Object obj)
+ {
+ if (obj == null)
+ return null;
+ else if (obj instanceof IORInterceptor_3_0)
+ return (IORInterceptor_3_0) obj;
+ else
+ {
+ Delegate delegate = ((ObjectImpl) obj)._get_delegate();
+ return new _IORInterceptor_3_0Stub(delegate);
+ }
+ }
+
+
+ /**
+ * Read the IORInterceptor_3_0 from the CDR intput stream (IOR profile
+ * expected).
+ *
+ * @param input a org.omg.CORBA.portable stream to read from.
+ */
+ public static IORInterceptor_3_0 read(InputStream input)
+ {
+ return unchecked_narrow(input.read_Object());
+ }
+
+ /**
+ * Write the IORInterceptor_3_0 to the CDR output stream (as IOR profile).
+ *
+ * @param output a org.omg.CORBA.portable stream stream to write into.
+ * @param value a value to write.
+ */
+ public static void write(OutputStream output, IORInterceptor_3_0 value)
+ {
+ output.write_Object(value);
+ }
+} \ No newline at end of file
diff --git a/org/omg/PortableInterceptor/IORInterceptor_3_0Holder.java b/org/omg/PortableInterceptor/IORInterceptor_3_0Holder.java
new file mode 100644
index 000000000..dc7ecf23f
--- /dev/null
+++ b/org/omg/PortableInterceptor/IORInterceptor_3_0Holder.java
@@ -0,0 +1,106 @@
+/* IORInterceptor_3_0Holder.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package org.omg.PortableInterceptor;
+
+import org.omg.CORBA.portable.InputStream;
+import org.omg.CORBA.portable.OutputStream;
+import org.omg.CORBA.portable.Streamable;
+
+/**
+ * A holder for the object {@link IORInterceptor_3_0}.
+ *
+ * @since 1.5
+ *
+ * @author Audrius Meskauskas, Lithuania (AudriusA@Bioinformatics.org)
+ */
+public class IORInterceptor_3_0Holder
+ implements Streamable
+{
+ /**
+ * The stored IORInterceptor_3_0 value.
+ */
+ public IORInterceptor_3_0 value;
+
+ /**
+ * Create the unitialised instance, leaving the value field with default
+ * <code>null</code> value.
+ */
+ public IORInterceptor_3_0Holder()
+ {
+ }
+
+ /**
+ * Create the initialised instance.
+ *
+ * @param initialValue the value that will be assigned to the
+ * <code>value</code> field.
+ */
+ public IORInterceptor_3_0Holder(IORInterceptor_3_0 initialValue)
+ {
+ value = initialValue;
+ }
+
+ /**
+ * Fill in the {@link value} by data from the CDR stream.
+ *
+ * @param input the org.omg.CORBA.portable stream to read.
+ */
+ public void _read(InputStream input)
+ {
+ value = IORInterceptor_3_0Helper.read(input);
+ }
+
+ /**
+ * Write the stored value into the CDR stream.
+ *
+ * @param output the org.omg.CORBA.portable stream to write.
+ */
+ public void _write(OutputStream output)
+ {
+ IORInterceptor_3_0Helper.write(output, value);
+ }
+
+ /**
+ * Get the typecode of the IORInterceptor_3_0.
+ */
+ public org.omg.CORBA.TypeCode _type()
+ {
+ return IORInterceptor_3_0Helper.type();
+ }
+} \ No newline at end of file
diff --git a/org/omg/PortableInterceptor/IORInterceptor_3_0Operations.java b/org/omg/PortableInterceptor/IORInterceptor_3_0Operations.java
new file mode 100644
index 000000000..ce6575a4c
--- /dev/null
+++ b/org/omg/PortableInterceptor/IORInterceptor_3_0Operations.java
@@ -0,0 +1,90 @@
+/* IORInterceptor_3_0Operations.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package org.omg.PortableInterceptor;
+
+/**
+ * Defines the operations, applicable to the IORInterceptor_3_0.
+ *
+ * @since 1.5
+ *
+ * @author Audrius Meskauskas, Lithuania (AudriusA@Bioinformatics.org)
+ */
+public interface IORInterceptor_3_0Operations
+ extends IORInterceptorOperations
+{
+ /**
+ * This method is invoked on all registered IORInterceptor_3_0 instances when
+ * the state of the adapter manager changes.
+ *
+ * @param adapterManagerId the Id of the adapter manager that has changed the
+ * state. The same value is returned by
+ * {@link IORInfoOperations#manager_id()}.
+ *
+ * @param adapterState the new state of the adapter manager, one of the
+ * {@link HOLDING#value}, {@link DISCARDING#value}, {@link INACTIVE#value}
+ * or {@link NON_EXISTENT#value}.
+ */
+ void adapter_manager_state_changed(int adapterManagerId, short adapterState);
+
+ /**
+ * Notifies the interceptor about the adapter state changes that are unrelated
+ * to adapter manager state changes. This method is invoked on all registered
+ * IORInterceptor_3_0 instances. The only currently possible change of state
+ * is when POA is destroyed. In this case, the method is invoked passing the
+ * single element array witn the reference template of the POA being destroyed
+ * and the {@link NON_EXISTENT#value} state.
+ *
+ * @param adapters identifies the object adapters that have changed they
+ * state.
+ * @param adaptersState the new state of the adapters, one of the
+ * {@link HOLDING#value}, {@link DISCARDING#value}, {@link INACTIVE#value}
+ * or {@link NON_EXISTENT#value}.
+ */
+ void adapter_state_changed(ObjectReferenceTemplate[] adapters,
+ short adaptersState);
+
+ /**
+ * This metod is invoked after the
+ * {@link IORInterceptorOperations#establish_components} have been called on
+ * all registered interceptor instances. At this stage, it is possible to set
+ * the object reference factory using
+ * {@link IORInfo#current_factory(ObjectReferenceFactory )}.
+ */
+ void components_established(IORInfo info);
+} \ No newline at end of file
diff --git a/org/omg/PortableInterceptor/ORBInitInfoOperations.java b/org/omg/PortableInterceptor/ORBInitInfoOperations.java
index 9cffbe1b5..7b545ff81 100644
--- a/org/omg/PortableInterceptor/ORBInitInfoOperations.java
+++ b/org/omg/PortableInterceptor/ORBInitInfoOperations.java
@@ -55,7 +55,7 @@ public interface ORBInitInfoOperations
*
* @param interceptor the interceptor to register.
*
- * @throws DuplicateName if the interceptor name is not an empty string and an
+ * @throws DuplicateName if the interceptor name is not an empty string and an
* interceptor with this name is already registered with the ORB being
* created.
*/
@@ -63,11 +63,14 @@ public interface ORBInitInfoOperations
throws DuplicateName;
/**
- * Register the IOR (object reference) interceptor.
- *
+ * Register the IOR (object reference) interceptor. If the registered
+ * interceptor implements the extended {@link IORInterceptor_3_0} interface,
+ * ORB will call its additional methods, defined in the
+ * {@link IORInterceptor_3_0Operations}.
+ *
* @param interceptor the interceptor to register.
- *
- * @throws DuplicateName if the interceptor name is not an empty string and an
+ *
+ * @throws DuplicateName if the interceptor name is not an empty string and an
* interceptor with this name is already registered with the ORB being
* created.
*/
@@ -79,7 +82,7 @@ public interface ORBInitInfoOperations
*
* @param interceptor the interceptor to register.
*
- * @throws DuplicateName if the interceptor name is not an empty string and an
+ * @throws DuplicateName if the interceptor name is not an empty string and an
* interceptor with this name is already registered with the ORB being
* created.
*/
@@ -90,7 +93,7 @@ public interface ORBInitInfoOperations
* Allocate a slot on a {@link PortableInterceptor.Current}. While slots can
* be allocated by this method, they cannot be initialized.
* {@link CurrentOperations#get_slot} and {@link CurrentOperations#set_slot}
- * throw {@link org.omg.CORBA.BAD_INV_ORDER} while called from the interceptor
+ * throw {@link org.omg.CORBA.BAD_INV_ORDER} while called from the interceptor
* initializer.
*
* @return the index to the slot that has been allocated.
diff --git a/org/omg/PortableInterceptor/ObjectReferenceFactory.java b/org/omg/PortableInterceptor/ObjectReferenceFactory.java
index df039901a..55cde585c 100644
--- a/org/omg/PortableInterceptor/ObjectReferenceFactory.java
+++ b/org/omg/PortableInterceptor/ObjectReferenceFactory.java
@@ -52,6 +52,6 @@ import org.omg.CORBA.portable.IDLEntity;
* @author Audrius Meskauskas, Lithuania (AudriusA@Bioinformatics.org)
*/
public interface ObjectReferenceFactory
- extends ObjectReferenceFactoryOperations, IDLEntity, org.omg.CORBA.Object
+ extends ObjectReferenceFactoryOperations, IDLEntity
{
} \ No newline at end of file
diff --git a/org/omg/PortableInterceptor/ObjectReferenceFactoryOperations.java b/org/omg/PortableInterceptor/ObjectReferenceFactoryOperations.java
index d2ce61423..b5d912d12 100644
--- a/org/omg/PortableInterceptor/ObjectReferenceFactoryOperations.java
+++ b/org/omg/PortableInterceptor/ObjectReferenceFactoryOperations.java
@@ -53,11 +53,16 @@ public interface ObjectReferenceFactoryOperations
/**
* Create an object with the given repository and object ids. This interface
* does not specify where and how the returned object must be connected and
- * activated.
- *
+ * activated. The derived {@link ObjectReferenceTemplate} interface assumes
+ * the the object must be connected to the POA that is specific to that
+ * template (name can be obtained).
+ *
+ * If the object with this objectId already exists in the given context, it is
+ * found and returned; the new object is <i>not</i> created.
+ *
* @param repositoryId the repository id of the object being created, defines
* the type of the object.
- *
+ *
* @param objectId the byte array, defining the identity of the object.
*/
org.omg.CORBA.Object make_object(String repositoryId, byte[] objectId);
diff --git a/org/omg/PortableInterceptor/ObjectReferenceTemplate.java b/org/omg/PortableInterceptor/ObjectReferenceTemplate.java
new file mode 100644
index 000000000..666735e76
--- /dev/null
+++ b/org/omg/PortableInterceptor/ObjectReferenceTemplate.java
@@ -0,0 +1,78 @@
+/* ObjectReferenceTemplate.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package org.omg.PortableInterceptor;
+
+import org.omg.PortableServer.POA;
+
+/**
+ * Defines the identity of the portable object adapter ({@link POA}}. The
+ * adapter name, orb id and server id together uniquely define the identity
+ * of this adapter.
+ *
+ * @author Audrius Meskauskas, Lithuania (AudriusA@Bioinformatics.org)
+ */
+public interface ObjectReferenceTemplate
+ extends ObjectReferenceFactory
+{
+ /**
+ * Get the name of this adapter. This name can be set by specifying
+ * the org.omg.CORBA.ORBid property in the ORB.Init(.., Properties).
+ * The default value includes the hashcode of the ORB instance and hence
+ * should normally differ for each ORB.
+ *
+ * @return the name of adapter, represented in the form of the string array.
+ */
+ String[] adapter_name();
+
+ /**
+ * The id of the {@link org.omg.CORBA.ORB} of this adapter.
+ *
+ * @return the ORB id, represented in the form of string.
+ */
+ String orb_id();
+
+ /**
+ * Get the server id of of this adapter. This name can be set by specifying
+ * the org.omg.CORBA.ServerId property in the ORB.Init(.., Properties) or
+ * in the system property. All ORB's on the same jre share the same value.
+ *
+ * @return the server id, represented in the form of string.
+ */
+ String server_id();
+} \ No newline at end of file
diff --git a/org/omg/PortableInterceptor/ObjectReferenceTemplateHelper.java b/org/omg/PortableInterceptor/ObjectReferenceTemplateHelper.java
new file mode 100644
index 000000000..258a73ae8
--- /dev/null
+++ b/org/omg/PortableInterceptor/ObjectReferenceTemplateHelper.java
@@ -0,0 +1,144 @@
+/* ObjectReferenceTemplateHelper.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package org.omg.PortableInterceptor;
+
+import gnu.CORBA.Minor;
+
+import org.omg.CORBA.Any;
+import org.omg.CORBA.BAD_OPERATION;
+import org.omg.CORBA.ORB;
+import org.omg.CORBA.TypeCode;
+import org.omg.CORBA.VM_ABSTRACT;
+import org.omg.CORBA.ValueMember;
+import org.omg.CORBA.portable.InputStream;
+import org.omg.CORBA.portable.OutputStream;
+
+/**
+ * The helper operations for the CORBA object
+ * {@link ObjectReferenceTemplate}.
+ *
+ * @author Audrius Meskauskas, Lithuania (AudriusA@Bioinformatics.org)
+ */
+public abstract class ObjectReferenceTemplateHelper
+{
+ /**
+ * The cached {@link ObjectReferenceTemplate} typecode, computed once.
+ */
+ private static TypeCode typeCode;
+
+ /**
+ * Get the type code of the {@link ObjectReferenceTemplate}.
+ *
+ * @return value type type code, named ObjectReferenceTemplate,
+ * no members, abstract.
+ */
+ public static TypeCode type()
+ {
+ if (typeCode == null)
+ typeCode =
+ ORB.init().create_value_tc(id(), "ObjectReferenceTemplate",
+ VM_ABSTRACT.value, null, new ValueMember[ 0 ]
+ );
+ return typeCode;
+ }
+
+ /**
+ * Insert the ObjectReferenceTemplate into the given Any.
+ *
+ * @param any the Any to insert into.
+ * @param that the ObjectReferenceTemplate to insert.
+ */
+ public static void insert(Any any, ObjectReferenceTemplate that)
+ {
+ any.insert_Streamable(new ObjectReferenceTemplateHolder(that));
+ }
+
+ /**
+ * Extract the ObjectReferenceTemplate from given Any.
+ *
+ * @throws BAD_OPERATION if the passed Any does not
+ * contain ObjectReferenceTemplate.
+ */
+ public static ObjectReferenceTemplate extract(Any any)
+ {
+ try
+ {
+ ObjectReferenceTemplateHolder h =
+ (ObjectReferenceTemplateHolder) any.extract_Streamable();
+ return h.value;
+ }
+ catch (ClassCastException ex)
+ {
+ BAD_OPERATION bad =
+ new BAD_OPERATION("ObjectReferenceTemplate expected");
+ bad.minor = Minor.Any;
+ bad.initCause(ex);
+ throw bad;
+ }
+ }
+
+ /**
+ * Get the ObjectReferenceTemplate repository id.
+ *
+ * @return "IDL:omg.org/PortableInterceptor/ObjectReferenceTemplate:1.0",
+ * always.
+ */
+ public static String id()
+ {
+ return "IDL:omg.org/PortableInterceptor/ObjectReferenceTemplate:1.0";
+ }
+
+ /**
+ * Read the object reference template (as the value type).
+ */
+ public static ObjectReferenceTemplate read(InputStream input)
+ {
+ return (ObjectReferenceTemplate)
+ ((org.omg.CORBA_2_3.portable.InputStream) input).read_value();
+ }
+
+ /**
+ * Write the object reference template (as the value type).
+ */
+ public static void write(OutputStream output, ObjectReferenceTemplate value)
+ {
+ ((org.omg.CORBA_2_3.portable.OutputStream) output).
+ write_value(value);
+ }
+} \ No newline at end of file
diff --git a/org/omg/PortableInterceptor/ObjectReferenceTemplateHolder.java b/org/omg/PortableInterceptor/ObjectReferenceTemplateHolder.java
new file mode 100644
index 000000000..9658e1fa7
--- /dev/null
+++ b/org/omg/PortableInterceptor/ObjectReferenceTemplateHolder.java
@@ -0,0 +1,103 @@
+/* ObjectReferenceTemplateHolder.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package org.omg.PortableInterceptor;
+
+import org.omg.CORBA.portable.Streamable;
+import org.omg.CORBA.portable.InputStream;
+import org.omg.CORBA.portable.OutputStream;
+
+ /**
+ * A holder for the object {@link ObjectReferenceTemplate}.
+ *
+* @author Audrius Meskauskas, Lithuania (AudriusA@Bioinformatics.org)
+ */
+public class ObjectReferenceTemplateHolder
+ implements Streamable
+{
+ /**
+ * The stored ObjectReferenceTemplate value.
+ */
+ public ObjectReferenceTemplate value;
+
+ /**
+ * Create the unitialised instance, leaving the value field
+ * with default <code>null</code> value.
+ */
+ public ObjectReferenceTemplateHolder()
+ {
+ }
+
+ /**
+ * Create the initialised instance.
+ * @param initialValue the value that will be assigned to
+ * the <code>value</code> field.
+ */
+ public ObjectReferenceTemplateHolder(ObjectReferenceTemplate initialValue)
+ {
+ value = initialValue;
+ }
+
+ /**
+ * Fill in the {@link value} by data from the CDR stream.
+ *
+ * @param input the org.omg.CORBA.portable stream to read.
+ */
+ public void _read(InputStream input)
+ {
+ value = ObjectReferenceTemplateHelper .read(input);
+ }
+
+ /**
+ * Write the stored value into the CDR stream.
+ *
+ * @param output the org.omg.CORBA.portable stream to write.
+ */
+ public void _write(OutputStream output)
+ {
+ ObjectReferenceTemplateHelper .write(output, value);
+ }
+
+ /**
+ * Get the typecode of the ObjectReferenceTemplate.
+ */
+ public org.omg.CORBA.TypeCode _type()
+ {
+ return ObjectReferenceTemplateHelper .type();
+ }
+}
diff --git a/org/omg/PortableInterceptor/ObjectReferenceTemplateSeqHelper.java b/org/omg/PortableInterceptor/ObjectReferenceTemplateSeqHelper.java
new file mode 100644
index 000000000..c4f09896f
--- /dev/null
+++ b/org/omg/PortableInterceptor/ObjectReferenceTemplateSeqHelper.java
@@ -0,0 +1,169 @@
+/* ObjectReferenceTemplateSeqHelper.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+package org.omg.PortableInterceptor;
+
+import gnu.CORBA.Minor;
+import gnu.CORBA.typecodes.GeneralTypeCode;
+
+import org.omg.CORBA.Any;
+import org.omg.CORBA.BAD_OPERATION;
+import org.omg.CORBA.TCKind;
+import org.omg.CORBA.TypeCode;
+import org.omg.CORBA.portable.InputStream;
+import org.omg.CORBA.portable.OutputStream;
+import org.omg.CORBA.portable.Streamable;
+
+/**
+ * Provides static helper methods for working with the array of object reference
+ * templates.
+ *
+ * @author Audrius Meskauskas (AudriusA@Bioinformatics.org)
+ */
+public abstract class ObjectReferenceTemplateSeqHelper
+{
+ /**
+ * The type code, computed once.
+ */
+ static TypeCode typecode;
+
+ /**
+ * Extract the <code>ObjectReferenceTemplate[]</code> from the given
+ * {@link Any}. This implementation expects the {@link Any} to hold the
+ * instance of {@link ObjectReferenceTemplateSeqHolder} that is returned by
+ * {@link Any#extract_Streamable() }.
+ *
+ * @param a an Any to extract the array from.
+ *
+ * @return the extracted array.
+ *
+ * @throws BAD_OPERATION if the Any contains something other than the the
+ * {@link ObjectReferenceTemplateSeqHolder}.
+ */
+ public static ObjectReferenceTemplate[] extract(Any a)
+ {
+ try
+ {
+ ObjectReferenceTemplateSeqHolder h = (ObjectReferenceTemplateSeqHolder)
+ a.extract_Streamable();
+ return h.value;
+ }
+ catch (ClassCastException cex)
+ {
+ BAD_OPERATION bad = new BAD_OPERATION(
+ "ObjectReferenceTemplate[] expected");
+ bad.initCause(cex);
+ bad.minor = Minor.Any;
+ throw bad;
+ }
+ }
+
+ /**
+ * Returns the object reference template sequence repository Id.
+ *
+ * @return "IDL:omg.org/PortableInterceptor/ObjectReferenceTemplateSeq:1.0",
+ * always.
+ */
+ public static String id()
+ {
+ return "IDL:omg.org/PortableInterceptor/ObjectReferenceTemplateSeq:1.0";
+ }
+
+ /**
+ * Insert into the given <code>ObjectReferenceTemplate[]</code> into the
+ * given {@link Any}. This implementation first creates a
+ * {@link ObjectReferenceTemplateSeqHolder} and then calls
+ * {@link Any#insert_Streamable(Streamable)}.
+ *
+ * @param into the target Any.
+ * @param that the array to insert.
+ */
+ public static void insert(Any into, ObjectReferenceTemplate[] that)
+ {
+ ObjectReferenceTemplateSeqHolder holder =
+ new ObjectReferenceTemplateSeqHolder(that);
+ into.insert_Streamable(holder);
+ }
+
+ /**
+ * Reads the <code>ObjectReferenceTemplate[]</code> from the CORBA input
+ * stream.
+ *
+ * @param input the CORBA (not java.io) stream to read from.
+ * @return the value from the stream.
+ */
+ public static ObjectReferenceTemplate[] read(InputStream input)
+ {
+ ObjectReferenceTemplate[] value =
+ new ObjectReferenceTemplate[input.read_long()];
+ for (int i = 0; i < value.length; i++)
+ value[i] = ObjectReferenceTemplateHelper.read(input);
+ return value;
+ }
+
+ /**
+ * Creates and returns a new instance of the TypeCode, corresponding the CORBA
+ * <code>ObjectReferenceTemplate[]</code>. The length of the sequence is
+ * left with the initial value 0.
+ */
+ public static TypeCode type()
+ {
+ if (typecode == null)
+ {
+ GeneralTypeCode t = new GeneralTypeCode(TCKind.tk_sequence);
+ t.setId(id());
+ t.setLength(0);
+ t.setContentType(ObjectReferenceTemplateHelper.type());
+ typecode = t;
+ }
+ return typecode;
+ }
+
+ /**
+ * Writes the <code>ObjectReferenceTemplate[]</code> into the given stream.
+ *
+ * @param output the CORBA (not java.io) output stream to write.
+ * @param value the value that must be written.
+ */
+ public static void write(OutputStream output, ObjectReferenceTemplate[] value)
+ {
+ output.write_long(value.length);
+
+ for (int i = 0; i < value.length; i++)
+ ObjectReferenceTemplateHelper.write(output, value[i]);
+ }
+}
diff --git a/org/omg/PortableInterceptor/ObjectReferenceTemplateSeqHolder.java b/org/omg/PortableInterceptor/ObjectReferenceTemplateSeqHolder.java
new file mode 100644
index 000000000..d16f5cedd
--- /dev/null
+++ b/org/omg/PortableInterceptor/ObjectReferenceTemplateSeqHolder.java
@@ -0,0 +1,104 @@
+/* ObjectReferenceTemplateSeqHolder.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package org.omg.PortableInterceptor;
+
+import org.omg.CORBA.portable.Streamable;
+import org.omg.CORBA.portable.InputStream;
+import org.omg.CORBA.portable.OutputStream;
+
+/**
+ * A holder for the array of {@link ObjectReferenceTemplate}s.
+ *
+ * @author Audrius Meskauskas, Lithuania (AudriusA@Bioinformatics.org)
+ */
+public class ObjectReferenceTemplateSeqHolder
+ implements Streamable
+{
+ /**
+ * The stored ObjectReferenceTemplate value.
+ */
+ public ObjectReferenceTemplate[] value;
+
+ /**
+ * Create the unitialised instance, leaving the value field with default
+ * <code>null</code> value.
+ */
+ public ObjectReferenceTemplateSeqHolder()
+ {
+ }
+
+ /**
+ * Create the initialised instance.
+ *
+ * @param initialValue the value that will be assigned to the
+ * <code>value</code> field.
+ */
+ public ObjectReferenceTemplateSeqHolder(ObjectReferenceTemplate[] initialValue)
+ {
+ value = initialValue;
+ }
+
+ /**
+ * Fill in the {@link value} by data from the CDR stream.
+ *
+ * @param input the org.omg.CORBA.portable stream to read.
+ */
+ public void _read(InputStream input)
+ {
+ value = ObjectReferenceTemplateSeqHelper.read(input);
+ }
+
+ /**
+ * Write the stored value into the CDR stream.
+ *
+ * @param output the org.omg.CORBA.portable stream to write.
+ */
+ public void _write(OutputStream output)
+ {
+ ObjectReferenceTemplateSeqHelper.write(output, value);
+ }
+
+ /**
+ * Get the typecode of the ObjectReferenceTemplate.
+ */
+ public org.omg.CORBA.TypeCode _type()
+ {
+ return ObjectReferenceTemplateSeqHelper.type();
+ }
+}
diff --git a/org/omg/PortableInterceptor/ServerRequestInfoOperations.java b/org/omg/PortableInterceptor/ServerRequestInfoOperations.java
index 7646253d1..a9ee7d920 100644
--- a/org/omg/PortableInterceptor/ServerRequestInfoOperations.java
+++ b/org/omg/PortableInterceptor/ServerRequestInfoOperations.java
@@ -216,7 +216,8 @@ import org.omg.IOP.ServiceContext;
*
* @author Audrius Meskauskas, Lithuania (AudriusA@Bioinformatics.org)
*/
-public interface ServerRequestInfoOperations extends RequestInfoOperations
+public interface ServerRequestInfoOperations
+ extends RequestInfoOperations
{
/**
* Allows the interceptor to add service contexts to the request. Such added
@@ -231,9 +232,7 @@ public interface ServerRequestInfoOperations extends RequestInfoOperations
* @throws BAD_INV_ORDER minor 15 if the context with the same Id already
* exists and replace=false.
*/
- void add_reply_service_context(ServiceContext service_context,
- boolean replace
- );
+ void add_reply_service_context(ServiceContext service_context, boolean replace);
/**
* Get the identifier for the object adapter (POA).
@@ -257,14 +256,15 @@ public interface ServerRequestInfoOperations extends RequestInfoOperations
* @throws INV_POLICY minor 2 if no factory was registered to produce this
* type of policy or the policy is otherwise invalid.
*/
- Policy get_server_policy(int type) throws INV_POLICY;
+ Policy get_server_policy(int type)
+ throws INV_POLICY;
/**
* Get the exception to be returned to the client. If the returned Any cannot
* not support holding of that exception, it holds
* {@link org.omg.CORBA.UNKNOWN} minor 1 instead.
*
- * @return an Any, holding exception that has been thrown and will be returned
+ * @return an Any, holding exception that has been thrown and will be returned
* to client.
*/
Any sending_exception();
@@ -281,7 +281,8 @@ public interface ServerRequestInfoOperations extends RequestInfoOperations
* @see RequestInfoOperations#get_slot(int)
* @see org.omg.PortableInterceptor#Current
*/
- void set_slot(int id, Any data) throws InvalidSlot;
+ void set_slot(int id, Any data)
+ throws InvalidSlot;
/**
* Checks if the servant is the given repository id.
@@ -299,4 +300,27 @@ public interface ServerRequestInfoOperations extends RequestInfoOperations
* @return the repository id of the servant.
*/
String target_most_derived_interface();
+
+ /**
+ * Returns the name of the adapter that is handling the current request.
+ * The name is returned as a string array, representing full path from
+ * the root poa till the current poa, for instance
+ * {"RootPOA", "childPOA","grandchildPOA"}.
+ */
+ public String[] adapter_name();
+
+ /**
+ * Returns the id of the ORB that is handling the current request. The ORB
+ * id can be specified as the property org.omg.CORBA.ORBid when creating
+ * the ORB.
+ */
+ public String orb_id();
+
+ /**
+ * Returs the id of the server that is handling the current request. The server
+ * id is the same for all POAs and ORBs in the current virtual machine and
+ * can be set as the property org.omg.CORBA.ServerId when creating one of the
+ * ORBs.
+ */
+ public String server_id();
} \ No newline at end of file
diff --git a/org/omg/PortableInterceptor/_IORInterceptor_3_0Stub.java b/org/omg/PortableInterceptor/_IORInterceptor_3_0Stub.java
new file mode 100644
index 000000000..52856407a
--- /dev/null
+++ b/org/omg/PortableInterceptor/_IORInterceptor_3_0Stub.java
@@ -0,0 +1,272 @@
+/* _IORInterceptor_3_0Stub.java --
+ Copyright (C) 2005 Free Software Foundation, Inc.
+
+This file is part of GNU Classpath.
+
+GNU Classpath is free software; you can redistribute it and/or modify
+it under the terms of the GNU General Public License as published by
+the Free Software Foundation; either version 2, or (at your option)
+any later version.
+
+GNU Classpath is distributed in the hope that it will be useful, but
+WITHOUT ANY WARRANTY; without even the implied warranty of
+MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+General Public License for more details.
+
+You should have received a copy of the GNU General Public License
+along with GNU Classpath; see the file COPYING. If not, write to the
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301 USA.
+
+Linking this library statically or dynamically with other modules is
+making a combined work based on this library. Thus, the terms and
+conditions of the GNU General Public License cover the whole
+combination.
+
+As a special exception, the copyright holders of this library give you
+permission to link this library with independent modules to produce an
+executable, regardless of the license terms of these independent
+modules, and to copy and distribute the resulting executable under
+terms of your choice, provided that you also meet, for each linked
+independent module, the terms and conditions of the license of that
+module. An independent module is a module which is not derived from
+or based on this library. If you modify this library, you may extend
+this exception to your version of the library, but you are not
+obligated to do so. If you do not wish to do so, delete this
+exception statement from your version. */
+
+
+package org.omg.PortableInterceptor;
+
+import org.omg.CORBA.MARSHAL;
+import org.omg.CORBA.portable.ApplicationException;
+import org.omg.CORBA.portable.Delegate;
+import org.omg.CORBA.portable.InputStream;
+import org.omg.CORBA.portable.ObjectImpl;
+import org.omg.CORBA.portable.OutputStream;
+import org.omg.CORBA.portable.RemarshalException;
+
+import java.io.Serializable;
+
+/**
+ * The IORInterceptor_3_0 stub (proxy), used on the client side. The
+ * {@link IORInterceptor_3_0} methods contain the code for remote invocaton. The
+ * stub is required by {@link IORInterceptor_3_0Helper} .read, .narrow and
+ * .unchecked_narrow methods.
+ *
+ * @specnote Being not specified in 1.5 API, this class is package private.
+ * From that happened to some other stubs, it will likely to appear in the 1.6
+ * or later. Because of this, it is placed here.
+ *
+ * @specnote The stub and the helper support the existence of the interceptor
+ * on the remote side only. To support the corresponding support on the side
+ * where the ORB is registered with this interceptor, you also need
+ * _IORInfoStub, IORInfoHelper and either servants or implementation bases
+ * for both POA and IORInfo. These classes are not defined in the 1.5 API,
+ * hence they are not included. You may need to generate the manually from
+ * the IDL descriptions, available from
+ * http://www.omg.org/docs/formal/04-03-12.pdf.
+ *
+ * @author Audrius Meskauskas, Lithuania (AudriusA@Bioinformatics.org)
+ */
+class _IORInterceptor_3_0Stub
+ extends ObjectImpl
+ implements IORInterceptor_3_0, Serializable
+{
+ /**
+ * Use serialVersionUID for interoperability.
+ */
+ private static final long serialVersionUID = 1;
+
+ /**
+ * Create the IORInterceptor_3_0 stub. To get the stub working, you must later
+ * set the delegate with {@link ObjectImpl#_set_delegate(Delegate)}.
+ */
+ public _IORInterceptor_3_0Stub()
+ {
+ }
+
+ /**
+ * Create the naming context stub with the given delegate.
+ */
+ public _IORInterceptor_3_0Stub(Delegate delegate)
+ {
+ _set_delegate(delegate);
+ }
+
+ /**
+ * Return the array of repository ids for this object.
+ */
+ public String[] _ids()
+ {
+ return new String[] { IORInterceptor_3_0Helper.id() };
+ }
+
+ /** {@inheritDoc} */
+ public void adapter_manager_state_changed(int adapterManagerId,
+ short adapterState)
+ {
+ InputStream input = null;
+ try
+ {
+ OutputStream output = _request("adapter_manager_state_changed", true);
+ output.write_long(adapterManagerId);
+ output.write_short(adapterState);
+ input = _invoke(output);
+
+ }
+ catch (ApplicationException ex)
+ {
+ input = ex.getInputStream();
+ String id = ex.getId();
+ throw new MARSHAL(id);
+ }
+ catch (RemarshalException remarsh)
+ {
+ adapter_manager_state_changed(adapterManagerId, adapterState);
+ }
+ finally
+ {
+ _releaseReply(input);
+ }
+ }
+
+ /** {@inheritDoc} */
+ public void adapter_state_changed(ObjectReferenceTemplate[] adapters,
+ short adaptersState)
+ {
+ InputStream input = null;
+ try
+ {
+ OutputStream output = _request("adapter_state_changed", true);
+ output.write_long(adapters.length);
+ for (int i0 = 0; i0 < adapters.length; i0++)
+ ObjectReferenceTemplateHelper.write(output, adapters[i0]);
+ output.write_short(adaptersState);
+ input = _invoke(output);
+
+ }
+ catch (ApplicationException ex)
+ {
+ input = ex.getInputStream();
+ String id = ex.getId();
+ throw new MARSHAL(id);
+ }
+ catch (RemarshalException remarsh)
+ {
+ adapter_state_changed(adapters, adaptersState);
+ }
+ finally
+ {
+ _releaseReply(input);
+ }
+ }
+
+ /** {@inheritDoc} */
+ public void components_established(IORInfo info)
+ {
+ InputStream input = null;
+ try
+ {
+ OutputStream output = _request("components_established", true);
+ output.write_Object(info);
+ input = _invoke(output);
+
+ }
+ catch (ApplicationException ex)
+ {
+ input = ex.getInputStream();
+ String id = ex.getId();
+ throw new MARSHAL(id);
+ }
+ catch (RemarshalException remarsh)
+ {
+ components_established(info);
+ }
+ finally
+ {
+ _releaseReply(input);
+ }
+ }
+
+ /** {@inheritDoc} */
+ public void establish_components(IORInfo info)
+ {
+ InputStream input = null;
+ try
+ {
+ OutputStream output = _request("establish_components", true);
+ output.write_Object(info);
+ input = _invoke(output);
+
+ }
+ catch (ApplicationException ex)
+ {
+ input = ex.getInputStream();
+ String id = ex.getId();
+ throw new MARSHAL(id);
+ }
+ catch (RemarshalException remarsh)
+ {
+ establish_components(info);
+ }
+ finally
+ {
+ _releaseReply(input);
+ }
+ }
+
+ /** {@inheritDoc} */
+ public String name()
+ {
+ InputStream input = null;
+ try
+ {
+ OutputStream output = _request("name", true);
+ input = _invoke(output);
+ String returns = input.read_string();
+
+ return returns;
+ }
+ catch (ApplicationException ex)
+ {
+ input = ex.getInputStream();
+ String id = ex.getId();
+ throw new MARSHAL(id);
+ }
+ catch (RemarshalException remarsh)
+ {
+ return name();
+ }
+ finally
+ {
+ _releaseReply(input);
+ }
+ }
+
+ /** {@inheritDoc} */
+ public void destroy()
+ {
+ InputStream input = null;
+ try
+ {
+ OutputStream output = _request("destroy", true);
+ input = _invoke(output);
+
+ }
+ catch (ApplicationException ex)
+ {
+ input = ex.getInputStream();
+ String id = ex.getId();
+ throw new MARSHAL(id);
+ }
+ catch (RemarshalException remarsh)
+ {
+ destroy();
+ }
+ finally
+ {
+ _releaseReply(input);
+ }
+ }
+} \ No newline at end of file
diff --git a/vm/reference/gnu/classpath/VMStackWalker.java b/vm/reference/gnu/classpath/VMStackWalker.java
index 28e4ce364..e995c4634 100644
--- a/vm/reference/gnu/classpath/VMStackWalker.java
+++ b/vm/reference/gnu/classpath/VMStackWalker.java
@@ -88,9 +88,9 @@ public final class VMStackWalker
/**
* Get the class loader associated with the Class returned by
- * <code>getCallingClass()</code>, or <code>null</code> if no
- * such class exists or it is the boot loader. This method is an optimization
- * for the expression <code>getClassContext()[1].getClassLoader()</code>
+ * <code>getCallingClass()</code>, or <code>null</code> if no such class
+ * exists or it is the boot loader. This method is an optimization for the
+ * expression <code>VMStackWalker.getClassLoader(getClassContext()[1])</code>
* and should return the same result.
*
* <p>
@@ -102,7 +102,15 @@ public final class VMStackWalker
Class[] ctx = getClassContext();
if (ctx.length < 3)
return null;
- return ctx[2].getClassLoader();
+ return getClassLoader(ctx[2]);
}
+
+ /**
+ * Retrieve the class's ClassLoader, or <code>null</code> if loaded
+ * by the bootstrap loader. I.e., this should return the same thing
+ * as {@link java.lang.VMClass#getClassLoader}. This duplicate version
+ * is here to work around access permissions.
+ */
+ public static native ClassLoader getClassLoader(Class cl);
}