2016-10-10 13 views
1

편집 3 :이 질문에 유래 stackoverflow.com 의해 질문 Gregory 응답이 명확하게 명시된 바와 같이이 일반적인 "나는 코드 내에서 indexoutofboundsexception 있습니다" 개발자가 확인한 널리 사용되는 타사 라이브러리 jide-common의 버그에는 아래 링크가 있습니다. 이 버그는 최근에 수정되어 (이 질문이 게시 된 후) 라이브러리의 많은 이전 버전이 여전히 영향을받습니다. 따라서이 정보는 jide-common에서 동일한 문제를 일으키는 다른 개발자에게 유용 할 수 있습니다.java.lang.IndexOutOfBoundsException : 인덱스 : 1, 크기 : 1, Jidesoft DocumentPane

Java GUI 프로그래밍에 문제가 있습니다. 문제의 특정 소스에 대해 확신하지 못합니다. (아직도 알아낼 수 없습니다.) 어딘가에서 내 오류가 발생할 수 있습니다. 자드 구성 요소의 일부 오류 코드 또는 awt/스윙 포커스 또는 이벤트 처리 오류 일 수 있습니다. JIDE - 그리드 : 3.5.1

  • com.jidesoft : JIDE 구성 성분 : 3.5.1
  • com.jidesoft : JIDE 공통

    다음 코드

    • com.jidesoft에 따라 : 3.5.1

    나는 Stackoverflow에 발견했으나 일부 ​​디버깅 후에는 CellEditor 및 다른 구성 요소에 대한 모든 수정이 EDT에서 수행되었다고 생각됩니다.

    버그를 재현하려면이 예제를 실행하고 CellEditor가 포함 된 탭을 열어야합니다 (마지막 줄에 있어야합니다. 그렇지 않으면 인덱스 오버플로가 발생하지 않습니다). 그런 다음 "잘못된"값을 입력하십시오. 편집기에서 이전 탭 중 하나에서 "x"버튼을 클릭하십시오. 그 후 다음과 같은 일련의 이벤트가 발생합니다. 1) 탭이 닫히고 제거됩니다. 2) CellEditor 검증자가 모달 대화 상자를 표시합니다.이 대화 상자는 탭이 누락 된 (탭이 누락 됨으로 인해) 3) ArrayIndexOutOfBounds 예외가 발생합니다.

    package com.example; 
    
    import com.jidesoft.document.DocumentComponent; 
    import com.jidesoft.document.DocumentPane; 
    import com.jidesoft.grid.JideTable; 
    import com.jidesoft.grid.TableModelWrapperUtils; 
    import com.jidesoft.grid.TextFieldCellEditor; 
    import com.jidesoft.swing.JideTabbedPane; 
    
    import javax.swing.*; 
    import javax.swing.table.DefaultTableModel; 
    import java.awt.*; 
    import java.awt.event.ActionEvent; 
    import java.math.BigDecimal; 
    import java.util.Random; 
    
    /** 
    * Dependends on: 
    * com.jidesoft:jide-grids:3.5.1 
    * com.jidesoft:jide-components:3.5.1 
    * com.jidesoft:jide-common:3.5.1 
    */ 
    public class ModalPopupFailure { 
    
        public static void main(String[] args) { 
         JFrame frame = new JFrame(); 
         frame.setTitle("test"); 
         frame.setDefaultCloseOperation(WindowConstants.EXIT_ON_CLOSE); 
         JComponent panel = new ModalPopupFailure().buildPanel(); 
         frame.setContentPane(panel); 
         frame.setBounds(450, 300, 700, 500); 
         frame.setVisible(true); 
        } 
    
        /** 
        * @return table editor panel 
        */ 
        private JPanel tableTab() { 
         JPanel result = new JPanel(new BorderLayout()); 
    
         DefaultTableModel model = new DefaultTableModel(1, 1); 
         model.setValueAt(new BigDecimal(0L), 0, 0); 
         JideTable table = new JideTable(model); 
         table.putClientProperty("terminateEditOnFocusLost", Boolean.TRUE); 
    
         final int actualCol0 = TableModelWrapperUtils.getActualColumnAt(table.getModel(), 0); 
         CustomCellEditor bdce = new CustomCellEditor(Integer.class); 
         table.getColumnModel().getColumn(actualCol0).setCellEditor(bdce); 
    
         result.add(table, BorderLayout.CENTER); 
         return result; 
        } 
    
        /** 
        * @return Main panel with tabs 
        */ 
        private JComponent buildPanel() { 
         JPanel mainPanel = new JPanel(new BorderLayout()); 
    
         final DocumentPane documentPane = new DocumentPane(); 
    
         DocumentComponent dc1 = new DocumentComponent(new JLabel("tab1 label"), "aaa"); 
         documentPane.openDocument(dc1); 
    
         DocumentComponent dc2 = new DocumentComponent(tableTab(), "TABLETAB"); 
         documentPane.openDocument(dc2); 
         documentPane.setActiveDocument("TABLETAB"); 
    
         documentPane.setTabbedPaneCustomizer(new DocumentPane.TabbedPaneCustomizer() { 
          @Override 
          public void customize(final JideTabbedPane tabbedPane) { 
           tabbedPane.setShowCloseButton(true); 
           tabbedPane.setUseDefaultShowCloseButtonOnTab(false); 
           tabbedPane.setShowCloseButtonOnTab(true); 
          } 
         }); 
    
         documentPane.setTabPlacement(SwingConstants.TOP); 
    
         mainPanel.add(documentPane, BorderLayout.CENTER); 
         mainPanel.add(new JButton(new AbstractAction("New tab") { 
            @Override 
            public void actionPerformed(ActionEvent e) { 
             Integer randInt = new Random().nextInt(); 
             DocumentComponent newdc = new DocumentComponent(
               new JLabel("Generated tab label " + randInt), 
               Integer.toString(randInt)); 
    
             documentPane.openDocument(newdc); 
            } 
           }), 
           BorderLayout.NORTH); 
         JLabel decription = new JLabel("<html>Steps to reproduce:<br />" + 
           "TABLETAB should be the last tab<br />" + 
           "The \"correct\" value for cell editor is 777.<br />" + 
           "Enter any \"incorrect\" number, then close any tab standing before TABLETAB.<br />" + 
           "An exception caused by window repaint should be raised by now.<br />" + 
           "If dialog would not be modal, there would be no window repaint triggered.</html>"); 
         mainPanel.add(decription, BorderLayout.SOUTH); 
    
         return mainPanel; 
        } 
    
        private class CustomCellEditor extends TextFieldCellEditor { 
    
         boolean firstTime = true; 
    
         public CustomCellEditor(Class<?> aClass) { 
          super(aClass); 
          _textField.setInputVerifier(new InputVerifier() { 
           @Override 
           public boolean verify(JComponent input) { 
            boolean valid = "777".equals(_textField.getText()); 
            if (valid) return true; 
    
            final JDialog dialog = new JDialog(); 
            dialog.setTitle("Exception expected"); 
            dialog.setContentPane(new JLabel("<html>If one of previous tabs was closed, an exception should be raised by now.</html>")); 
            dialog.setLocationRelativeTo(null); 
    
            dialog.setModal(true); // Switching to false seems to fix the problem 
    
            dialog.setSize(new Dimension(300, 100)); 
            dialog.setVisible(true); 
    
            return true; 
           } 
          }); 
         } 
    
         @Override 
         public boolean stopCellEditing() { 
          System.out.println("Stopping cell edit " + new Random().nextInt() + "in edt: " + SwingUtilities.isEventDispatchThread()); 
          if (firstTime) { 
           firstTime = false; 
           return false; 
          } 
    
          return _textField.getInputVerifier().shouldYieldFocus(_textField) && super.stopCellEditing(); 
         } 
        } 
    } 
    

    예외 :

    Exception in thread "AWT-EventQueue-0" java.lang.IndexOutOfBoundsException: Index: 1, Size: 1 
        at java.util.ArrayList.rangeCheck(ArrayList.java:635) 
        at java.util.ArrayList.get(ArrayList.java:411) 
        at javax.swing.JTabbedPane.getComponentAt(JTabbedPane.java:1224) 
        at com.jidesoft.plaf.vsnet.VsnetJideTabbedPaneUI.paintContentBorder(Unknown Source) 
        at com.jidesoft.plaf.basic.BasicJideTabbedPaneUI.paintContentBorder(Unknown Source) 
        at com.jidesoft.plaf.basic.BasicJideTabbedPaneUI.paint(Unknown Source) 
        at javax.swing.plaf.ComponentUI.update(ComponentUI.java:161) 
        at javax.swing.JComponent.paintComponent(JComponent.java:779) 
        at javax.swing.JComponent.paint(JComponent.java:1055) 
        at javax.swing.JComponent.paintChildren(JComponent.java:888) 
        at javax.swing.JComponent.paint(JComponent.java:1064) 
        at javax.swing.JComponent.paintChildren(JComponent.java:888) 
        at javax.swing.JComponent.paint(JComponent.java:1064) 
        at javax.swing.JComponent.paintToOffscreen(JComponent.java:5232) 
        at javax.swing.BufferStrategyPaintManager.paint(BufferStrategyPaintManager.java:295) 
        at javax.swing.RepaintManager.paint(RepaintManager.java:1249) 
        at javax.swing.JComponent._paintImmediately(JComponent.java:5180) 
        at javax.swing.JComponent.paintImmediately(JComponent.java:4991) 
        at javax.swing.RepaintManager$3.run(RepaintManager.java:808) 
        at javax.swing.RepaintManager$3.run(RepaintManager.java:796) 
        at java.security.AccessController.doPrivileged(Native Method) 
        at java.security.ProtectionDomain$1.doIntersectionPrivilege(ProtectionDomain.java:76) 
        at javax.swing.RepaintManager.paintDirtyRegions(RepaintManager.java:796) 
        at javax.swing.RepaintManager.paintDirtyRegions(RepaintManager.java:769) 
        at javax.swing.RepaintManager.prePaintDirtyRegions(RepaintManager.java:718) 
        at javax.swing.RepaintManager.access$1100(RepaintManager.java:62) 
        at javax.swing.RepaintManager$ProcessingRunnable.run(RepaintManager.java:1677) 
        at java.awt.event.InvocationEvent.dispatch(InvocationEvent.java:312) 
        at java.awt.EventQueue.dispatchEventImpl(EventQueue.java:745) 
        at java.awt.EventQueue.access$300(EventQueue.java:103) 
        at java.awt.EventQueue$3.run(EventQueue.java:706) 
        at java.awt.EventQueue$3.run(EventQueue.java:704) 
        at java.security.AccessController.doPrivileged(Native Method) 
        at java.security.ProtectionDomain$1.doIntersectionPrivilege(ProtectionDomain.java:76) 
        at java.awt.EventQueue.dispatchEvent(EventQueue.java:715) 
        at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:242) 
        at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:161) 
        at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:154) 
        at java.awt.WaitDispatchSupport$2.run(WaitDispatchSupport.java:182) 
        at java.awt.WaitDispatchSupport$4.run(WaitDispatchSupport.java:221) 
        at java.security.AccessController.doPrivileged(Native Method) 
        at java.awt.WaitDispatchSupport.enter(WaitDispatchSupport.java:219) 
        at java.awt.Dialog.show(Dialog.java:1082) 
        at java.awt.Component.show(Component.java:1655) 
        at java.awt.Component.setVisible(Component.java:1607) 
        at java.awt.Window.setVisible(Window.java:1014) 
        at java.awt.Dialog.setVisible(Dialog.java:1005) 
        at com.example.ModalPopupFailure$CustomCellEditor$1.verify(ModalPopupFailure.java:124) 
        at javax.swing.InputVerifier.shouldYieldFocus(InputVerifier.java:132) 
        at javax.swing.JComponent$1.acceptRequestFocus(JComponent.java:3589) 
        at java.awt.Component.isRequestFocusAccepted(Component.java:7739) 
        at java.awt.Component.requestFocusHelper(Component.java:7621) 
        at java.awt.Component.requestFocusInWindow(Component.java:7544) 
        at java.awt.Component.transferFocus(Component.java:7842) 
        at java.awt.Component.hide(Component.java:1688) 
        at javax.swing.JComponent.hide(JComponent.java:5585) 
        at java.awt.Component.show(Component.java:1657) 
        at java.awt.Component.setVisible(Component.java:1607) 
        at javax.swing.JComponent.setVisible(JComponent.java:2641) 
        at com.jidesoft.plaf.basic.BasicJideTabbedPaneUI.setVisibleComponent(Unknown Source) 
        at com.jidesoft.plaf.basic.BasicJideTabbedPaneUI$PropertyChangeHandler.propertyChange(Unknown Source) 
        at java.beans.PropertyChangeSupport.fire(PropertyChangeSupport.java:335) 
        at java.beans.PropertyChangeSupport.firePropertyChange(PropertyChangeSupport.java:327) 
        at java.beans.PropertyChangeSupport.firePropertyChange(PropertyChangeSupport.java:263) 
        at java.awt.Component.firePropertyChange(Component.java:8393) 
        at javax.swing.JComponent.putClientProperty(JComponent.java:4103) 
        at javax.swing.JTabbedPane.removeTabAt(JTabbedPane.java:971) 
        at com.jidesoft.swing.JideTabbedPane.removeTabAt(Unknown Source) 
        at com.jidesoft.document.TdiGroup.removeDocument(Unknown Source) 
        at com.jidesoft.document.DocumentPane.a(Unknown Source) 
        at com.jidesoft.document.DocumentPane.a(Unknown Source) 
        at com.jidesoft.document.DocumentPane.a(Unknown Source) 
        at com.jidesoft.document.DocumentPane.a(Unknown Source) 
        at com.jidesoft.document.DocumentPane.closeDocument(Unknown Source) 
        at com.jidesoft.document.DocumentPane.closeSingleDocument(Unknown Source) 
        at com.jidesoft.document.DocumentPane$34.actionPerformed(Unknown Source) 
        at com.jidesoft.plaf.basic.BasicJideTabbedPaneUI$CloseTabAction.actionPerformed(Unknown Source) 
        at javax.swing.AbstractButton.fireActionPerformed(AbstractButton.java:2018) 
        at javax.swing.AbstractButton$Handler.actionPerformed(AbstractButton.java:2341) 
        at javax.swing.DefaultButtonModel.fireActionPerformed(DefaultButtonModel.java:402) 
        at javax.swing.DefaultButtonModel.setPressed(DefaultButtonModel.java:259) 
        at javax.swing.plaf.basic.BasicButtonListener.mouseReleased(BasicButtonListener.java:252) 
        at java.awt.AWTEventMulticaster.mouseReleased(AWTEventMulticaster.java:289) 
        at java.awt.AWTEventMulticaster.mouseReleased(AWTEventMulticaster.java:289) 
        at java.awt.Component.processMouseEvent(Component.java:6516) 
        at javax.swing.JComponent.processMouseEvent(JComponent.java:3321) 
        at java.awt.Component.processEvent(Component.java:6281) 
        at java.awt.Container.processEvent(Container.java:2229) 
        at java.awt.Component.dispatchEventImpl(Component.java:4872) 
        at java.awt.Container.dispatchEventImpl(Container.java:2287) 
        at java.awt.Component.dispatchEvent(Component.java:4698) 
        at java.awt.LightweightDispatcher.retargetMouseEvent(Container.java:4832) 
        at java.awt.LightweightDispatcher.processMouseEvent(Container.java:4492) 
        at java.awt.LightweightDispatcher.dispatchEvent(Container.java:4422) 
        at java.awt.Container.dispatchEventImpl(Container.java:2273) 
        at java.awt.Window.dispatchEventImpl(Window.java:2719) 
        at java.awt.Component.dispatchEvent(Component.java:4698) 
        at java.awt.EventQueue.dispatchEventImpl(EventQueue.java:747) 
        at java.awt.EventQueue.access$300(EventQueue.java:103) 
        at java.awt.EventQueue$3.run(EventQueue.java:706) 
        at java.awt.EventQueue$3.run(EventQueue.java:704) 
        at java.security.AccessController.doPrivileged(Native Method) 
        at java.security.ProtectionDomain$1.doIntersectionPrivilege(ProtectionDomain.java:76) 
        at java.security.ProtectionDomain$1.doIntersectionPrivilege(ProtectionDomain.java:87) 
        at java.awt.EventQueue$4.run(EventQueue.java:720) 
        at java.awt.EventQueue$4.run(EventQueue.java:718) 
        at java.security.AccessController.doPrivileged(Native Method) 
        at java.security.ProtectionDomain$1.doIntersectionPrivilege(ProtectionDomain.java:76) 
        at java.awt.EventQueue.dispatchEvent(EventQueue.java:717) 
        at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:242) 
        at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:161) 
        at java.awt.EventDispatchThread.pumpEventsForHierarchy(EventDispatchThread.java:150) 
        at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:146) 
        at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:138) 
        at java.awt.EventDispatchThread.run(EventDispatchThread.java:91) 
    

    정보를 디버깅 약간의 추가와 함께 "extended" version of code을있다. 여전히 문제의 원인을 알 수는 없지만 해결 방법은 언급하지 않았습니다. 미리 감사드립니다.

    편집 : 나는 지금까지 알아 낸 확인을 한 가지 내에서 대화 상자를 표시하는 확인하는 것이있다() 메소드 is wrong, according to docs :

    방법을 확인 입력이 결코해야 유효한지 여부를 결정하는 데에만 존재 대화 상자를 표시하거나 다른 부작용을 유발할 수 있습니다. shouldYieldFocus 메서드는 verify를 호출하고 값이 유효하지 않으면 최소값 또는 최대 값으로 설정합니다. shouldYieldFocus 메서드는 부작용을 일으킬 수 있습니다 ...

    그래서 모든 실제 확인 코드를 shouldYieldFocus()로 옮겼습니다. 그게 문제를 해결하지는 못했지만, dialog.show()를 SwingUtilities.invokeLater()로 더 지연 시키면 문제가없는 것처럼 보입니다.

    public CustomCellEditor(Class<?> aClass) { 
        super(aClass); 
        _textField.setInputVerifier(new InputVerifier() { 
    
         @Override 
         public boolean shouldYieldFocus(JComponent input) { 
          boolean inputOK = verify(input); 
          if (!inputOK) { 
           final ru.esc.erp.core.components.Dialog dialog = new ru.esc.erp.core.components.Dialog(); 
           dialog.setTitle("Exception may be raised"); 
           dialog.setContentPane(new JLabel("<html>Modal dialog opened with yet another delay.</html>")); 
           dialog.setLocationRelativeTo(null); 
    
           dialog.setModal(true); // false "fixes" the problem 
    
           dialog.setSize(new Dimension(300, 100)); 
           SwingUtilities.invokeLater(new Runnable() { 
            @Override 
            public void run() { 
             dialog.setVisible(true); 
            } 
           }); 
          } 
          return inputOK; 
         } 
    
         @Override 
         public boolean verify(JComponent input) { 
          return "777".equals(_textField.getText()); 
         } 
        }); 
    } 
    

    Edit2가이 :gif with captured video

  • +0

    나는 [코드 단순화] (http://pastebin.com/4GqZixm7). DocumentPane, 표 및 셀 편집기를 더 이상 사용하지 않습니다. JideTabbedPane에서 간단한 텍스트 필드 (확인이 실패 할 경우 모달 대화 상자를 표시 함). 이제는 oss 라이브러리 만 사용하므로 누구나이 예제를 실행할 수 있습니다. 하지만 jide-oss-3.5.1에서는 여전히 버그가 있습니다. jide-oss-3.6.16에서도 마찬가지입니다. –

    답변

    1

    OK, 그것은 JideTabbedPaneUI에서 a bug했다. 예제와 함께 jide-oss 패치를 테스트했지만 더 이상 예외는 없습니다 (그러나 탭을 닫을 때 중요하지 않은 UI 글리치가 있음). 문제의 원인을 찾았습니다.

    편집 : 그들은 3.6.17 이후에이 버그를 수정 : 그냥 그렇게 알고,이 버그는 3.6.17에서 수정되었습니다 2017년 2월 1일 오전 12시 10분 JIDE 지원»수요일에 의해

    하는 방금 출시되었습니다.