2009-12-20 11 views
0

J'essaie de charger tous les types de fichiers (comme le Bloc-notes Microsoft). Le SwingWorker que j'ai peut charger le texte normal très bien mais quand un dossier tel que mp3, pdf, etc. est essayé pour être chargé je reçois une exception de NullPointerException. Est-ce que quelqu'un peut jeter un coup d'oeil à mon code et peut-être voir pourquoi je continue à obtenir cette erreur pour des fichiers tels que mp3, pdf, etc? Comme je l'ai dit, je peux charger des fichiers texte .html ordinaires sans erreurs.Faire la version Java du Bloc-notes et j'ai un problème

class Open extends SwingWorker<StringBuilder, Void> 
{ 
    File file; 
    JTextArea jta; 

    Open(File file, JTextArea jta) 
    { 
     this.file = file; 
     this.jta = jta; 
    } 

    @Override 
    protected StringBuilder doInBackground() throws Exception 
    { 
     BufferedReader br = null; 
     StringBuilder b = new StringBuilder(); 

     try 
     { 
      br = new BufferedReader(new FileReader(file)); 

      while(br.ready()) 
      { 
       b.append(br.readLine() + "\n"); 
      } 
     } 
     finally 
     { 
      try 
      { 
       br.close(); 
      } catch (IOException e) { } 
     } 
     return b; 
    } 

    @Override 
    protected void done() 
    { 
     try { 
      jta.append(get().toString()); 
     } catch (InterruptedException ex) { 
      Logger.getLogger(Open.class.getName()).log(Level.SEVERE, null, ex); 
     } catch (ExecutionException ex) { 
      Logger.getLogger(Open.class.getName()).log(Level.SEVERE, null, ex); 
     } 
    } 
} 

C'est ce que je reçois après avoir tourné le code dans:

class Open extends SwingWorker<Void, String> 
{ 
    File file; 
    JTextArea jta; 

    Open(File file, JTextArea jta) 
    { 
     this.file = file; 
     this.jta = jta; 
    } 

    @Override 
    protected Void doInBackground() throws Exception 
    { 
     BufferedReader br = null; 

     try 
     { 
      br = new BufferedReader(new FileReader(file)); 

      String line = br.readLine(); 

      while(line != null) 
      { 
       publish(line); 
       line = br.readLine(); 
      } 
     } 
     catch (Exception e) 
     { 
      e.printStackTrace(); 
     } 
     finally 
     { 
      try 
      { 
       br.close(); 
      } catch (IOException e) { } 
     } 
     return null; 
    } 

    @Override 
    protected void process(List<String> chunks) 
    { 
     for(String s : chunks) 
      jta.append(s + "\n"); 
    } 
} 

C'est le 'stacktrace' (je pense) de Netbeans:

Exception in thread "AWT-EventQueue-0" java.lang.NullPointerException 
     at java.util.Hashtable.put(Hashtable.java:394) 
     at sun.font.PhysicalStrike.getGlyphPoint(PhysicalStrike.java:112) 
     at sun.font.SunLayoutEngine.nativeLayout(Native Method) 
     at sun.font.SunLayoutEngine.layout(SunLayoutEngine.java:133) 
     at sun.font.GlyphLayout$EngineRecord.layout(GlyphLayout.java:648) 
     at sun.font.GlyphLayout.layout(GlyphLayout.java:447) 
     at sun.font.ExtendedTextSourceLabel.createGV(ExtendedTextSourceLabel.java:308) 
     at sun.font.ExtendedTextSourceLabel.getGV(ExtendedTextSourceLabel.java:294) 
     at sun.font.ExtendedTextSourceLabel.createCharinfo(ExtendedTextSourceLabel.java:563) 
     at sun.font.ExtendedTextSourceLabel.getCharinfo(ExtendedTextSourceLabel.java:492) 
     at sun.font.ExtendedTextSourceLabel.getLineBreakIndex(ExtendedTextSourceLabel.java:438) 
     at java.awt.font.TextMeasurer.calcLineBreak(TextMeasurer.java:308) 
     at java.awt.font.TextMeasurer.getLineBreakIndex(TextMeasurer.java:544) 
     at java.awt.font.LineBreakMeasurer.nextOffset(LineBreakMeasurer.java:340) 
     at java.awt.font.LineBreakMeasurer.nextLayout(LineBreakMeasurer.java:422) 
     at javax.swing.text.TextLayoutStrategy.sync(TextLayoutStrategy.java:298) 
     at javax.swing.text.TextLayoutStrategy.insertUpdate(TextLayoutStrategy.java:52) 
     at javax.swing.text.FlowView.loadChildren(FlowView.java:126) 
     at javax.swing.text.CompositeView.setParent(CompositeView.java:122) 
     at javax.swing.text.FlowView.setParent(FlowView.java:272) 
     at javax.swing.plaf.basic.BasicTextAreaUI$PlainParagraph.setParent(BasicTextAreaUI.java:222) 
     at javax.swing.text.CompositeView.replace(CompositeView.java:200) 
     at javax.swing.text.BoxView.replace(BoxView.java:164) 
     at javax.swing.text.View.updateChildren(View.java:1095) 
     at javax.swing.text.View.insertUpdate(View.java:679) 
     at javax.swing.plaf.basic.BasicTextUI$RootView.insertUpdate(BasicTextUI.java:1590) 
     at javax.swing.plaf.basic.BasicTextUI$UpdateHandler.insertUpdate(BasicTextUI.java:1849) 
     at javax.swing.text.AbstractDocument.fireInsertUpdate(AbstractDocument.java:185) 
     at javax.swing.text.AbstractDocument.handleInsertString(AbstractDocument.java:734) 
     at javax.swing.text.AbstractDocument.insertString(AbstractDocument.java:693) 
     at javax.swing.text.PlainDocument.insertString(PlainDocument.java:114) 
     at javax.swing.JTextArea.append(JTextArea.java:470) 
     at Open.process(main.java:313) 
     at javax.swing.SwingWorker$3.run(SwingWorker.java:391) 
     at sun.swing.AccumulativeRunnable.run(AccumulativeRunnable.java:95) 
     at javax.swing.SwingWorker$DoSubmitAccumulativeRunnable.run(SwingWorker.java:860) 
     at sun.swing.AccumulativeRunnable.run(AccumulativeRunnable.java:95) 
     at javax.swing.SwingWorker$DoSubmitAccumulativeRunnable.actionPerformed(SwingWorker.java:870) 
     at javax.swing.Timer.fireActionPerformed(Timer.java:271) 
     at javax.swing.Timer$DoPostEvent.run(Timer.java:201) 
     at java.awt.event.InvocationEvent.dispatch(InvocationEvent.java:209) 
     at java.awt.EventQueue.dispatchEvent(EventQueue.java:597) 
     at java.awt.EventDispatchThread.pumpOneEventForFilters(EventDispatchThread.java:269) 
     at java.awt.EventDispatchThread.pumpEventsForFilter(EventDispatchThread.java:184) 
     at java.awt.EventDispatchThread.pumpEventsForHierarchy(EventDispatchThread.java:174) 
     at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:169) 
     at java.awt.EventDispatchThread.pumpEvents(EventDispatchThread.java:161) 
     at java.awt.EventDispatchThread.run(EventDispatchThread.java:122) 

J'ai changé le code à:

class Open extends SwingWorker<Void, String> 
{ 
    File file; 
    JTextArea jta; 

    Open(File file, JTextArea jta) 
    { 
     this.file = file; 
     this.jta = jta; 
    } 

    @Override 
    protected Void doInBackground() throws Exception 
    { 
     BufferedReader br = null; 

     try 
     { 
      br = new BufferedReader(new InputStreamReader(new FileInputStream(file))); 

      String line = br.readLine(); 

      while(line != null) 
      { 
       publish(line); 
       line = br.readLine(); 
      } 
     } 
     catch (Exception e) { e.printStackTrace(); } 
     finally 
     { 
      try 
      { 
       if(br != null) 
        br.close(); 
      } catch (IOException e) { } 
     } 
     return null; 
    } 

    @Override 
    protected void process(List<String> chunks) 
    { 
     for(String s : chunks) 
      jta.append(s + "\n"); 
    } 
} 

A Je reçois toujours des NPE.

+2

donnez-nous une trace de la pile – Woot4Moo

+0

Je ne peux rien obtenir ... Où devrais-je mettre le stacktrace? –

+0

Utilisez une capture sur ce bloc try/finally où vous configurez le lecteur. –

Répondre

1

Si l'ouverture de fichier échoue, le br sera toujours null dans le bloc finally où vous appelez br.close(). Par conséquent, vous obtiendrez un NPE.

Je devrais ajouter qu'essayer de lire un fichier png, pdf ou n'importe quel fichier utilisant FileReader est inutile. Même si vous réussissez à ouvrir le fichier, la lecture à l'aide d'un Reader risque de déformer le contenu (binaire) lors de la conversion d'octets en caractères. L'appel BufferedReader.readLine() ne fera qu'aggraver les choses ...

EDIT - la pile stack fournie indique clairement que votre problème n'est pas lié au code que vous avez posté. Mais mon point demeure. Le code que vous avez posté lancera un NPE dans les circonstances que j'ai décrites. La pile de lignes semble dire qu'un 'PlainDocument' ne peut pas rendre le masquage de la merde aléatoire comme du texte. Il semble qu'il essaie de créer des informations glyphes pour un caractère (probablement corrompu), et échoue parce que certaines structures de données n'ont pas été créées/fournies. Je pense que vous devrez commencer à regarder le code source de Sun pour comprendre cela. Un IDE décent aidera probablement aussi bien.

EDIT 2 - AFAIK, il y a deux façons de traiter les fichiers binaires dans le contexte d'une Swing JTextArea.

  1. Vous pouvez lire le fichier en octets (à l'aide d'un flux), traduire les octets en quelque chose affichable (en remplaçant par exemple des caractères non affichables avec des séquences de caractères affichables), puis utiliser une lecture seule PlainDocument pour les afficher.

  2. Si vous voulez quelque chose qui vous permette d'éditer des fichiers binaires (et je ne suis pas sûr que ce soit une idée raisonnable), je pense que vous devrez créer votre propre type de document. Cela pourrait être une grosse tâche.

+0

J'aurais aimé que ça fonctionne si br! = Null ne résolvait pas le problème. –

+0

Que recommandez-vous que je fasse? Je veux réaliser la même chose que le Bloc-notes. –

0

Votre erreur est la fonction Open.process()

est ici la partie clé du stacktrace:

at javax.swing.JTextArea.append(JTextArea.java:470) 
at Open.process(main.java:313) 

Très probablement le problème est que vous annexant une chaîne vide. Assurez-vous que le texte que vous insérez est non nul.

essayez ceci:

for(String s : chunks) 
     if(s != null) 
      jta.append(s + "\n"); 

L'autre chose, assurez-vous jamais ignorer ces exceptions: Vous ne voulez jamais avoir le code comme

try { ...} catch (Exception e) {

À moins que vous sais pour sûr que les exceptions n'auront pas d'importance (comme une exception interrompue pendant que vous attendez quelque chose dans un lis). Vous devriez appeler e.printStackTrace(); au moins de sorte que vous pouvez au moins voir qu'un problème inattendu est apparu.

Dans le code que vous avez affiché, vous avez ignoré deux erreurs, d'abord sur la lecture, puis sur la fermeture.

+0

si (s! = Null) ne fonctionnait pas aussi bien. Pensez-vous qu'il est possible que la chaîne se remplisse et que cela cause le NPE? –

+0

Voir mon autre réponse. Je pense que vous rencontrez des problèmes parce que vous essayez de dessiner des personnages qui n'existent pas. –

0

Essayez ceci pour créer br

br = new BufferedReader(new InputStreamReader(new FileInputStream(file), Charset.forName("US-ASCII"))); 

Si cela fonctionne aussi essayer

br = new BufferedReader(new InputStreamReader(new FileInputStream(file), Charset.forName("UTF-8"))); 

Et voir si cela fonctionne (vous devez importer java.nio.charset.Charset)