plugin from example cordova datepicker phonegap-plugins android-datepicker

cordova - from - El complemento datePicker no funciona en Phonegap 2.0



ionic datepicker (3)

Después de actualizar a Phonegap 2.0, el complemento de datePicker no funciona. El error es: TypeError no detectado: no se puede leer la propiedad ''datePicker'' de undefined.

el error aparece en el código javascript: window.plugins.datePicker.show ({...

El archivo DatePicker js:

/** * Phonegap DatePicker Plugin Copyright (c) Greg Allen 2011 MIT Licensed * Reused and ported to Android plugin by Daniel van ''t Oever */ if (typeof cordova !== "undefined") { /** * Constructor */ function DatePicker() { this._callback; } /** * show - true to show the ad, false to hide the ad */ DatePicker.prototype.show = function(options, cb) { if (options.date) { options.date = (options.date.getMonth() + 1) + "/" + (options.date.getDate()) + "/" + (options.date.getFullYear()) + "/" + (options.date.getHours()) + "/" + (options.date.getMinutes()); } var defaults = { mode : '''', date : '''', allowOldDates : true }; for ( var key in defaults) { if (typeof options[key] !== "undefined") defaults[key] = options[key]; } this._callback = cb; return cordova.exec(cb, failureCallback, ''DatePickerPlugin'', defaults.mode, new Array(defaults)); }; DatePicker.prototype._dateSelected = function(date) { var d = new Date(parseFloat(date) * 1000); if (this._callback) this._callback(d); }; function failureCallback(err) { console.log("datePickerPlugin.js failed: " + err); } cordova.addConstructor(function() {debugger; if (!window.plugins) { window.plugins = {}; } window.plugins.datePicker = new DatePicker(); }); };

El archivo java del plugin DatePicker:

/** * */ package com.phonegap.plugin; import java.util.Calendar; import java.util.Date; import org.json.JSONArray; import org.json.JSONException; import org.json.JSONObject; import android.app.Activity; import android.app.DatePickerDialog; import android.app.DatePickerDialog.OnDateSetListener; import android.app.TimePickerDialog; import android.app.TimePickerDialog.OnTimeSetListener; import android.util.Log; import android.widget.DatePicker; import android.widget.TimePicker; import org.apache.cordova.DroidGap; import org.apache.cordova.api.Plugin; import org.apache.cordova.api.PluginResult; /** * @author ng4e * @author Daniel van ''t Oever * * Rewrote plugin so it it similar to the iOS datepicker plugin and it * accepts prefilled dates and time */ public class DatePickerPlugin extends Plugin { private static final String ACTION_DATE = "date"; private static final String ACTION_TIME = "time"; private final String pluginName = "DatePickerPlugin"; /* * (non-Javadoc) * * @see com.phonegap.api.Plugin#execute(java.lang.String, * org.json.JSONArray, java.lang.String) */ @Override public PluginResult execute(final String action, final JSONArray data, final String callBackId) { Log.d(pluginName, "DatePicker called with options: " + data); PluginResult result = null; this.show(data, callBackId); result = new PluginResult(PluginResult.Status.NO_RESULT); result.setKeepCallback(true); return result; } public synchronized void show(final JSONArray data, final String callBackId) { final DatePickerPlugin datePickerPlugin = this; @SuppressWarnings("deprecation") final DroidGap currentCtx = (DroidGap) ctx.getContext(); final Calendar c = Calendar.getInstance(); final Runnable runnable; String action = "date"; /* * Parse information from data parameter and where possible, override * above date fields */ int month = -1, day = -1, year = -1, hour = -1, min = -1; try { JSONObject obj = data.getJSONObject(0); action = obj.getString("mode"); String optionDate = obj.getString("date"); String[] datePart = optionDate.split("/"); month = Integer.parseInt(datePart[0]); day = Integer.parseInt(datePart[1]); year = Integer.parseInt(datePart[2]); hour = Integer.parseInt(datePart[3]); min = Integer.parseInt(datePart[4]); /* currently not handled in Android */ // boolean optionAllowOldDates = obj.getBoolean("allowOldDates"); } catch (JSONException e) { e.printStackTrace(); } // By default initialize these fields to ''now'' final int mYear = year == -1 ? c.get(Calendar.YEAR) : year; final int mMonth = month == -1 ? c.get(Calendar.MONTH) : month - 1; final int mDay = day == -1 ? c.get(Calendar.DAY_OF_MONTH) : day; final int mHour = hour == -1 ? c.get(Calendar.HOUR_OF_DAY) : hour; final int mMinutes = min == -1 ? c.get(Calendar.MINUTE) : min; if (ACTION_TIME.equalsIgnoreCase(action)) { runnable = new Runnable() { public void run() { final TimeSetListener timeSetListener = new TimeSetListener(datePickerPlugin, callBackId); final TimePickerDialog timeDialog = new TimePickerDialog(currentCtx, timeSetListener, mHour, mMinutes, true); timeDialog.show(); } }; } else if (ACTION_DATE.equalsIgnoreCase(action)) { runnable = new Runnable() { public void run() { final DateSetListener dateSetListener = new DateSetListener(datePickerPlugin, callBackId); final DatePickerDialog dateDialog = new DatePickerDialog(currentCtx, dateSetListener, mYear, mMonth, mDay); dateDialog.show(); } }; } else { Log.d(pluginName, "Unknown action. Only ''date'' or ''time'' are valid actions"); return; } //((Activity) ctx).runOnUiThread(runnable); } private final class DateSetListener implements OnDateSetListener { private final DatePickerPlugin datePickerPlugin; private final String callBackId; private DateSetListener(DatePickerPlugin datePickerPlugin, String callBackId) { this.datePickerPlugin = datePickerPlugin; this.callBackId = callBackId; } /** * Return a string containing the date in the format YYYY/MM/DD */ public void onDateSet(final DatePicker view, final int year, final int monthOfYear, final int dayOfMonth) { String returnDate = year + "/" + (monthOfYear + 1) + "/" + dayOfMonth; datePickerPlugin.success(new PluginResult(PluginResult.Status.OK, returnDate), callBackId); } } private final class TimeSetListener implements OnTimeSetListener { private final DatePickerPlugin datePickerPlugin; private final String callBackId; private TimeSetListener(DatePickerPlugin datePickerPlugin, String callBackId) { this.datePickerPlugin = datePickerPlugin; this.callBackId = callBackId; } /** * Return the current date with the time modified as it was set in the * time picker. */ public void onTimeSet(final TimePicker view, final int hourOfDay, final int minute) { /*Date date = new Date(); date.setHours(hourOfDay); date.setMinutes(minute);*/ Calendar today = Calendar.getInstance(); today.set(Calendar.HOUR_OF_DAY, hourOfDay); today.set(Calendar.MINUTE, minute); Date date = today.getTime(); datePickerPlugin.success(new PluginResult(PluginResult.Status.OK, date.toString()), callBackId); } } }

Después de pasar tiempo en Google, hice los siguientes cambios: reemplazar

cordova.addConstructor(function() {debugger; if (!window.plugins) { window.plugins = {}; } window.plugins.datePicker = new DatePicker(); });

con

window.datePicker = new DatePicker();

Actualice el código js de llamarlo a

window.datePicker.show({...

Ahora puedo obtener el objeto datePicker de todos modos, pero tengo este nuevo error:

Unkeught TypeError: Object # no tiene el método ''exec''

en

DatePicker.prototype.show = function(options, cb) { ... return cordova.exec(cb, failureCallback, ''DatePickerPlugin'', defaults.mode, new Array(defaults)); })

¡Gracias por cualquier ayuda!


al configurar un campo de entrada para escribir "fecha" aparece el selector de fecha nativo. forma super simple de hacerlo


http://docs.phonegap.com/en/2.0.0/guide_plugin-development_android_index.md.html#Developing%20a%20Plugin%20on%20Android

Después de comprobar esto, encontré:

Errores comunes

Los complementos tienen acceso a un objeto CordovaInterface. Este objeto tiene acceso a la actividad de Android que ejecuta la aplicación. Este es el contexto requerido para lanzar una nueva intención de Android. CordovaInterface permite que los complementos inicien una Actividad para obtener un resultado, y establecer el complemento de devolución de llamada cuando el Intento vuelve a la aplicación. Esto es importante, ya que el sistema Intents es la forma en que Android se comunica entre los procesos.

Los complementos no tienen acceso directo al Contexto como lo han hecho en el pasado. El miembro heredado de ctx está en desuso, y se eliminará seis meses después de que se libere 2.0. Todos los métodos que ctx tienen existen en el Contexto, por lo que tanto getContext () como getActivity () son capaces de devolver el objeto adecuado requerido.

Evite llamar a JavaScript usando webView.loadUrl (). La razón por la que tenemos un servidor de devolución de llamada es para permitir que la ejecución de JavaScript sea segura para subprocesos, y loadUrl interrumpe explícitamente el subproceso de interfaz de usuario, y puede afectar la usabilidad de su complemento.

Aquí está mi solución:

en DatePickerPlugin.java

import android.content.Context; .... public synchronized void show(final JSONArray data, final String callBackId) { final DatePickerPlugin datePickerPlugin = this; final DroidGap currentCtx = (DroidGap) ctx.getContext(); final Calendar c = Calendar.getInstance(); .....

reemplazar línea:

final DroidGap currentCtx = (DroidGap) ctx.getContext();

por:

final Context currentCtx = cordova.getActivity();

Encontrar:

ctx.runOnUiThread(runnable);

sustituir por:

cordova.getActivity().runOnUiThread(runnable);

Esto funciona bien en mi emulador 4.0.3 con Phonegap 2.0