summaryrefslogtreecommitdiffstats
path: root/libjava/classpath/javax/swing/text/StyledEditorKit.java
diff options
context:
space:
mode:
Diffstat (limited to 'libjava/classpath/javax/swing/text/StyledEditorKit.java')
-rw-r--r--libjava/classpath/javax/swing/text/StyledEditorKit.java569
1 files changed, 387 insertions, 182 deletions
diff --git a/libjava/classpath/javax/swing/text/StyledEditorKit.java b/libjava/classpath/javax/swing/text/StyledEditorKit.java
index 459f2438679..89c4cf18ee4 100644
--- a/libjava/classpath/javax/swing/text/StyledEditorKit.java
+++ b/libjava/classpath/javax/swing/text/StyledEditorKit.java
@@ -46,458 +46,663 @@ import java.io.Serializable;
import javax.swing.Action;
import javax.swing.JEditorPane;
+import javax.swing.JTextPane;
import javax.swing.event.CaretEvent;
import javax.swing.event.CaretListener;
/**
- * StyledEditorKit
+ * An {@link EditorKit} that supports editing styled text.
*
* @author Andrew Selkirk
+ * @author Roman Kennke (roman@kennke.org)
*/
public class StyledEditorKit extends DefaultEditorKit
{
+ /** The serialVersionUID. */
private static final long serialVersionUID = 7002391892985555948L;
/**
- * UnderlineAction
+ * Toggles the underline attribute for the selected text.
*/
public static class UnderlineAction extends StyledEditorKit.StyledTextAction
{
/**
- * Constructor UnderlineAction
+ * Creates an instance of <code>UnderlineAction</code>.
*/
public UnderlineAction()
{
- super("TODO");
- // TODO
+ super("TODO"); // TODO: Figure out name for this action.
}
/**
- * actionPerformed
- * @param event TODO
+ * Performs the action.
+ *
+ * @param event the <code>ActionEvent</code> that describes the action
*/
public void actionPerformed(ActionEvent event)
{
- // TODO
+ JEditorPane editor = getEditor(event);
+ StyledDocument doc = getStyledDocument(editor);
+ Element el = doc.getCharacterElement(editor.getSelectionStart());
+ boolean isUnderline = StyleConstants.isUnderline(el.getAttributes());
+ SimpleAttributeSet atts = new SimpleAttributeSet();
+ StyleConstants.setUnderline(atts, ! isUnderline);
+ setCharacterAttributes(editor, atts, false);
}
}
/**
- * ItalicAction
+ * Toggles the italic attribute for the selected text.
*/
public static class ItalicAction extends StyledEditorKit.StyledTextAction
{
/**
- * Constructor ItalicAction
+ * Creates an instance of <code>ItalicAction</code>.
*/
public ItalicAction()
{
- super("TODO");
- // TODO
+ super("TODO"); // TODO: Figure out correct name of this Action.
}
/**
- * actionPerformed
- * @param event TODO
+ * Performs the action.
+ *
+ * @param event the <code>ActionEvent</code> that describes the action
*/
public void actionPerformed(ActionEvent event)
{
- // TODO
+ JEditorPane editor = getEditor(event);
+ StyledDocument doc = getStyledDocument(editor);
+ Element el = doc.getCharacterElement(editor.getSelectionStart());
+ boolean isItalic = StyleConstants.isItalic(el.getAttributes());
+ SimpleAttributeSet atts = new SimpleAttributeSet();
+ StyleConstants.setItalic(atts, ! isItalic);
+ setCharacterAttributes(editor, atts, false);
}
}
/**
- * BoldAction
+ * Toggles the bold attribute for the selected text.
*/
public static class BoldAction extends StyledEditorKit.StyledTextAction
{
/**
- * Constructor BoldAction
+ * Creates an instance of <code>BoldAction</code>.
*/
public BoldAction()
{
- super("TODO");
- // TODO
+ super("TODO"); // TODO: Figure out correct name of this Action.
}
/**
- * actionPerformed
- * @param event TODO
+ * Performs the action.
+ *
+ * @param event the <code>ActionEvent</code> that describes the action
*/
public void actionPerformed(ActionEvent event)
{
- // TODO
+ JEditorPane editor = getEditor(event);
+ StyledDocument doc = getStyledDocument(editor);
+ Element el = doc.getCharacterElement(editor.getSelectionStart());
+ boolean isBold = StyleConstants.isBold(el.getAttributes());
+ SimpleAttributeSet atts = new SimpleAttributeSet();
+ StyleConstants.setItalic(atts, ! isBold);
+ setCharacterAttributes(editor, atts, false);
}
}
/**
- * AlignmentAction
+ * Sets the alignment attribute on the selected text.
*/
public static class AlignmentAction extends StyledEditorKit.StyledTextAction
{
/**
- * a
+ * The aligment to set.
*/
private int a;
/**
- * Constructor AlignmentAction
- * @param nm TODO
- * @param a TODO
+ * Creates a new instance of <code>AlignmentAction</code> to set the
+ * alignment to <code>a</code>.
+ *
+ * @param nm the name of the Action
+ * @param a the alignment to set
*/
public AlignmentAction(String nm, int a)
{
- super("TODO");
- // TODO
+ super(nm);
+ this.a = a;
}
/**
- * actionPerformed
- * @param event TODO
+ * Performs the action.
+ *
+ * @param event the <code>ActionEvent</code> that describes the action
*/
public void actionPerformed(ActionEvent event)
{
- // TODO
+ SimpleAttributeSet atts = new SimpleAttributeSet();
+ StyleConstants.setAlignment(atts, a);
+ setParagraphAttributes(getEditor(event), atts, false);
}
}
/**
- * ForegroundAction
+ * Sets the foreground color attribute on the selected text.
*/
public static class ForegroundAction extends StyledEditorKit.StyledTextAction
{
/**
- * fg
+ * The foreground color to set.
*/
private Color fg;
/**
- * Constructor ForegroundAction
- * @param nm TODO
- * @param fg TODO
+ * Creates a new instance of <code>ForegroundAction</code> to set the
+ * foreground color to <code>fg</code>.
+ *
+ * @param nm the name of the Action
+ * @param fg the foreground color to set
*/
public ForegroundAction(String nm, Color fg)
{
- super("TODO");
- // TODO
+ super(nm);
+ this.fg = fg;
}
/**
- * actionPerformed
- * @param event TODO
+ * Performs the action.
+ *
+ * @param event the <code>ActionEvent</code> that describes the action
*/
public void actionPerformed(ActionEvent event)
{
- // TODO
+ SimpleAttributeSet atts = new SimpleAttributeSet();
+ StyleConstants.setForeground(atts, fg);
+ setCharacterAttributes(getEditor(event), atts, false);
}
}
/**
- * FontSizeAction
+ * Sets the font size attribute on the selected text.
*/
public static class FontSizeAction extends StyledEditorKit.StyledTextAction
{
/**
- * size
+ * The font size to set.
*/
private int size;
/**
- * Constructor FontSizeAction
- * @param nm TODO
- * @param size TODO
+ * Creates a new instance of <code>FontSizeAction</code> to set the
+ * font size to <code>size</code>.
+ *
+ * @param nm the name of the Action
+ * @param size the font size to set
*/
public FontSizeAction(String nm, int size)
{
- super("TODO");
- // TODO
+ super(nm);
+ this.size = size;
}
/**
- * actionPerformed
- * @param event TODO
+ * Performs the action.
+ *
+ * @param event the <code>ActionEvent</code> that describes the action
*/
public void actionPerformed(ActionEvent event)
{
- // TODO
+ SimpleAttributeSet atts = new SimpleAttributeSet();
+ StyleConstants.setFontSize(atts, size);
+ setCharacterAttributes(getEditor(event), atts, false);
}
}
/**
- * FontFamilyAction
+ * Sets the font family attribute on the selected text.
*/
public static class FontFamilyAction extends StyledEditorKit.StyledTextAction
{
/**
- * family
+ * The font family to set.
*/
private String family;
/**
- * Constructor FontFamilyAction
- * @param nm TODO
- * @param family TODO
+ * Creates a new instance of <code>FontFamilyAction</code> to set the
+ * font family to <code>family</code>.
+ *
+ * @param nm the name of the Action
+ * @param family the font family to set
*/
public FontFamilyAction(String nm, String family)
{
- super("TODO");
- // TODO
+ super(nm);
+ this.family = family;
}
/**
- * actionPerformed
- * @param event TODO
+ * Performs the action.
+ *
+ * @param event the <code>ActionEvent</code> that describes the action
*/
public void actionPerformed(ActionEvent event)
{
- // TODO
+ SimpleAttributeSet atts = new SimpleAttributeSet();
+ StyleConstants.setFontFamily(atts, family);
+ setCharacterAttributes(getEditor(event), atts, false);
}
}
/**
- * StyledTextAction
+ * The abstract superclass of all styled TextActions. This class
+ * provides some useful methods to manipulate the text attributes.
*/
public abstract static class StyledTextAction extends TextAction
{
/**
- * Constructor StyledTextAction
- * @param nm TODO
+ * Creates a new instance of <code>StyledTextAction</code>.
+ *
+ * @param nm the name of the <code>StyledTextAction</code>
*/
public StyledTextAction(String nm)
{
super(nm);
- // TODO
}
/**
- * getEditor
- * @param event TODO
- * @returns JEditorPane
+ * Returns the <code>JEditorPane</code> component from which the
+ * <code>ActionEvent</code> originated.
+ *
+ * @param event the <code>ActionEvent</code>
+ * @return the <code>JEditorPane</code> component from which the
+ * <code>ActionEvent</code> originated
*/
protected final JEditorPane getEditor(ActionEvent event)
{
- return null; // TODO
+ return (JEditorPane) getTextComponent(event);
}
/**
- * setCharacterAttributes
- * @param value0 TODO
- * @param value1 TODO
- * @param value2 TODO
+ * Sets the specified character attributes on the currently selected
+ * text of <code>editor</code>. If <code>editor</code> does not have
+ * a selection, then the attributes are used as input attributes
+ * for newly inserted content.
+ *
+ * @param editor the <code>JEditorPane</code> component
+ * @param atts the text attributes to set
+ * @param replace if <code>true</code> the current attributes of the
+ * selection are replaces, otherwise they are merged
*/
- protected final void setCharacterAttributes(JEditorPane value0,
- AttributeSet value1,
- boolean value2)
+ protected final void setCharacterAttributes(JEditorPane editor,
+ AttributeSet atts,
+ boolean replace)
{
- // TODO
+ Document doc = editor.getDocument();
+ if (doc instanceof StyledDocument)
+ {
+ StyledDocument styleDoc = (StyledDocument) editor.getDocument();
+ EditorKit kit = editor.getEditorKit();
+ if (!(kit instanceof StyledEditorKit))
+ {
+ StyledEditorKit styleKit = (StyledEditorKit) kit;
+ int start = editor.getSelectionStart();
+ int end = editor.getSelectionEnd();
+ int dot = editor.getCaret().getDot();
+ if (start == dot && end == dot)
+ {
+ // If there is no selection, then we only update the
+ // input attributes.
+ MutableAttributeSet inputAttributes =
+ styleKit.getInputAttributes();
+ inputAttributes.addAttributes(atts);
+ }
+ else
+ styleDoc.setCharacterAttributes(start, end, atts, replace);
+ }
+ else
+ throw new AssertionError("The EditorKit for StyledTextActions "
+ + "is expected to be a StyledEditorKit");
+ }
+ else
+ throw new AssertionError("The Document for StyledTextActions is "
+ + "expected to be a StyledDocument.");
}
/**
- * getStyledDocument
- * @param value0 TODO
- * @returns StyledDocument
+ * Returns the {@link StyledDocument} that is used by <code>editor</code>.
+ *
+ * @param editor the <code>JEditorPane</code> from which to get the
+ * <code>StyledDocument</code>
+ *
+ * @return the {@link StyledDocument} that is used by <code>editor</code>
*/
- protected final StyledDocument getStyledDocument(JEditorPane value0)
+ protected final StyledDocument getStyledDocument(JEditorPane editor)
{
- return null; // TODO
+ Document doc = editor.getDocument();
+ if (!(doc instanceof StyledDocument))
+ throw new AssertionError("The Document for StyledEditorKits is "
+ + "expected to be a StyledDocument.");
+
+ return (StyledDocument) doc;
}
/**
- * getStyledEditorKit
- * @param value0 TODO
- * @returns StyledEditorKit
+ * Returns the {@link StyledEditorKit} that is used by <code>editor</code>.
+ *
+ * @param editor the <code>JEditorPane</code> from which to get the
+ * <code>StyledEditorKit</code>
+ *
+ * @return the {@link StyledEditorKit} that is used by <code>editor</code>
*/
- protected final StyledEditorKit getStyledEditorKit(JEditorPane value0)
+ protected final StyledEditorKit getStyledEditorKit(JEditorPane editor)
{
- return null; // TODO
+ EditorKit kit = editor.getEditorKit();
+ if (!(kit instanceof StyledEditorKit))
+ throw new AssertionError("The EditorKit for StyledDocuments is "
+ + "expected to be a StyledEditorKit.");
+
+ return (StyledEditorKit) kit;
}
/**
- * setParagraphAttributes
- * @param value0 TODO
- * @param value1 TODO
- * @param value2 TODO
+ * Sets the specified character attributes on the paragraph that
+ * contains the currently selected
+ * text of <code>editor</code>. If <code>editor</code> does not have
+ * a selection, then the attributes are set on the paragraph that
+ * contains the current caret position.
+ *
+ * @param editor the <code>JEditorPane</code> component
+ * @param atts the text attributes to set
+ * @param replace if <code>true</code> the current attributes of the
+ * selection are replaces, otherwise they are merged
*/
- protected final void setParagraphAttributes(JEditorPane value0,
- AttributeSet value1,
- boolean value2)
+ protected final void setParagraphAttributes(JEditorPane editor,
+ AttributeSet atts,
+ boolean replace)
{
- // TODO
+ Document doc = editor.getDocument();
+ if (doc instanceof StyledDocument)
+ {
+ StyledDocument styleDoc = (StyledDocument) editor.getDocument();
+ EditorKit kit = editor.getEditorKit();
+ if (!(kit instanceof StyledEditorKit))
+ {
+ StyledEditorKit styleKit = (StyledEditorKit) kit;
+ int start = editor.getSelectionStart();
+ int end = editor.getSelectionEnd();
+ int dot = editor.getCaret().getDot();
+ if (start == dot && end == dot)
+ {
+ // If there is no selection, then we only update the
+ // input attributes.
+ MutableAttributeSet inputAttributes =
+ styleKit.getInputAttributes();
+ inputAttributes.addAttributes(atts);
+ }
+ else
+ styleDoc.setParagraphAttributes(start, end, atts, replace);
+ }
+ else
+ throw new AssertionError("The EditorKit for StyledTextActions "
+ + "is expected to be a StyledEditorKit");
+ }
+ else
+ throw new AssertionError("The Document for StyledTextActions is "
+ + "expected to be a StyledDocument.");
}
}
/**
- * StyledViewFactory
+ * A {@link ViewFactory} that is able to create {@link View}s for
+ * the <code>Element</code>s that are supported by
+ * <code>StyledEditorKit</code>, namely the following types of Elements:
+ *
+ * <ul>
+ * <li>{@link AbstractDocument.ContentElementName}</li>
+ * <li>{@link AbstractDocument.ParagraphElementName}</li>
+ * <li>{@link AbstractDocument.SectionElementName}</li>
+ * <li>{@link StyleContext.ComponentElementName}</li>
+ * <li>{@link StyleContext.IconElementName}</li>
+ * </ul>
*/
static class StyledViewFactory
implements ViewFactory
{
/**
- * Constructor StyledViewFactory
- */
- StyledViewFactory()
- {
- // TODO
- }
-
- /**
- * create
- * @param value0 TODO
- * @returns View
+ * Creates a {@link View} for the specified <code>Element</code>.
+ *
+ * @param element the <code>Element</code> to create a <code>View</code>
+ * for
+ * @return the <code>View</code> for the specified <code>Element</code>
+ * or <code>null</code> if the type of <code>element</code> is
+ * not supported
*/
- public View create(Element value0)
+ public View create(Element element)
{
- return null; // TODO
+ String name = element.getName();
+ View view = null;
+ if (name.equals(AbstractDocument.ContentElementName))
+ view = new LabelView(element);
+ else if (name.equals(AbstractDocument.ParagraphElementName))
+ view = new ParagraphView(element);
+ else if (name.equals(AbstractDocument.SectionElementName))
+ view = new BoxView(element, View.Y_AXIS);
+ else if (name.equals(StyleConstants.ComponentElementName))
+ view = new ComponentView(element);
+ else if (name.equals(StyleConstants.IconElementName))
+ view = new IconView(element);
+ else
+ throw new AssertionError("Unknown Element type: "
+ + element.getClass().getName() + " : "
+ + name);
+ return view;
}
}
/**
- * AttributeTracker
+ * Keeps track of the caret position and updates the currentRun
+ * <code>Element</code> and the <code>inputAttributes</code>.
*/
- class AttributeTracker
- implements CaretListener, PropertyChangeListener, Serializable
+ class CaretTracker
+ implements CaretListener
{
/**
- * Constructor AttributeTracker
- * @param value0 TODO
- */
- AttributeTracker(StyledEditorKit value0)
- {
- // TODO
- }
-
- /**
- * updateInputAttributes
- * @param value0 TODO
- * @param value1 TODO
- * @param value2 TODO
+ * Notifies an update of the caret position.
+ *
+ * @param ev the event for the caret update
*/
- void updateInputAttributes(int value0, int value1, JTextComponent value2)
+ public void caretUpdate(CaretEvent ev)
{
- // TODO
- }
-
- /**
- * propertyChange
- * @param value0 TODO
- */
- public void propertyChange(PropertyChangeEvent value0)
- {
- // TODO
- }
-
- /**
- * caretUpdate
- * @param value0 TODO
- */
- public void caretUpdate(CaretEvent value0)
- {
- // TODO
+ Object source = ev.getSource();
+ if (!(source instanceof JTextComponent))
+ throw new AssertionError("CaretEvents are expected to come from a"
+ + "JTextComponent.");
+
+ JTextComponent text = (JTextComponent) source;
+ Document doc = text.getDocument();
+ if (!(doc instanceof StyledDocument))
+ throw new AssertionError("The Document used by StyledEditorKits is"
+ + "expected to be a StyledDocument");
+
+ StyledDocument styleDoc = (StyledDocument) doc;
+ currentRun = styleDoc.getCharacterElement(ev.getDot());
+ createInputAttributes(currentRun, inputAttributes);
}
}
/**
- * currentRun
+ * Stores the <code>Element</code> at the current caret position. This
+ * is updated by {@link CaretTracker}.
*/
Element currentRun;
/**
- * currentParagraph
+ * The current input attributes. This is updated by {@link CaretTracker}.
*/
- Element currentParagraph;
+ MutableAttributeSet inputAttributes;
/**
- * inputAttributes
+ * The CaretTracker that keeps track of the current input attributes, and
+ * the current character run Element.
*/
- MutableAttributeSet inputAttributes;
+ CaretTracker caretTracker;
+
+ /**
+ * The ViewFactory for StyledEditorKits.
+ */
+ StyledViewFactory viewFactory;
/**
- * Constructor StyledEditorKit
+ * Creates a new instance of <code>StyledEditorKit</code>.
*/
public StyledEditorKit()
{
- // TODO
+ inputAttributes = new SimpleAttributeSet();
}
/**
- * clone
- * @returns Object
+ * Creates an exact copy of this <code>StyledEditorKit</code>.
+ *
+ * @return an exact copy of this <code>StyledEditorKit</code>
*/
public Object clone()
{
- return null; // TODO
+ StyledEditorKit clone = (StyledEditorKit) super.clone();
+ // FIXME: Investigate which fields must be copied.
+ return clone;
}
/**
- * getActions
- * @returns Action[]
+ * Returns the <code>Action</code>s supported by this {@link EditorKit}.
+ * This includes the {@link BoldAction}, {@link ItalicAction} and
+ * {@link UnderlineAction} as well as the <code>Action</code>s supported
+ * by {@link DefaultEditorKit}.
+ *
+ * The other <code>Action</code>s of <code>StyledEditorKit</code> are not
+ * returned here, since they require a parameter and thus custom
+ * instantiation.
+ *
+ * @return the <code>Action</code>s supported by this {@link EditorKit}
*/
public Action[] getActions()
{
- return null; // TODO
+ Action[] actions1 = super.getActions();
+ Action[] myActions = new Action[] { new BoldAction(), new ItalicAction(),
+ new UnderlineAction() };
+ return TextAction.augmentList(actions1, myActions);
}
/**
- * getInputAttributes
- * @returns MutableAttributeSet
+ * Returns the current input attributes. These are automatically set on
+ * any newly inserted content, if not specified otherwise.
+ *
+ * @return the current input attributes
*/
public MutableAttributeSet getInputAttributes()
{
- return null; // TODO
+ return inputAttributes;
}
/**
- * getCharacterAttributeRun
- * @returns Element
+ * Returns the {@link Element} that represents the character run at the
+ * current caret position.
+ *
+ * @return the {@link Element} that represents the character run at the
+ * current caret position
*/
public Element getCharacterAttributeRun()
{
- return null; // TODO
+ return currentRun;
}
/**
- * createDefaultDocument
- * @returns Document
+ * Creates the default {@link Document} supported by this
+ * <code>EditorKit</code>. This is an instance of
+ * {@link DefaultStyledDocument} in this case but may be overridden by
+ * subclasses.
+ *
+ * @return an instance of <code>DefaultStyledDocument</code>
*/
public Document createDefaultDocument()
{
- return null; // TODO
+ return new DefaultStyledDocument();
}
/**
- * install
- * @param component TODO
+ * Installs this <code>EditorKit</code> on the specified {@link JEditorPane}.
+ * This basically involves setting up required listeners on the
+ * <code>JEditorPane</code>.
+ *
+ * @param component the <code>JEditorPane</code> to install this
+ * <code>EditorKit</code> on
*/
public void install(JEditorPane component)
{
- // TODO
+ CaretTracker tracker = new CaretTracker();
+ component.addCaretListener(tracker);
}
/**
- * deinstall
- * @param component TODO
+ * Deinstalls this <code>EditorKit</code> from the specified
+ * {@link JEditorPane}. This basically involves removing all listeners from
+ * <code>JEditorPane</code> that have been set up by this
+ * <code>EditorKit</code>.
+ *
+ * @param component the <code>JEditorPane</code> from which to deinstall this
+ * <code>EditorKit</code>
*/
public void deinstall(JEditorPane component)
{
- // TODO
+ CaretTracker t = caretTracker;
+ if (t != null)
+ component.removeCaretListener(t);
+ caretTracker = null;
}
/**
- * getViewFactory
- * @returns ViewFactory
+ * Returns a {@link ViewFactory} that is able to create {@link View}s
+ * for {@link Element}s that are supported by this <code>EditorKit</code>,
+ * namely the following types of <code>Element</code>s:
+ *
+ * <ul>
+ * <li>{@link AbstractDocument.ContentElementName}</li>
+ * <li>{@link AbstractDocument.ParagraphElementName}</li>
+ * <li>{@link AbstractDocument.SectionElementName}</li>
+ * <li>{@link StyleContext.ComponentElementName}</li>
+ * <li>{@link StyleContext.IconElementName}</li>
+ * </ul>
+ *
+ * @return a {@link ViewFactory} that is able to create {@link View}s
+ * for {@link Element}s that are supported by this <code>EditorKit</code>
*/
public ViewFactory getViewFactory()
{
- return null; // TODO
+ if (viewFactory == null)
+ viewFactory = new StyledViewFactory();
+ return viewFactory;
}
/**
- * createInputAttributes
- * @param element TODO
- * @param set TODO
+ * Copies the text attributes from <code>element</code> to <code>set</code>.
+ * This is called everytime when the caret position changes to keep
+ * track of the current input attributes. The attributes in <code>set</code>
+ * are cleaned before adding the attributes of <code>element</code>.
+ *
+ * This method filters out attributes for element names, <code>Icon</code>s
+ * and <code>Component</code>s.
+ *
+ * @param element the <code>Element</code> from which to copy the text
+ * attributes
+ * @param set the inputAttributes to copy the attributes to
*/
- protected void createInputAttributes(Element element, MutableAttributeSet set)
+ protected void createInputAttributes(Element element,
+ MutableAttributeSet set)
{
- // TODO
+ AttributeSet atts = element.getAttributes();
+ set.removeAttributes(set);
+ // FIXME: Filter out component, icon and element name attributes.
+ set.addAttributes(atts);
}
}
OpenPOWER on IntegriCloud