Java tutorial
/* * Copyright (c) 2007 - 2011 by Michael Mimo Moratti * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, * software distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions * and limitations under the License. */ package de.anbos.eclipse.logviewer.plugin.file.document; import java.lang.reflect.InvocationTargetException; import java.nio.charset.Charset; import org.eclipse.jface.preference.IPreferenceStore; import org.eclipse.jface.text.AbstractDocument; import org.eclipse.jface.text.BadLocationException; import org.eclipse.jface.text.DefaultLineTracker; import org.eclipse.jface.text.DocumentEvent; import org.eclipse.jface.text.GapTextStore; import org.eclipse.jface.util.IPropertyChangeListener; import org.eclipse.jface.util.PropertyChangeEvent; import org.eclipse.swt.widgets.Display; import org.eclipse.ui.PartInitException; import de.anbos.eclipse.logviewer.plugin.ILogViewerConstants; import de.anbos.eclipse.logviewer.plugin.LogFile; import de.anbos.eclipse.logviewer.plugin.LogViewerPlugin; import de.anbos.eclipse.logviewer.plugin.file.BackgroundReader; import de.anbos.eclipse.logviewer.plugin.file.IFileChangedListener; public class LogDocument extends AbstractDocument implements IFileChangedListener { // Attribute --------------------------------------------------------------- private LogFile file; private Charset charset; private String encoding; private BackgroundReader reader; private boolean monitor; private int backlogLines; // Constructor ------------------------------------------------------------- public LogDocument(LogFile file, String encoding) throws SecurityException, IllegalArgumentException, ClassNotFoundException, NoSuchMethodException, InstantiationException, IllegalAccessException, InvocationTargetException, PartInitException { super(); if (file.getEncoding() == null) file.setEncoding(encoding); this.file = file; this.encoding = file.getEncoding(); this.charset = Charset.forName(file.getEncoding()); IPreferenceStore store = LogViewerPlugin.getDefault().getPreferenceStore(); store.addPropertyChangeListener(new PropertyChangeListener()); backlogLines = store.getInt(ILogViewerConstants.PREF_BACKLOG); setTextStore(new GapTextStore(50, 300, 1f)); setLineTracker(new DefaultLineTracker()); completeInitialization(); reader = new BackgroundReader(file.getFileType(), file.getFileName(), charset, this); } // Public ------------------------------------------------------------------ /** * invoking that setter will cause the tail thread to stop and a new FileTail * instance is created with the given charset. */ public void setEncoding(String encoding) { setMonitor(false); this.file.setEncoding(encoding); this.encoding = encoding; this.charset = Charset.forName(encoding); try { reader = new BackgroundReader(file.getFileType(), file.getFileName(), charset, this); } catch (SecurityException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (IllegalArgumentException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (ClassNotFoundException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (NoSuchMethodException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (InstantiationException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (IllegalAccessException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (InvocationTargetException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (PartInitException e) { // TODO Auto-generated catch block e.printStackTrace(); } setMonitor(true); } /** * @return the current content encoding */ public String getEncoding() { return encoding; } /** * invoking that method will cause the tail thread to stop and a new FileTail * instance is create. */ public void synchronize() { setMonitor(false); getStore().set(""); getTracker().set(""); try { reader = new BackgroundReader(file.getFileType(), file.getFileName(), charset, this); } catch (SecurityException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (IllegalArgumentException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (ClassNotFoundException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (NoSuchMethodException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (InstantiationException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (IllegalAccessException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (InvocationTargetException e) { // TODO Auto-generated catch block e.printStackTrace(); } catch (PartInitException e) { // TODO Auto-generated catch block e.printStackTrace(); } setMonitor(true); } /** * setter for the amount of lines that the view has to dislay at any time. * It is although possible that the view can display some more lines for * a short time. But that amount can be consideret unimportant towards the * memory consumption. * @param lines int amount of lines to display */ public void setBacklog(int lines) { backlogLines = lines; } /** * if the monitor parameter is true and the current FileTail instance thread * is not running the Thread will be inovked and the tail begins to update * this document. * * if the monitor parameter is false the FileTail instance thread is notified * to stop at the next possbile exit point. * @param monitor */ public void setMonitor(boolean monitorIn) { if (monitorIn && !monitor) { getStore().set(""); //$NON-NLS-1$ getTracker().set(""); //$NON-NLS-1$ } monitor = monitorIn; reader.setMonitorStatus(monitor); file.setMonitor(monitor); } public boolean isMonitor() { return monitor; } /* (non-Javadoc) * @see de.anbos.eclipse.logviewer.plugin.file.IFileChangedListener#contentAboutToBeChanged() */ public void contentAboutToBeChanged() { Runnable runnable = new Runnable() { public void run() { DocumentEvent event = new DocumentEvent(LogDocument.this, getStore().getLength(), 0, ""); //$NON-NLS-1$ fireDocumentAboutToBeChanged(event); } }; if (Display.getDefault() != null) { Display.getDefault().asyncExec(runnable); } } /* (non-Javadoc) * @see de.anbos.eclipse.logviewer.plugin.file.IFileChangedListener#fileChanged(char[]) */ public void fileChanged(final char[] content, final boolean isFirstTimeRead) { Runnable runnable = new Runnable() { public void run() { String text = new String(content); int offset = calculateBacklogOffset(); String currentText = getStore().get(offset, getStore().getLength() - offset); currentText = currentText.concat(text); getStore().set(currentText); getTracker().set(currentText); if (isFirstTimeRead) { offset = calculateBacklogOffset(); currentText = getStore().get(offset, getStore().getLength() - offset); getStore().set(currentText); getTracker().set(currentText); } //int newOffset = getStore().getLength() > content.length ? getStore().getLength() - content.length : 0; DocumentEvent event = new DocumentEvent(LogDocument.this, getStore().getLength(), content.length, text); fireDocumentChanged(event); } }; if (Display.getDefault() != null) { Display.getDefault().asyncExec(runnable); } } public LogFile getFile() { return file; } // Private ----------------------------------------------------------------- /** * @return the offset from where we have to read on in the Store */ private int calculateBacklogOffset() { int numberOfLines = getTracker().getNumberOfLines(); if (numberOfLines <= backlogLines) { return 0; } int overflow = numberOfLines - backlogLines; try { return getTracker().getLineOffset(overflow); } catch (BadLocationException ble) { return 0; } } // Inner classes ---------------------------------------------------------------- private class PropertyChangeListener implements IPropertyChangeListener { /* (non-Javadoc) * @see org.eclipse.jface.util.IPropertyChangeListener#propertyChange(org.eclipse.jface.util.PropertyChangeEvent) */ public void propertyChange(PropertyChangeEvent event) { if (event.getProperty().equals(ILogViewerConstants.PREF_BACKLOG)) { backlogLines = LogViewerPlugin.getDefault().getPreferenceStore() .getInt(ILogViewerConstants.PREF_BACKLOG); } } } }