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

com.google.gwt.user.client.impl.DOMImpl Maven / Gradle / Ivy

Go to download

Vaadin is a web application framework for Rich Internet Applications (RIA). Vaadin enables easy development and maintenance of fast and secure rich web applications with a stunning look and feel and a wide browser support. It features a server-side architecture with the majority of the logic running on the server. Ajax technology is used at the browser-side to ensure a rich and interactive user experience.

There is a newer version: 8.25.2
Show newest version
/*
 * Copyright 2008 Google Inc.
 * 
 * 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 com.google.gwt.user.client.impl;

import com.google.gwt.core.client.GWT;
import com.google.gwt.core.client.JavaScriptObject;
import com.google.gwt.core.client.impl.Disposable;
import com.google.gwt.core.client.impl.Impl;
import com.google.gwt.dom.client.Document;
import com.google.gwt.dom.client.NodeList;
import com.google.gwt.user.client.Element;
import com.google.gwt.user.client.Event;
import com.google.gwt.user.client.EventListener;

/**
 * Native implementation associated with {@link com.google.gwt.user.client.DOM}.
 */
public abstract class DOMImpl {

  protected static boolean eventSystemIsInitialized;

  /**
   * Registers a raw DOM event listener to be cleaned up when the module is unloaded.
   */
  public static native void addDisposableEvent(com.google.gwt.dom.client.Element elem, String event,
                                               JavaScriptObject handler, boolean capture) /*-{
      elem.__gwt_disposeEvent = elem.__gwt_disposeEvent || [];
      elem.__gwt_disposeEvent.push({event: event, handler: handler, capture: capture});
  }-*/;

  /**
   * Scan all DOM elements looking for event listeners from our module and remove event listeners from them.
   * @param dom
   */
  public static void cleanupDOM(DOMImpl dom) {
    NodeList allElements = Document.get().getElementsByTagName("*");
    for (int i = 0; i < allElements.getLength(); i++) {
      com.google.gwt.dom.client.Element elem = allElements.getItem(i);
      Element userElem = (Element) elem;
      if (dom.getEventsSunk(userElem) != 0) {
        dom.sinkEvents(userElem, 0);
      }
      EventListener listener = dom.getEventListener(userElem);
      // nulls out event listener if and only if it was assigned from our module
      if (GWT.isScript() && listener != null && isMyListener(listener)) {
        dom.setEventListener(userElem, null);
      }
      // cleans up DOM-style addEventListener registered handlers
      maybeRemoveDisposableEvent(elem);
    }
  }

  /**
   * Returns trueif the object is an instance of EventListener and
   * the object belongs to this module.
   */
  protected static boolean isMyListener(Object object) {
    /*
     * The first test ensures the Object belongs to this module in Production
     * Mode by ensuring this is not a JavaScriptObject. In Production Mode,
     * foreign Java objects appear to be JavaScriptObject. See
     * Cast.isJavaScriptObject().
     * 
     * The second test then checks the exact type.
     * 
     * TODO: make the generated code smaller!
     */
    return !(object instanceof JavaScriptObject)
        && (object instanceof com.google.gwt.user.client.EventListener);
  }

  private static native void maybeRemoveDisposableEvent(com.google.gwt.dom.client.Element elem) /*-{
    var diEvents = elem.__gwt_disposeEvent;
    if (diEvents) {
      for (var i = 0, l = diEvents.length; i < l; i++) {
        var diEvent = diEvents[i];
        elem.removeEventListener(diEvent.event, diEvent.handler, diEvent.capture);
        elem.__gwt_disposeEvent = null;
      }
    }
  }-*/;

  public native void eventCancelBubble(Event evt, boolean cancel) /*-{
    evt.cancelBubble = cancel;
  }-*/;

  public abstract Element eventGetFromElement(Event evt);
  
  public native boolean eventGetRepeat(Event evt) /*-{
    return !!evt.repeat;
  }-*/; 
 
  public abstract Element eventGetToElement(Event evt);

  public final int eventGetTypeInt(Event evt) {
    return eventGetTypeInt(evt.getType());
  }
  
  public native int eventGetTypeInt(String eventType) /*-{
    switch (eventType) {
    case "blur": return 0x01000;
    case "change": return 0x00400;
    case "click": return 0x00001;
    case "dblclick": return 0x00002;
    case "focus": return 0x00800;
    case "keydown": return 0x00080;
    case "keypress": return 0x00100;
    case "keyup": return 0x00200;
    case "load": return 0x08000;
    case "losecapture": return 0x02000;
    case "mousedown": return 0x00004;
    case "mousemove": return 0x00040;
    case "mouseout": return 0x00020;
    case "mouseover": return 0x00010;
    case "mouseup": return 0x00008;
    case "scroll": return 0x04000;
    case "error": return 0x10000;
    case "mousewheel": return 0x20000;
    case "DOMMouseScroll": return 0x20000;
    case "contextmenu": return 0x40000;
    case "paste": return 0x80000;
    case "touchstart": return 0x100000;
    case "touchmove": return 0x200000;
    case "touchend": return 0x400000;
    case "touchcancel": return 0x800000;
    case "gesturestart": return 0x1000000;
    case "gesturechange": return 0x2000000;
    case "gestureend": return 0x4000000;
    default: return -1;
    }
  }-*/; 
  
  public native void eventSetKeyCode(Event evt, char key) /*-{
    evt.keyCode = key;
  }-*/;
 
  public abstract Element getChild(Element elem, int index);

  public abstract int getChildCount(Element elem);

  public abstract int getChildIndex(Element parent, Element child);

  public native EventListener getEventListener(Element elem) /*-{
    return elem.__listener;
  }-*/;

  public native int getEventsSunk(Element elem) /*-{
    return elem.__eventBits || 0;
  }-*/;

  public abstract void insertChild(Element parent, Element child, int index);

  public void maybeInitializeEventSystem() {
    if (!eventSystemIsInitialized) {
      initEventSystem();
      Impl.scheduleDispose(new Disposable() {
        @Override
        public void dispose() {
          disposeEventSystem();
          cleanupDOM(DOMImpl.this);
        }
      });
      eventSystemIsInitialized = true;
    }
  }

  public abstract void releaseCapture(Element elem);

  public abstract void setCapture(Element elem);

  public native void setEventListener(Element elem, EventListener listener) /*-{
    elem.__listener = listener;
  }-*/;

  public abstract void sinkBitlessEvent(Element elem, String eventTypeName);

  public abstract void sinkEvents(Element elem, int eventBits);

  protected abstract void disposeEventSystem();

  /**
   * Initializes the event dispatch system.
   */
  protected abstract void initEventSystem();
}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy