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

org.pepstock.charba.client.annotation.EventsHandler Maven / Gradle / Ivy

There is a newer version: 6.5-gwt
Show newest version
/**
    Licensed to the Apache Software Foundation (ASF) under one
    or more contributor license agreements.  See the NOTICE file
    distributed with this work for additional information
    regarding copyright ownership.  The ASF licenses this file
    to you 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 org.pepstock.charba.client.annotation;

import org.pepstock.charba.client.IsChart;
import org.pepstock.charba.client.annotation.listeners.ClickCallback;
import org.pepstock.charba.client.annotation.listeners.EnterCallback;
import org.pepstock.charba.client.annotation.listeners.LeaveCallback;
import org.pepstock.charba.client.callbacks.ScriptableFunctions.ProxyHandlerEventAndRedraw;
import org.pepstock.charba.client.commons.CallbackPropertyHandler;
import org.pepstock.charba.client.commons.CallbackProxy;
import org.pepstock.charba.client.commons.JsHelper;
import org.pepstock.charba.client.commons.Key;
import org.pepstock.charba.client.commons.NativeObject;
import org.pepstock.charba.client.commons.PropertyHandler;
import org.pepstock.charba.client.events.ChartEventContext;

/**
 * Base object to map the events callbacks options.
 * 
 * @author Andrea "Stock" Stocchero
 *
 */
final class EventsHandler extends PropertyHandler {

	/**
	 * Name of properties of native object.
	 */
	private enum Property implements Key
	{
		ENTER("enter"),
		LEAVE("leave"),
		CLICK("click");

		// name value of property
		private final String value;

		/**
		 * Creates with the property value to use in the native object.
		 * 
		 * @param value value of property name
		 */
		private Property(String value) {
			this.value = value;
		}

		/*
		 * (non-Javadoc)
		 * 
		 * @see org.pepstock.charba.client.commons.Key#value()
		 */
		@Override
		public String value() {
			return value;
		}

	}

	// ---------------------------
	// -- CALLBACKS PROXIES ---
	// ---------------------------
	// callback proxy to invoke the ENTER function
	private final CallbackProxy enterCallbackProxy = JsHelper.get().newCallbackProxy();
	// callback proxy to invoke the LEAVE function
	private final CallbackProxy leaveCallbackProxy = JsHelper.get().newCallbackProxy();
	// callback proxy to invoke the CLICK function
	private final CallbackProxy clickCallbackProxy = JsHelper.get().newCallbackProxy();

	// callback instance to handle click event
	private static final CallbackPropertyHandler CLICK_PROPERTY_HANDLER = new CallbackPropertyHandler<>(Property.CLICK);
	// callback instance to handle enter event
	private static final CallbackPropertyHandler ENTER_PROPERTY_HANDLER = new CallbackPropertyHandler<>(Property.ENTER);
	// callback instance to handle leave event
	private static final CallbackPropertyHandler LEAVE_PROPERTY_HANDLER = new CallbackPropertyHandler<>(Property.LEAVE);

	// the annotation options instance if the handlers is set at annotation plugin level
	private final AnnotationOptions commonParent;
	// the annotation options instance if the handlers is set at annotation element level
	private final AbstractAnnotation parent;

	/**
	 * Creates a events callbacks handler with the native object where events callbacks properties must be managed and the default value to use when the property does not exist.
	 * 
	 * @param parent model which contains the events callbacks handler.
	 * @param defaultValues default value of events callbacks to use when the properties do not exist
	 * @param nativeObject native object where events callbacks handler properties must be managed
	 */
	EventsHandler(AbstractAnnotation parent, IsDefaultsEventsHandler defaultValues, NativeObject nativeObject) {
		this(null, parent, defaultValues, nativeObject);
	}

	/**
	 * Creates a events callbacks handler with the native object where events callbacks properties must be managed and the default value to use when the property does not exist.
	 * 
	 * @param commonParent model which contains the events callbacks handler.
	 * @param defaultValues default value of events callbacks to use when the properties do not exist
	 * @param nativeObject native object where events callbacks handler properties must be managed
	 */
	EventsHandler(AnnotationOptions commonParent, IsDefaultsEventsHandler defaultValues, NativeObject nativeObject) {
		this(commonParent, null, defaultValues, nativeObject);
	}

	/**
	 * Creates a events callbacks handler with the native object where events callbacks properties must be managed and the default value to use when the property does not exist.
	 * 
	 * @param commonParent model which contains the events callbacks handler.
	 * @param parent model which contains the events callbacks handler.
	 * @param defaultValues default value of events callbacks to use when the properties do not exist
	 * @param nativeObject native object where events callbacks handler properties must be managed
	 */
	private EventsHandler(AnnotationOptions commonParent, AbstractAnnotation parent, IsDefaultsEventsHandler defaultValues, NativeObject nativeObject) {
		super(parent, defaultValues, nativeObject);
		// stores attribute
		this.parent = parent;
		this.commonParent = commonParent;
		// ------------------------------------------
		// -- SET CALLBACKS to PROXIES for EVENTs ---
		// ------------------------------------------
		// sets proxy handler to callback proxy to invoke the ENTER function
		this.enterCallbackProxy.setCallback(this::onEnter);
		// sets proxy handler to callback proxy to invoke the LEAVE function
		this.leaveCallbackProxy.setCallback(this::onLeave);
		// sets proxy handler to callback proxy to invoke the CLICK function
		this.clickCallbackProxy.setCallback(this::onClick);
	}

	/**
	 * Returns the callback called when a "enter" event is occurring.
	 * 
	 * @return the callback called when a "enter" event is occurring
	 */
	EnterCallback getEnterCallback() {
		return ENTER_PROPERTY_HANDLER.getCallback(this, getDefaultValues().getEnterCallback());
	}

	/**
	 * Sets the callback called when a "enter" event is occurring.
	 * 
	 * @param enterCallback the callback called when a "enter" event is occurring
	 */
	void setEnterCallback(EnterCallback enterCallback) {
		ENTER_PROPERTY_HANDLER.setCallback(this, AnnotationPlugin.ID, enterCallback, enterCallbackProxy.getProxy());
	}

	/**
	 * Returns the callback called when a "leave" event is occurring.
	 * 
	 * @return the callback called when a "leave" event is occurring
	 */
	LeaveCallback getLeaveCallback() {
		return LEAVE_PROPERTY_HANDLER.getCallback(this, getDefaultValues().getLeaveCallback());
	}

	/**
	 * Sets the callback called when a "leave" event is occurring.
	 * 
	 * @param leaveCallback the callback called when a "leave" event is occurring
	 */
	void setLeaveCallback(LeaveCallback leaveCallback) {
		LEAVE_PROPERTY_HANDLER.setCallback(this, AnnotationPlugin.ID, leaveCallback, leaveCallbackProxy.getProxy());
	}

	/**
	 * Returns the callback called when a "click" event is occurring.
	 * 
	 * @return the callback called when a "click" event is occurring
	 */
	ClickCallback getClickCallback() {
		return CLICK_PROPERTY_HANDLER.getCallback(this, getDefaultValues().getClickCallback());
	}

	/**
	 * Sets the callback called when a "click" event is occurring.
	 * 
	 * @param clickCallback the callback called when a "click" event is occurring
	 */
	void setClickCallback(ClickCallback clickCallback) {
		CLICK_PROPERTY_HANDLER.setCallback(this, AnnotationPlugin.ID, clickCallback, clickCallbackProxy.getProxy());
	}

	/**
	 * Returns the annotation context wrapper by the native context.
	 * 
	 * @param context native context, coming from JS annotation plugin
	 * @return the annotation context wrapper by the native context or null if the annotation id is not set
	 */
	private AnnotationContext getAnnotationContext(NativeObject context) {
		// checks if the handler has been set by an annotation element
		if (this.parent != null) {
			return new AnnotationContext(this.parent, context);
		}
		// if here, the handler has been set to the annotation common options
		// then gets the annotation ID from native object
		String annotationId = JsHelper.get().getStringProperty(AbstractAnnotation.Property.ID, context);
		// checks if ID is consistent
		if (annotationId != null && this.commonParent != null && this.commonParent.hasAnnotation(annotationId)) {
			// retrieves the annotation by id
			AbstractAnnotation annotation = this.commonParent.getAnnotation(annotationId);
			// creates context
			return new AnnotationContext(annotation, context);
		}
		// if here, the annotation element is not retrieved
		// the returns null
		return null;
	}

	/**
	 * Returns true if the context, inner chart and callbacks instance are consistent.
	 * 
	 * @param context callback annotation context instance
	 * @param callback user callback instance
	 * @return true if the context, inner chart and callbacks instance are consistent
	 */
	private boolean mustBeTriggered(AnnotationContext context, Object callback) {
		// checks if context is consistent
		if (context != null) {
			// gets chart instance from function context
			IsChart chart = context.getChart();
			// checks if chart and callback are consistent
			return IsChart.isValid(chart) && callback != null;
		}
		// if here, the context is not consistent
		return false;
	}

	/**
	 * Manages the ENTER event invoking the callback is exists.
	 * 
	 * @param context context instance
	 * @param event event instance
	 * @return if true, it will ask to Chart.js to redraw
	 */
	private boolean onEnter(NativeObject context, NativeObject event) {
		// gets callback
		EnterCallback enterCallback = getEnterCallback();
		// creates a context wrapper
		AnnotationContext internalContext = getAnnotationContext(context);
		// checks if event must be triggered
		if (mustBeTriggered(internalContext, enterCallback)) {
			// creates a chart event context
			ChartEventContext eventContext = new ChartEventContext(new AnnotationEnvelop<>(event));
			// invokes callback
			return enterCallback.onEnter(internalContext, eventContext);
		}
		// if here, returns default
		return false;
	}

	/**
	 * Manages the LEAVE event firing an annotation event.
	 * 
	 * @param context context instance
	 * @param event event instance
	 * @return if true, it will ask to Chart.js to redraw
	 */
	private boolean onLeave(NativeObject context, NativeObject event) {
		// gets callback
		LeaveCallback leaveCallback = getLeaveCallback();
		// creates a context wrapper
		AnnotationContext internalContext = getAnnotationContext(context);
		// checks if event must be triggered
		if (mustBeTriggered(internalContext, leaveCallback)) {
			// creates a chart event context
			ChartEventContext eventContext = new ChartEventContext(new AnnotationEnvelop<>(event));
			// invokes callback
			return leaveCallback.onLeave(internalContext, eventContext);
		}
		// if here, returns default
		return false;
	}

	/**
	 * Manages the CLICK event firing an annotation event.
	 * 
	 * @param context context instance
	 * @param event event instance
	 * @return if true, it will ask to Chart.js to redraw
	 */
	private boolean onClick(NativeObject context, NativeObject event) {
		// gets callback
		ClickCallback clickCallback = getClickCallback();
		// creates a context wrapper
		AnnotationContext internalContext = getAnnotationContext(context);
		// checks if event must be triggered
		if (mustBeTriggered(internalContext, clickCallback)) {
			// creates a chart event context
			ChartEventContext eventContext = new ChartEventContext(new AnnotationEnvelop<>(event));
			// invokes callback
			return clickCallback.onClick(internalContext, eventContext);
		}
		// if here, returns default
		return false;
	}

}




© 2015 - 2024 Weber Informatics LLC | Privacy Policy