Passaggio 4: apri i link esterni con un componente WebView

In questo passaggio scoprirai:

  • Come mostrare contenuti web esterni all'interno della tua app in modo sicuro e in una sandbox.

Tempo stimato per completare questo passaggio: 10 minuti.
Per visualizzare un'anteprima di ciò che dovrai completare in questo passaggio, vai in fondo a questa pagina ↓.

Scopri di più sul tag WebView

Alcune applicazioni devono presentare contenuti web esterni direttamente all'utente, ma mantenerli all'interno dell'esperienza con l'applicazione. Ad esempio, un aggregatore di notizie potrebbe voler incorporare le notizie di siti esterni con tutta la formattazione, le immagini e il comportamento del sito originale. Per questi e altri utilizzi, le app di Chrome dispongono di un tag HTML personalizzato chiamato webview.

L'app Todo che utilizza una webview

Implementare il tag WebView

Aggiorna l'app To Do per cercare gli URL nel testo dell'elemento della lista di cose da fare e creare un link ipertestuale. Se fai clic sul link, si apre una nuova finestra dell'app Chrome (non una scheda del browser) con un componente WebView che mostra i contenuti.

Aggiorna autorizzazioni

In manifest.json, richiedi l'autorizzazione webview:

"permissions": [
  "storage",
  "alarms",
  "notifications",
  "webview"
],

Creare una pagina di incorporamento di webview

Crea un nuovo file nella radice della cartella del progetto e denominalo webview.html. Questo file è una pagina web di base con un tag <webview>:

<!DOCTYPE html>
<html>
<head>
  <meta charset="utf-8">
</head>
<body>
  <webview style="width: 100%; height: 100%;"></webview>
</body>
</html>

Analizza gli URL negli elementi della lista di cose da fare

Al termine di controller.js, aggiungi un nuovo metodo denominato _parseForURLs():

  Controller.prototype._getCurrentPage = function () {
    return document.location.hash.split('/')[1];
  };

  Controller.prototype._parseForURLs = function (text) {
    var re = /(https?:\/\/[^\s"<>,]+)/g;
    return text.replace(re, '<a href="$1" data-src="$1">$1</a>');
  };

  // Export to window
  window.app.Controller = Controller;
})(window);

Ogni volta che viene trovata una stringa che inizia con "http://" o "https://", viene creato un tag di ancoraggio HTML per avvolgere l'URL.

Trova showAll() in controller.js. Aggiorna showAll() per eseguire l'analisi dei link utilizzando il metodo _parseForURLs() aggiunto in precedenza:

/**
 * An event to fire on load. Will get all items and display them in the
 * todo-list
 */
Controller.prototype.showAll = function () {
  this.model.read(function (data) {
    this.$todoList.innerHTML = this.view.show(data);
    this.$todoList.innerHTML = this._parseForURLs(this.view.show(data));
  }.bind(this));
};

Ripeti la stessa operazione per showActive() e showCompleted():

/**
 * Renders all active tasks
 */
Controller.prototype.showActive = function () {
  this.model.read({ completed: 0 }, function (data) {
    this.$todoList.innerHTML = this.view.show(data);
    this.$todoList.innerHTML = this._parseForURLs(this.view.show(data));
  }.bind(this));
};

/**
 * Renders all completed tasks
 */
Controller.prototype.showCompleted = function () {
  this.model.read({ completed: 1 }, function (data) {
    this.$todoList.innerHTML = this.view.show(data);
    this.$todoList.innerHTML = this._parseForURLs(this.view.show(data));
  }.bind(this));
};

Infine, aggiungi _parseForURLs() a editItem():

Controller.prototype.editItem = function (id, label) {
  ...
  var onSaveHandler = function () {
    ...
      // Instead of re-rendering the whole view just update
      // this piece of it
      label.innerHTML = value;
      label.innerHTML = this._parseForURLs(value);
    ...
  }.bind(this);
  ...
}

Sempre in editItem(), correggi il codice in modo che utilizzi il innerText dell'etichetta anziché il innerHTML dell'etichetta:

Controller.prototype.editItem = function (id, label) {
  ...
  // Get the innerHTML of the label instead of requesting the data from the
  // Get the innerText of the label instead of requesting the data from the
  // ORM. If this were a real DB this would save a lot of time and would avoid
  // a spinner gif.
  input.value = label.innerHTML;
  input.value = label.innerText;
  ...
}

Apri una nuova finestra contenente WebView

Aggiungi un metodo _doShowUrl() a controller.js. Questo metodo apre una nuova finestra dell'app di Chrome tramite chrome.app.window.create() con webview.html come origine della finestra:

  Controller.prototype._parseForURLs = function (text) {
    var re = /(https?:\/\/[^\s"<>,]+)/g;
    return text.replace(re, '<a href="$1" data-src="$1">$1</a>');
  };

  Controller.prototype._doShowUrl = function(e) {
    // only applies to elements with data-src attributes
    if (!e.target.hasAttribute('data-src')) {
      return;
    }
    e.preventDefault();
    var url = e.target.getAttribute('data-src');
    chrome.app.window.create(
     'webview.html',
     {hidden: true},   // only show window when webview is configured
     function(appWin) {
       appWin.contentWindow.addEventListener('DOMContentLoaded',
         function(e) {
           // when window is loaded, set webview source
           var webview = appWin.contentWindow.
                document.querySelector('webview');
           webview.src = url;
           // now we can show it:
           appWin.show();
         }
       );
     });
  };

  // Export to window
  window.app.Controller = Controller;
})(window);

Nel callback chrome.app.window.create(), nota come l'URL del webview viene impostato tramite l'attributo del tag src.

Infine, aggiungi un listener di eventi di clic all'interno del costruttore Controller per chiamare doShowUrl() quando un utente fa clic su un link:

function Controller(model, view) {
  ...
  this.router = new Router();
  this.router.init();

  this.$todoList.addEventListener('click', this._doShowUrl);

  window.addEventListener('load', function () {
    this._updateFilterState();
  }.bind(this));
  ...
}

Avvia l'app To Do completata

Hai completato il passaggio 4. Se ricarichi l'app e aggiungi un elemento della lista di cose da fare con un URL completo che inizia con http:// o https://, dovresti visualizzare qualcosa di simile a quanto segue:

Per ulteriori informazioni

Per informazioni più dettagliate su alcune delle API introdotte in questo passaggio, consulta:

Vuoi andare al passaggio successivo? Vai al passaggio 5: aggiungi immagini dal web »