/******************************************************************************* * Copyright (c) 2014-2015 Codenvy, S.A. * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at * http://www.eclipse.org/legal/epl-v10.html * * Contributors: * Codenvy, S.A. - initial API and implementation *******************************************************************************/ package org.eclipse.che.ide.editor.orion.client; import com.google.gwt.core.client.GWT; import com.google.gwt.core.client.JavaScriptObject; import com.google.gwt.core.client.JsArray; import com.google.gwt.dom.client.Document; import com.google.gwt.dom.client.Element; import com.google.gwt.event.dom.client.BlurEvent; import com.google.gwt.event.dom.client.BlurHandler; import com.google.gwt.event.dom.client.ChangeEvent; import com.google.gwt.event.dom.client.ChangeHandler; import com.google.gwt.event.dom.client.DomEvent; import com.google.gwt.event.dom.client.FocusEvent; import com.google.gwt.event.dom.client.FocusHandler; import com.google.gwt.event.dom.client.HasChangeHandlers; import com.google.gwt.event.shared.HandlerRegistration; import com.google.gwt.json.client.JSONBoolean; import com.google.gwt.json.client.JSONNumber; import com.google.gwt.json.client.JSONObject; import com.google.gwt.resources.client.CssResource; import com.google.gwt.uibinder.client.UiBinder; import com.google.gwt.uibinder.client.UiField; import com.google.gwt.user.client.ui.SimplePanel; import com.google.inject.Provider; import com.google.inject.assistedinject.Assisted; import com.google.inject.assistedinject.AssistedInject; import com.google.web.bindery.event.shared.EventBus; import org.eclipse.che.api.promises.client.Operation; import org.eclipse.che.api.promises.client.OperationException; import org.eclipse.che.ide.api.event.SelectionChangedEvent; import org.eclipse.che.ide.api.event.SelectionChangedHandler; import org.eclipse.che.ide.api.text.Position; import org.eclipse.che.ide.api.text.Region; import org.eclipse.che.ide.api.text.RegionImpl; import org.eclipse.che.ide.api.text.annotation.Annotation; import org.eclipse.che.ide.api.texteditor.HandlesUndoRedo; import org.eclipse.che.ide.editor.orion.client.jso.OrionAnnotationModelOverlay; import org.eclipse.che.ide.editor.orion.client.jso.OrionAnnotationOverlay; import org.eclipse.che.ide.editor.orion.client.jso.OrionCodeEditWidgetOverlay; import org.eclipse.che.ide.editor.orion.client.jso.OrionContentAssistOverlay; import org.eclipse.che.ide.editor.orion.client.jso.OrionEditorOverlay; import org.eclipse.che.ide.editor.orion.client.jso.OrionEditorViewOverlay; import org.eclipse.che.ide.editor.orion.client.jso.OrionEventTargetOverlay; import org.eclipse.che.ide.editor.orion.client.jso.OrionExtRulerOverlay; import org.eclipse.che.ide.editor.orion.client.jso.OrionInputChangedEventOverlay; import org.eclipse.che.ide.editor.orion.client.jso.OrionKeyBindingModule; import org.eclipse.che.ide.editor.orion.client.jso.OrionKeyBindingsRelationOverlay; import org.eclipse.che.ide.editor.orion.client.jso.OrionKeyModeOverlay; import org.eclipse.che.ide.editor.orion.client.jso.OrionKeyStrokeOverlay; import org.eclipse.che.ide.editor.orion.client.jso.OrionProblemOverlay; import org.eclipse.che.ide.editor.orion.client.jso.OrionRulerClickEventOverlay; import org.eclipse.che.ide.editor.orion.client.jso.OrionSelectionOverlay; import org.eclipse.che.ide.editor.orion.client.jso.OrionStyleOverlay; import org.eclipse.che.ide.editor.orion.client.jso.OrionTextThemeOverlay; import org.eclipse.che.ide.editor.orion.client.jso.OrionTextViewOverlay; import org.eclipse.che.ide.editor.orion.client.jso.UiUtilsOverlay; import org.eclipse.che.ide.hotkeys.HotKeyItem; import org.eclipse.che.ide.jseditor.client.annotation.AnnotationModel; import org.eclipse.che.ide.jseditor.client.annotation.AnnotationModelEvent; import org.eclipse.che.ide.jseditor.client.codeassist.CompletionProposal; import org.eclipse.che.ide.jseditor.client.codeassist.CompletionReadyCallback; import org.eclipse.che.ide.jseditor.client.codeassist.CompletionsSource; import org.eclipse.che.ide.jseditor.client.editortype.EditorType; import org.eclipse.che.ide.jseditor.client.events.CursorActivityEvent; import org.eclipse.che.ide.jseditor.client.events.CursorActivityHandler; import org.eclipse.che.ide.jseditor.client.events.GutterClickEvent; import org.eclipse.che.ide.jseditor.client.events.GutterClickHandler; import org.eclipse.che.ide.jseditor.client.events.HasCursorActivityHandlers; import org.eclipse.che.ide.jseditor.client.events.HasScrollHandlers; import org.eclipse.che.ide.jseditor.client.events.ScrollEvent; import org.eclipse.che.ide.jseditor.client.events.ScrollHandler; import org.eclipse.che.ide.jseditor.client.gutter.Gutter; import org.eclipse.che.ide.jseditor.client.gutter.Gutters; import org.eclipse.che.ide.jseditor.client.gutter.HasGutter; import org.eclipse.che.ide.jseditor.client.keymap.Keybinding; import org.eclipse.che.ide.jseditor.client.keymap.Keymap; import org.eclipse.che.ide.jseditor.client.keymap.KeymapChangeEvent; import org.eclipse.che.ide.jseditor.client.keymap.KeymapChangeHandler; import org.eclipse.che.ide.jseditor.client.link.LinkedMode; import org.eclipse.che.ide.jseditor.client.position.PositionConverter; import org.eclipse.che.ide.jseditor.client.prefmodel.KeymapPrefReader; import org.eclipse.che.ide.jseditor.client.requirejs.ModuleHolder; import org.eclipse.che.ide.jseditor.client.text.TextRange; import org.eclipse.che.ide.jseditor.client.texteditor.CompositeEditorWidget; import org.eclipse.che.ide.jseditor.client.texteditor.ContentInitializedHandler; import org.eclipse.che.ide.jseditor.client.texteditor.EditorWidget; import org.eclipse.che.ide.jseditor.client.texteditor.LineStyler; import org.eclipse.che.ide.util.browser.UserAgent; import org.eclipse.che.ide.util.loging.Log; import java.util.ArrayList; import java.util.List; import java.util.logging.Level; import java.util.logging.Logger; import static org.eclipse.che.ide.editor.orion.client.KeyMode.EMACS; import static org.eclipse.che.ide.editor.orion.client.KeyMode.VI; /** * Orion implementation for {@link EditorWidget}. * * @author "Mickaël Leduque" */ public class OrionEditorWidget extends CompositeEditorWidget implements HasChangeHandlers, HasCursorActivityHandlers, HasScrollHandlers, HasGutter { /** The UI binder instance. */ private static final OrionEditorWidgetUiBinder UIBINDER = GWT.create(OrionEditorWidgetUiBinder.class); /** The logger. */ private static final Logger LOG = Logger.getLogger(OrionEditorWidget.class.getSimpleName()); private final OrionCodeEditWidgetOverlay codeEditWidgetModule; private final ModuleHolder moduleHolder; private final EventBus eventBus; private final KeyModeInstances keyModeInstances; private final JavaScriptObject uiUtilsOverlay; private final KeymapPrefReader keymapPrefReader; private final ContentAssistWidgetFactory contentAssistWidgetFactory; @UiField SimplePanel panel; /** The instance of the orion editor native element style. */ @UiField EditorElementStyle editorElementStyle; private OrionEditorViewOverlay editorViewOverlay; private OrionEditorOverlay editorOverlay; private String modeName; private OrionExtRulerOverlay orionLineNumberRuler; /** Component that handles undo/redo. */ private HandlesUndoRedo undoRedo; private OrionDocument embeddedDocument; private OrionKeyModeOverlay cheContentAssistMode; private Keymap keymap; private Provider<OrionKeyBindingModule> keyBindingModuleProvider; private ContentAssistWidget assistWidget; private Gutter gutter; private boolean changeHandlerAdded = false; private boolean focusHandlerAdded = false; private boolean blurHandlerAdded = false; private boolean scrollHandlerAdded = false; private boolean cursorHandlerAdded = false; private boolean gutterClickHandlerAdded = false; /** Component that handles line styling. */ private LineStyler lineStyler; @AssistedInject public OrionEditorWidget(final ModuleHolder moduleHolder, final KeyModeInstances keyModeInstances, final EventBus eventBus, final KeymapPrefReader keymapPrefReader, final Provider<OrionKeyBindingModule> keyBindingModuleProvider, final ContentAssistWidgetFactory contentAssistWidgetFactory, @Assisted final List<String> editorModes, @Assisted final WidgetInitializedCallback widgetInitializedCallback) { this.keyBindingModuleProvider = keyBindingModuleProvider; this.contentAssistWidgetFactory = contentAssistWidgetFactory; this.moduleHolder = moduleHolder; this.keyModeInstances = keyModeInstances; this.eventBus = eventBus; initWidget(UIBINDER.createAndBindUi(this)); this.keymapPrefReader = keymapPrefReader; this.codeEditWidgetModule = moduleHolder.getModule("CodeEditWidget").cast(); this.uiUtilsOverlay = moduleHolder.getModule("UiUtils"); // just first choice for the moment if (editorModes != null && !editorModes.isEmpty()) { setMode(editorModes.get(0)); } panel.getElement().setId("orion-parent-" + Document.get().createUniqueId()); panel.getElement().addClassName(this.editorElementStyle.editorParent()); codeEditWidgetModule.createEditorView(panel.getElement(), JavaScriptObject.createObject()) .then(new EditorViewCreatedOperation(widgetInitializedCallback)); } private static JavaScriptObject getEditorSettings() { final JSONObject json = new JSONObject(); json.put("theme", new JSONObject(OrionTextThemeOverlay.getDefautTheme())); // TextViewOptions (tabs) json.put("expandTab", JSONBoolean.getInstance(true)); json.put("tabSize", new JSONNumber(4)); // SourceCodeActions (typing) json.put("autoPairParentheses", JSONBoolean.getInstance(true)); json.put("autoPairBraces", JSONBoolean.getInstance(true)); json.put("autoPairSquareBrackets", JSONBoolean.getInstance(true)); json.put("autoPairAngleBrackets", JSONBoolean.getInstance(true)); json.put("autoPairQuotations", JSONBoolean.getInstance(true)); json.put("autoCompleteComments", JSONBoolean.getInstance(true)); json.put("smartIndentation", JSONBoolean.getInstance(true)); // editor features (rulers) json.put("annotationRuler", JSONBoolean.getInstance(true)); json.put("lineNumberRuler", JSONBoolean.getInstance(true)); json.put("foldingRuler", JSONBoolean.getInstance(true)); json.put("overviewRuler", JSONBoolean.getInstance(true)); json.put("zoomRuler", JSONBoolean.getInstance(true)); // language tools json.put("showOccurrences", JSONBoolean.getInstance(true)); json.put("contentAssistAutoTrigger", JSONBoolean.getInstance(true)); return json.getJavaScriptObject(); } private Gutter initBreakpointRuler(ModuleHolder moduleHolder) { JavaScriptObject orionEventTargetModule = moduleHolder.getModule("OrionEventTarget"); orionLineNumberRuler = editorOverlay.getTextView().getRulers()[1]; orionLineNumberRuler.overrideOnClickEvent(); OrionEventTargetOverlay.addMixin(orionEventTargetModule, orionLineNumberRuler); return new OrionBreakpointRuler(orionLineNumberRuler, editorOverlay); } @Override public String getValue() { return editorOverlay.getText(); } @Override public void setValue(String newValue, final ContentInitializedHandler initializationHandler) { editorOverlay.addEventListener(OrionInputChangedEventOverlay.TYPE, new OrionEditorOverlay.EventHandler<OrionInputChangedEventOverlay>() { @Override public void onEvent(OrionInputChangedEventOverlay event) { if (initializationHandler != null) { initializationHandler.onContentInitialized(); } } }, true); this.editorViewOverlay.setContents(newValue, modeName); this.editorOverlay.getUndoStack().reset(); } @Override public String getMode() { return modeName; } public void setMode(final String modeName) { String mode = modeName; if (modeName.equals("text/x-java")) { mode = "text/x-java-source"; } LOG.fine("Requested mode: " + modeName + " kept " + mode); this.modeName = mode; } @Override public boolean isReadOnly() { return this.editorOverlay.getTextView().getOptions().isReadOnly(); } @Override public void setReadOnly(final boolean isReadOnly) { this.editorOverlay.getTextView().getOptions().setReadOnly(isReadOnly); this.editorOverlay.getTextView().update(); } @Override public boolean isDirty() { return this.editorOverlay.isDirty(); } @Override public void markClean() { this.editorOverlay.setDirty(false); } private void selectKeyMode(Keymap keymap) { resetKeyModes(); Keymap usedKeymap = keymap; if (usedKeymap == null) { usedKeymap = KeyMode.DEFAULT; } if (KeyMode.DEFAULT.equals(usedKeymap)) { // nothing to do } else if (EMACS.equals(usedKeymap)) { this.editorOverlay.getTextView().addKeyMode(keyModeInstances.getInstance(EMACS)); } else if (VI.equals(usedKeymap)) { this.editorOverlay.getTextView().addKeyMode(keyModeInstances.getInstance(VI)); } else { usedKeymap = KeyMode.DEFAULT; Log.error(OrionEditorWidget.class, "Unknown keymap type: " + keymap + " - changing to default one."); } this.keymap = usedKeymap; } private void resetKeyModes() { this.editorOverlay.getTextView().removeKeyMode(keyModeInstances.getInstance(VI)); this.editorOverlay.getTextView().removeKeyMode(keyModeInstances.getInstance(EMACS)); } @Override public org.eclipse.che.ide.jseditor.client.document.Document getDocument() { if (this.embeddedDocument == null) { this.embeddedDocument = new OrionDocument(this.editorOverlay.getTextView(), this, editorOverlay); } return this.embeddedDocument; } @Override public Region getSelectedRange() { final OrionSelectionOverlay selection = this.editorOverlay.getSelection(); final int start = selection.getStart(); final int end = selection.getEnd(); if (start < 0 || end > this.editorOverlay.getModel().getCharCount() || start > end) { throw new RuntimeException("Invalid selection"); } return new RegionImpl(start, end - start); } @Override public void setSelectedRange(final Region selection, final boolean show) { this.editorOverlay.setSelection(selection.getOffset(), selection.getLength(), show); } @Override public void setDisplayRange(final Region range) { // show the line at the head of the range final int headOffset = range.getOffset() + range.getLength(); if (range.getLength() < 0) { this.editorOverlay.getTextView().setTopIndex(headOffset); } else { this.editorOverlay.getTextView().setBottomIndex(headOffset); } } @Override public int getTabSize() { return this.editorOverlay.getTextView().getOptions().getTabSize(); } @Override public void setTabSize(int tabSize) { this.editorOverlay.getTextView().getOptions().setTabSize(tabSize); } @Override public HandlerRegistration addChangeHandler(final ChangeHandler handler) { if (!changeHandlerAdded) { changeHandlerAdded = true; final OrionTextViewOverlay textView = this.editorOverlay.getTextView(); textView.addEventListener(OrionEventContants.MODEL_CHANGED_EVENT, new OrionTextViewOverlay.EventHandlerNoParameter() { @Override public void onEvent() { fireChangeEvent(); } }); } return addHandler(handler, ChangeEvent.getType()); } private void fireChangeEvent() { DomEvent.fireNativeEvent(Document.get().createChangeEvent(), this); } @Override public HandlerRegistration addCursorActivityHandler(CursorActivityHandler handler) { if (!cursorHandlerAdded) { cursorHandlerAdded = true; final OrionTextViewOverlay textView = this.editorOverlay.getTextView(); textView.addEventListener(OrionEventContants.SELECTION_EVENT, new OrionTextViewOverlay.EventHandlerNoParameter() { @Override public void onEvent() { fireCursorActivityEvent(); } }); } return addHandler(handler, CursorActivityEvent.TYPE); } private void fireCursorActivityEvent() { fireEvent(new CursorActivityEvent()); } @Override public HandlerRegistration addFocusHandler(FocusHandler handler) { if (!focusHandlerAdded) { focusHandlerAdded = true; final OrionTextViewOverlay textView = this.editorOverlay.getTextView(); textView.addEventListener(OrionEventContants.FOCUS_EVENT, new OrionTextViewOverlay.EventHandlerNoParameter() { @Override public void onEvent() { fireFocusEvent(); } }); } return addHandler(handler, FocusEvent.getType()); } private void fireFocusEvent() { DomEvent.fireNativeEvent(Document.get().createFocusEvent(), this); } @Override public HandlerRegistration addBlurHandler(BlurHandler handler) { if (!blurHandlerAdded) { blurHandlerAdded = true; final OrionTextViewOverlay textView = this.editorOverlay.getTextView(); textView.addEventListener(OrionEventContants.BLUR_EVENT, new OrionTextViewOverlay.EventHandlerNoParameter() { @Override public void onEvent() { fireBlurEvent(); } }); } return addHandler(handler, BlurEvent.getType()); } private void fireBlurEvent() { DomEvent.fireNativeEvent(Document.get().createBlurEvent(), this); } @Override public HandlerRegistration addScrollHandler(final ScrollHandler handler) { if (!scrollHandlerAdded) { scrollHandlerAdded = true; final OrionTextViewOverlay textView = this.editorOverlay.getTextView(); textView.addEventListener(OrionEventContants.SCROLL_EVENT, new OrionTextViewOverlay.EventHandlerNoParameter() { @Override public void onEvent() { fireScrollEvent(); } }); } return addHandler(handler, ScrollEvent.TYPE); } private void fireScrollEvent() { fireEvent(new ScrollEvent()); } private void setupKeymode() { final String propertyValue = this.keymapPrefReader.readPref(OrionEditorExtension.ORION_EDITOR_KEY); Keymap keymap; try { keymap = Keymap.fromKey(propertyValue); } catch (final IllegalArgumentException e) { LOG.log(Level.WARNING, "Unknown value in keymap preference.", e); return; } selectKeyMode(keymap); } @Override public EditorType getEditorType() { return EditorType.getInstance(OrionEditorExtension.ORION_EDITOR_KEY); } @Override public Keymap getKeymap() { return this.keymap; } @Override public PositionConverter getPositionConverter() { return embeddedDocument.getPositionConverter(); } @Override public void setFocus() { this.editorOverlay.focus(); } @Override public void showMessage(final String message) { this.editorOverlay.reportStatus(message); } @Override protected void onLoad() { // fix for native editor height if (panel.getElement().getChildCount() > 0) { final Element child = panel.getElement().getFirstChildElement(); child.setId("orion-editor-" + Document.get().createUniqueId()); child.getStyle().clearHeight(); } else { LOG.severe("Orion insertion failed."); } } @Override public void onResize() { // redraw text and rulers // maybe just redrawing the text would be enough this.editorOverlay.getTextView().redraw(); } @Override public HandlesUndoRedo getUndoRedo() { return this.undoRedo; } @Override public void addKeybinding(final Keybinding keybinding) { addKeybinding(keybinding, ""); } @Override public void addKeybinding(final Keybinding keybinding, String actionDescription) { OrionKeyStrokeOverlay strokeOverlay; if (UserAgent.isMac()) { strokeOverlay = OrionKeyStrokeOverlay.create(keybinding.getKeyCode(), keybinding.isCmd(), keybinding.isShift(), keybinding.isAlt(), keybinding.isControl(), "keydown", keyBindingModuleProvider.get()); } else { strokeOverlay = OrionKeyStrokeOverlay.create(keybinding.getKeyCode(), keybinding.isControl(), keybinding.isShift(), keybinding.isAlt(), false, "keydown", keyBindingModuleProvider.get()); } String actionId = "che-action-" + keybinding.getAction().toString(); editorOverlay.getTextView().setKeyBinding(strokeOverlay, actionId); editorOverlay.getTextView().setAction(actionId, new Action() { @Override public void onAction() { keybinding.getAction().action(); } }, actionDescription); } @Override public List<HotKeyItem> getHotKeys() { OrionTextViewOverlay orionTextViewOverlay = editorOverlay.getTextView(); List<HotKeyItem> hotKeyItems = new ArrayList<>(); JsArray<OrionKeyBindingsRelationOverlay> keyBindings = OrionKeyModeOverlay.getKeyBindings_(orionTextViewOverlay); for (int i = 0; i < keyBindings.length(); i++) { OrionKeyBindingsRelationOverlay key = keyBindings.get(i); String actionId = key.getActionId(); String actionDescription = orionTextViewOverlay.getActionDescription(actionId); String hotKey = UiUtilsOverlay.getUserKeyString(uiUtilsOverlay, key.getKeyBindings()); if (actionDescription != null) { hotKeyItems.add(new HotKeyItem(actionDescription, hotKey)); } } return hotKeyItems; } @Override public MarkerRegistration addMarker(final TextRange range, final String className) { final OrionAnnotationOverlay annotation = OrionAnnotationOverlay.create(); OrionStyleOverlay styleOverlay = OrionStyleOverlay.create(); styleOverlay.setStyleClass(className); int start = embeddedDocument.getIndexFromPosition(range.getFrom()); int end = embeddedDocument.getIndexFromPosition(range.getTo()); annotation.setStart(start); annotation.setEnd(end); annotation.setRangeStyle(styleOverlay); annotation.setType("che-marker"); editorOverlay.getAnnotationModel().addAnnotation(annotation); return new MarkerRegistration() { @Override public void clearMark() { editorOverlay.getAnnotationModel().removeAnnotation(annotation); } }; } @Override public void showCompletionsProposals(final List<CompletionProposal> proposals) { if (proposals == null || proposals.isEmpty()) { /** Hide autocompletion when it's visible and it is nothing to propose */ if (assistWidget.isVisible()) { assistWidget.hide(); } return; } assistWidget.show(proposals); } @Override public void showCompletionProposals(final CompletionsSource completionsSource) { completionsSource.computeCompletions(new CompletionReadyCallback() { @Override public void onCompletionReady(List<CompletionProposal> proposals) { showCompletionsProposals(proposals); } }); } @Override public LineStyler getLineStyler() { return lineStyler; } @Override public HandlerRegistration addGutterClickHandler(final GutterClickHandler handler) { if (!gutterClickHandlerAdded) { gutterClickHandlerAdded = true; orionLineNumberRuler.addEventListener(OrionEventContants.RULER_CLICK_EVENT, new OrionExtRulerOverlay.EventHandler<OrionRulerClickEventOverlay>() { @Override public void onEvent(OrionRulerClickEventOverlay parameter) { final int lineIndex = parameter.getLineIndex(); fireGutterClickEvent(lineIndex); } }, false); } return addHandler(handler, GutterClickEvent.TYPE); } private void fireGutterClickEvent(final int line) { final GutterClickEvent gutterEvent = new GutterClickEvent(line, Gutters.BREAKPOINTS_GUTTER, null); fireEvent(gutterEvent); this.embeddedDocument.getDocEventBus().fireEvent(gutterEvent); } @Override public void showCompletionProposals() { editorOverlay.getContentAssist().activate(); } @Override public void refresh() { this.editorOverlay.getTextView().redraw(); } @Override public boolean isCompletionProposalsShowing() { return assistWidget.isVisible(); } public void scrollToLine(int line) { this.editorOverlay.getTextView().setTopIndex(line); } public void showErrors(AnnotationModelEvent event) { List<Annotation> addedAnnotations = event.getAddedAnnotations(); JsArray<OrionProblemOverlay> jsArray = JsArray.createArray().cast(); AnnotationModel annotationModel = event.getAnnotationModel(); for (Annotation annotation : addedAnnotations) { Position position = annotationModel.getPosition(annotation); OrionProblemOverlay problem = JavaScriptObject.createObject().cast(); problem.setDescription(annotation.getText()); problem.setStart(position.getOffset()); problem.setEnd(position.getOffset() + position.getLength()); problem.setId("che-annotation"); problem.setSeverity(getSeverity(annotation.getType())); jsArray.push(problem); } editorOverlay.showProblems(jsArray); } private String getSeverity(String type) { switch (type) { case "org.eclipse.jdt.ui.error": return "error"; case "org.eclipse.jdt.ui.warning": return "warning"; default: return "task"; } } public void clearErrors() { editorOverlay.showProblems(JavaScriptObject.createArray().<JsArray<OrionProblemOverlay>>cast()); } public OrionTextViewOverlay getTextView() { return editorOverlay.getTextView(); } public LinkedMode getLinkedMode() { return editorOverlay.getLinkedMode(editorOverlay.getAnnotationModel()); } public void showCompletionInformation() { if (assistWidget.isVisible()) { assistWidget.showCompletionInfo(); } } public OrionAnnotationModelOverlay getAnnotationModel() { return editorOverlay.getAnnotationModel(); } @Override public Gutter getGutter() { return gutter; } /** * UI binder interface for this component. * * @author "Mickaël Leduque" */ interface OrionEditorWidgetUiBinder extends UiBinder<SimplePanel, OrionEditorWidget> { } /** * CSS style for the orion native editor element. * * @author "Mickaël Leduque" */ public interface EditorElementStyle extends CssResource { @ClassName("editor-parent") String editorParent(); } private class EditorViewCreatedOperation implements Operation<OrionEditorViewOverlay> { private final WidgetInitializedCallback widgetInitializedCallback; private EditorViewCreatedOperation(WidgetInitializedCallback widgetInitializedCallback) { this.widgetInitializedCallback = widgetInitializedCallback; } @Override public void apply(OrionEditorViewOverlay arg) throws OperationException { editorViewOverlay = arg; editorOverlay = arg.getEditor(); final OrionContentAssistOverlay contentAssist = editorOverlay.getContentAssist(); eventBus.addHandler(SelectionChangedEvent.TYPE, new SelectionChangedHandler() { @Override public void onSelectionChanged(SelectionChangedEvent event) { if (contentAssist.isActive()) { contentAssist.deactivate(); } } }); lineStyler = new OrionLineStyler(editorOverlay); final OrionTextViewOverlay textView = editorOverlay.getTextView(); keyModeInstances.add(VI, OrionKeyModeOverlay.getViKeyMode(moduleHolder.getModule("OrionVi"), textView)); keyModeInstances.add(EMACS, OrionKeyModeOverlay.getEmacsKeyMode(moduleHolder.getModule("OrionEmacs"), textView)); setupKeymode(); eventBus.addHandler(KeymapChangeEvent.TYPE, new KeymapChangeHandler() { @Override public void onKeymapChanged(final KeymapChangeEvent event) { setupKeymode(); } }); undoRedo = new OrionUndoRedo(editorOverlay.getUndoStack()); editorOverlay.setZoomRulerVisible(true); editorOverlay.getAnnotationStyler().addAnnotationType("che-marker", 100); cheContentAssistMode = OrionKeyModeOverlay.getCheCodeAssistMode(moduleHolder.getModule("CheContentAssistMode"), editorOverlay.getTextView()); assistWidget = contentAssistWidgetFactory.create(OrionEditorWidget.this, cheContentAssistMode); gutter = initBreakpointRuler(moduleHolder); editorViewOverlay.updateSettings(getEditorSettings()); widgetInitializedCallback.initialized(OrionEditorWidget.this); } } }