lunedì 7 luglio 2014

Lista comandi Google Now

Oggi mi è arrivato l'orologio di LG con Android Wear. Per l'occasione e perché ne avrò bisogno ecco la lista dei comandi Google Now che ho trovato qua e la su internet:

Inizia nuova telefonata
  • chiama [nome persona] [cognome] [tipo: cellulare, lavoro, casa, ecc..]
Invia messaggio di testo
  • invia messaggio a [nome persona] [cognome] [tipo: cellulare, lavoro, casa, ecc..] [messaggio] 
  • email a [nome persona] [cognome] [messaggio] 
Foto online di qualcosa
  • foto [soggetto: luogo, persona, oggetto, ecc..] [quando? Momento temporale o condizione ]
    Es.: foto di Roma al tramonto
Navigazione web
  • apri [indirizzo web]
  • accedi a [sito web] 
Cose nei paraggi
  • ristorante, pizzeria, pub, ecc.. vicino a me
Informazioni turistiche
  • chiesa, monumento, teatro, ecc.. [nome dell'oggetto della ricerca]
Informazioni generiche
  • quando, quanto, quanti, dove, ecc..  [richiesta]
    Es.: quando sorge il sole
  • che cos'è [oggetto] 
  • chi ha inventato [oggetto]
  • quale è il significato di [parola] 
  • chi è [nome di personaggio famoso] 
  • l'autore di [nome libro]
  • orario a [nome luogo]
  • che ore sono a [nome luogo]
  • fuso orario [nazione] 
Musica
  • ascolta [titolo canzone] 
  • come si intitola questo brano? 
  • ... (lui ascolta e ti dice che brano stai sentendo)
Informazioni meteo specifiche
  • che tempo fa [oggi, domani] [a: nome luogo]
  • [domanda] [periodo temporale]
    Es.: pioverà domani? 
Informazioni meteo generiche
  • meteo [luogo] 
Calcoli matematici somma
  • numero più numero
Calcoli matematici sottrazione
  • numero meno numero
Calcoli matematici divisione
  • numero diviso numero
Calcoli matematici moltiplicazione
  • numero moltiplicato per numero
  • numero X numero
Calcoli matematici percentuale
  • numero percento di numero
Calcoli matematici modulo
  • numero modulo numero
Calcoli matematici radice
  • radice quadrata di [numero] 
Conversioni di unità
  • numero [unità] in [unità]
    Es.: 3 litri in ettolitri
Sport classifiche
  • classifica [serie: A, B, ecc..]
Sport eventi
  • quando giocherà [nome squadra]
Sport risultati
  • chi ha vinto tra [squadra] e [squadra]
Sport domanda risultato
  • [squadra]  ha [vinto, perso] 
Programmazione di un film
  • cinema, film [nome del film] 
Film con un certo attore
  • film [nome cognome attore] 
Serie tv
  • serie tv [nome serie, attore] 
Appunti
  • ricordami di [cosa da ricordare] alle [ora e minuto] di [giorno] (oppure si può specificare: mattina, pomeriggio, sera, notte) 
  • scrivi nota [nota da scrivere]
Sveglia programmata
  • sveglia [giorno] alle [ora e minuto]
  • svegliami tra [numero] minuti
Appuntamento su calendario
  • appuntamento [giorno] alle [ora e minuto] [descrizione] 
Avvio applicazioni
  • avvia, lancia [nome applicazione] 
Voli aerei
  • volo [partenza] [destinazione] 
Pubblicazione social
  • pubblica su [google plus, twitter, facebook] [descrizione]
Navigatore
  • naviga fino a [nome città] 
  • mappa di [nome città] 
  • foto di [nome città]
  • vai a [nome città] 
  • quanto è lontano [luogo] 
  • portami a [luogo] 
  • traffico [località, nome autostrada]

Man mano che scopro nuovi comandi vocali li aggiungerò a questa lista.

venerdì 4 luglio 2014

From C# to Qt: Thread sleep

Eccomi alla prima parte della rubrica dedicata al confronto fra C# e Qt. In C# quando vogliamo mettere in pausa il thread corrente in cui ci troviamo per tot millisecondi usiamo la funzione statica: Thread.Sleep([numero di millisecondi]).
In Qt invece ci sono almeno 3 possibilità diverse:
//METODO 1:
//Usare la classe QTest
QTest::qSleep(100); // blocca l' event processing
QTest::qWait(100);  // non blocca l' event processing

//METODO 2:
//Usare QWaitCondition / QMutex
QWaitCondition waitCondition;
QMutex mutex;

waitCondition.wait(&mutex, 100);

//METODO 3:
//Oppure fare derivare la nostra classe da QThread.
class Thread : public QThread
{
public:
    static void msleep(int ms)
    {
        QThread::msleep(ms);
    }
};

Thread::msleep(100);

mercoledì 27 marzo 2013

The operation cannot be completed. “Puntatore non valido”

Se per caso vi dovesse capitare con Visual Studio 2012 di ricevere il messaggio: The operation cannot be completed. “Puntatore non valido”, quando state tentando di visualizzare un file di risorse .resx, per ripristinarlo, vi basta aprire il file incriminato con un editor di testo e rimuovere tutti gli elementi “data”, dell’xml che contengono l’attributo type="System.Resources.ResXNullRef, System.Windows.Forms".
Es. va eliminato:
<data name="lblLavoroSuLinea.Image" type="System.Resources.ResXNullRef, System.Windows.Forms">
    <value />
</data>

mercoledì 5 settembre 2012

Rimuovere elementi da una lista in maniera intelligente

Di solito quando vogliamo fare eseguire un operazione e poi rimuovere degli elementi da una lista, come facciamo?

Verrebbe naturale di fare un ciclo su ogni elemento della lista, eseguire l’operazione e rimuovere l’elemento:

foreach (Command c in itsCommands)
{        
    c.Execute();
    itsCommands.Remove(c);
}

Purtroppo però così facendo otteniamo un eccezione che ci avvisa che la collezione è stata modificata (in effetti abbiamo rimosso un elemento) e quindi l’operazione di ciclo sulla collezione non è più valida.

Come soluzione al problema si potrebbe crea un altra collezione con gli elementi da rimuovere ed eseguire un altro ciclo per eliminare i comandi eseguiti:

Commands itsCommandsForDelete = new Commands();

foreach (Command c in itsCommands)
{
    c.Execute();
    itsCommandsForDelete.Add(c);
}

foreach (Command c in itsCommandsForDelete)
{
    itsCommands.Remove(c);
}

Questa soluzione non è molto performante perchè ci obbliga ad eseguire il ciclo su ogni elemento per due volte.

Ecco una soluzione alternativa per eseguire il tutto in un solo ciclo:

while (itsCommands.Count > 0)
{
    Command c = (Command) itsCommands[0];
    itsCommands.RemoveAt(0);
    c.Execute();
}

martedì 26 giugno 2012

Carta di credito su internet

Spesso le informazioni che ci arrivano dai media e soprattutto dai telegiornali, sono storie sentite raccontare da altri, gonfiate e mal capite ed esposte che incutono paura al consumatore. Ad esempio:

E'sicuro usare la carta di credito su internet?

Il giorno prima di Pasqua ho avuto una discussione con amici di mio padre, i quali, non si fidano ad usare la carta di credito su web, perché hanno sentito al tg che non va bene e che si viene spesso e volentieri truffati.

La mia prima reazione è stata quella di tentare di rassicurarli spiegando che in realtà, esitono anche siti famosi e sicuri, nei quali si hanno vantaggi economici e si trovano prodotti altrimenti introvabili.

Un altro aspetto negativo è che questa mancanza di fiducia è alimentata dall'idea di voler tastare con mano il prodotto, prima di comprarlo.

Inoltre si ha il timore che una volta effettuato l'acquisto non ci siano garanazie nel caso arrivasse rotto o difettoso.

Per esperienza, sono anni ormai che faccio acquisti su internet e non ho mai avuto problemi. Per prima cosa se mi piace un prodotto, mi reco al primo centro commerciale per tastarmelo e provarlo. Nel caso non fosse disponibile, cerco eventuali video ed informazioni su YouTube o nei blog del settore di competenza.
Se decido di effettuare l'acquisto ci sono due strade da percorrere:

La prima è l'acquisto da siti più famosi tipo Amazon. Qui mi sento sicuro al 100% perché non ho mai avuto problemi ed inoltre quasi sempre il prezzo è nettamente inferiore rispetto ai comuni centri commerciali (per alcuni prodotti ho risparmiato anche 200 euro). Su amazon inoltre il prezzo di un prodotto è molto variabile di giorno in giorno.

E tutto semplicissimo. Mi basta accede al sito con le mie credenziali, guardare i prodotti, metterli nel carrello virtuale, completare l'acquisto fornendo il numero della carta di credito (la prima volta, poi viene memorizzata sul sito), e attendere il pacco comodo a casa in poltrona.

In caso di prodotto rotto o difettoso si hanno 30 giorni per restituirlo e farselo rimborsare. Passati i 30 giorni (ed entro 2 anni dati dalla garanzia e come qualsiasi altro prodotto acquistato in un normale negozio) bisogna cercare il più vicino centro di assistenza che si occupa della marca del prodotto acquistato (basta una piccola ricerca su Google per trovarlo).

Nel secondo caso cioè quello di siti sconosciuti ci sono un paio di regole da seguire ma niente di complicato:

- Prima di tutto dobbiamo fare una ricerca, per capire l'opinione della gente riguardo al negozio, se si sono trovati bene, in quanto tempo la merce ordinata è arrivata, se hanno avuto esperienze negative, se c'è e se è buona l'assistenza post vendita. Riassumendo è importante conoscere la reputazione online del negozio (feedback positivi e negativi).

- Bisogna confrontare l'offerta con quella di altri negozi e se è eccessivamente bassa stare molto attenti perché si tratta di una provabile trappola, o ci sono delle clausole nascoste. Molte volte ad esempio la tecnica di marketing usata è proporre un prezzo molto basso rispetto alla concorrenza, ma prima di terminare l'acquisto vi vengono richieste spese di spedizione molto alte che riportano la spesa totale allo stesso livello o superiore a quella dei concorrenti.

- Controllate che sia presente un servizio post vendita e che i numeri di telefono esitano veramente (si può contollare sul sito delle pagine bianche).

Una volta che avete appreso abbastanza informazioni e vi fidate, effettuate l'acquisto.

Se proprio vi va male denunciate l'accaduto alla polizia postale.

venerdì 27 gennaio 2012

String format .NET semplificato e naturale

Molte volte ci troviamo a dover inserire delle stringhe in una stringa più grande (di solito una frase, per notificare un messaggio all’utente dell’applicazione).
Per fare ciò usiamo il metodo “String.Format()” che accetta in input la stringa da formattare, e un array contenete le altre stringhe da inserire, al posto di segna posti speciali, costruiti con la regola: {indice dell’array}.
Es.:
MessageBox.Show(String.Format("Errore numero {0}, l'utente {1}, non ha i permessi di lettura del file
 {2}, inoltre {1}, non appartiene al ruolo {3}", new String[]{"123", "Mario", "file.txt", "admin"}));
Di solito la scrittura di questo codice avviene nella seguente maniera:
  1. Si scrive: MessageBox.Show(
  2. Si pensa al messaggio e si inizia a scriverlo: "Errore numero …
  3. Ci si accorge che il messaggio dovrà contenere dei pezzi di stringa all’interno della stringa principale.
  4. Si aggiungono i segna posto per i pezzi di stringa: numero {0}, l'utente {1}, non
  5. Completata la frase, ci si posiziona all’inizio della frase stessa.
  6. Si digita String.Format(
  7. Si va alla fine della frase e si chiude la parentesi )
Come si vede a lungo andare si perde molto tempo a compiere tale operazione e non è del tutto naturale, perché ci impegna a cercare l’inizio della frase scritta per aggiungere un pezzo di codice e a tornare alla fine di essa, per chiudere la parentesi.
Per risparmiare tempo e trovare più naturalezza nella scrittura, ho implementato la seguente classe per estendere la classe System.String:
namespace System
{
    /// <summary>
    /// Estensioni per le classi stringa
    /// </summary>
    public static class StringEx
    {
        /// <summary>
        /// Formatta la stringa
        /// </summary>
        /// <param name="pValue">Stringa</param>
        /// <param name="args">Parametri</param>
        /// <returns>Stringa formattata</returns>
        public static string Formatting(this String pValue, params object[] args)
        {
            return String.Format(pValue, args);
        }

        /// <summary>
        /// Formatta la stringa
        /// </summary>
        /// <param name="pValue">Stringa</param>
        /// <param name="format">Format provider</param>
        /// <param name="args">Parametri</param>
        /// <returns>Stringa formattata</returns>
        public static string Formatting(this String pValue, IFormatProvider format, params object[] args)
        {
            return String.Format(format, pValue, args);
        }
    }
}
Ora potere scrivere lo stesso codice dell’esempio di prima in maniera naturale, senza bisogno di tornare a cercare dove inizia la vostra Stringa:
MessageBox.Show("Errore numero {0}, l'utente {1}, non ha i permessi di lettura del file {2}, inoltre {1},
 non appartiene al ruolo {3}".Formatting(new String[] { "123", "Mario", "file.txt", "admin" }));

sabato 14 gennaio 2012

Implementare il Databindings di oggetti

Oggi mi è capitato di dover implementare il databindings di un controllo che ne era sprovvisto (il treenode). Per aggiungere il databindings ad un oggetto TreeNode, come nel mio caso, ma anche per qualsiasi altro oggetto, basta implementare l’interfaccia IBindableComponent.

In questo modo potete usare il Binding su tutte le proprietà del TreeNode; in particolare a me interessava collegare la proprietà “Name” di un mio oggetto alla proprietà “Text” di un TreeNode.

Ecco un esempio in C# dell’implementazione del databindings per la proprietà “Text” di un oggetto TreeNode:
public class TreeNodeBind : TreeNode, IBindableComponent
    {
        //Implementazione dei costruttori base
        public TreeNodeBind()
            : base()
        {
        }

        public TreeNodeBind(string text) 
            : base(text)
        {
        }

        public TreeNodeBind(string text, TreeNode[] children)
            : base(text, children)
        {
        }

        public TreeNodeBind(string text, int imgIndex, int selImgIndex) 
            : base(text, imgIndex, selImgIndex)
        {
        }

        public TreeNodeBind(string text, int imgIndex, int selImgIndex, TreeNode[] children)
            : base(text, imgIndex, selImgIndex, children)
        {
        }

        //Implementazione di IBindableComponent
        #region IBindableComponent Members

        private BindingContext _bindingContext;
        private ControlBindingsCollection _dataBindings;

        [Browsable(false)]
        public BindingContext BindingContext
        {
            get
            {
                if (_bindingContext == null)
                {
                    _bindingContext = new BindingContext();
                }
                return _bindingContext;
            }
            set
            {
                _bindingContext = value;
            }
        }

        [DesignerSerializationVisibility(DesignerSerializationVisibility.Content)]
        public ControlBindingsCollection DataBindings
        {
            get { return _dataBindings ?? (_dataBindings = new ControlBindingsCollection(this)); }
        }

        public ISite Site { get; set; }

        public event EventHandler Disposed;

        public void Dispose()
        {
            if (Disposed != null)
                Disposed(this, EventArgs.Empty);
        }

        #endregion
    }
Ora potete creare ed usare nodi di tipo TreeNodeBind che supportano il Binding:
TreeNodeBind nodoBind = new TreeNodeBind();
nodoBind.DataBindings.Add(new System.Windows.Forms.Binding("Text", oggettoConDati, "Name", true));
tree.Nodes.Add(nodoBind);