Очень часто в приложении необходимо передать данные, введенные пользователем, из одной формы в другую. В Palm WebOS для этих целей можно использовать Cookies. API для использования Cookies довольно прозрачно, как и многие другие вещи в WebOS, не требует особых умений.

В этот раз мы рассмотрим пример того, как различные сцены могут обмениваться данными.

Для начала создадим новое приложение, в нем новую сцену с названием Main и еще одну с названием Second. Как создать проект и сцену можно узнать из этой статьи.

Напишем HTML-шаблоны сцен:

views/main/main-scene.html

<div id="main" class="palm-hasheader">
<div class="palm-header">Main</div>
<div id="SecondSceneButton" x-mojo-element="Button"></div>
<div id="ExitButton" x-mojo-element="Button"></div>
<div id="counter" class="palm-body-text"></div>
</div>

views/second/second-scene.html

<div id="main" class="palm-hasheader">
     <div class="palm-header">Second Scene</div>
     <div id="CloseButton" x-mojo-element="Button"></div>
     <div id="valuetext" class="palm-body-text">Unknown value</div>
</div>

Главная сцена состоит из контейнера с заголовком, двух кнопок и текстового поля.
Вторая сцена состоит из контейнера с заголовком, кнопки и текстового поля.
Ничего сверхъестественного. 🙂

Перед тем, как написать логику, стоит ознакомиться со схемой, описывающей жизненный цикл сцены:

WebOS Scene Lifecycle

Из схемы можно узнать, что первым делом вызывается конструктор сцены, затем метод setup(), а когда сцена загрузилась, вызывается метод activate(). Также activate() вызывается при каждом появлении сцены на экране.

Что это нам даст? Посмотрим на пример кода ниже:

MainAssistant.prototype.setup = function() {
  this.controller.setupWidget("SecondSceneButton",
    {}, {label:"Second Scene"});
  this.controller.setupWidget("ExitButton",
    {}, {label:"Exit"});

  Mojo.Event.listen(this.controller.get("SecondSceneButton"),
    Mojo.Event.tap,
    this.handleSecondSceneButton.bind(this));
  Mojo.Event.listen(this.controller.get("ExitButton"),
    Mojo.Event.tap,
    this.handleExitButton.bind(this));

  this.counter = 0;
  this.counterCookie = new Mojo.Model.Cookie("counterCookie");
  this.counterCookie.put(this.counter);
}

MainAssistant.prototype.activate = function(event) {
  this.counter = this.counterCookie.get();
  this.controller.get("counter").update(this.counter);
}

MainAssistant.prototype.cleanup = function(event) {
  this.counterCookie.remove();
}

В методе setup() мы создали переменную counter, поместили ее в Cookie с названием counterCookie, а в методе activate() мы берем значение из Cookie и отображаем в текстовом поле. И каждый раз, когда форма будет активизироваться, в текстовом поле будет появляться актуальное значение из Cookie.
Метод cleanup() вызывается в конце жизненного цикла сцены и в нем мы удаляем созданную Cookie.

Теперь напишем обработчик нажатия кнопки SecondSceneButton:

MainAssistant.prototype.handleSecondSceneButton = function(event) {
  this.counter++;
  this.counterCookie.put(this.counter);
  this.controller.stageController.pushScene("second", 1);
}

В обработчике мы прибавляем единицу к переменной counter, записываем ее значение в Cookie и отображаем сцену Second.

Дальше нам необходимо получить значение в сцене Second и как-то там поиспользовать.

function SecondAssistant() {
}

SecondAssistant.prototype.setup = function() {
  this.controller.setupWidget("CloseButton",
    {}, {label:"Close"});

  Mojo.Event.listen(this.controller.get("CloseButton"),
    Mojo.Event.tap,
    this.handleCloseButton.bind(this));
  this.counterCookie = new Mojo.Model.Cookie("counterCookie");
  this.controller.get("valuetext").update(this.counterCookie.get());
}

SecondAssistant.prototype.handleCloseButton = function(event) {
  var value = this.counterCookie.get();
  value++;
  this.counterCookie.put(value);
  this.controller.stageController.popScene();
}

В методе setup() сцены мы создаем объект Cookie, получаем сохраненное значение и отображаем его в текстовом поле.

В обработчике нажатия кнопки мы берем значение Cookie, прибавляем к нему единицу и записываем обратно в Cookie. Затем закрываем сцену.

После закрытия сцены Second будет отображена главная сцена Main и при активации вызовется метод activate(), в котором измененное значение снова появится в текстовом поле.

После всего наше приложение будет выглядеть так:

WebOS Cookies Test GUI

Скачать исходный код примера.

Previous ArticleNext Article
Технический директор IT-Dimension, компании-разработчика кросс-платформенного программного обеспечения

Leave a Reply

Your email address will not be published. Required fields are marked *

О.

Определяем подключение к сети в Palm WebOS

В этот раз речь пойдет об использовании сервиса Connection Manager, который позволяет определить состояние подключения к сети. В WebOS существует возможность узнать состояние подключения к:

  • Bluetoot
  • Wi-Fi
  • WAN

Использовать сервис Connection Manager можно как для одноразового получения состояния сетевых подключений, так и для подписки на уведомление об изменении состояния подключений.Для определения текущего состояния сетевых соединений необходимо вызвать метод serviceRequest() объекта-контроллера, в который передать идентификатор сервиса Connection Manager, а также JSON-объект с параметрами вызова сервиса. Параметры вызова сервиса могут быть такими:

  • method – обязательный параметр. У сервиса Connection Manager есть всего один метод – getstatus.
  • parameters – JSON-объект, который будет передан в качестве параметра методу getstatus. У этого объекта есть одно значимое булевое свойство – subscribe. Если свойство subscribe имеет значение true, то будет выполнена подписка на уведомления об изменении состояния подключений. При каждом изменении состояния будет вызвана наша callback-функция.
  • onSuccess – callback-функция, вызываемая при успешном завершении запроса состояния подключений.
  • onFailure – callback-функция, вызываемая если запрос состояния подключений завершился с ошибкой.

Пример вызова Connection Manager

this.controller.serviceRequest('palm://com.palm.connectionmanager', {
    method: 'getstatus',
    parameters: {subscribe:true},
    onSuccess: this.handleOKResponse.bind(this),
    onFailure: this.handleErrResponse
});

Теперь рассмотрим более детально callback-функции, вызываемые при завершении запроса состояния соединения.

onSuccess

Callback-функция onSuccess принимает в качестве параметра объект, содержащий информацию о состоянии подключений. Этот объект содержит такие поля:

Свойство Тип Описание
errorCode integer Код завершения операции проверки статуса подключения.
errorText string Описание ошибки если errorCode содержит ненулевое значение.
isInternetConnectionAvailable boolean Содержит значение true если есть подключение к Internet.
returnValue boolean true если была выполнена подписка на уведомление об изменении состояния подключений. Может быть получено только первый раз при выполнении подписки.
wifi object Содержит информацию о подключении к Wi-Fi.
btpan object Содержит информацию о подключении к Bluetooth.
wan object Содержит информацию о подключении к WAN.

Теперь посмотрим что можно узнать о подключениях:

Свойства объекта btpan
Свойство Тип Описание
ipAddress string IP-адрес в сети Bluetooth PAN.
panUser string Содержит название клиента сети Bluetooth PAN, подключенного к устройству.
state string Имеет значение “connected” если соединение есть и “disconnected” если соединения нет.
Свойства объекта wifi
Свойство Тип Описание
bssid string Basic service set identifier (BSSID) точки доступа.
ipAddress string IP-адрес в сети Wi-Fi.
ssid string Service set identifier (BSSID) точки доступа.
state string Имеет значение “connected” если соединение есть и “disconnected” если соединения нет.
Свойства объекта wan
Свойство Тип Описание
ipAddress string IP-адрес в сети WAN.
network string Сожет иметь значения: “unknown”, “unusable”, “gprs”, “edge”, “umts”, “hsdpa”, “1x”, or “evdo.”
Внимание: значение “unusable” используется в случае если интерфейс WAN подключен, но данніе не могут быть отправлены или получены по каким-либо причинам.
state string Имеет значение “connected” если соединение есть и “disconnected” если соединения нет.

onFailure

Callback-функция onFailure принимает в качетве параметра объект, содержащий информацию об ошибке. Свойства этого объекта приведены ниже:

Свойство Тип Описание
errorCode string Строка, содержащая код ошибки:

  1. Неизвестная ошибка.
  2. Ошибка подписки на уведомления о состоянии соединения.
errorText string Строка, содержащая описание ошибки.
returnValue boolean false

Пример использования

С теоретической частью мы закончили. Теперь рассмотрим пример.

Создадим новый проект и в нем сцену с названием first.

app/views/first/first-scene.html

<div id="SubscribeButton" x-mojo-element="Button"></div>
<div id="area-to-update"></div>
<div class="palm-inline-error" style="display:none" id="ErrorMessage">
<div class="error-message">Unable to subscribe to Connection Manager's event.</div>
</div>

<div class="palm-group">
  <div class="palm-group-title">Wi-Fi</div>
  <div class="palm-list">
    <div class="palm-row first">
      <div class="palm-row-wrapper textfield-group" x-mojo-focus-highlight="true">
        <div class="title">
          <div class="label">IP Address</div>
          <div id="WiFiIPTextBox" x-mojo-element="TextField"></div>
        </div>
      </div>
    </div>
    <div class="palm-row">
      <div class="palm-row-wrapper textfield-group" x-mojo-focus-highlight="true">
        <div class="title">
          <div class="label">BSSID</div>
          <div id="WiFiBSSIDTextBox" x-mojo-element="TextField"></div>
        </div>
      </div>
    </div>
    <div class="palm-row">
      <div class="palm-row-wrapper textfield-group" x-mojo-focus-highlight="true">
        <div class="title">
          <div class="label">SSID</div>
          <div id="WiFiSSIDTextBox" x-mojo-element="TextField"></div>
        </div>
      </div>
    </div>
    <div class="palm-row last">
      <div class="palm-row-wrapper textfield-group" x-mojo-focus-highlight="true">
        <div class="title">
          <div class="label">State</div>
          <div id="WiFiStateTextBox" x-mojo-element="TextField"></div>
        </div>
      </div>
    </div>
  </div>
</div>

<div class="palm-group">
  <div class="palm-group-title">Bluetooth</div>
  <div class="palm-list">
    <div class="palm-row first">
      <div class="palm-row-wrapper textfield-group" x-mojo-focus-highlight="true">
        <div class="title">
          <div class="label">IP Address</div>
          <div id="BTPanIPTextBox" x-mojo-element="TextField"></div>
        </div>
      </div>
    </div>
    <div class="palm-row">
      <div class="palm-row-wrapper textfield-group" x-mojo-focus-highlight="true">
        <div class="title">
          <div class="label">User</div>
          <div id="BTPanUserTextBox" x-mojo-element="TextField"></div>
        </div>
      </div>
    </div>
    <div class="palm-row last">
      <div class="palm-row-wrapper textfield-group" x-mojo-focus-highlight="true">
        <div class="title">
          <div class="label">State</div>
          <div id="BTPanStateTextBox" x-mojo-element="TextField"></div>
        </div>
      </div>
    </div>
  </div>
</div>

<div class="palm-group">
  <div class="palm-group-title">WAN</div>
  <div class="palm-list">
    <div class="palm-row first">
      <div class="palm-row-wrapper textfield-group" x-mojo-focus-highlight="true">
        <div class="title">
          <div class="label">IP Address</div>
          <div id="WanIPTextBox" x-mojo-element="TextField"></div>
        </div>
      </div>
    </div>
    <div class="palm-row">
      <div class="palm-row-wrapper textfield-group" x-mojo-focus-highlight="true">
        <div class="title">
          <div class="label">Network</div>
          <div id="WanNetworkTextBox" x-mojo-element="TextField"></div>
        </div>
      </div>
    </div>
    <div class="palm-row last">
      <div class="palm-row-wrapper textfield-group" x-mojo-focus-highlight="true">
        <div class="title">
          <div class="label">State</div>
          <div id="WanStateTextBox" x-mojo-element="TextField"></div>
        </div>
      </div>
    </div>
  </div>
</div>

app/assistants/first-assistant.js

function FirstAssistant() {
}

FirstAssistant.prototype.setup = function() {
    this.controller.setupWidget('SubscribeButton', {}, {label:'Subscribe'});
    this.controller.setupWidget("BTPanIPTextBox",
        {
            modelProperty: 'originalValue'
        },
        this.btpanIPModel =
        {
            originalValue: '',
            disabled: true
        });
    this.controller.setupWidget("BTPanUserTextBox",
        {
            modelProperty: 'originalValue'
        },
        this.btpanUserModel =
        {
            originalValue: '',
            disabled: true
        });
    this.controller.setupWidget("BTPanStateTextBox",
        {
            modelProperty: 'originalValue'
        },
        this.btpanStateModel =
        {
            originalValue: '',
            disabled: true
        });

    this.controller.setupWidget("WiFiIPTextBox",
        {
            modelProperty: 'originalValue'
        },
        this.wifiIPModel =
        {
            originalValue: '',
            disabled: true
        });
    this.controller.setupWidget("WiFiBSSIDTextBox",
        {
            modelProperty: 'originalValue'
        },
        this.wifiBSSIDModel =
        {
            originalValue: '',
            disabled: true
        });
    this.controller.setupWidget("WiFiSSIDTextBox",
    {
            modelProperty: 'originalValue'
        },
        this.wifiSSIDModel =
        {
            originalValue: '',
            disabled: true
        });
    this.controller.setupWidget("WiFiStateTextBox",
        {
            modelProperty: 'originalValue'
        },
        this.wifiStateModel =
        {
            originalValue: '',
            disabled: true
        });

    this.controller.setupWidget("WanIPTextBox",
        {
            modelProperty: 'originalValue'
        },
        this.wanIPModel =
        {
            originalValue: '',
            disabled: true
        });
    this.controller.setupWidget("WanNetworkTextBox",
        {
            modelProperty: 'originalValue'
        },
        this.wanNetworkModel =
        {
            originalValue: '',
            disabled: true
        });
    this.controller.setupWidget("WanStateTextBox",
        {
            modelProperty: 'originalValue'
        },
        this.wanStateModel =
        {
            originalValue: '',
            disabled: true
        });

    Mojo.Event.listen(this.controller.get('SubscribeButton'),
        Mojo.Event.tap, this.handleSubscribeButton.bind(this));
}

FirstAssistant.prototype.handleSubscribeButton = function(){
    this.controller.serviceRequest('palm://com.palm.connectionmanager', {
        method: 'getstatus',
        parameters: {subscribe:true},
        onSuccess: this.handleOKResponse.bind(this),
        onFailure: this.handleErrResponse
    });
}

FirstAssistant.prototype.handleOKResponse = function(response){
    this.controller.get('ErrorMessage').hide();
    this.controller.get('ErrorMessage').setStyle({visibility:'hidden'});

    this.btpanStateModel.originalValue = response.btpan.state;
    this.btpanIPModel.originalValue = response.btpan.ipAddress;
    this.btpanUserModel.originalValue = response.btpan.panUser;
    this.controller.modelChanged(this.btpanStateModel);
    this.controller.modelChanged(this.btpanIPModel);
    this.controller.modelChanged(this.btpanUserModel);

    this.wifiStateModel.originalValue = response.wifi.state;
    this.wifiIPModel.originalValue = response.wifi.ipAddress;
    this.wifiSSIDModel.originalValue = response.wifi.ssid;
    this.wifiBSSIDModel.originalValue = response.wifi.bssid;
    this.controller.modelChanged(this.wifiStateModel);
    this.controller.modelChanged(this.wifiIPModel);
    this.controller.modelChanged(this.wifiSSIDModel);
    this.controller.modelChanged(this.wifiBSSIDModel);

    this.wanStateModel.originalValue = response.wan.state;
    this.wanIPModel.originalValue = response.wan.ipAddress;
    this.wanNetworkModel.originalValue = response.wan.network;
    this.controller.modelChanged(this.wanStateModel);
    this.controller.modelChanged(this.wanIPModel);
    this.controller.modelChanged(this.wanNetworkModel);
}

FirstAssistant.prototype.handleErrResponse = function(response){
    this.controller.get('ErrorMessage').show();
    this.controller.get('ErrorMessage').setStyle({visibility:'visible'});
}

FirstAssistant.prototype.cleanup = function(event) {
    Mojo.Event.stopListening(this.controller.get("SubscribeButton"),
        Mojo.Event.tap, this.handleSubscribeButton);
}

Сцена содержит кнопку, при нажатии на которую приложение осуществляет подписку на уведомления об изменении состояния сетевых подключений.

Также сцена содержит три группы контролов (текстовых полей), в которых, по приходу уведомления, будет отображаться информация о подключениях.

WebOS Connection Manager Test

В обработчике onSuccess мы получаем значения всех полей из объектов wan, wifi и btpan и отображаем их в соответствующих текстовых полях.

В эмуляторе валидной будет информация только о подключении к Wi-Fi. Другие сетевые подключения на данный момент не доступны под эмулятором.

Скачать исходный код примера.

Д.

Доступно Palm Mojo SDK v1.3.5 – Инструментарий разработки для Palm WebOS

Вышлв новая версия инструментарий разработки для Palm WebOS – Mojo SDK v1.3.5

Из полезных нововведений:

  • Возможность установки приложений в раздел media
  • Поддержка эмулятором сочитаний клавиш для симуляции поворота экрана и встряхивания
  • Программный интерфейс для получения состояния акселерометра с высокой скоростью.
  • Куча багфиксов

Из неприятных моментов – поддержка Windows XP x64 и Ubuntu x64 довольно корявая.