diff --git a/iOS/Twitter/native/ios/TwitterPlugin.h b/iOS/Twitter/TwitterPlugin.h similarity index 84% rename from iOS/Twitter/native/ios/TwitterPlugin.h rename to iOS/Twitter/TwitterPlugin.h index d2cd308f..2cd222a9 100755 --- a/iOS/Twitter/native/ios/TwitterPlugin.h +++ b/iOS/Twitter/TwitterPlugin.h @@ -5,14 +5,10 @@ // Created by Antonelli Brian on 10/13/11. // -#import -#import -#import -#ifdef CORDOVA_FRAMEWORK + #import + #import + #import #import -#else - #import "CDVPlugin.h" -#endif @interface TwitterPlugin : CDVPlugin{ } diff --git a/iOS/Twitter/native/ios/TwitterPlugin.m b/iOS/Twitter/TwitterPlugin.m similarity index 98% rename from iOS/Twitter/native/ios/TwitterPlugin.m rename to iOS/Twitter/TwitterPlugin.m index 98aa1900..5eb79373 100755 --- a/iOS/Twitter/native/ios/TwitterPlugin.m +++ b/iOS/Twitter/TwitterPlugin.m @@ -5,14 +5,9 @@ // Created by Antonelli Brian on 10/13/11. // -#import "TwitterPlugin.h" -#ifdef CORDOVA_FRAMEWORK + #import "TwitterPlugin.h" #import #import -#else - #import "JSONKit.h" - #import "CDVAvailability.h" -#endif #define TWITTER_URL @"http://api.twitter.com/1/" @@ -92,7 +87,7 @@ - (void) composeTweet:(NSMutableArray*)arguments withDict:(NSMutableDictionary*) else{ #if TARGET_IPHONE_SIMULATOR - NSString *simWarning = @"Test TwitterPlugin on Real Hardware. Tested on Cordova 1.7.0"; + NSString *simWarning = @"Test TwitterPlugin on Real Hardware. Tested on Cordova 2.0.0"; //EXC_BAD_ACCESS occurs on simulator unable to reproduce on real device //running iOS 5.1 and Cordova 1.6.1 NSLog(@"%@",simWarning); diff --git a/iOS/Twitter/example/www/index.html b/iOS/Twitter/example/www/index.html index c40a334a..6849e7fc 100644 --- a/iOS/Twitter/example/www/index.html +++ b/iOS/Twitter/example/www/index.html @@ -10,9 +10,18 @@ + +

Hey, it's Twitter on PhoneGap!

+

Apache Cordova™

+
+ + +
+ +
  1. isAvailable
  2. diff --git a/iOS/Twitter/www/TwitterPlugin.js b/iOS/Twitter/example/www2.0/TwitterPlugin.js similarity index 100% rename from iOS/Twitter/www/TwitterPlugin.js rename to iOS/Twitter/example/www2.0/TwitterPlugin.js diff --git a/iOS/Twitter/example/www2.0/config.xml b/iOS/Twitter/example/www2.0/config.xml new file mode 100644 index 00000000..a7e35db9 --- /dev/null +++ b/iOS/Twitter/example/www2.0/config.xml @@ -0,0 +1,47 @@ + + + Hello Cordova + + + A sample Apache Cordova application that responds to the deviceready event. + + + + Apache Cordova Team + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + + diff --git a/iOS/Twitter/example/www2.0/cordova-2.0.0.js b/iOS/Twitter/example/www2.0/cordova-2.0.0.js new file mode 100644 index 00000000..c2caa2ff --- /dev/null +++ b/iOS/Twitter/example/www2.0/cordova-2.0.0.js @@ -0,0 +1,5240 @@ +// commit 114cf5304a74ff8f7c9ff1d21cf5652298af04b0 + +// File generated at :: Wed Jul 18 2012 16:47:25 GMT-0700 (PDT) + +/* + 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. +*/ + +;(function() { + +// file: lib/scripts/require.js +var require, + define; + +(function () { + var modules = {}; + + function build(module) { + var factory = module.factory; + module.exports = {}; + delete module.factory; + factory(require, module.exports, module); + return module.exports; + } + + require = function (id) { + if (!modules[id]) { + throw "module " + id + " not found"; + } + return modules[id].factory ? build(modules[id]) : modules[id].exports; + }; + + define = function (id, factory) { + if (modules[id]) { + throw "module " + id + " already defined"; + } + + modules[id] = { + id: id, + factory: factory + }; + }; + + define.remove = function (id) { + delete modules[id]; + }; + +})(); + +//Export for use in node +if (typeof module === "object" && typeof require === "function") { + module.exports.require = require; + module.exports.define = define; +} +// file: lib/cordova.js +define("cordova", function(require, exports, module) { +var channel = require('cordova/channel'); + +/** + * Listen for DOMContentLoaded and notify our channel subscribers. + */ +document.addEventListener('DOMContentLoaded', function() { + channel.onDOMContentLoaded.fire(); +}, false); +if (document.readyState == 'complete' || document.readyState == 'interactive') { + channel.onDOMContentLoaded.fire(); +} + +/** + * Intercept calls to addEventListener + removeEventListener and handle deviceready, + * resume, and pause events. + */ +var m_document_addEventListener = document.addEventListener; +var m_document_removeEventListener = document.removeEventListener; +var m_window_addEventListener = window.addEventListener; +var m_window_removeEventListener = window.removeEventListener; + +/** + * Houses custom event handlers to intercept on document + window event listeners. + */ +var documentEventHandlers = {}, + windowEventHandlers = {}; + +document.addEventListener = function(evt, handler, capture) { + var e = evt.toLowerCase(); + if (typeof documentEventHandlers[e] != 'undefined') { + if (evt === 'deviceready') { + documentEventHandlers[e].subscribeOnce(handler); + } else { + documentEventHandlers[e].subscribe(handler); + } + } else { + m_document_addEventListener.call(document, evt, handler, capture); + } +}; + +window.addEventListener = function(evt, handler, capture) { + var e = evt.toLowerCase(); + if (typeof windowEventHandlers[e] != 'undefined') { + windowEventHandlers[e].subscribe(handler); + } else { + m_window_addEventListener.call(window, evt, handler, capture); + } +}; + +document.removeEventListener = function(evt, handler, capture) { + var e = evt.toLowerCase(); + // If unsubcribing from an event that is handled by a plugin + if (typeof documentEventHandlers[e] != "undefined") { + documentEventHandlers[e].unsubscribe(handler); + } else { + m_document_removeEventListener.call(document, evt, handler, capture); + } +}; + +window.removeEventListener = function(evt, handler, capture) { + var e = evt.toLowerCase(); + // If unsubcribing from an event that is handled by a plugin + if (typeof windowEventHandlers[e] != "undefined") { + windowEventHandlers[e].unsubscribe(handler); + } else { + m_window_removeEventListener.call(window, evt, handler, capture); + } +}; + +function createEvent(type, data) { + var event = document.createEvent('Events'); + event.initEvent(type, false, false); + if (data) { + for (var i in data) { + if (data.hasOwnProperty(i)) { + event[i] = data[i]; + } + } + } + return event; +} + +if(typeof window.console === "undefined") { + window.console = { + log:function(){} + }; +} + +var cordova = { + define:define, + require:require, + /** + * Methods to add/remove your own addEventListener hijacking on document + window. + */ + addWindowEventHandler:function(event, opts) { + return (windowEventHandlers[event] = channel.create(event, opts)); + }, + addDocumentEventHandler:function(event, opts) { + return (documentEventHandlers[event] = channel.create(event, opts)); + }, + removeWindowEventHandler:function(event) { + delete windowEventHandlers[event]; + }, + removeDocumentEventHandler:function(event) { + delete documentEventHandlers[event]; + }, + /** + * Retreive original event handlers that were replaced by Cordova + * + * @return object + */ + getOriginalHandlers: function() { + return {'document': {'addEventListener': m_document_addEventListener, 'removeEventListener': m_document_removeEventListener}, + 'window': {'addEventListener': m_window_addEventListener, 'removeEventListener': m_window_removeEventListener}}; + }, + /** + * Method to fire event from native code + */ + fireDocumentEvent: function(type, data) { + var evt = createEvent(type, data); + if (typeof documentEventHandlers[type] != 'undefined') { + setTimeout(function() { + documentEventHandlers[type].fire(evt); + }, 0); + } else { + document.dispatchEvent(evt); + } + }, + fireWindowEvent: function(type, data) { + var evt = createEvent(type,data); + if (typeof windowEventHandlers[type] != 'undefined') { + setTimeout(function() { + windowEventHandlers[type].fire(evt); + }, 0); + } else { + window.dispatchEvent(evt); + } + }, + // TODO: this is Android only; think about how to do this better + shuttingDown:false, + UsePolling:false, + // END TODO + + // TODO: iOS only + // This queue holds the currently executing command and all pending + // commands executed with cordova.exec(). + commandQueue:[], + // Indicates if we're currently in the middle of flushing the command + // queue on the native side. + commandQueueFlushing:false, + // END TODO + /** + * Plugin callback mechanism. + */ + callbackId: 0, + callbacks: {}, + callbackStatus: { + NO_RESULT: 0, + OK: 1, + CLASS_NOT_FOUND_EXCEPTION: 2, + ILLEGAL_ACCESS_EXCEPTION: 3, + INSTANTIATION_EXCEPTION: 4, + MALFORMED_URL_EXCEPTION: 5, + IO_EXCEPTION: 6, + INVALID_ACTION: 7, + JSON_EXCEPTION: 8, + ERROR: 9 + }, + + /** + * Called by native code when returning successful result from an action. + * + * @param callbackId + * @param args + */ + callbackSuccess: function(callbackId, args) { + if (cordova.callbacks[callbackId]) { + + // If result is to be sent to callback + if (args.status == cordova.callbackStatus.OK) { + try { + if (cordova.callbacks[callbackId].success) { + cordova.callbacks[callbackId].success(args.message); + } + } + catch (e) { + console.log("Error in success callback: "+callbackId+" = "+e); + } + } + + // Clear callback if not expecting any more results + if (!args.keepCallback) { + delete cordova.callbacks[callbackId]; + } + } + }, + + /** + * Called by native code when returning error result from an action. + * + * @param callbackId + * @param args + */ + callbackError: function(callbackId, args) { + if (cordova.callbacks[callbackId]) { + try { + if (cordova.callbacks[callbackId].fail) { + cordova.callbacks[callbackId].fail(args.message); + } + } + catch (e) { + console.log("Error in error callback: "+callbackId+" = "+e); + } + + // Clear callback if not expecting any more results + if (!args.keepCallback) { + delete cordova.callbacks[callbackId]; + } + } + }, + addConstructor: function(func) { + channel.onCordovaReady.subscribeOnce(function() { + try { + func(); + } catch(e) { + console.log("Failed to run constructor: " + e); + } + }); + } +}; + +// Register pause, resume and deviceready channels as events on document. +channel.onPause = cordova.addDocumentEventHandler('pause'); +channel.onResume = cordova.addDocumentEventHandler('resume'); +channel.onDeviceReady = cordova.addDocumentEventHandler('deviceready'); + +module.exports = cordova; + +}); + +// file: lib/common/builder.js +define("cordova/builder", function(require, exports, module) { +var utils = require('cordova/utils'); + +function each(objects, func, context) { + for (var prop in objects) { + if (objects.hasOwnProperty(prop)) { + func.apply(context, [objects[prop], prop]); + } + } +} + +function include(parent, objects, clobber, merge) { + each(objects, function (obj, key) { + try { + var result = obj.path ? require(obj.path) : {}; + + if (clobber) { + // Clobber if it doesn't exist. + if (typeof parent[key] === 'undefined') { + parent[key] = result; + } else if (typeof obj.path !== 'undefined') { + // If merging, merge properties onto parent, otherwise, clobber. + if (merge) { + recursiveMerge(parent[key], result); + } else { + parent[key] = result; + } + } + result = parent[key]; + } else { + // Overwrite if not currently defined. + if (typeof parent[key] == 'undefined') { + parent[key] = result; + } else if (merge && typeof obj.path !== 'undefined') { + // If merging, merge parent onto result + recursiveMerge(result, parent[key]); + parent[key] = result; + } else { + // Set result to what already exists, so we can build children into it if they exist. + result = parent[key]; + } + } + + if (obj.children) { + include(result, obj.children, clobber, merge); + } + } catch(e) { + utils.alert('Exception building cordova JS globals: ' + e + ' for key "' + key + '"'); + } + }); +} + +/** + * Merge properties from one object onto another recursively. Properties from + * the src object will overwrite existing target property. + * + * @param target Object to merge properties into. + * @param src Object to merge properties from. + */ +function recursiveMerge(target, src) { + for (var prop in src) { + if (src.hasOwnProperty(prop)) { + if (typeof target.prototype !== 'undefined' && target.prototype.constructor === target) { + // If the target object is a constructor override off prototype. + target.prototype[prop] = src[prop]; + } else { + target[prop] = typeof src[prop] === 'object' ? recursiveMerge( + target[prop], src[prop]) : src[prop]; + } + } + } + return target; +} + +module.exports = { + build: function (objects) { + return { + intoButDontClobber: function (target) { + include(target, objects, false, false); + }, + intoAndClobber: function(target) { + include(target, objects, true, false); + }, + intoAndMerge: function(target) { + include(target, objects, true, true); + } + }; + } +}; + +}); + +// file: lib/common/channel.js +define("cordova/channel", function(require, exports, module) { +var utils = require('cordova/utils'); + +/** + * Custom pub-sub "channel" that can have functions subscribed to it + * This object is used to define and control firing of events for + * cordova initialization. + * + * The order of events during page load and Cordova startup is as follows: + * + * onDOMContentLoaded Internal event that is received when the web page is loaded and parsed. + * onNativeReady Internal event that indicates the Cordova native side is ready. + * onCordovaReady Internal event fired when all Cordova JavaScript objects have been created. + * onCordovaInfoReady Internal event fired when device properties are available. + * onCordovaConnectionReady Internal event fired when the connection property has been set. + * onDeviceReady User event fired to indicate that Cordova is ready + * onResume User event fired to indicate a start/resume lifecycle event + * onPause User event fired to indicate a pause lifecycle event + * onDestroy Internal event fired when app is being destroyed (User should use window.onunload event, not this one). + * + * The only Cordova events that user code should register for are: + * deviceready Cordova native code is initialized and Cordova APIs can be called from JavaScript + * pause App has moved to background + * resume App has returned to foreground + * + * Listeners can be registered as: + * document.addEventListener("deviceready", myDeviceReadyListener, false); + * document.addEventListener("resume", myResumeListener, false); + * document.addEventListener("pause", myPauseListener, false); + * + * The DOM lifecycle events should be used for saving and restoring state + * window.onload + * window.onunload + * + */ + +/** + * Channel + * @constructor + * @param type String the channel name + * @param opts Object options to pass into the channel, currently + * supports: + * onSubscribe: callback that fires when + * something subscribes to the Channel. Sets + * context to the Channel. + * onUnsubscribe: callback that fires when + * something unsubscribes to the Channel. Sets + * context to the Channel. + */ +var Channel = function(type, opts) { + this.type = type; + this.handlers = {}; + this.numHandlers = 0; + this.guid = 1; + this.fired = false; + this.enabled = true; + this.events = { + onSubscribe:null, + onUnsubscribe:null + }; + if (opts) { + if (opts.onSubscribe) this.events.onSubscribe = opts.onSubscribe; + if (opts.onUnsubscribe) this.events.onUnsubscribe = opts.onUnsubscribe; + } +}, + channel = { + /** + * Calls the provided function only after all of the channels specified + * have been fired. + */ + join: function (h, c) { + var i = c.length; + var len = i; + var f = function() { + if (!(--i)) h(); + }; + for (var j=0; j} phoneNumbers array of phone numbers +* @param {Array.} emails array of email addresses +* @param {Array.} addresses array of addresses +* @param {Array.} ims instant messaging user ids +* @param {Array.} organizations +* @param {DOMString} birthday contact's birthday +* @param {DOMString} note user notes about contact +* @param {Array.} photos +* @param {Array.} categories +* @param {Array.} urls contact's web sites +*/ +var Contact = function (id, displayName, name, nickname, phoneNumbers, emails, addresses, + ims, organizations, birthday, note, photos, categories, urls) { + this.id = id || null; + this.rawId = null; + this.displayName = displayName || null; + this.name = name || null; // ContactName + this.nickname = nickname || null; + this.phoneNumbers = phoneNumbers || null; // ContactField[] + this.emails = emails || null; // ContactField[] + this.addresses = addresses || null; // ContactAddress[] + this.ims = ims || null; // ContactField[] + this.organizations = organizations || null; // ContactOrganization[] + this.birthday = birthday || null; + this.note = note || null; + this.photos = photos || null; // ContactField[] + this.categories = categories || null; // ContactField[] + this.urls = urls || null; // ContactField[] +}; + +/** +* Removes contact from device storage. +* @param successCB success callback +* @param errorCB error callback +*/ +Contact.prototype.remove = function(successCB, errorCB) { + var fail = function(code) { + errorCB(new ContactError(code)); + }; + if (this.id === null) { + fail(ContactError.UNKNOWN_ERROR); + } + else { + exec(successCB, fail, "Contacts", "remove", [this.id]); + } +}; + +/** +* Creates a deep copy of this Contact. +* With the contact ID set to null. +* @return copy of this Contact +*/ +Contact.prototype.clone = function() { + var clonedContact = utils.clone(this); + var i; + clonedContact.id = null; + clonedContact.rawId = null; + // Loop through and clear out any id's in phones, emails, etc. + if (clonedContact.phoneNumbers) { + for (i = 0; i < clonedContact.phoneNumbers.length; i++) { + clonedContact.phoneNumbers[i].id = null; + } + } + if (clonedContact.emails) { + for (i = 0; i < clonedContact.emails.length; i++) { + clonedContact.emails[i].id = null; + } + } + if (clonedContact.addresses) { + for (i = 0; i < clonedContact.addresses.length; i++) { + clonedContact.addresses[i].id = null; + } + } + if (clonedContact.ims) { + for (i = 0; i < clonedContact.ims.length; i++) { + clonedContact.ims[i].id = null; + } + } + if (clonedContact.organizations) { + for (i = 0; i < clonedContact.organizations.length; i++) { + clonedContact.organizations[i].id = null; + } + } + if (clonedContact.categories) { + for (i = 0; i < clonedContact.categories.length; i++) { + clonedContact.categories[i].id = null; + } + } + if (clonedContact.photos) { + for (i = 0; i < clonedContact.photos.length; i++) { + clonedContact.photos[i].id = null; + } + } + if (clonedContact.urls) { + for (i = 0; i < clonedContact.urls.length; i++) { + clonedContact.urls[i].id = null; + } + } + return clonedContact; +}; + +/** +* Persists contact to device storage. +* @param successCB success callback +* @param errorCB error callback +*/ +Contact.prototype.save = function(successCB, errorCB) { + var fail = function(code) { + errorCB(new ContactError(code)); + }; + var success = function(result) { + if (result) { + if (typeof successCB === 'function') { + var fullContact = require('cordova/plugin/contacts').create(result); + successCB(convertIn(fullContact)); + } + } + else { + // no Entry object returned + fail(ContactError.UNKNOWN_ERROR); + } + }; + var dupContact = convertOut(utils.clone(this)); + exec(success, fail, "Contacts", "save", [dupContact]); +}; + + +module.exports = Contact; + +}); + +// file: lib/common/plugin/ContactAddress.js +define("cordova/plugin/ContactAddress", function(require, exports, module) { +/** +* Contact address. +* @constructor +* @param {DOMString} id unique identifier, should only be set by native code +* @param formatted // NOTE: not a W3C standard +* @param streetAddress +* @param locality +* @param region +* @param postalCode +* @param country +*/ + +var ContactAddress = function(pref, type, formatted, streetAddress, locality, region, postalCode, country) { + this.id = null; + this.pref = (typeof pref != 'undefined' ? pref : false); + this.type = type || null; + this.formatted = formatted || null; + this.streetAddress = streetAddress || null; + this.locality = locality || null; + this.region = region || null; + this.postalCode = postalCode || null; + this.country = country || null; +}; + +module.exports = ContactAddress; +}); + +// file: lib/common/plugin/ContactError.js +define("cordova/plugin/ContactError", function(require, exports, module) { +/** + * ContactError. + * An error code assigned by an implementation when an error has occured + * @constructor + */ +var ContactError = function(err) { + this.code = (typeof err != 'undefined' ? err : null); +}; + +/** + * Error codes + */ +ContactError.UNKNOWN_ERROR = 0; +ContactError.INVALID_ARGUMENT_ERROR = 1; +ContactError.TIMEOUT_ERROR = 2; +ContactError.PENDING_OPERATION_ERROR = 3; +ContactError.IO_ERROR = 4; +ContactError.NOT_SUPPORTED_ERROR = 5; +ContactError.PERMISSION_DENIED_ERROR = 20; + +module.exports = ContactError; +}); + +// file: lib/common/plugin/ContactField.js +define("cordova/plugin/ContactField", function(require, exports, module) { +/** +* Generic contact field. +* @constructor +* @param {DOMString} id unique identifier, should only be set by native code // NOTE: not a W3C standard +* @param type +* @param value +* @param pref +*/ +var ContactField = function(type, value, pref) { + this.id = null; + this.type = (type && type.toString()) || null; + this.value = (value && value.toString()) || null; + this.pref = (typeof pref != 'undefined' ? pref : false); +}; + +module.exports = ContactField; +}); + +// file: lib/common/plugin/ContactFindOptions.js +define("cordova/plugin/ContactFindOptions", function(require, exports, module) { +/** + * ContactFindOptions. + * @constructor + * @param filter used to match contacts against + * @param multiple boolean used to determine if more than one contact should be returned + */ + +var ContactFindOptions = function(filter, multiple) { + this.filter = filter || ''; + this.multiple = (typeof multiple != 'undefined' ? multiple : false); +}; + +module.exports = ContactFindOptions; +}); + +// file: lib/common/plugin/ContactName.js +define("cordova/plugin/ContactName", function(require, exports, module) { +/** +* Contact name. +* @constructor +* @param formatted // NOTE: not part of W3C standard +* @param familyName +* @param givenName +* @param middle +* @param prefix +* @param suffix +*/ +var ContactName = function(formatted, familyName, givenName, middle, prefix, suffix) { + this.formatted = formatted || null; + this.familyName = familyName || null; + this.givenName = givenName || null; + this.middleName = middle || null; + this.honorificPrefix = prefix || null; + this.honorificSuffix = suffix || null; +}; + +module.exports = ContactName; +}); + +// file: lib/common/plugin/ContactOrganization.js +define("cordova/plugin/ContactOrganization", function(require, exports, module) { +/** +* Contact organization. +* @constructor +* @param {DOMString} id unique identifier, should only be set by native code // NOTE: not a W3C standard +* @param name +* @param dept +* @param title +* @param startDate +* @param endDate +* @param location +* @param desc +*/ + +var ContactOrganization = function(pref, type, name, dept, title) { + this.id = null; + this.pref = (typeof pref != 'undefined' ? pref : false); + this.type = type || null; + this.name = name || null; + this.department = dept || null; + this.title = title || null; +}; + +module.exports = ContactOrganization; +}); + +// file: lib/common/plugin/Coordinates.js +define("cordova/plugin/Coordinates", function(require, exports, module) { +/** + * This class contains position information. + * @param {Object} lat + * @param {Object} lng + * @param {Object} alt + * @param {Object} acc + * @param {Object} head + * @param {Object} vel + * @param {Object} altacc + * @constructor + */ +var Coordinates = function(lat, lng, alt, acc, head, vel, altacc) { + /** + * The latitude of the position. + */ + this.latitude = lat; + /** + * The longitude of the position, + */ + this.longitude = lng; + /** + * The accuracy of the position. + */ + this.accuracy = acc; + /** + * The altitude of the position. + */ + this.altitude = (alt !== undefined ? alt : null); + /** + * The direction the device is moving at the position. + */ + this.heading = (head !== undefined ? head : null); + /** + * The velocity with which the device is moving at the position. + */ + this.speed = (vel !== undefined ? vel : null); + + if (this.speed === 0 || this.speed === null) { + this.heading = NaN; + } + + /** + * The altitude accuracy of the position. + */ + this.altitudeAccuracy = (altacc !== undefined) ? altacc : null; +}; + +module.exports = Coordinates; + +}); + +// file: lib/common/plugin/DirectoryEntry.js +define("cordova/plugin/DirectoryEntry", function(require, exports, module) { +var utils = require('cordova/utils'), + exec = require('cordova/exec'), + Entry = require('cordova/plugin/Entry'), + FileError = require('cordova/plugin/FileError'), + DirectoryReader = require('cordova/plugin/DirectoryReader'); + +/** + * An interface representing a directory on the file system. + * + * {boolean} isFile always false (readonly) + * {boolean} isDirectory always true (readonly) + * {DOMString} name of the directory, excluding the path leading to it (readonly) + * {DOMString} fullPath the absolute full path to the directory (readonly) + * TODO: implement this!!! {FileSystem} filesystem on which the directory resides (readonly) + */ +var DirectoryEntry = function(name, fullPath) { + DirectoryEntry.__super__.constructor.apply(this, [false, true, name, fullPath]); +}; + +utils.extend(DirectoryEntry, Entry); + +/** + * Creates a new DirectoryReader to read entries from this directory + */ +DirectoryEntry.prototype.createReader = function() { + return new DirectoryReader(this.fullPath); +}; + +/** + * Creates or looks up a directory + * + * @param {DOMString} path either a relative or absolute path from this directory in which to look up or create a directory + * @param {Flags} options to create or excluively create the directory + * @param {Function} successCallback is called with the new entry + * @param {Function} errorCallback is called with a FileError + */ +DirectoryEntry.prototype.getDirectory = function(path, options, successCallback, errorCallback) { + var win = typeof successCallback !== 'function' ? null : function(result) { + var entry = new DirectoryEntry(result.name, result.fullPath); + successCallback(entry); + }; + var fail = typeof errorCallback !== 'function' ? null : function(code) { + errorCallback(new FileError(code)); + }; + exec(win, fail, "File", "getDirectory", [this.fullPath, path, options]); +}; + +/** + * Deletes a directory and all of it's contents + * + * @param {Function} successCallback is called with no parameters + * @param {Function} errorCallback is called with a FileError + */ +DirectoryEntry.prototype.removeRecursively = function(successCallback, errorCallback) { + var fail = typeof errorCallback !== 'function' ? null : function(code) { + errorCallback(new FileError(code)); + }; + exec(successCallback, fail, "File", "removeRecursively", [this.fullPath]); +}; + +/** + * Creates or looks up a file + * + * @param {DOMString} path either a relative or absolute path from this directory in which to look up or create a file + * @param {Flags} options to create or excluively create the file + * @param {Function} successCallback is called with the new entry + * @param {Function} errorCallback is called with a FileError + */ +DirectoryEntry.prototype.getFile = function(path, options, successCallback, errorCallback) { + var win = typeof successCallback !== 'function' ? null : function(result) { + var FileEntry = require('cordova/plugin/FileEntry'); + var entry = new FileEntry(result.name, result.fullPath); + successCallback(entry); + }; + var fail = typeof errorCallback !== 'function' ? null : function(code) { + errorCallback(new FileError(code)); + }; + exec(win, fail, "File", "getFile", [this.fullPath, path, options]); +}; + +module.exports = DirectoryEntry; + +}); + +// file: lib/common/plugin/DirectoryReader.js +define("cordova/plugin/DirectoryReader", function(require, exports, module) { +var exec = require('cordova/exec'), + FileError = require('cordova/plugin/FileError') ; + +/** + * An interface that lists the files and directories in a directory. + */ +function DirectoryReader(path) { + this.path = path || null; +} + +/** + * Returns a list of entries from a directory. + * + * @param {Function} successCallback is called with a list of entries + * @param {Function} errorCallback is called with a FileError + */ +DirectoryReader.prototype.readEntries = function(successCallback, errorCallback) { + var win = typeof successCallback !== 'function' ? null : function(result) { + var retVal = []; + for (var i=0; i][;base64], + * + * @param file {File} File object containing file properties + */ +FileReader.prototype.readAsDataURL = function(file) { + this.fileName = ""; + if (typeof file.fullPath === "undefined") { + this.fileName = file; + } else { + this.fileName = file.fullPath; + } + + // Already loading something + if (this.readyState == FileReader.LOADING) { + throw new FileError(FileError.INVALID_STATE_ERR); + } + + // LOADING state + this.readyState = FileReader.LOADING; + + // If loadstart callback + if (typeof this.onloadstart === "function") { + this.onloadstart(new ProgressEvent("loadstart", {target:this})); + } + + var me = this; + + // Read file + exec( + // Success callback + function(r) { + // If DONE (cancelled), then don't do anything + if (me.readyState === FileReader.DONE) { + return; + } + + // DONE state + me.readyState = FileReader.DONE; + + // Save result + me.result = r; + + // If onload callback + if (typeof me.onload === "function") { + me.onload(new ProgressEvent("load", {target:me})); + } + + // If onloadend callback + if (typeof me.onloadend === "function") { + me.onloadend(new ProgressEvent("loadend", {target:me})); + } + }, + // Error callback + function(e) { + // If DONE (cancelled), then don't do anything + if (me.readyState === FileReader.DONE) { + return; + } + + // DONE state + me.readyState = FileReader.DONE; + + me.result = null; + + // Save error + me.error = new FileError(e); + + // If onerror callback + if (typeof me.onerror === "function") { + me.onerror(new ProgressEvent("error", {target:me})); + } + + // If onloadend callback + if (typeof me.onloadend === "function") { + me.onloadend(new ProgressEvent("loadend", {target:me})); + } + }, "File", "readAsDataURL", [this.fileName]); +}; + +/** + * Read file and return data as a binary data. + * + * @param file {File} File object containing file properties + */ +FileReader.prototype.readAsBinaryString = function(file) { + // TODO - Can't return binary data to browser. + console.log('method "readAsBinaryString" is not supported at this time.'); +}; + +/** + * Read file and return data as a binary data. + * + * @param file {File} File object containing file properties + */ +FileReader.prototype.readAsArrayBuffer = function(file) { + // TODO - Can't return binary data to browser. + console.log('This method is not supported at this time.'); +}; + +module.exports = FileReader; +}); + +// file: lib/common/plugin/FileSystem.js +define("cordova/plugin/FileSystem", function(require, exports, module) { +var DirectoryEntry = require('cordova/plugin/DirectoryEntry'); + +/** + * An interface representing a file system + * + * @constructor + * {DOMString} name the unique name of the file system (readonly) + * {DirectoryEntry} root directory of the file system (readonly) + */ +var FileSystem = function(name, root) { + this.name = name || null; + if (root) { + this.root = new DirectoryEntry(root.name, root.fullPath); + } +}; + +module.exports = FileSystem; + +}); + +// file: lib/common/plugin/FileTransfer.js +define("cordova/plugin/FileTransfer", function(require, exports, module) { +var exec = require('cordova/exec'), + FileTransferError = require('cordova/plugin/FileTransferError'); + +/** + * FileTransfer uploads a file to a remote server. + * @constructor + */ +var FileTransfer = function() {}; + +/** +* Given an absolute file path, uploads a file on the device to a remote server +* using a multipart HTTP request. +* @param filePath {String} Full path of the file on the device +* @param server {String} URL of the server to receive the file +* @param successCallback (Function} Callback to be invoked when upload has completed +* @param errorCallback {Function} Callback to be invoked upon error +* @param options {FileUploadOptions} Optional parameters such as file name and mimetype +* @param trustAllHosts {Boolean} Optional trust all hosts (e.g. for self-signed certs), defaults to false +*/ +FileTransfer.prototype.upload = function(filePath, server, successCallback, errorCallback, options, trustAllHosts) { + // sanity parameter checking + if (!filePath || !server) throw new Error("FileTransfer.upload requires filePath and server URL parameters at the minimum."); + // check for options + var fileKey = null; + var fileName = null; + var mimeType = null; + var params = null; + var chunkedMode = true; + if (options) { + fileKey = options.fileKey; + fileName = options.fileName; + mimeType = options.mimeType; + if (options.chunkedMode !== null || typeof options.chunkedMode != "undefined") { + chunkedMode = options.chunkedMode; + } + if (options.params) { + params = options.params; + } + else { + params = {}; + } + } + + var fail = function(e) { + var error = new FileTransferError(e.code, e.source, e.target, e.http_status); + errorCallback(error); + }; + + exec(successCallback, fail, 'FileTransfer', 'upload', [filePath, server, fileKey, fileName, mimeType, params, trustAllHosts, chunkedMode]); +}; + +/** + * Downloads a file form a given URL and saves it to the specified directory. + * @param source {String} URL of the server to receive the file + * @param target {String} Full path of the file on the device + * @param successCallback (Function} Callback to be invoked when upload has completed + * @param errorCallback {Function} Callback to be invoked upon error + */ +FileTransfer.prototype.download = function(source, target, successCallback, errorCallback) { + // sanity parameter checking + if (!source || !target) throw new Error("FileTransfer.download requires source URI and target URI parameters at the minimum."); + var win = function(result) { + var entry = null; + if (result.isDirectory) { + entry = new (require('cordova/plugin/DirectoryEntry'))(); + } + else if (result.isFile) { + entry = new (require('cordova/plugin/FileEntry'))(); + } + entry.isDirectory = result.isDirectory; + entry.isFile = result.isFile; + entry.name = result.name; + entry.fullPath = result.fullPath; + successCallback(entry); + }; + + var fail = function(e) { + var error = new FileTransferError(e.code, e.source, e.target, e.http_status); + errorCallback(error); + }; + + exec(win, errorCallback, 'FileTransfer', 'download', [source, target]); +}; + +module.exports = FileTransfer; + +}); + +// file: lib/common/plugin/FileTransferError.js +define("cordova/plugin/FileTransferError", function(require, exports, module) { +/** + * FileTransferError + * @constructor + */ +var FileTransferError = function(code, source, target, status) { + this.code = code || null; + this.source = source || null; + this.target = target || null; + this.http_status = status || null; +}; + +FileTransferError.FILE_NOT_FOUND_ERR = 1; +FileTransferError.INVALID_URL_ERR = 2; +FileTransferError.CONNECTION_ERR = 3; + +module.exports = FileTransferError; + +}); + +// file: lib/common/plugin/FileUploadOptions.js +define("cordova/plugin/FileUploadOptions", function(require, exports, module) { +/** + * Options to customize the HTTP request used to upload files. + * @constructor + * @param fileKey {String} Name of file request parameter. + * @param fileName {String} Filename to be used by the server. Defaults to image.jpg. + * @param mimeType {String} Mimetype of the uploaded file. Defaults to image/jpeg. + * @param params {Object} Object with key: value params to send to the server. + */ +var FileUploadOptions = function(fileKey, fileName, mimeType, params) { + this.fileKey = fileKey || null; + this.fileName = fileName || null; + this.mimeType = mimeType || null; + this.params = params || null; +}; + +module.exports = FileUploadOptions; +}); + +// file: lib/common/plugin/FileUploadResult.js +define("cordova/plugin/FileUploadResult", function(require, exports, module) { +/** + * FileUploadResult + * @constructor + */ +var FileUploadResult = function() { + this.bytesSent = 0; + this.responseCode = null; + this.response = null; +}; + +module.exports = FileUploadResult; +}); + +// file: lib/common/plugin/FileWriter.js +define("cordova/plugin/FileWriter", function(require, exports, module) { +var exec = require('cordova/exec'), + FileError = require('cordova/plugin/FileError'), + ProgressEvent = require('cordova/plugin/ProgressEvent'); + +/** + * This class writes to the mobile device file system. + * + * For Android: + * The root directory is the root of the file system. + * To write to the SD card, the file name is "sdcard/my_file.txt" + * + * @constructor + * @param file {File} File object containing file properties + * @param append if true write to the end of the file, otherwise overwrite the file + */ +var FileWriter = function(file) { + this.fileName = ""; + this.length = 0; + if (file) { + this.fileName = file.fullPath || file; + this.length = file.size || 0; + } + // default is to write at the beginning of the file + this.position = 0; + + this.readyState = 0; // EMPTY + + this.result = null; + + // Error + this.error = null; + + // Event handlers + this.onwritestart = null; // When writing starts + this.onprogress = null; // While writing the file, and reporting partial file data + this.onwrite = null; // When the write has successfully completed. + this.onwriteend = null; // When the request has completed (either in success or failure). + this.onabort = null; // When the write has been aborted. For instance, by invoking the abort() method. + this.onerror = null; // When the write has failed (see errors). +}; + +// States +FileWriter.INIT = 0; +FileWriter.WRITING = 1; +FileWriter.DONE = 2; + +/** + * Abort writing file. + */ +FileWriter.prototype.abort = function() { + // check for invalid state + if (this.readyState === FileWriter.DONE || this.readyState === FileWriter.INIT) { + throw new FileError(FileError.INVALID_STATE_ERR); + } + + // set error + this.error = new FileError(FileError.ABORT_ERR); + + this.readyState = FileWriter.DONE; + + // If abort callback + if (typeof this.onabort === "function") { + this.onabort(new ProgressEvent("abort", {"target":this})); + } + + // If write end callback + if (typeof this.onwriteend === "function") { + this.onwriteend(new ProgressEvent("writeend", {"target":this})); + } +}; + +/** + * Writes data to the file + * + * @param text to be written + */ +FileWriter.prototype.write = function(text) { + // Throw an exception if we are already writing a file + if (this.readyState === FileWriter.WRITING) { + throw new FileError(FileError.INVALID_STATE_ERR); + } + + // WRITING state + this.readyState = FileWriter.WRITING; + + var me = this; + + // If onwritestart callback + if (typeof me.onwritestart === "function") { + me.onwritestart(new ProgressEvent("writestart", {"target":me})); + } + + // Write file + exec( + // Success callback + function(r) { + // If DONE (cancelled), then don't do anything + if (me.readyState === FileWriter.DONE) { + return; + } + + // position always increases by bytes written because file would be extended + me.position += r; + // The length of the file is now where we are done writing. + + me.length = me.position; + + // DONE state + me.readyState = FileWriter.DONE; + + // If onwrite callback + if (typeof me.onwrite === "function") { + me.onwrite(new ProgressEvent("write", {"target":me})); + } + + // If onwriteend callback + if (typeof me.onwriteend === "function") { + me.onwriteend(new ProgressEvent("writeend", {"target":me})); + } + }, + // Error callback + function(e) { + // If DONE (cancelled), then don't do anything + if (me.readyState === FileWriter.DONE) { + return; + } + + // DONE state + me.readyState = FileWriter.DONE; + + // Save error + me.error = new FileError(e); + + // If onerror callback + if (typeof me.onerror === "function") { + me.onerror(new ProgressEvent("error", {"target":me})); + } + + // If onwriteend callback + if (typeof me.onwriteend === "function") { + me.onwriteend(new ProgressEvent("writeend", {"target":me})); + } + }, "File", "write", [this.fileName, text, this.position]); +}; + +/** + * Moves the file pointer to the location specified. + * + * If the offset is a negative number the position of the file + * pointer is rewound. If the offset is greater than the file + * size the position is set to the end of the file. + * + * @param offset is the location to move the file pointer to. + */ +FileWriter.prototype.seek = function(offset) { + // Throw an exception if we are already writing a file + if (this.readyState === FileWriter.WRITING) { + throw new FileError(FileError.INVALID_STATE_ERR); + } + + if (!offset && offset !== 0) { + return; + } + + // See back from end of file. + if (offset < 0) { + this.position = Math.max(offset + this.length, 0); + } + // Offset is bigger then file size so set position + // to the end of the file. + else if (offset > this.length) { + this.position = this.length; + } + // Offset is between 0 and file size so set the position + // to start writing. + else { + this.position = offset; + } +}; + +/** + * Truncates the file to the size specified. + * + * @param size to chop the file at. + */ +FileWriter.prototype.truncate = function(size) { + // Throw an exception if we are already writing a file + if (this.readyState === FileWriter.WRITING) { + throw new FileError(FileError.INVALID_STATE_ERR); + } + + // WRITING state + this.readyState = FileWriter.WRITING; + + var me = this; + + // If onwritestart callback + if (typeof me.onwritestart === "function") { + me.onwritestart(new ProgressEvent("writestart", {"target":this})); + } + + // Write file + exec( + // Success callback + function(r) { + // If DONE (cancelled), then don't do anything + if (me.readyState === FileWriter.DONE) { + return; + } + + // DONE state + me.readyState = FileWriter.DONE; + + // Update the length of the file + me.length = r; + me.position = Math.min(me.position, r); + + // If onwrite callback + if (typeof me.onwrite === "function") { + me.onwrite(new ProgressEvent("write", {"target":me})); + } + + // If onwriteend callback + if (typeof me.onwriteend === "function") { + me.onwriteend(new ProgressEvent("writeend", {"target":me})); + } + }, + // Error callback + function(e) { + // If DONE (cancelled), then don't do anything + if (me.readyState === FileWriter.DONE) { + return; + } + + // DONE state + me.readyState = FileWriter.DONE; + + // Save error + me.error = new FileError(e); + + // If onerror callback + if (typeof me.onerror === "function") { + me.onerror(new ProgressEvent("error", {"target":me})); + } + + // If onwriteend callback + if (typeof me.onwriteend === "function") { + me.onwriteend(new ProgressEvent("writeend", {"target":me})); + } + }, "File", "truncate", [this.fileName, size]); +}; + +module.exports = FileWriter; + +}); + +// file: lib/common/plugin/Flags.js +define("cordova/plugin/Flags", function(require, exports, module) { +/** + * Supplies arguments to methods that lookup or create files and directories. + * + * @param create + * {boolean} file or directory if it doesn't exist + * @param exclusive + * {boolean} used with create; if true the command will fail if + * target path exists + */ +function Flags(create, exclusive) { + this.create = create || false; + this.exclusive = exclusive || false; +} + +module.exports = Flags; +}); + +// file: lib/common/plugin/LocalFileSystem.js +define("cordova/plugin/LocalFileSystem", function(require, exports, module) { +var exec = require('cordova/exec'); + +/** + * Represents a local file system. + */ +var LocalFileSystem = function() { + +}; + +LocalFileSystem.TEMPORARY = 0; //temporary, with no guarantee of persistence +LocalFileSystem.PERSISTENT = 1; //persistent + +module.exports = LocalFileSystem; +}); + +// file: lib/common/plugin/Media.js +define("cordova/plugin/Media", function(require, exports, module) { +var utils = require('cordova/utils'), + exec = require('cordova/exec'); + +var mediaObjects = {}; + +/** + * This class provides access to the device media, interfaces to both sound and video + * + * @constructor + * @param src The file name or url to play + * @param successCallback The callback to be called when the file is done playing or recording. + * successCallback() + * @param errorCallback The callback to be called if there is an error. + * errorCallback(int errorCode) - OPTIONAL + * @param statusCallback The callback to be called when media status has changed. + * statusCallback(int statusCode) - OPTIONAL + */ +var Media = function(src, successCallback, errorCallback, statusCallback) { + + // successCallback optional + if (successCallback && (typeof successCallback !== "function")) { + console.log("Media Error: successCallback is not a function"); + return; + } + + // errorCallback optional + if (errorCallback && (typeof errorCallback !== "function")) { + console.log("Media Error: errorCallback is not a function"); + return; + } + + // statusCallback optional + if (statusCallback && (typeof statusCallback !== "function")) { + console.log("Media Error: statusCallback is not a function"); + return; + } + + this.id = utils.createUUID(); + mediaObjects[this.id] = this; + this.src = src; + this.successCallback = successCallback; + this.errorCallback = errorCallback; + this.statusCallback = statusCallback; + this._duration = -1; + this._position = -1; + exec(null, this.errorCallback, "Media", "create", [this.id, this.src]); +}; + +// Media messages +Media.MEDIA_STATE = 1; +Media.MEDIA_DURATION = 2; +Media.MEDIA_POSITION = 3; +Media.MEDIA_ERROR = 9; + +// Media states +Media.MEDIA_NONE = 0; +Media.MEDIA_STARTING = 1; +Media.MEDIA_RUNNING = 2; +Media.MEDIA_PAUSED = 3; +Media.MEDIA_STOPPED = 4; +Media.MEDIA_MSG = ["None", "Starting", "Running", "Paused", "Stopped"]; + +// "static" function to return existing objs. +Media.get = function(id) { + return mediaObjects[id]; +}; + +/** + * Start or resume playing audio file. + */ +Media.prototype.play = function(options) { + exec(null, null, "Media", "startPlayingAudio", [this.id, this.src, options]); +}; + +/** + * Stop playing audio file. + */ +Media.prototype.stop = function() { + var me = this; + exec(function() { + me._position = 0; + me.successCallback(); + }, this.errorCallback, "Media", "stopPlayingAudio", [this.id]); +}; + +/** + * Seek or jump to a new time in the track.. + */ +Media.prototype.seekTo = function(milliseconds) { + var me = this; + exec(function(p) { + me._position = p; + }, this.errorCallback, "Media", "seekToAudio", [this.id, milliseconds]); +}; + +/** + * Pause playing audio file. + */ +Media.prototype.pause = function() { + exec(null, this.errorCallback, "Media", "pausePlayingAudio", [this.id]); +}; + +/** + * Get duration of an audio file. + * The duration is only set for audio that is playing, paused or stopped. + * + * @return duration or -1 if not known. + */ +Media.prototype.getDuration = function() { + return this._duration; +}; + +/** + * Get position of audio. + */ +Media.prototype.getCurrentPosition = function(success, fail) { + var me = this; + exec(function(p) { + me._position = p; + success(p); + }, fail, "Media", "getCurrentPositionAudio", [this.id]); +}; + +/** + * Start recording audio file. + */ +Media.prototype.startRecord = function() { + exec(this.successCallback, this.errorCallback, "Media", "startRecordingAudio", [this.id, this.src]); +}; + +/** + * Stop recording audio file. + */ +Media.prototype.stopRecord = function() { + exec(this.successCallback, this.errorCallback, "Media", "stopRecordingAudio", [this.id]); +}; + +/** + * Release the resources. + */ +Media.prototype.release = function() { + exec(null, this.errorCallback, "Media", "release", [this.id]); +}; + +/** + * Adjust the volume. + */ +Media.prototype.setVolume = function(volume) { + exec(null, null, "Media", "setVolume", [this.id, volume]); +}; + +/** + * Audio has status update. + * PRIVATE + * + * @param id The media object id (string) + * @param status The status code (int) + * @param msg The status message (string) + */ +Media.onStatus = function(id, msg, value) { + var media = mediaObjects[id]; + // If state update + if (msg === Media.MEDIA_STATE) { + if (value === Media.MEDIA_STOPPED) { + if (media.successCallback) { + media.successCallback(); + } + } + if (media.statusCallback) { + media.statusCallback(value); + } + } + else if (msg === Media.MEDIA_DURATION) { + media._duration = value; + } + else if (msg === Media.MEDIA_ERROR) { + if (media.errorCallback) { + // value should be a MediaError object when msg == MEDIA_ERROR + media.errorCallback(value); + } + } + else if (msg === Media.MEDIA_POSITION) { + media._position = value; + } +}; + +module.exports = Media; +}); + +// file: lib/common/plugin/MediaError.js +define("cordova/plugin/MediaError", function(require, exports, module) { +/** + * This class contains information about any Media errors. + * @constructor + */ +var MediaError = function(code, msg) { + this.code = (code !== undefined ? code : null); + this.message = msg || ""; +}; + +MediaError.MEDIA_ERR_NONE_ACTIVE = 0; +MediaError.MEDIA_ERR_ABORTED = 1; +MediaError.MEDIA_ERR_NETWORK = 2; +MediaError.MEDIA_ERR_DECODE = 3; +MediaError.MEDIA_ERR_NONE_SUPPORTED = 4; + +module.exports = MediaError; +}); + +// file: lib/common/plugin/MediaFile.js +define("cordova/plugin/MediaFile", function(require, exports, module) { +var utils = require('cordova/utils'), + exec = require('cordova/exec'), + File = require('cordova/plugin/File'), + CaptureError = require('cordova/plugin/CaptureError'); +/** + * Represents a single file. + * + * name {DOMString} name of the file, without path information + * fullPath {DOMString} the full path of the file, including the name + * type {DOMString} mime type + * lastModifiedDate {Date} last modified date + * size {Number} size of the file in bytes + */ +var MediaFile = function(name, fullPath, type, lastModifiedDate, size){ + MediaFile.__super__.constructor.apply(this, arguments); +}; + +utils.extend(MediaFile, File); + +/** + * Request capture format data for a specific file and type + * + * @param {Function} successCB + * @param {Function} errorCB + */ +MediaFile.prototype.getFormatData = function(successCallback, errorCallback) { + if (typeof this.fullPath === "undefined" || this.fullPath === null) { + errorCallback(new CaptureError(CaptureError.CAPTURE_INVALID_ARGUMENT)); + } else { + exec(successCallback, errorCallback, "Capture", "getFormatData", [this.fullPath, this.type]); + } +}; + +// TODO: can we axe this? +/** + * Casts a PluginResult message property (array of objects) to an array of MediaFile objects + * (used in Objective-C and Android) + * + * @param {PluginResult} pluginResult + */ +MediaFile.cast = function(pluginResult) { + var mediaFiles = []; + for (var i=0; i.dispatchEvent + // need to first figure out how to implement EventTarget + } + } + return event; + }; + try { + var ev = createEvent({type:"abort",target:document}); + return function ProgressEvent(type, data) { + data.type = type; + return createEvent(data); + }; + } catch(e){ + */ + return function ProgressEvent(type, dict) { + this.type = type; + this.bubbles = false; + this.cancelBubble = false; + this.cancelable = false; + this.lengthComputable = false; + this.loaded = dict && dict.loaded ? dict.loaded : 0; + this.total = dict && dict.total ? dict.total : 0; + this.target = dict && dict.target ? dict.target : null; + }; + //} +})(); + +module.exports = ProgressEvent; +}); + +// file: lib/common/plugin/accelerometer.js +define("cordova/plugin/accelerometer", function(require, exports, module) { +/** + * This class provides access to device accelerometer data. + * @constructor + */ +var utils = require("cordova/utils"), + exec = require("cordova/exec"), + Acceleration = require('cordova/plugin/Acceleration'); + +// Is the accel sensor running? +var running = false; + +// Keeps reference to watchAcceleration calls. +var timers = {}; + +// Array of listeners; used to keep track of when we should call start and stop. +var listeners = []; + +// Last returned acceleration object from native +var accel = null; + +// Tells native to start. +function start() { + exec(function(a) { + var tempListeners = listeners.slice(0); + accel = new Acceleration(a.x, a.y, a.z, a.timestamp); + for (var i = 0, l = tempListeners.length; i < l; i++) { + tempListeners[i].win(accel); + } + }, function(e) { + var tempListeners = listeners.slice(0); + for (var i = 0, l = tempListeners.length; i < l; i++) { + tempListeners[i].fail(e); + } + }, "Accelerometer", "start", []); + running = true; +} + +// Tells native to stop. +function stop() { + exec(null, null, "Accelerometer", "stop", []); + running = false; +} + +// Adds a callback pair to the listeners array +function createCallbackPair(win, fail) { + return {win:win, fail:fail}; +} + +// Removes a win/fail listener pair from the listeners array +function removeListeners(l) { + var idx = listeners.indexOf(l); + if (idx > -1) { + listeners.splice(idx, 1); + if (listeners.length === 0) { + stop(); + } + } +} + +var accelerometer = { + /** + * Asynchronously aquires the current acceleration. + * + * @param {Function} successCallback The function to call when the acceleration data is available + * @param {Function} errorCallback The function to call when there is an error getting the acceleration data. (OPTIONAL) + * @param {AccelerationOptions} options The options for getting the accelerometer data such as timeout. (OPTIONAL) + */ + getCurrentAcceleration: function(successCallback, errorCallback, options) { + // successCallback required + if (typeof successCallback !== "function") { + throw "getCurrentAcceleration must be called with at least a success callback function as first parameter."; + } + + var p; + var win = function(a) { + removeListeners(p); + successCallback(a); + }; + var fail = function(e) { + removeListeners(p); + errorCallback(e); + }; + + p = createCallbackPair(win, fail); + listeners.push(p); + + if (!running) { + start(); + } + }, + + /** + * Asynchronously aquires the acceleration repeatedly at a given interval. + * + * @param {Function} successCallback The function to call each time the acceleration data is available + * @param {Function} errorCallback The function to call when there is an error getting the acceleration data. (OPTIONAL) + * @param {AccelerationOptions} options The options for getting the accelerometer data such as timeout. (OPTIONAL) + * @return String The watch id that must be passed to #clearWatch to stop watching. + */ + watchAcceleration: function(successCallback, errorCallback, options) { + // Default interval (10 sec) + var frequency = (options && options.frequency && typeof options.frequency == 'number') ? options.frequency : 10000; + + // successCallback required + if (typeof successCallback !== "function") { + throw "watchAcceleration must be called with at least a success callback function as first parameter."; + } + + // Keep reference to watch id, and report accel readings as often as defined in frequency + var id = utils.createUUID(); + + var p = createCallbackPair(function(){}, function(e) { + removeListeners(p); + errorCallback(e); + }); + listeners.push(p); + + timers[id] = { + timer:window.setInterval(function() { + if (accel) { + successCallback(accel); + } + }, frequency), + listeners:p + }; + + if (running) { + // If we're already running then immediately invoke the success callback + // but only if we have retreived a value, sample code does not check for null ... + if(accel) { + successCallback(accel); + } + } else { + start(); + } + + return id; + }, + + /** + * Clears the specified accelerometer watch. + * + * @param {String} id The id of the watch returned from #watchAcceleration. + */ + clearWatch: function(id) { + // Stop javascript timer & remove from timer list + if (id && timers[id]) { + window.clearInterval(timers[id].timer); + removeListeners(timers[id].listeners); + delete timers[id]; + } + } +}; + +module.exports = accelerometer; + +}); + +// file: lib/common/plugin/battery.js +define("cordova/plugin/battery", function(require, exports, module) { +/** + * This class contains information about the current battery status. + * @constructor + */ +var cordova = require('cordova'), + exec = require('cordova/exec'); + +function handlers() { + return battery.channels.batterystatus.numHandlers + + battery.channels.batterylow.numHandlers + + battery.channels.batterycritical.numHandlers; +} + +var Battery = function() { + this._level = null; + this._isPlugged = null; + // Create new event handlers on the window (returns a channel instance) + var subscriptionEvents = { + onSubscribe:this.onSubscribe, + onUnsubscribe:this.onUnsubscribe + }; + this.channels = { + batterystatus:cordova.addWindowEventHandler("batterystatus", subscriptionEvents), + batterylow:cordova.addWindowEventHandler("batterylow", subscriptionEvents), + batterycritical:cordova.addWindowEventHandler("batterycritical", subscriptionEvents) + }; +}; +/** + * Event handlers for when callbacks get registered for the battery. + * Keep track of how many handlers we have so we can start and stop the native battery listener + * appropriately (and hopefully save on battery life!). + */ +Battery.prototype.onSubscribe = function() { + var me = battery; + // If we just registered the first handler, make sure native listener is started. + if (handlers() === 1) { + exec(me._status, me._error, "Battery", "start", []); + } +}; + +Battery.prototype.onUnsubscribe = function() { + var me = battery; + + // If we just unregistered the last handler, make sure native listener is stopped. + if (handlers() === 0) { + exec(null, null, "Battery", "stop", []); + } +}; + +/** + * Callback for battery status + * + * @param {Object} info keys: level, isPlugged + */ +Battery.prototype._status = function(info) { + if (info) { + var me = battery; + var level = info.level; + if (me._level !== level || me._isPlugged !== info.isPlugged) { + // Fire batterystatus event + cordova.fireWindowEvent("batterystatus", info); + + // Fire low battery event + if (level === 20 || level === 5) { + if (level === 20) { + cordova.fireWindowEvent("batterylow", info); + } + else { + cordova.fireWindowEvent("batterycritical", info); + } + } + } + me._level = level; + me._isPlugged = info.isPlugged; + } +}; + +/** + * Error callback for battery start + */ +Battery.prototype._error = function(e) { + console.log("Error initializing Battery: " + e); +}; + +var battery = new Battery(); + +module.exports = battery; +}); + +// file: lib/common/plugin/capture.js +define("cordova/plugin/capture", function(require, exports, module) { +var exec = require('cordova/exec'), + MediaFile = require('cordova/plugin/MediaFile'); + +/** + * Launches a capture of different types. + * + * @param (DOMString} type + * @param {Function} successCB + * @param {Function} errorCB + * @param {CaptureVideoOptions} options + */ +function _capture(type, successCallback, errorCallback, options) { + var win = function(pluginResult) { + var mediaFiles = []; + var i; + for (i = 0; i < pluginResult.length; i++) { + var mediaFile = new MediaFile(); + mediaFile.name = pluginResult[i].name; + mediaFile.fullPath = pluginResult[i].fullPath; + mediaFile.type = pluginResult[i].type; + mediaFile.lastModifiedDate = pluginResult[i].lastModifiedDate; + mediaFile.size = pluginResult[i].size; + mediaFiles.push(mediaFile); + } + successCallback(mediaFiles); + }; + exec(win, errorCallback, "Capture", type, [options]); +} +/** + * The Capture interface exposes an interface to the camera and microphone of the hosting device. + */ +function Capture() { + this.supportedAudioModes = []; + this.supportedImageModes = []; + this.supportedVideoModes = []; +} + +/** + * Launch audio recorder application for recording audio clip(s). + * + * @param {Function} successCB + * @param {Function} errorCB + * @param {CaptureAudioOptions} options + */ +Capture.prototype.captureAudio = function(successCallback, errorCallback, options){ + _capture("captureAudio", successCallback, errorCallback, options); +}; + +/** + * Launch camera application for taking image(s). + * + * @param {Function} successCB + * @param {Function} errorCB + * @param {CaptureImageOptions} options + */ +Capture.prototype.captureImage = function(successCallback, errorCallback, options){ + _capture("captureImage", successCallback, errorCallback, options); +}; + +/** + * Launch device camera application for recording video(s). + * + * @param {Function} successCB + * @param {Function} errorCB + * @param {CaptureVideoOptions} options + */ +Capture.prototype.captureVideo = function(successCallback, errorCallback, options){ + _capture("captureVideo", successCallback, errorCallback, options); +}; + + +module.exports = new Capture(); + +}); + +// file: lib/common/plugin/compass.js +define("cordova/plugin/compass", function(require, exports, module) { +var exec = require('cordova/exec'), + utils = require('cordova/utils'), + CompassHeading = require('cordova/plugin/CompassHeading'), + CompassError = require('cordova/plugin/CompassError'), + timers = {}, + compass = { + /** + * Asynchronously acquires the current heading. + * @param {Function} successCallback The function to call when the heading + * data is available + * @param {Function} errorCallback The function to call when there is an error + * getting the heading data. + * @param {CompassOptions} options The options for getting the heading data (not used). + */ + getCurrentHeading:function(successCallback, errorCallback, options) { + // successCallback required + if (typeof successCallback !== "function") { + console.log("Compass Error: successCallback is not a function"); + return; + } + + // errorCallback optional + if (errorCallback && (typeof errorCallback !== "function")) { + console.log("Compass Error: errorCallback is not a function"); + return; + } + + var win = function(result) { + var ch = new CompassHeading(result.magneticHeading, result.trueHeading, result.headingAccuracy, result.timestamp); + successCallback(ch); + }; + var fail = function(code) { + var ce = new CompassError(code); + errorCallback(ce); + }; + + // Get heading + exec(win, fail, "Compass", "getHeading", [options]); + }, + + /** + * Asynchronously acquires the heading repeatedly at a given interval. + * @param {Function} successCallback The function to call each time the heading + * data is available + * @param {Function} errorCallback The function to call when there is an error + * getting the heading data. + * @param {HeadingOptions} options The options for getting the heading data + * such as timeout and the frequency of the watch. For iOS, filter parameter + * specifies to watch via a distance filter rather than time. + */ + watchHeading:function(successCallback, errorCallback, options) { + // Default interval (100 msec) + var frequency = (options !== undefined && options.frequency !== undefined) ? options.frequency : 100; + var filter = (options !== undefined && options.filter !== undefined) ? options.filter : 0; + + // successCallback required + if (typeof successCallback !== "function") { + console.log("Compass Error: successCallback is not a function"); + return; + } + + // errorCallback optional + if (errorCallback && (typeof errorCallback !== "function")) { + console.log("Compass Error: errorCallback is not a function"); + return; + } + + var id = utils.createUUID(); + if (filter > 0) { + // is an iOS request for watch by filter, no timer needed + timers[id] = "iOS"; + compass.getCurrentHeading(successCallback, errorCallback, options); + } else { + // Start watch timer to get headings + timers[id] = window.setInterval(function() { + compass.getCurrentHeading(successCallback, errorCallback); + }, frequency); + } + + return id; + }, + + /** + * Clears the specified heading watch. + * @param {String} watchId The ID of the watch returned from #watchHeading. + */ + clearWatch:function(id) { + // Stop javascript timer & remove from timer list + if (id && timers[id]) { + if (timers[id] != "iOS") { + clearInterval(timers[id]); + } else { + // is iOS watch by filter so call into device to stop + exec(null, null, "Compass", "stopHeading", []); + } + delete timers[id]; + } + } + }; + +module.exports = compass; +}); + +// file: lib/common/plugin/console-via-logger.js +define("cordova/plugin/console-via-logger", function(require, exports, module) { +//------------------------------------------------------------------------------ + +var logger = require("cordova/plugin/logger"); +var utils = require("cordova/utils"); + +//------------------------------------------------------------------------------ +// object that we're exporting +//------------------------------------------------------------------------------ +var console = module.exports; + +//------------------------------------------------------------------------------ +// copy of the original console object +//------------------------------------------------------------------------------ +var WinConsole = window.console; + +//------------------------------------------------------------------------------ +// whether to use the logger +//------------------------------------------------------------------------------ +var UseLogger = false; + +//------------------------------------------------------------------------------ +// Timers +//------------------------------------------------------------------------------ +var Timers = {}; + +//------------------------------------------------------------------------------ +// used for unimplemented methods +//------------------------------------------------------------------------------ +function noop() {} + +//------------------------------------------------------------------------------ +// used for unimplemented methods +//------------------------------------------------------------------------------ +console.useLogger = function (value) { + if (arguments.length) UseLogger = !!value; + + if (UseLogger) { + if (logger.useConsole()) { + throw new Error("console and logger are too intertwingly"); + } + } + + return UseLogger; +}; + +//------------------------------------------------------------------------------ +console.log = function() { + if (logger.useConsole()) return; + logger.log.apply(logger, [].slice.call(arguments)); +}; + +//------------------------------------------------------------------------------ +console.error = function() { + if (logger.useConsole()) return; + logger.error.apply(logger, [].slice.call(arguments)); +}; + +//------------------------------------------------------------------------------ +console.warn = function() { + if (logger.useConsole()) return; + logger.warn.apply(logger, [].slice.call(arguments)); +}; + +//------------------------------------------------------------------------------ +console.info = function() { + if (logger.useConsole()) return; + logger.info.apply(logger, [].slice.call(arguments)); +}; + +//------------------------------------------------------------------------------ +console.debug = function() { + if (logger.useConsole()) return; + logger.debug.apply(logger, [].slice.call(arguments)); +}; + +//------------------------------------------------------------------------------ +console.assert = function(expression) { + if (expression) return; + + var message = utils.vformat(arguments[1], [].slice.call(arguments, 2)); + console.log("ASSERT: " + message); +}; + +//------------------------------------------------------------------------------ +console.clear = function() {}; + +//------------------------------------------------------------------------------ +console.dir = function(object) { + console.log("%o", object); +}; + +//------------------------------------------------------------------------------ +console.dirxml = function(node) { + console.log(node.innerHTML); +}; + +//------------------------------------------------------------------------------ +console.trace = noop; + +//------------------------------------------------------------------------------ +console.group = console.log; + +//------------------------------------------------------------------------------ +console.groupCollapsed = console.log; + +//------------------------------------------------------------------------------ +console.groupEnd = noop; + +//------------------------------------------------------------------------------ +console.time = function(name) { + Timers[name] = new Date().valueOf(); +}; + +//------------------------------------------------------------------------------ +console.timeEnd = function(name) { + var timeStart = Timers[name]; + if (!timeStart) { + console.warn("unknown timer: " + name); + return; + } + + var timeElapsed = new Date().valueOf() - timeStart; + console.log(name + ": " + timeElapsed + "ms"); +}; + +//------------------------------------------------------------------------------ +console.timeStamp = noop; + +//------------------------------------------------------------------------------ +console.profile = noop; + +//------------------------------------------------------------------------------ +console.profileEnd = noop; + +//------------------------------------------------------------------------------ +console.count = noop; + +//------------------------------------------------------------------------------ +console.exception = console.log; + +//------------------------------------------------------------------------------ +console.table = function(data, columns) { + console.log("%o", data); +}; + +//------------------------------------------------------------------------------ +// return a new function that calls both functions passed as args +//------------------------------------------------------------------------------ +function wrapperedOrigCall(orgFunc, newFunc) { + return function() { + var args = [].slice.call(arguments); + try { orgFunc.apply(WinConsole, args); } catch (e) {} + try { newFunc.apply(console, args); } catch (e) {} + }; +} + +//------------------------------------------------------------------------------ +// For every function that exists in the original console object, that +// also exists in the new console object, wrap the new console method +// with one that calls both +//------------------------------------------------------------------------------ +for (var key in console) { + if (typeof WinConsole[key] == "function") { + console[key] = wrapperedOrigCall(WinConsole[key], console[key]); + } +} + +}); + +// file: lib/common/plugin/contacts.js +define("cordova/plugin/contacts", function(require, exports, module) { +var exec = require('cordova/exec'), + ContactError = require('cordova/plugin/ContactError'), + utils = require('cordova/utils'), + Contact = require('cordova/plugin/Contact'); + +/** +* Represents a group of Contacts. +* @constructor +*/ +var contacts = { + /** + * Returns an array of Contacts matching the search criteria. + * @param fields that should be searched + * @param successCB success callback + * @param errorCB error callback + * @param {ContactFindOptions} options that can be applied to contact searching + * @return array of Contacts matching search criteria + */ + find:function(fields, successCB, errorCB, options) { + if (!successCB) { + throw new TypeError("You must specify a success callback for the find command."); + } + if (!fields || (utils.isArray(fields) && fields.length === 0)) { + if (typeof errorCB === "function") { + errorCB(new ContactError(ContactError.INVALID_ARGUMENT_ERROR)); + } + } else { + var win = function(result) { + var cs = []; + for (var i = 0, l = result.length; i < l; i++) { + cs.push(contacts.create(result[i])); + } + successCB(cs); + }; + exec(win, errorCB, "Contacts", "search", [fields, options]); + } + }, + + /** + * This function creates a new contact, but it does not persist the contact + * to device storage. To persist the contact to device storage, invoke + * contact.save(). + * @param properties an object who's properties will be examined to create a new Contact + * @returns new Contact object + */ + create:function(properties) { + var i; + var contact = new Contact(); + for (i in properties) { + if (typeof contact[i] !== 'undefined' && properties.hasOwnProperty(i)) { + contact[i] = properties[i]; + } + } + return contact; + } +}; + +module.exports = contacts; + +}); + +// file: lib/common/plugin/device.js +define("cordova/plugin/device", function(require, exports, module) { +var channel = require('cordova/channel'), + utils = require('cordova/utils'), + exec = require('cordova/exec'); + +// Tell cordova channel to wait on the CordovaInfoReady event +channel.waitForInitialization('onCordovaInfoReady'); + +/** + * This represents the mobile device, and provides properties for inspecting the model, version, UUID of the + * phone, etc. + * @constructor + */ +function Device() { + this.available = false; + this.platform = null; + this.version = null; + this.name = null; + this.uuid = null; + this.cordova = null; + + var me = this; + + channel.onCordovaReady.subscribeOnce(function() { + me.getInfo(function(info) { + me.available = true; + me.platform = info.platform; + me.version = info.version; + me.name = info.name; + me.uuid = info.uuid; + me.cordova = info.cordova; + channel.onCordovaInfoReady.fire(); + },function(e) { + me.available = false; + utils.alert("[ERROR] Error initializing Cordova: " + e); + }); + }); +} + +/** + * Get device info + * + * @param {Function} successCallback The function to call when the heading data is available + * @param {Function} errorCallback The function to call when there is an error getting the heading data. (OPTIONAL) + */ +Device.prototype.getInfo = function(successCallback, errorCallback) { + + // successCallback required + if (typeof successCallback !== "function") { + console.log("Device Error: successCallback is not a function"); + return; + } + + // errorCallback optional + if (errorCallback && (typeof errorCallback !== "function")) { + console.log("Device Error: errorCallback is not a function"); + return; + } + + // Get info + exec(successCallback, errorCallback, "Device", "getDeviceInfo", []); +}; + +module.exports = new Device(); + +}); + +// file: lib/common/plugin/geolocation.js +define("cordova/plugin/geolocation", function(require, exports, module) { +var utils = require('cordova/utils'), + exec = require('cordova/exec'), + PositionError = require('cordova/plugin/PositionError'), + Position = require('cordova/plugin/Position'); + +var timers = {}; // list of timers in use + +// Returns default params, overrides if provided with values +function parseParameters(options) { + var opt = { + maximumAge: 0, + enableHighAccuracy: false, + timeout: Infinity + }; + + if (options) { + if (options.maximumAge !== undefined && !isNaN(options.maximumAge) && options.maximumAge > 0) { + opt.maximumAge = options.maximumAge; + } + if (options.enableHighAccuracy !== undefined) { + opt.enableHighAccuracy = options.enableHighAccuracy; + } + if (options.timeout !== undefined && !isNaN(options.timeout)) { + if (options.timeout < 0) { + opt.timeout = 0; + } else { + opt.timeout = options.timeout; + } + } + } + + return opt; +} + +// Returns a timeout failure, closed over a specified timeout value and error callback. +function createTimeout(errorCallback, timeout) { + var t = setTimeout(function() { + clearTimeout(t); + t = null; + errorCallback({ + code:PositionError.TIMEOUT, + message:"Position retrieval timed out." + }); + }, timeout); + return t; +} + +var geolocation = { + lastPosition:null, // reference to last known (cached) position returned + /** + * Asynchronously aquires the current position. + * + * @param {Function} successCallback The function to call when the position data is available + * @param {Function} errorCallback The function to call when there is an error getting the heading position. (OPTIONAL) + * @param {PositionOptions} options The options for getting the position data. (OPTIONAL) + */ + getCurrentPosition:function(successCallback, errorCallback, options) { + if (arguments.length === 0) { + throw new Error("getCurrentPosition must be called with at least one argument."); + } + options = parseParameters(options); + + // Timer var that will fire an error callback if no position is retrieved from native + // before the "timeout" param provided expires + var timeoutTimer = null; + + var win = function(p) { + clearTimeout(timeoutTimer); + if (!timeoutTimer) { + // Timeout already happened, or native fired error callback for + // this geo request. + // Don't continue with success callback. + return; + } + var pos = new Position( + { + latitude:p.latitude, + longitude:p.longitude, + altitude:p.altitude, + accuracy:p.accuracy, + heading:p.heading, + velocity:p.velocity, + altitudeAccuracy:p.altitudeAccuracy + }, + (p.timestamp === undefined ? new Date() : ((p.timestamp instanceof Date) ? p.timestamp : new Date(p.timestamp))) + ); + geolocation.lastPosition = pos; + successCallback(pos); + }; + var fail = function(e) { + clearTimeout(timeoutTimer); + timeoutTimer = null; + var err = new PositionError(e.code, e.message); + if (errorCallback) { + errorCallback(err); + } + }; + + // Check our cached position, if its timestamp difference with current time is less than the maximumAge, then just + // fire the success callback with the cached position. + if (geolocation.lastPosition && options.maximumAge && (((new Date()).getTime() - geolocation.lastPosition.timestamp.getTime()) <= options.maximumAge)) { + successCallback(geolocation.lastPosition); + // If the cached position check failed and the timeout was set to 0, error out with a TIMEOUT error object. + } else if (options.timeout === 0) { + fail({ + code:PositionError.TIMEOUT, + message:"timeout value in PositionOptions set to 0 and no cached Position object available, or cached Position object's age exceed's provided PositionOptions' maximumAge parameter." + }); + // Otherwise we have to call into native to retrieve a position. + } else { + if (options.timeout !== Infinity) { + // If the timeout value was not set to Infinity (default), then + // set up a timeout function that will fire the error callback + // if no successful position was retrieved before timeout expired. + timeoutTimer = createTimeout(fail, options.timeout); + } else { + // This is here so the check in the win function doesn't mess stuff up + // may seem weird but this guarantees timeoutTimer is + // always truthy before we call into native + timeoutTimer = true; + } + exec(win, fail, "Geolocation", "getLocation", [options.enableHighAccuracy, options.maximumAge]); + } + return timeoutTimer; + }, + /** + * Asynchronously watches the geolocation for changes to geolocation. When a change occurs, + * the successCallback is called with the new location. + * + * @param {Function} successCallback The function to call each time the location data is available + * @param {Function} errorCallback The function to call when there is an error getting the location data. (OPTIONAL) + * @param {PositionOptions} options The options for getting the location data such as frequency. (OPTIONAL) + * @return String The watch id that must be passed to #clearWatch to stop watching. + */ + watchPosition:function(successCallback, errorCallback, options) { + if (arguments.length === 0) { + throw new Error("watchPosition must be called with at least one argument."); + } + options = parseParameters(options); + + var id = utils.createUUID(); + + // Tell device to get a position ASAP, and also retrieve a reference to the timeout timer generated in getCurrentPosition + timers[id] = geolocation.getCurrentPosition(successCallback, errorCallback, options); + + var fail = function(e) { + clearTimeout(timers[id]); + var err = new PositionError(e.code, e.message); + if (errorCallback) { + errorCallback(err); + } + }; + + var win = function(p) { + clearTimeout(timers[id]); + if (options.timeout !== Infinity) { + timers[id] = createTimeout(fail, options.timeout); + } + var pos = new Position( + { + latitude:p.latitude, + longitude:p.longitude, + altitude:p.altitude, + accuracy:p.accuracy, + heading:p.heading, + velocity:p.velocity, + altitudeAccuracy:p.altitudeAccuracy + }, + (p.timestamp === undefined ? new Date() : ((p.timestamp instanceof Date) ? p.timestamp : new Date(p.timestamp))) + ); + geolocation.lastPosition = pos; + successCallback(pos); + }; + + exec(win, fail, "Geolocation", "addWatch", [id, options.enableHighAccuracy]); + + return id; + }, + /** + * Clears the specified heading watch. + * + * @param {String} id The ID of the watch returned from #watchPosition + */ + clearWatch:function(id) { + if (id && timers[id] !== undefined) { + clearTimeout(timers[id]); + delete timers[id]; + exec(null, null, "Geolocation", "clearWatch", [id]); + } + } +}; + +module.exports = geolocation; + +}); + +// file: lib/ios/plugin/ios/Contact.js +define("cordova/plugin/ios/Contact", function(require, exports, module) { +var exec = require('cordova/exec'), + ContactError = require('cordova/plugin/ContactError'); + +/** + * Provides iOS Contact.display API. + */ +module.exports = { + display : function(errorCB, options) { + /* + * Display a contact using the iOS Contact Picker UI + * NOT part of W3C spec so no official documentation + * + * @param errorCB error callback + * @param options object + * allowsEditing: boolean AS STRING + * "true" to allow editing the contact + * "false" (default) display contact + */ + + if (this.id === null) { + if (typeof errorCB === "function") { + var errorObj = new ContactError(ContactError.UNKNOWN_ERROR); + errorCB(errorObj); + } + } + else { + exec(null, errorCB, "Contacts","displayContact", [this.id, options]); + } + } +}; +}); + +// file: lib/ios/plugin/ios/Entry.js +define("cordova/plugin/ios/Entry", function(require, exports, module) { +module.exports = { + toURL:function() { + // TODO: refactor path in a cross-platform way so we can eliminate + // these kinds of platform-specific hacks. + return "file://localhost" + this.fullPath; + }, + toURI: function() { + console.log("DEPRECATED: Update your code to use 'toURL'"); + return "file://localhost" + this.fullPath; + } +}; +}); + +// file: lib/ios/plugin/ios/FileReader.js +define("cordova/plugin/ios/FileReader", function(require, exports, module) { +var exec = require('cordova/exec'), + FileError = require('cordova/plugin/FileError'), + FileReader = require('cordova/plugin/FileReader'), + ProgressEvent = require('cordova/plugin/ProgressEvent'); + +module.exports = { + readAsText:function(file, encoding) { + // Figure out pathing + this.fileName = ''; + if (typeof file.fullPath === 'undefined') { + this.fileName = file; + } else { + this.fileName = file.fullPath; + } + + // Already loading something + if (this.readyState == FileReader.LOADING) { + throw new FileError(FileError.INVALID_STATE_ERR); + } + + // LOADING state + this.readyState = FileReader.LOADING; + + // If loadstart callback + if (typeof this.onloadstart === "function") { + this.onloadstart(new ProgressEvent("loadstart", {target:this})); + } + + // Default encoding is UTF-8 + var enc = encoding ? encoding : "UTF-8"; + + var me = this; + + // Read file + exec( + // Success callback + function(r) { + // If DONE (cancelled), then don't do anything + if (me.readyState === FileReader.DONE) { + return; + } + + // Save result + me.result = decodeURIComponent(r); + + // If onload callback + if (typeof me.onload === "function") { + me.onload(new ProgressEvent("load", {target:me})); + } + + // DONE state + me.readyState = FileReader.DONE; + + // If onloadend callback + if (typeof me.onloadend === "function") { + me.onloadend(new ProgressEvent("loadend", {target:me})); + } + }, + // Error callback + function(e) { + // If DONE (cancelled), then don't do anything + if (me.readyState === FileReader.DONE) { + return; + } + + // DONE state + me.readyState = FileReader.DONE; + + // null result + me.result = null; + + // Save error + me.error = new FileError(e); + + // If onerror callback + if (typeof me.onerror === "function") { + me.onerror(new ProgressEvent("error", {target:me})); + } + + // If onloadend callback + if (typeof me.onloadend === "function") { + me.onloadend(new ProgressEvent("loadend", {target:me})); + } + }, + "File", "readAsText", [this.fileName, enc]); + } +}; +}); + +// file: lib/ios/plugin/ios/console.js +define("cordova/plugin/ios/console", function(require, exports, module) { +var exec = require('cordova/exec'); + +/** + * This class provides access to the debugging console. + * @constructor + */ +var DebugConsole = function() { + this.winConsole = window.console; + this.logLevel = DebugConsole.INFO_LEVEL; +}; + +// from most verbose, to least verbose +DebugConsole.ALL_LEVEL = 1; // same as first level +DebugConsole.INFO_LEVEL = 1; +DebugConsole.WARN_LEVEL = 2; +DebugConsole.ERROR_LEVEL = 4; +DebugConsole.NONE_LEVEL = 8; + +DebugConsole.prototype.setLevel = function(level) { + this.logLevel = level; +}; + +var stringify = function(message) { + try { + if (typeof message === "object" && JSON && JSON.stringify) { + try { + return JSON.stringify(message); + } + catch (e) { + return "error JSON.stringify()ing argument: " + e; + } + } else { + return message.toString(); + } + } catch (e) { + return e.toString(); + } +}; + +/** + * Print a normal log message to the console + * @param {Object|String} message Message or object to print to the console + */ +DebugConsole.prototype.log = function(message) { + if (this.logLevel <= DebugConsole.INFO_LEVEL) { + exec(null, null, 'Debug Console', 'log', [ stringify(message), { logLevel: 'INFO' } ]); + } + else if (this.winConsole && this.winConsole.log) { + this.winConsole.log(message); + } +}; + +/** + * Print a warning message to the console + * @param {Object|String} message Message or object to print to the console + */ +DebugConsole.prototype.warn = function(message) { + if (this.logLevel <= DebugConsole.WARN_LEVEL) { + exec(null, null, 'Debug Console', 'log', [ stringify(message), { logLevel: 'WARN' } ]); + } + else if (this.winConsole && this.winConsole.warn) { + this.winConsole.warn(message); + } +}; + +/** + * Print an error message to the console + * @param {Object|String} message Message or object to print to the console + */ +DebugConsole.prototype.error = function(message) { + if (this.logLevel <= DebugConsole.ERROR_LEVEL) { + exec(null, null, 'Debug Console', 'log', [ stringify(message), { logLevel: 'ERROR' } ]); + } + else if (this.winConsole && this.winConsole.error){ + this.winConsole.error(message); + } +}; + +module.exports = new DebugConsole(); +}); + +// file: lib/ios/plugin/ios/contacts.js +define("cordova/plugin/ios/contacts", function(require, exports, module) { +var exec = require('cordova/exec'); + +/** + * Provides iOS enhanced contacts API. + */ +module.exports = { + newContactUI : function(successCallback) { + /* + * Create a contact using the iOS Contact Picker UI + * NOT part of W3C spec so no official documentation + * + * returns: the id of the created contact as param to successCallback + */ + exec(successCallback, null, "Contacts","newContact", []); + }, + chooseContact : function(successCallback, options) { + /* + * Select a contact using the iOS Contact Picker UI + * NOT part of W3C spec so no official documentation + * + * @param errorCB error callback + * @param options object + * allowsEditing: boolean AS STRING + * "true" to allow editing the contact + * "false" (default) display contact + * + * returns: the id of the selected contact as param to successCallback + */ + exec(successCallback, null, "Contacts","chooseContact", [options]); + } +}; +}); + +// file: lib/ios/plugin/ios/nativecomm.js +define("cordova/plugin/ios/nativecomm", function(require, exports, module) { +var cordova = require('cordova'); + +/** + * Called by native code to retrieve all queued commands and clear the queue. + */ +module.exports = function() { + var json = JSON.stringify(cordova.commandQueue); + cordova.commandQueue = []; + return json; +}; +}); + +// file: lib/ios/plugin/ios/notification.js +define("cordova/plugin/ios/notification", function(require, exports, module) { +var Media = require('cordova/plugin/Media'); + +module.exports = { + beep:function(count) { + (new Media('beep.wav')).play(); + } +}; +}); + +// file: lib/common/plugin/logger.js +define("cordova/plugin/logger", function(require, exports, module) { +//------------------------------------------------------------------------------ +// The logger module exports the following properties/functions: +// +// LOG - constant for the level LOG +// ERROR - constant for the level ERROR +// WARN - constant for the level WARN +// INFO - constant for the level INFO +// DEBUG - constant for the level DEBUG +// logLevel() - returns current log level +// logLevel(value) - sets and returns a new log level +// useConsole() - returns whether logger is using console +// useConsole(value) - sets and returns whether logger is using console +// log(message,...) - logs a message at level LOG +// error(message,...) - logs a message at level ERROR +// warn(message,...) - logs a message at level WARN +// info(message,...) - logs a message at level INFO +// debug(message,...) - logs a message at level DEBUG +// logLevel(level,message,...) - logs a message specified level +// +//------------------------------------------------------------------------------ + +var logger = exports; + +var exec = require('cordova/exec'); +var utils = require('cordova/utils'); + +var UseConsole = true; +var Queued = []; +var DeviceReady = false; +var CurrentLevel; + +/** + * Logging levels + */ + +var Levels = [ + "LOG", + "ERROR", + "WARN", + "INFO", + "DEBUG" +]; + +/* + * add the logging levels to the logger object and + * to a separate levelsMap object for testing + */ + +var LevelsMap = {}; +for (var i=0; i CurrentLevel) return; + + // queue the message if not yet at deviceready + if (!DeviceReady && !UseConsole) { + Queued.push([level, message]); + return; + } + + // if not using the console, use the native logger + if (!UseConsole) { + exec(null, null, "Logger", "logLevel", [level, message]); + return; + } + + // make sure console is not using logger + if (console.__usingCordovaLogger) { + throw new Error("console and logger are too intertwingly"); + } + + // log to the console + switch (level) { + case logger.LOG: console.log(message); break; + case logger.ERROR: console.log("ERROR: " + message); break; + case logger.WARN: console.log("WARN: " + message); break; + case logger.INFO: console.log("INFO: " + message); break; + case logger.DEBUG: console.log("DEBUG: " + message); break; + } +}; + +// when deviceready fires, log queued messages +logger.__onDeviceReady = function() { + if (DeviceReady) return; + + DeviceReady = true; + + for (var i=0; i 3) { + fail(FileError.SYNTAX_ERR); + } else { + // if successful, return a FileSystem object + var success = function(file_system) { + if (file_system) { + if (typeof successCallback === 'function') { + // grab the name and root from the file system object + var result = new FileSystem(file_system.name, file_system.root); + successCallback(result); + } + } + else { + // no FileSystem object returned + fail(FileError.NOT_FOUND_ERR); + } + }; + exec(success, fail, "File", "requestFileSystem", [type, size]); + } +}; + +module.exports = requestFileSystem; +}); + +// file: lib/common/plugin/resolveLocalFileSystemURI.js +define("cordova/plugin/resolveLocalFileSystemURI", function(require, exports, module) { +var DirectoryEntry = require('cordova/plugin/DirectoryEntry'), + FileEntry = require('cordova/plugin/FileEntry'), + FileError = require('cordova/plugin/FileError'), + exec = require('cordova/exec'); + +/** + * Look up file system Entry referred to by local URI. + * @param {DOMString} uri URI referring to a local file or directory + * @param successCallback invoked with Entry object corresponding to URI + * @param errorCallback invoked if error occurs retrieving file system entry + */ +module.exports = function(uri, successCallback, errorCallback) { + // error callback + var fail = function(error) { + if (typeof errorCallback === 'function') { + errorCallback(new FileError(error)); + } + }; + // sanity check for 'not:valid:filename' + if(!uri || uri.split(":").length > 2) { + setTimeout( function() { + fail(FileError.ENCODING_ERR); + },0); + return; + } + // if successful, return either a file or directory entry + var success = function(entry) { + var result; + if (entry) { + if (typeof successCallback === 'function') { + // create appropriate Entry object + result = (entry.isDirectory) ? new DirectoryEntry(entry.name, entry.fullPath) : new FileEntry(entry.name, entry.fullPath); + try { + successCallback(result); + } + catch (e) { + console.log('Error invoking callback: ' + e); + } + } + } + else { + // no Entry object returned + fail(FileError.NOT_FOUND_ERR); + } + }; + + exec(success, fail, "File", "resolveLocalFileSystemURI", [uri]); +}; + +}); + +// file: lib/common/plugin/splashscreen.js +define("cordova/plugin/splashscreen", function(require, exports, module) { +var exec = require('cordova/exec'); + +var splashscreen = { + show:function() { + exec(null, null, "SplashScreen", "show", []); + }, + hide:function() { + exec(null, null, "SplashScreen", "hide", []); + } +}; + +module.exports = splashscreen; +}); + +// file: lib/common/utils.js +define("cordova/utils", function(require, exports, module) { +var utils = exports; + +/** + * Returns an indication of whether the argument is an array or not + */ +utils.isArray = function(a) { + return Object.prototype.toString.call(a) == '[object Array]'; +}; + +/** + * Returns an indication of whether the argument is a Date or not + */ +utils.isDate = function(d) { + return Object.prototype.toString.call(d) == '[object Date]'; +}; + +/** + * Does a deep clone of the object. + */ +utils.clone = function(obj) { + if(!obj || typeof obj == 'function' || utils.isDate(obj) || typeof obj != 'object') { + return obj; + } + + var retVal, i; + + if(utils.isArray(obj)){ + retVal = []; + for(i = 0; i < obj.length; ++i){ + retVal.push(utils.clone(obj[i])); + } + return retVal; + } + + retVal = {}; + for(i in obj){ + if(!(i in retVal) || retVal[i] != obj[i]) { + retVal[i] = utils.clone(obj[i]); + } + } + return retVal; +}; + +/** + * Returns a wrappered version of the function + */ +utils.close = function(context, func, params) { + if (typeof params == 'undefined') { + return function() { + return func.apply(context, arguments); + }; + } else { + return function() { + return func.apply(context, params); + }; + } +}; + +/** + * Create a UUID + */ +utils.createUUID = function() { + return UUIDcreatePart(4) + '-' + + UUIDcreatePart(2) + '-' + + UUIDcreatePart(2) + '-' + + UUIDcreatePart(2) + '-' + + UUIDcreatePart(6); +}; + +/** + * Extends a child object from a parent object using classical inheritance + * pattern. + */ +utils.extend = (function() { + // proxy used to establish prototype chain + var F = function() {}; + // extend Child from Parent + return function(Child, Parent) { + F.prototype = Parent.prototype; + Child.prototype = new F(); + Child.__super__ = Parent.prototype; + Child.prototype.constructor = Child; + }; +}()); + +/** + * Alerts a message in any available way: alert or console.log. + */ +utils.alert = function(msg) { + if (alert) { + alert(msg); + } else if (console && console.log) { + console.log(msg); + } +}; + +/** + * Formats a string and arguments following it ala sprintf() + * + * see utils.vformat() for more information + */ +utils.format = function(formatString /* ,... */) { + var args = [].slice.call(arguments, 1); + return utils.vformat(formatString, args); +}; + +/** + * Formats a string and arguments following it ala vsprintf() + * + * format chars: + * %j - format arg as JSON + * %o - format arg as JSON + * %c - format arg as '' + * %% - replace with '%' + * any other char following % will format it's + * arg via toString(). + * + * for rationale, see FireBug's Console API: + * http://getfirebug.com/wiki/index.php/Console_API + */ +utils.vformat = function(formatString, args) { + if (formatString === null || formatString === undefined) return ""; + if (arguments.length == 1) return formatString.toString(); + if (typeof formatString != "string") return formatString.toString(); + + var pattern = /(.*?)%(.)(.*)/; + var rest = formatString; + var result = []; + + while (args.length) { + var arg = args.shift(); + var match = pattern.exec(rest); + + if (!match) break; + + rest = match[3]; + + result.push(match[1]); + + if (match[2] == '%') { + result.push('%'); + args.unshift(arg); + continue; + } + + result.push(formatted(arg, match[2])); + } + + result.push(rest); + + return result.join(''); +}; + +//------------------------------------------------------------------------------ +function UUIDcreatePart(length) { + var uuidpart = ""; + for (var i=0; i + + + + + + + + Hello Cordova + + +
    +

    Apache Cordova™

    +
    + + +
    +
    + + + + + + + + +

    Hey, it's Twitter on PhoneGap!

    +
    +
      +
    1. isAvailable
    2. +
    3. isSetup
    4. +
    5. tweet (text, img, url)
    6. +
    7. tweet (text, remote img)
    8. +
    9. tweet (text, local img)
    10. +
    11. tweet (text, url)
    12. +
    13. tweet (text)
    14. +
    15. tweet (empty)
    16. +
    17. timeline
    18. +
    19. mentions
    20. +
    21. friendsIds
    22. +
    23. usersLookup
    24. +
    +
    + + + + diff --git a/iOS/Twitter/example/www2.0/js/index.js b/iOS/Twitter/example/www2.0/js/index.js new file mode 100644 index 00000000..40de817e --- /dev/null +++ b/iOS/Twitter/example/www2.0/js/index.js @@ -0,0 +1,24 @@ +var app = { +initialize: function() { + this.bind(); +}, +bind: function() { + document.addEventListener('deviceready', this.deviceready, false); +}, +deviceready: function() { + // note that this is an event handler so the scope is that of the event + // so we need to call app.report(), and not this.report() + app.report('deviceready'); + + TwitterDemo.setup(); + + +}, +report: function(id) { + console.log("report:" + id); + // hide the .pending

    and show the .complete

    + document.querySelector('#' + id + ' .pending').className += ' hide'; + var completeElem = document.querySelector('#' + id + ' .complete'); + completeElem.className = completeElem.className.split('hide').join(''); +} +}; diff --git a/iOS/Twitter/example/www2.0/ninja-lolcat.gif b/iOS/Twitter/example/www2.0/ninja-lolcat.gif new file mode 100644 index 00000000..51f19595 Binary files /dev/null and b/iOS/Twitter/example/www2.0/ninja-lolcat.gif differ diff --git a/iOS/Twitter/example/www2.0/res/icon/cordova_128.png b/iOS/Twitter/example/www2.0/res/icon/cordova_128.png new file mode 100644 index 00000000..3516df32 Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/icon/cordova_128.png differ diff --git a/iOS/Twitter/example/www2.0/res/icon/cordova_16.png b/iOS/Twitter/example/www2.0/res/icon/cordova_16.png new file mode 100644 index 00000000..54e19c55 Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/icon/cordova_16.png differ diff --git a/iOS/Twitter/example/www2.0/res/icon/cordova_24.png b/iOS/Twitter/example/www2.0/res/icon/cordova_24.png new file mode 100644 index 00000000..c7d43ad5 Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/icon/cordova_24.png differ diff --git a/iOS/Twitter/example/www2.0/res/icon/cordova_256.png b/iOS/Twitter/example/www2.0/res/icon/cordova_256.png new file mode 100644 index 00000000..e1cd0e61 Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/icon/cordova_256.png differ diff --git a/iOS/Twitter/example/www2.0/res/icon/cordova_32.png b/iOS/Twitter/example/www2.0/res/icon/cordova_32.png new file mode 100644 index 00000000..734fffca Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/icon/cordova_32.png differ diff --git a/iOS/Twitter/example/www2.0/res/icon/cordova_48.png b/iOS/Twitter/example/www2.0/res/icon/cordova_48.png new file mode 100644 index 00000000..8ad8bac0 Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/icon/cordova_48.png differ diff --git a/iOS/Twitter/example/www2.0/res/icon/cordova_512.png b/iOS/Twitter/example/www2.0/res/icon/cordova_512.png new file mode 100644 index 00000000..c9465f3f Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/icon/cordova_512.png differ diff --git a/iOS/Twitter/example/www2.0/res/icon/cordova_64.png b/iOS/Twitter/example/www2.0/res/icon/cordova_64.png new file mode 100644 index 00000000..03b38495 Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/icon/cordova_64.png differ diff --git a/iOS/Twitter/example/www2.0/res/icon/cordova_android_36.png b/iOS/Twitter/example/www2.0/res/icon/cordova_android_36.png new file mode 100644 index 00000000..cd5032a4 Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/icon/cordova_android_36.png differ diff --git a/iOS/Twitter/example/www2.0/res/icon/cordova_android_48.png b/iOS/Twitter/example/www2.0/res/icon/cordova_android_48.png new file mode 100644 index 00000000..e79c6062 Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/icon/cordova_android_48.png differ diff --git a/iOS/Twitter/example/www2.0/res/icon/cordova_android_72.png b/iOS/Twitter/example/www2.0/res/icon/cordova_android_72.png new file mode 100644 index 00000000..4d276344 Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/icon/cordova_android_72.png differ diff --git a/iOS/Twitter/example/www2.0/res/icon/cordova_android_96.png b/iOS/Twitter/example/www2.0/res/icon/cordova_android_96.png new file mode 100644 index 00000000..ec7ffbfb Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/icon/cordova_android_96.png differ diff --git a/iOS/Twitter/example/www2.0/res/icon/cordova_bb_80.png b/iOS/Twitter/example/www2.0/res/icon/cordova_bb_80.png new file mode 100644 index 00000000..f86a27a9 Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/icon/cordova_bb_80.png differ diff --git a/iOS/Twitter/example/www2.0/res/icon/cordova_ios_114.png b/iOS/Twitter/example/www2.0/res/icon/cordova_ios_114.png new file mode 100644 index 00000000..efd9c374 Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/icon/cordova_ios_114.png differ diff --git a/iOS/Twitter/example/www2.0/res/icon/cordova_ios_144.png b/iOS/Twitter/example/www2.0/res/icon/cordova_ios_144.png new file mode 100644 index 00000000..dd819da6 Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/icon/cordova_ios_144.png differ diff --git a/iOS/Twitter/example/www2.0/res/icon/cordova_ios_57.png b/iOS/Twitter/example/www2.0/res/icon/cordova_ios_57.png new file mode 100644 index 00000000..c795fc4e Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/icon/cordova_ios_57.png differ diff --git a/iOS/Twitter/example/www2.0/res/icon/cordova_ios_72.png b/iOS/Twitter/example/www2.0/res/icon/cordova_ios_72.png new file mode 100644 index 00000000..b1cfde7d Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/icon/cordova_ios_72.png differ diff --git a/iOS/Twitter/example/www2.0/res/screen/android_hdpi_landscape.png b/iOS/Twitter/example/www2.0/res/screen/android_hdpi_landscape.png new file mode 100644 index 00000000..a61e2b1a Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/screen/android_hdpi_landscape.png differ diff --git a/iOS/Twitter/example/www2.0/res/screen/android_hdpi_portrait.png b/iOS/Twitter/example/www2.0/res/screen/android_hdpi_portrait.png new file mode 100644 index 00000000..5d6a28a8 Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/screen/android_hdpi_portrait.png differ diff --git a/iOS/Twitter/example/www2.0/res/screen/android_ldpi_landscape.png b/iOS/Twitter/example/www2.0/res/screen/android_ldpi_landscape.png new file mode 100644 index 00000000..f3934cdc Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/screen/android_ldpi_landscape.png differ diff --git a/iOS/Twitter/example/www2.0/res/screen/android_ldpi_portrait.png b/iOS/Twitter/example/www2.0/res/screen/android_ldpi_portrait.png new file mode 100644 index 00000000..65ad163a Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/screen/android_ldpi_portrait.png differ diff --git a/iOS/Twitter/example/www2.0/res/screen/android_mdpi_landscape.png b/iOS/Twitter/example/www2.0/res/screen/android_mdpi_landscape.png new file mode 100644 index 00000000..a1b697c5 Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/screen/android_mdpi_landscape.png differ diff --git a/iOS/Twitter/example/www2.0/res/screen/android_mdpi_portrait.png b/iOS/Twitter/example/www2.0/res/screen/android_mdpi_portrait.png new file mode 100644 index 00000000..ea156935 Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/screen/android_mdpi_portrait.png differ diff --git a/iOS/Twitter/example/www2.0/res/screen/android_xhdpi_landscape.png b/iOS/Twitter/example/www2.0/res/screen/android_xhdpi_landscape.png new file mode 100644 index 00000000..79f2f094 Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/screen/android_xhdpi_landscape.png differ diff --git a/iOS/Twitter/example/www2.0/res/screen/android_xhdpi_portrait.png b/iOS/Twitter/example/www2.0/res/screen/android_xhdpi_portrait.png new file mode 100644 index 00000000..c2e80421 Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/screen/android_xhdpi_portrait.png differ diff --git a/iOS/Twitter/example/www2.0/res/screen/blackberry_transparent_300.png b/iOS/Twitter/example/www2.0/res/screen/blackberry_transparent_300.png new file mode 100644 index 00000000..b548bdc4 Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/screen/blackberry_transparent_300.png differ diff --git a/iOS/Twitter/example/www2.0/res/screen/blackberry_transparent_400.png b/iOS/Twitter/example/www2.0/res/screen/blackberry_transparent_400.png new file mode 100644 index 00000000..3facdf9e Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/screen/blackberry_transparent_400.png differ diff --git a/iOS/Twitter/example/www2.0/res/screen/ipad_landscape.png b/iOS/Twitter/example/www2.0/res/screen/ipad_landscape.png new file mode 100644 index 00000000..04be5acf Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/screen/ipad_landscape.png differ diff --git a/iOS/Twitter/example/www2.0/res/screen/ipad_portrait.png b/iOS/Twitter/example/www2.0/res/screen/ipad_portrait.png new file mode 100644 index 00000000..41e839d9 Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/screen/ipad_portrait.png differ diff --git a/iOS/Twitter/example/www2.0/res/screen/ipad_retina_landscape.png b/iOS/Twitter/example/www2.0/res/screen/ipad_retina_landscape.png new file mode 100644 index 00000000..95c542dc Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/screen/ipad_retina_landscape.png differ diff --git a/iOS/Twitter/example/www2.0/res/screen/ipad_retina_portrait.png b/iOS/Twitter/example/www2.0/res/screen/ipad_retina_portrait.png new file mode 100644 index 00000000..aae1862c Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/screen/ipad_retina_portrait.png differ diff --git a/iOS/Twitter/example/www2.0/res/screen/iphone_landscape.png b/iOS/Twitter/example/www2.0/res/screen/iphone_landscape.png new file mode 100644 index 00000000..d1548837 Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/screen/iphone_landscape.png differ diff --git a/iOS/Twitter/example/www2.0/res/screen/iphone_portrait.png b/iOS/Twitter/example/www2.0/res/screen/iphone_portrait.png new file mode 100644 index 00000000..6fcba565 Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/screen/iphone_portrait.png differ diff --git a/iOS/Twitter/example/www2.0/res/screen/iphone_retina_landscape.png b/iOS/Twitter/example/www2.0/res/screen/iphone_retina_landscape.png new file mode 100644 index 00000000..0165669d Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/screen/iphone_retina_landscape.png differ diff --git a/iOS/Twitter/example/www2.0/res/screen/iphone_retina_portrait.png b/iOS/Twitter/example/www2.0/res/screen/iphone_retina_portrait.png new file mode 100644 index 00000000..bd24886a Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/screen/iphone_retina_portrait.png differ diff --git a/iOS/Twitter/example/www2.0/res/screen/windows_phone_portrait.jpg b/iOS/Twitter/example/www2.0/res/screen/windows_phone_portrait.jpg new file mode 100644 index 00000000..9f953870 Binary files /dev/null and b/iOS/Twitter/example/www2.0/res/screen/windows_phone_portrait.jpg differ diff --git a/iOS/Twitter/example/www2.0/spec.html b/iOS/Twitter/example/www2.0/spec.html new file mode 100644 index 00000000..83d7d2e3 --- /dev/null +++ b/iOS/Twitter/example/www2.0/spec.html @@ -0,0 +1,50 @@ + + + + Jasmine Spec Runner + + + + + + + + + + + + + + + + + +

    + + diff --git a/iOS/Twitter/example/www2.0/spec/helper.js b/iOS/Twitter/example/www2.0/spec/helper.js new file mode 100644 index 00000000..9f994450 --- /dev/null +++ b/iOS/Twitter/example/www2.0/spec/helper.js @@ -0,0 +1,11 @@ +afterEach(function() { + document.getElementById('stage').innerHTML = ''; +}); + +var helper = { + trigger: function(obj, name) { + var e = document.createEvent('Event'); + e.initEvent(name, true, true); + obj.dispatchEvent(e); + } +}; diff --git a/iOS/Twitter/example/www2.0/spec/index.js b/iOS/Twitter/example/www2.0/spec/index.js new file mode 100644 index 00000000..121cf631 --- /dev/null +++ b/iOS/Twitter/example/www2.0/spec/index.js @@ -0,0 +1,49 @@ +describe('app', function() { + describe('initialize', function() { + it('should bind deviceready', function() { + runs(function() { + spyOn(app, 'deviceready'); + app.initialize(); + helper.trigger(window.document, 'deviceready'); + }); + + waitsFor(function() { + return (app.deviceready.calls.length > 0); + }, 'deviceready should be called once', 500); + + runs(function() { + expect(app.deviceready).toHaveBeenCalled(); + }); + }); + }); + + describe('deviceready', function() { + it('should report that it fired', function() { + spyOn(app, 'report'); + app.deviceready(); + expect(app.report).toHaveBeenCalledWith('deviceready'); + }); + }); + + describe('report', function() { + beforeEach(function() { + var el = document.getElementById('stage'); + el.innerHTML = ['
    ', + '

    Pending

    ', + '

    Complete

    ', + '
    '].join('\n'); + }); + + it('should show the completion state', function() { + app.report('deviceready'); + var el = document.querySelector('#deviceready .complete:not(.hide)'); + expect(el).toBeTruthy(); + }); + + it('should hide the pending state', function() { + app.report('deviceready'); + var el = document.querySelector('#deviceready .pending.hide'); + expect(el).toBeTruthy(); + }); + }); +}); diff --git a/iOS/Twitter/install b/iOS/Twitter/install deleted file mode 100644 index 3a320241..00000000 --- a/iOS/Twitter/install +++ /dev/null @@ -1,22 +0,0 @@ -#!/usr/bin/env ruby - -def replace_in_file(filepath, regexp, *args, &block) - content = File.read(filepath).gsub(regexp, *args, &block) - File.open(filepath, 'wb') { |file| file.write(content) } -end - -file = File.expand_path(ARGV[0]) -platform = ( File.extension(file) == ".plist" ? "ios" : "android" ) - -if (platform == "ios") - replace_in_file(file, /\s*com.phonegap.twitter<\/key>\n/mi) do |match| - "" - end - replace_in_file(file, /\s*TwitterPlugin<\/string>\n/mi) do |match| - "" - end - replace_in_file(file, /Plugins<\/key>\n\s*/mi) do |match| - "Plugins\n\t\n\t\tcom.phonegap.twitter\n\t\tTwitterPlugin" - end -elsif (platform == "android") -end \ No newline at end of file diff --git a/iOS/Twitter/js/TwitterPlugin.js b/iOS/Twitter/js/TwitterPlugin.js new file mode 100644 index 00000000..a4c64ff8 --- /dev/null +++ b/iOS/Twitter/js/TwitterPlugin.js @@ -0,0 +1,140 @@ +/** + * @constructor + */ +var Twitter = function(){}; +/** + * Checks if the Twitter SDK is loaded + * @param {Function} response callback on result + * @param {Number} response.response is 1 for success, 0 for failure + * @example + * window.plugins.twitter.isTwitterAvailable(function (response) { + * console.log("twitter available? " + response); + * }); + */ +Twitter.prototype.isTwitterAvailable = function(response){ + cordova.exec(response, null, "TwitterPlugin", "isTwitterAvailable", []); +}; +/** + * Checks if the Twitter SDK can send a tweet + * @param {Function} response callback on result + * @param {Number} response.response is 1 for success, 0 for failure + * @example + * window.plugins.twitter.isTwitterSetup(function (r) { + * console.log("twitter configured? " + r); + * }); + */ +Twitter.prototype.isTwitterSetup = function(response){ + cordova.exec(response, null, "TwitterPlugin", "isTwitterSetup", []); +}; +/** + * Sends a Tweet to Twitter + * @param {Function} success callback + * @param {Function} failure callback + * @param {String} failure.error reason for failure + * @param {String} tweetText message to send to twitter + * @param {Object} options (optional) + * @param {String} options.urlAttach URL to embed in Tweet + * @param {String} options.imageAttach Image URL to embed in Tweet + * @param {Number} response.response - 1 on success, 0 on failure + * @example + * window.plugins.twitter.composeTweet( + * function () { console.log("tweet success"); }, + * function (error) { console.log("tweet failure: " + error); }, + * "Text, Image, URL", + * { + * urlAttach:"http://m.youtube.com/#/watch?v=obx2VOtx0qU", + * imageAttach:"http://i.ytimg.com/vi/obx2VOtx0qU/hqdefault.jpg?w=320&h=192&sigh=QD3HYoJj9dtiytpCSXhkaq1oG8M" + * } + * ); + */ +Twitter.prototype.composeTweet = function(success, failure, tweetText, options){ + options = options || {}; + options.text = tweetText; + cordova.exec(success, failure, "TwitterPlugin", "composeTweet", [options]); +}; +/** + * Gets Tweets from Twitter Timeline + * @param {Function} success callback + * @param {Object[]} success.response Tweet objects, see [Twitter Timeline Doc] + * @param {Function} failure callback + * @param {String} failure.error reason for failure + * @example + * window.plugins.twitter.getPublicTimeline( + * function (response) { console.log("timeline success: " + JSON.stringify(response)); }, + * function (error) { console.log("timeline failure: " + error); } + * ); + * + * [Twitter Timeline Doc]: https://dev.twitter.com/docs/api/1/get/statuses/public_timeline + */ +Twitter.prototype.getPublicTimeline = function(success, failure){ + cordova.exec(success, failure, "TwitterPlugin", "getPublicTimeline", []); +}; +/** + * Gets Tweets from Twitter Mentions + * @param {Function} success callback + * @param {Object[]} success.result Tweet objects, see [Twitter Mentions Doc] + * @param {Function} failure callback + * @param {String} failure.error reason for failure + * @example + * window.plugins.twitter.getMentions( + * function (response) { console.log("mentions success: " + JSON.stringify(response)); }, + * function (error) { console.log("mentions failure: " + error); } + * ); + * + * [Twitter Timeline Doc]: https://dev.twitter.com/docs/api/1/get/statuses/public_timeline + */ +Twitter.prototype.getMentions = function(success, failure){ + cordova.exec(success, failure, "TwitterPlugin", "getMentions", []); +}; +/** + * Gets Tweets from Twitter Mentions API + * @param {Function} success callback + * @param {String} success.response Twitter Username + * @param {Object[]} success.result Tweet objects, see [Twitter Mentions Doc] + * @param {Function} failure callback + * @param {String} failure.error reason for failure + * + * [Twitter Mentions Doc]: https://dev.twitter.com/docs/api/1/get/statuses/mentions + */ +Twitter.prototype.getTwitterUsername = function(success, failure) { + cordova.exec(success, failure, "TwitterPlugin", "getTwitterUsername", []); +}; +/** + * Gets Tweets from Twitter Mentions API + * @param {String} url of [Twitter API Endpoint] + * @param {Object} params key-value map, matching [Twitter API Endpoint] + * @param {Function} success callback + * @param {Object[]} success.response objects returned from Twitter API (Tweets, Users,...) + * @param {Function} failure callback + * @param {String} failure.error reason for failure + * @param {Object} options (optional) other options for the HTTP request + * @param {String} options.requestMethod HTTP Request type, ex: "POST" + * @example + * window.plugins.twitter.getTWRequest( + * 'users/lookup.json', + * {user_id: '16141659,783214,6253282'}, + * function (response) { console.log("usersLookup success: " + JSON.stringify(response)); }, + * function (error) { console.log("usersLookup failure: " + error); }, + * {requestMethod: 'POST'} + * ); + * + * [Twitter API Endpoints]: https://dev.twitter.com/docs/api + */ +Twitter.prototype.getTWRequest = function(url, params, success, failure, options){ + options = options || {}; + options.url = url; + options.params = params; + cordova.exec(success, failure, "TwitterPlugin", "getTWRequest", [options]); +}; +// Plug in to Cordova +cordova.addConstructor(function() { + + /* shim to work in 1.5 and 1.6 */ + if (!window.Cordova) { + window.Cordova = cordova; + }; + + + if(!window.plugins) window.plugins = {}; + window.plugins.twitter = new Twitter(); + }); diff --git a/iOS/Twitter/package.json b/iOS/Twitter/package.json deleted file mode 100644 index dd069145..00000000 --- a/iOS/Twitter/package.json +++ /dev/null @@ -1,15 +0,0 @@ -{ - "author": "Brian Antonelli", - "name": "com.phonegap.twitter", - "description": "PhoneGap Twitter Plugin", - "version": "0.0.1", - "repository": { - "type": "git", - "url": "git://github.com/phonegap/phonegap-plugins.git" - }, - "engines": { - "phonegap": "1.2.0" - }, - "dependencies": {}, - "development_dependencies": {} -} \ No newline at end of file