All Downloads are FREE. Search and download functionalities are using the official Maven repository.

org.netbeans.editor.ext.CompletionJavaDoc Maven / Gradle / Ivy

/*
 *                 Sun Public License Notice
 * 
 * The contents of this file are subject to the Sun Public License
 * Version 1.0 (the "License"). You may not use this file except in
 * compliance with the License. A copy of the License is available at
 * http://www.sun.com/
 * 
 * The Original Code is NetBeans. The Initial Developer of the Original
 * Code is Sun Microsystems, Inc. Portions Copyright 1997-2003 Sun
 * Microsystems, Inc. All Rights Reserved.
 */


package org.netbeans.editor.ext;

import java.awt.Color;
import java.awt.Rectangle;
import java.lang.Comparable;
import java.beans.PropertyChangeListener;
import java.beans.PropertyChangeEvent;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.lang.StringBuffer;

import javax.swing.event.ListSelectionListener;
import javax.swing.event.ListSelectionEvent;
import javax.swing.JList;
import javax.swing.SwingUtilities;
import javax.swing.event.CaretEvent;
import javax.swing.event.CaretListener;
import javax.swing.text.JTextComponent;
import javax.swing.Timer;

import org.netbeans.editor.WeakTimerListener;
import org.netbeans.editor.SettingsChangeListener;
import org.netbeans.editor.Settings;
import org.netbeans.editor.Utilities;
import org.netbeans.editor.ext.ExtSettingsNames;
import org.netbeans.editor.ext.ExtSettingsDefaults;
import org.netbeans.editor.SettingsChangeEvent;
import org.netbeans.editor.SettingsUtil;
import org.netbeans.editor.LocaleSupport;

import java.util.*;

import org.netbeans.editor.ext.java.JCResultItem;


/**
 *  Support for javadoc in code completion.
 *  Contains also static utilities methods for preparing javadoc HTML content
 *
 *  @author  Martin Roskanin
 *  @since   03/2002
 */
public abstract class CompletionJavaDoc implements ActionListener, SettingsChangeListener, PropertyChangeListener  {
    
    /** Editor UI supporting this completion */
    protected ExtEditorUI extEditorUI;
    
    // javadoc browser history
    private List history = new ArrayList(5);
    
    private int curHistoryItem = -1;
    
    private JavaDocPane pane;
    private JavaDocView view;
    private int javaDocDelay;
    private Timer timer;
    protected Object currentContent;
    protected boolean addToHistory;
    private ListSelectionListener completionListener;    
    private boolean javaDocAutoPopup;
    private CaretListener caretL;

    public static final String BUNDLE_PREFIX = "javadoc-tag-"; //NOI18N
    public static final String LOADING = "javadoc-loading"; //NOI18N
    
    private static final int POPUP_DELAY = 200;
    
    
    /** Creates a new instance of CompletionJavaDoc */
    public CompletionJavaDoc(ExtEditorUI extEditorUI) {
        this.extEditorUI = extEditorUI;
        
        // Initialize timer
        timer = new Timer(0, new WeakTimerListener(this)); // delay will be set later
        timer.setRepeats(false);
        Settings.addSettingsChangeListener(this);
        
        javaDocDelay = getJavaDocDelay();
        javaDocAutoPopup = getJavaDocAutoPopup();
        
        
        /**
         * Hides JavaDoc if completion is hidden.
         */
        final ExtEditorUI extUI = extEditorUI;
        class MyCaretListener implements CaretListener {
            public void caretUpdate( CaretEvent e ) {
                Completion com = extUI.getCompletion();
                if (com == null) return;
                JDCPopupPanel panel = com.getJDCPopupPanelIfExists();
                if (panel == null) return;
                if (panel.isVisible() && !com.isPaneVisible()){
                    setJavaDocVisible(false);
                }
            }            
        }
        caretL = new MyCaretListener();
        
        synchronized (extEditorUI.getComponentLock()) {
            // if component already installed in ExtEditorUI simulate installation
            JTextComponent component = extEditorUI.getComponent();
            if (component != null) {
                propertyChange(new PropertyChangeEvent(extEditorUI,
                                                       ExtEditorUI.COMPONENT_PROPERTY, null, component));
            }

            extEditorUI.addPropertyChangeListener(this);
        }
        
    }


    protected Object convertCompletionObject(Object obj){
        return obj;
    }
    
    /** If true, the javadoc popup will remain open during completion item change 
     *  and "Searching..." dialog will be shown. If the javadoc item will not be found, 
     *  the "Javadoc Not Found" message will be also shown
     *  If false, then only valid javadoc content will be shown
     */
    protected boolean alwaysDisplayPopup(){
        return true;
    }

    protected Comparator getContentComparator() {
        return null;
    }

    public void propertyChange(PropertyChangeEvent evt) {
        String propName = evt.getPropertyName();

        // add completion listener
        final ExtEditorUI extUI = extEditorUI;
        class ClearTask implements Runnable {
            public void run(){
                Completion com = extUI.getCompletion();
                if (com != null && com.isPaneVisible()){
                    Object selectedCompletionObject = com.getSelectedValue();
                    CompletionJavaDoc completionJavaDoc = extUI.getCompletionJavaDoc();                    
                    if (selectedCompletionObject == null) {
                        if ( completionJavaDoc != null && isVisible()){
                            completionJavaDoc.setContent(null);
                        }
                        return;
                    }
                    Object selectedValue = convertCompletionObject(selectedCompletionObject);

                    if (alwaysDisplayPopup() == false) setJavaDocVisible(false);

                    if (completionJavaDoc!=null){
                        if(completionJavaDoc.autoPopup()){
                            Comparator comparator = getContentComparator();
                            if (currentContent!=null && !LOADING.equals(currentContent) && (comparator != null ? comparator.compare(currentContent, selectedValue) == 0 : currentContent.equals(selectedValue))){
                                if (!isVisible() && alwaysDisplayPopup()) setJavaDocVisible(true);
                                return;
                            }
                            if (!LOADING.equals(currentContent) && alwaysDisplayPopup()) completionJavaDoc.setContent(LocaleSupport.getString(LOADING));
                            clearHistory();
                            completionJavaDoc.setContent(selectedValue);
                            addToHistory(selectedValue);
                        }else{
                            if (isVisible()) completionJavaDoc.setContent(null);
                        }
                    }
                }
            }                    
        }

        class SelectionObserver implements ListSelectionListener {
            public void valueChanged(ListSelectionEvent e){
                SwingUtilities.invokeLater(new ClearTask());
            }
        };
    
        if (ExtEditorUI.COMPONENT_PROPERTY.equals(propName)) {
            JTextComponent component = (JTextComponent)evt.getNewValue();
            if (component != null) { // just installed
                component.addCaretListener( caretL );

                completionListener = new SelectionObserver();

                Completion completion = extEditorUI.getCompletion();
                if (completion != null){
                    if (completion.getView() instanceof JList){
                        JList completionList = (JList)completion.getView();
                        completionList.addListSelectionListener(completionListener);
                    }
                }
                
            } else { // just deinstalled
                
                cancelPerformingThread();
                component = (JTextComponent)evt.getOldValue();

                if( component != null ) {
                    component.removeCaretListener( caretL );
                }
                
                Completion completion = extEditorUI.getCompletion();
                if (completion != null){
                    if (completion.getView() instanceof JList){
                        JList completionList = (JList)completion.getView();
                        completionList.removeListSelectionListener(completionListener);
                    }
                }
                
            }

        }
    }
    
    private JDCPopupPanel getJDCPopupPanel(){
        Completion completion = extEditorUI.getCompletion();
        if (completion != null){
            return completion.getJDCPopupPanelIfExists();
        }
        return null;
    }

    /** Returns JavaDoc popup pane */
    public JavaDocPane getJavaDocPane(){
        Completion completion = extEditorUI.getCompletion();
        if (completion != null){
            return completion.getJDCPopupPanel().getJavaDocPane();
        }
        
        if (pane == null){
            pane = new ScrollJavaDocPane(extEditorUI);
        }
        return pane;
     }
    
    /** Returns JavaDoc View */
    public JavaDocView getJavaDocView(){
        if (view == null) {
            view = new HTMLJavaDocView(getJavaDocBGColor());
        }
        return view;        
    }
    
    /** Sets javadoc popup window visibility */
    public void setJavaDocVisible(final boolean visible){
        final JDCPopupPanel jdc = getJDCPopupPanel();
        if (jdc!=null){
            if (visible) getJavaDocPane().setShowWebEnabled(isExternalJavaDocMounted());
            if (!SwingUtilities.isEventDispatchThread()){
                SwingUtilities.invokeLater(
                new Runnable() {
                    public void run() {
                        jdc.setJavaDocVisible(visible);
                    }
                });
            }else{
                jdc.setJavaDocVisible(visible);
            }
        }
    }
    
    public synchronized void addToHistory(Object url){
        int histSize = history.size();
        for (int i=curHistoryItem+1; i 0) getJavaDocPane().setBackEnabled(true);
        getJavaDocPane().setForwardEnabled(false);
    }
    
    public synchronized void backHistory(){
        if (curHistoryItem > 0) {
            curHistoryItem--;
            setContent(history.get(curHistoryItem), false, false);            
            if (curHistoryItem == 0) getJavaDocPane().setBackEnabled(false);
            getJavaDocPane().setForwardEnabled(true);
        }
    }
    
    public synchronized void forwardHistory(){
        if (curHistoryItem null in this case javaDoc popup will be hidden
     */
    public void setContent(String content){
        if (content == null){
            setJavaDocVisible(false);
            return;
        }
        getJavaDocView().setContent(content);
    }
    
    /**
     * Invoked when an action occurs.
     */
    public synchronized void actionPerformed(ActionEvent e) {
        //[PENDING] - javaDoc for standalone editor
    }    

    /** Retrieve a background color of javadoc from options */
    private Color getJavaDocBGColor(){
        Class kitClass = Utilities.getKitClass(extEditorUI.getComponent());
        if (kitClass != null) {
            return (Color)SettingsUtil.getValue(kitClass,
                      ExtSettingsNames.JAVADOC_BG_COLOR,
                      ExtSettingsDefaults.defaultJavaDocBGColor);
        }
        return ExtSettingsDefaults.defaultJavaDocBGColor;
    }

    /** Retrieve a javadoc popup delay from options */
    private int getJavaDocDelay(){
        Class kitClass = Utilities.getKitClass(extEditorUI.getComponent());
        if (kitClass != null) {
            return ((Integer)SettingsUtil.getValue(kitClass,
                      ExtSettingsNames.JAVADOC_AUTO_POPUP_DELAY,
                      ExtSettingsDefaults.defaultJavaDocAutoPopupDelay)).intValue();
        }
        return ExtSettingsDefaults.defaultJavaDocAutoPopupDelay.intValue();
    }

    /** Retrieve a auto popup of javadoc property from options */    
    private boolean  getJavaDocAutoPopup(){
        Class kitClass = Utilities.getKitClass(extEditorUI.getComponent());
        if (kitClass != null) {
            return ((Boolean)SettingsUtil.getValue(kitClass,
                      ExtSettingsNames.JAVADOC_AUTO_POPUP,
                      ExtSettingsDefaults.defaultJavaDocAutoPopup)).booleanValue();
        }
        return ExtSettingsDefaults.defaultJavaDocAutoPopup.booleanValue();
    }
    
    /** Returns whether javadoc window should be invoked automatically */
    public boolean autoPopup(){
        return javaDocAutoPopup;
    }
    
    public void settingsChange(SettingsChangeEvent evt) {
        if (ExtSettingsNames.JAVADOC_BG_COLOR.equals(evt.getSettingName())){
            getJavaDocView().setBGColor(getJavaDocBGColor());
        }
        
        if (ExtSettingsNames.JAVADOC_AUTO_POPUP_DELAY.equals(evt.getSettingName())){
            javaDocDelay = getJavaDocDelay();
        }

        if (ExtSettingsNames.JAVADOC_AUTO_POPUP.equals(evt.getSettingName())){
            javaDocAutoPopup = getJavaDocAutoPopup();
        }
        
    }
    

    
    /** Parses given link such as java.awt.Component#addHierarchyListener
     *  and returns parsed Object
     *  @return Object of JCClass, JCMethod, JCConstructor or JCField 
     */
    public Object parseLink(String link, Object baseObj){
        return null;
    }

    
    protected String getTagName(CompletionJavaDoc.JavaDocTagItem tag){
        return LocaleSupport.getString(BUNDLE_PREFIX+tag.getName(),tag.getName());
    }
    
    
    public void goToSource(){
    }
    
    public void openInExternalBrowser(){
    }
    
    public boolean isExternalJavaDocMounted(){
        return false;
    }
    
    public interface JavaDocTagItem extends Comparable{
        public String getName();
        public String getText();
    }

}




© 2015 - 2025 Weber Informatics LLC | Privacy Policy