Cordova non funziona? Forse la soluzione è semplice…

Che vi siate approcciati a Cordova da molto tempo o che siate dei neofiti, probabilmente c’è un piccolo scoglio che dovrete superare: installare plugin e vederli non funzionare nel simulatore (o sul device reale).

Che la vostra app utilizzi un framework conosciuto come Ionic o React, oppure una interfaccia in javascript totalmente custom (come spesso faccio io per piccoli progetti low budget), dovrete passare per forza da Cordova per interfacciarvi con gli smartphone.

Fate estrema attenzione ad inserire (anche se non ne fate uso nella vostra applicazione) della libreria cordova.js, possibilmente prima della chiusura del tag .

<script type="text/javascript" src="cordova.js"></script>

Cordova 3.4, XCode 5.1 e InAppBrowser

Ciao a tutti,
probabilmente, se siete finiti su questa pagina, state smadonnando come dei cinghiali sul perchè e sul per come Cordova non funzioni a dovere su XCode 5.1.

Tutto questo malfunzionare mi ha fatto bellamente scaricare ed installare ( da http://developer.apple.com/downloads ) la versione di XCode 5.0.4. Tutti quei warnings erano veramente fastidiosi, per non parlare delle modifiche manuali che bisogna apporre alle librerie CDVViewController e CDVCommandQueue.
Sicuramente avrete provato ed avrete incontrato non pochi errori di build.
Leggete qui, probabilmente vi risolverà non poco la vita.

Tutti questi errori con la vecchia versione di XCode non li avrete, quindi, se usate XCode prevalentemente per Cordova o Phonegap, vi consiglio vivamente di disattivarne gli aggiornamenti automatici. Gli sviluppatori di Apple sono molto più laboriosi di quelli di Cordova…

Il mio enorme problema era con InAppBrowser, il plugin che permette di aprire in una finestra separata, nella vostra app, qualsiasi URL esterno.
Nel mio caso è fondamentale poichè debbo aprire una pagina di pagamento bancario, impensabile fare tutto mediante Ajax, per non parlare della sicurezza…

Alcune cose che voglio condividere con voi: se avete scritto tutto bene, se  avete seguito alla lettera le indicazioni sulla pagina git del plugin stesso (che trovate qui), e nonostante tutto la finestra non vi si apre, beh, è colpa di Cordova, consolatevi.

Dovete sapere che, anche se il CLI di Cordova sembra fare tutto per bene, in verità così non è, e dovete fare qualche piccola modifica a manina in XCode.

Una volta che avete copiato tutti i vostri files nella cartella www (esterna a quella della piattaforma, COME SAPETE BENE, vero? ), andare a terminale e fate un bel cordova build.

Aprite XCode e verificate il nome della libreria inappbrowser.js situata in: www/plugins/org.apache.cordova.inappbrowser. Noterete che si chiama InAppBrowser.js.

Fin qui tutto bene, non è mica colpa sua se si chiama così.
Ora però il nome deve ritornarmi uguale nell’elenco plugins cordova_plugins.js, tenendo a mente che XCode si incazza perchè Case Sensitive.
Aprendo la libreria scopro che cosa?
La seguente riga: “file”:”plugins/org.apache.cordova.inappbrowser/www/inappbrowser.js”…MINUSCOLO!

Ma vai a morire ammazzato, va! 3 giorni di lavoro buttati, per non parlare del mal di testa!
Considerate una cosa: il simulatore, queste finezze pare non considerarle, quindi vi ritrovate con l’app che funziona nel simulatore e non nel device. Bella merda, eh?

Modificate il nome mettendo le maiuscole al posto giusto nel file cordova_plugins.js e re-buildate l’app, tutto andrà per il meglio (o almeno spero per voi, per me ha risolto).

CUSTOMIZZARE INAPPBROWSER

Ora che funziona, non ci accontentiamo del risultato (inguardabile) offerto dalle impostazioni di default.
Usando la sintassi corretta, apriamo l’InAppBrowser mediante il comando window.open(url, target, options);

URL
Fondamentale fare un bel encodeURI(url), vi risolvete un bel po’ di problemi di encoding del’URL.

TARGET
_blank serve per aprire la finestra correttamente nell’app, dando l’opportunità di chiuderla con l’apposito tasto.
_system vi aprirà il browser di default;
_self aprirà usando la WebView corrente, mandando a ramengo la vostra index.html

OPTIONS
Tenete bene a mente che dovrete passare le variabili divise da virgola e senza spazi.
Un esempio? Io volevo personalizzare l’InAppBrowser cambiando scritta, posizione e togliendo quell’orribile barra dell’URL.
Bene, il risultato, funzionante, è il seguente:
location=no,closebuttoncaption=Chiudi,toolbarposition=top

Manca però una cosa fondamentale: il colore della parola CHIUDI!
Mi sta tutto bene, sono attendo alla grafica ed ai dettagli, e questi fenomeni non mi mettono una opzione per customizzare il colore del link?

Risolviamo il problema aprendo, in XCode, Plugins/CDVInAppBrowser.m.
CMD-F e ricercate, all’interno del documento, la parola “tint”.
Troverete la riga
self.closeButton.tintColor = [UIColor colorWithRed:246.00 / 255.0 green:102.0  / 255.0 blue:66.0 / 255.0 alpha:1];

Cambiate i valori usando il formato RGB ed il gioco è fatto.
Spero di esservi stato utile!

Cordova 3.4 e InAppBrowser

Ultimamente mi sto parecchio concentrando sul discorso APP HTML5 con Cordova ( o Phonegap, chiamatelo come vi pare, io uso il primo perchè di PhonegapBuild non me ne frega una mazza ).

Oramai siamo arrivati alla versione 3.4, direi una versione piuttosto stabile.
Una cosa però, oggi, mi ha fatto uscire fuori di testa pesantemente.
Sto realizzando una app che ha, nella sua tabbar, un bel link per una pagina HTML esterna.

Procedo come al mio solito: accedo alla mia cartella delle app, apro il terminale del mio fido iMac, e digito:

cordova create "nomeapp" "com.nomeazienda.nomeapp" "nomeapp"

Successivamente

cd nomeapp

cordova platform add android

cordova platform add ios

Cosa ho fatto?

Ho semplicemente inserito le due piattaforme iOs e Android all’interno del progetto.

Per coloro che non fossero avvezzi alle nuove dinamiche Cordova, è molto facilitato il compito di gestire tutti i file ed i plugin, e io vi consiglio sicuramente di usare il terminale. Risparmierete una montagna di ore di prove, copia ed incolla, e incazzamenti vari.

Dentro la cartella nomeapp, chiaramente, avrò la struttura creatami da Cordova. Quella che vi interessa è la cartella WWW, che contiene i files HTML della vostra app. Cordova, in fase di build, si occuperà di copiare i files dentro la cartella platform/android.

Bene. Ma cosa vi sto a spiegare tutto questo torrone, tanto sicuramente siete più bravi di me.

Se poi avete bisogno di una mano, contattatemi qui:

Vengo al problema InAppBrowser: molto semplice. Non funzionava.
Niente da fare. Eppure nel file config.xml di base, la whitelist era a posto ( se per a posto consideriamo un * ).
Semplicemente i miei link esterni si aprivano nell’app stessa, senza alcuna possibilità di tornare indietro. Risultato? Fallimento su tutta la linea, una pagina web che si apre in _self è peggio che un calcio nel culo. Allora ho provato a forzare l’app a considerare NON in whitelist il mio dominio.

Da:

<access origin="*" />

a:

<access origin="http://www.google.com" />

Ho quindi rifatto il build di entrambe le piattaforme con un bel

cordova build

e poi ho lanciato l’app nel mio device Android:

cordova run --device android

Risultato? LA MAGIA.
InAppBrowser è tornato a funzionare come per magia, e per giunta su entrambi i domini!

Regola d’oro quindi: aggiungete a manina santa i domini che dovranno comunicare con la vostra app. Vi risparmierete un bel mal di testa.

Aggiornamento dell 18:50

Ho provato la stessa soluzione su XCode: le bestemmie.
Sul mio iPhone 3GS mi da problemi di Whitelist, a prescindere da cosa metta, dovrò approfondire come risolverlo, presumo che sia sufficiente mettere a posto nel file .plist.
Sul simulatore, invece, perfetto, apre l’InAppBrowser perfettamente.

Phonegap app su iTunes Store. Si può fare!

Su moltissimi forum di Phonegap si leggono messaggi di persone disperate perchè iTunes Store non accetta le loro app realizzate con HTML5 e Phonegap.

Proporre una app ad Apple per vedersela esporre sull’iTunes Store non è affare da poco: prima di tutto devi avere un Mac, dopo di che devi passare indenne tutta la procedura di verifica delle varie licenze di sviluppatore, devi inserire l’ID di qua, l’ID di la…a prima vista, una giungla burocratica pazzesca.

Una volta che, invece, si è presa la mano sulle operazioni da compiere, risulta piuttosto veloce ed indolore avere un pacchetto valido da proporre ad Apple. Altro discorso è quello di riuscire a proporre una applicazione ad Apple che risponda ai canoni indicati dall’azienda di Cupertino nella loro guideline.

L’errore più frequente (e per più frequente parliamo del 95% delle volte) che viene compiuto dai programmatori o presunti tali di app è quella di proporre una versione “app” di un normalissimo sito internet. Apple, giustamente, rifiuta l’applicazione indicando che il progetto non è abbastanza…”app”. Non sfrutta in nessuna maniera le peculiarità dello smartphone o del tablet, non da alcun plusvalore all’utente rispetto alla navigazione con safari del sito stesso. Quindi…se volete accingervi a creare la vostra app, fermatevi e ragionate un secondo su quale potrebbe essere una funzionalità in più per la vostra applicazione.

La mia prima app realizzata con Phonegap è la versione mobile del sito Ilportaledelpoker.com, portale dedicato al mondo del texas e sue varianti. Poker, roba da malati. Un po’ come la programmazione, via…

Alla fine, è niente altro che l’archivio delle news inserite sul sito, con però una aggiunta fondamentale: la possibilità di aggiungere, su un database creato on-the-fly sul telefono, gli articoli a preferiti, potendoli poi sfogliare in un secondo tempo.
Attenzione: gli articoli non vengono salvati interamente sul telefono, ma solamente “indicizzati” attraverso il loro ID univoco. Entrando nella sezione preferiti, la app prima carica dal database l’array con gli ID degli articoli, dopo di che ne carica titolo e testo da remoto, direttamente dal database centrale del sito.

Utilizzo, in sostanza, l’oggetto Storage datomi da Phonegap.
Il codice per gestire lo Storage è semplicissimo:

function populateDB(tx) {
     tx.executeSql('DROP TABLE IF EXISTS DEMO');
     tx.executeSql('CREATE TABLE IF NOT EXISTS DEMO (id unique, data)');
     tx.executeSql('INSERT INTO DEMO (id, data) VALUES (1, "First row")');
     tx.executeSql('INSERT INTO DEMO (id, data) VALUES (2, "Second row")');
}

function errorCB(err) {
    alert("Error processing SQL: "+err.code);
}

function successCB() {
    alert("success!");
}

var db = window.openDatabase("Database", "1.0", "Cordova Demo", 200000);
db.transaction(populateDB, errorCB, successCB);

Dichiaro una variabile db, che esegue un comando, ossia window.openDatabase( nome del database, versione del db, nome “visibile” del db e la sua dimensione ); subito dopo eseguo una azione chiamata transaction, che consiste in 3 azioni distinte: azione, errore, successo.
Devo fare delle operazioni sul database? Le carico nella funzione populateDB, ossia quella che, nell’esempio:

  • elimina il database se esiste già
  • ricrea la tabella
  • inserisce una riga con id=1
  • inserisce una riga con id=2

Semplicissimo!
Il sistema poi, a seconda che la funzione populateDB sia andata a buon fine o a vacca totale, richiamerà errorDB e successDB. A voi l’incredibile difficoltà di capire quale verrà lanciata in caso di errore.

Questo piccolo excursus per farvi capire che basta utilizzare un oggettino ed avere un minimo di fantasia per vedere le proprie app accettate da Apple. Certo, se la vostra app è un cesso, non funziona bene a prescindere dalle sue funzionalità oppure gliela proponete dicendogli subito che è una demo o una beta, beh…allora avete proprio tanto tempo da perdere!

Phonegap e Android: missing one of the following

Oggi ho provato ad installare tutto il sistema per poter esportare la mia Phonegap App su ambiente Android. Più facile a dirsi che a farsi.
Giusto per non farsi mancare nulla, Windows comincia sempre con rispondere con messaggi di errori del tipo: comando non riconosciuto. E già bestemmie come se piovesse…

Scarico Phonegap 2.5.0 e provo, così, senza aver letto niente altro, a lanciare il comando create..

create c:\apps com.nomeazienza.nomeapp nomeapp

Ovviamente terremoto e tragedia, non funziona niente.
Mi accorgo immediatamente che, differentemente da quanto pensassi, non ho installato nè il Java SDK nè ANT, di cui ignoravo l’esistenza fino a qualche minuto prima.

Nel dubbio mi riscarico tutto:

Non grandi cose, siamo sui 300mb.
Installo il tutto e per controllare che tutto sia funzionante apro la shell e rilancio il comando create come sopra.

Nonostante tutto, continua a non funzionare, mi viene presentato un messaggio Missing one of the following (JDK, SDK, ANT).
Per ovviare a tutto ciò, dovete controllare che tutti i comandi elencati qui siano funzionanti:

  • java
  • javac
  • ant
  • adb
  • android

Non funzionano? Probabilmente nelle variabili di sistema mancano i riferimenti alle cartelle dei vari SDK.
Un esempio su tutti, per far funzionare il comando javac si può inserire in variabile di sistema il riferimento alla cartella JavaSdk:

set path="%path%;c:\program files\java\jdk7\bin"

Cosa fa questo comando?
Semplicemente setta la variabile di sistema path con un nuovo valore, c:\program files\java\jdk7\bin, e lo aggiunge al contenuto della variabile stessa %path%.

Per tutti i comandi elencati sopra il discorso è lo stesso.

Ok, il comando create ora funziona, ma cosa fa?

Una volta indicato al comando create dove creare il progetto, dovete semplicemente aprire la cartella generata ( nel mio caso sarà c:\apps\nomeapp ). Troverete tutti i files necessari per generare la vostra Phonegap App per Android.

Ora non vi resta che aprire Eclipse, seguire le istruzioni indicate sulla pagina di Phonegap, Getting started per Android.


Elenco links utili:
Android SDK: http://developer.android.com/sdk/index.html
java sdk: http://www.oracle.com/technetwork/java/javase/downloads/jdk7-downloads-1880260.html
Apache Ant: http://ant.apache.org/bindownload.cgi
Phonegap per Android: come iniziare: http://docs.phonegap.com/en/2.5.0/guide_getting-started_android_index.md.html#Getting%20Started%20with%20Android
Aggiungere alle variabili di sistema: http://stackoverflow.com/questions/1678520/javac-not-working-in-windows-command-prompt
far funzionare il comando create di phonegap per android: http://simonmacdonald.blogspot.ca/2012/11/getting-create-command-to-work-on.html