Tizen 上的 HTML5 功能

1 为什么在 Tizen 上使用 HTML5?

W3C(万维网联盟)在 2008年就已经开始制定 HTML5 标准规范。 当时只有 PC 浏览器实施了部分的 HTML5 工作草案。 那时候只有为数不多的移动设备支持基于 web 的应用程序。 这种情况的主要原因是:

  • HTML 4.01 不足于为移动设备创建用户界面
  • 设备性能还不够好,无法基于 web 的应用程序提供流畅的用户体验
  • HTML 4.01 没有提供与本机 API 兼容的 web API

在 2010 年,随着 W3C 发布新的 HTML5 草案,产生了一批卓有前途的 API:如 Web工作者,Web 存储,Web 套接字和地理位置 API 等。 开发人员开始清楚地意识到 HTML5 对移动式应用程序的开发可能是一个很好的替代。 现在,移动设备的质量已经能够以与本机应用程序几乎相同的速度有效地运行 Web 浏览器。 基于 HTML5 的 web 应用程序的最显著优点是跨平台体验。

示例应用程序的屏幕快照

示例应用程序屏幕快照

2 先决条件

示例应用程序利用以下 HTML5 API:Web 套接字,Web 存储,Web 工作者。 也有的代码示例演示如何在 Tizen 上使用 HTML5 视频元素和 API。 该示例应用程序基于 jQuery Mobile 1.2.0 框架,允许用户创建带有直观一致用户界面,高度可扩展的 Web 应用程序。 若要使用 jQuery Mobile,应用程序必须包括 jQuery 1.8.0 库。 示例应用程序在 Tizen SDK 2.0.0a2 上通过测试

 

在 jQuery 应用程序中可以将 JSON 对象序列化为使用 JSON.stringify(object) 方法的字符串。 要反序列化字符串到 JSON 对象,使用:$.parseJSON(string); 

所以,建议用以下视区设置对 360 × 640 分辨率使用较低的 dpi:

对以上代码的 target-densitydpi 没有明确的值。 这与开发人员设置 target-densitydpi=medium-dpi 是一样的情况。

每个 jQuery Mobile 项目中的视区设置是至关重要的。 目前 Tizen 设备的当前最大分辨率为 720p,即 720 x 1280。 不幸的是,以这样的设置, jQuery Mobile 的用户界面会相当小,而且触摸屏元素的 UX 也很差。 720p 分辨率的视口元素配置。
提示
jQuery Mobile 的框架专门用来通过 HTTP 协议处理来自 HTTP 服务器的网页,而 Tizen 的应用程序设计用于使用 FILE 协议。 因此,我们建议关闭 AJAX 页面请求,因为它们无法与 FILE 协议协同工作。 这种差异仅适用于 jQuery 移动框架的页面过渡效果,而并非适用于所有的 AJAX 请求。

3 Tizen 上的特定 HTML5 功能

HTML5 不仅推出了 HTML 新标签,而且也推出了新的 web API。 Web Api 是在各个 W3C 文档中定义的。 附加的示例显示如何利用 Tizen 上的一些 W3C Web API。

Web 套接字允许基于浏览器的应用程序能够与支持 WS 或 WSS 协议的服务器进行全双工通信。 HTML4.01 介绍的 AJAX 是一个单向通信 API。 使用 AJAX,只有客户端能够向服务器发送请求。 比方说开发人员需要创建一个聊天应用程序,这样做的唯一方法就是通过 XHR 轮询请求。 现在有了 Web 套接字,开发人员就可以设置在从服务器接收到新邮件时便立即触发侦听器事件。

Web 存储 是浏览器内置的存储区域。 它可以用于存储 web 应用程序或 web 站点的键/值对等。 存储区域可以分为:

  • 本地存储 — — 此存储可用于任何应用程序,无论浏览器会话。 从 Tizen 设备卸载 web 应用程序时,它便被删除。
  • 会话存储 — — 只为持久会话保留的存储

在本地存储对于在文件系统中存储的 cookie 或数据而言是一个很好的替代。 在 Tizen 上,本地存储区的大小限于每个应用程序 2.49 MB,而对会话存储则没有任何限制。 Web 存储只接受字符串值。 你需要将 JSON 对象序列化为字符串以使用网络存储将其存储,并在检索式将它们反序列化。

Web 工作人员 是基于 Web 的应用程序解决方案,用于在网络环境中使用多线程功能。 它们主要用于 CPU 密集型任务,以防止应用程序用户界面无响应的情况。 . 下面是使用 web 工作人员的一个示例: 开发人员以一个 JSON 对象初始化 web 工作人员、 web 工作人员在一个单独的事件循环中执行一些计算,然后返回结果。

触摸事件 被游戏开发商广泛应用于在 2D 表面创建高度响应的网页游戏。 W3C 规范中定义了 3 个基本触摸事件:

  • touchstart: 手指放在 DOM 元素上。
  • touchmove: 手指沿 DOM 元素拖动。
  • touchend: 手指从 DOM 元素移开。

触控事件允许开发人员检测在选定的 HTML 元素上,屏幕和用户的手指之间存在多少触摸点 。 有可能检测到多达 3 个触摸点。

HTML5 还借助视频标签和 AV API 支持在 Web 应用程序中嵌入视频和音频内容..

本文下面显示的 JavaScript 代码段 (未包括 HTML 代码)可以复制黏贴到任何应用程序中。

a) Web 套接字

网上有一个免费的 web 套接字服务器可用 - ws://echo.websocket.org available over WS protocol or WSS protocol - wss://echo.websocket.org。 我们将它们用于我们的示例 web 套接字应用程序。 示例 Tizen 应用程序将使用 WSS 协议连接到 wss://echo.websocket.org 回显服务器并发送邮件。 我们创建 JavaScript 模块 tizenWebSocket 以发送邮件。

// JS module to handle web socket communication
var tizenWebSocket = function(options) {
    var states = {
        CONNECTED : 1,
        DISCONNECTED : 2,
        ERROR : 3
    };
    var state = states.DISCONNECTED;
    var wsUri =  "wss://echo.websocket.org/";
    var output = function(txt) {
        console.log(txt);
    };
    var websocket;
    return {
        connect : function(callback) {
            var that = this;
            websocket = new WebSocket(wsUri);
            websocket.onopen = function(evt) {
                that.onOpen(evt);
                (typeof callback === "function") ? callback() : '';
            };
            websocket.onclose = function(evt) {
                that.onClose(evt);
            };
            websocket.onmessage = function(evt) {
                that.onMessage(evt);
            };
            websocket.onerror = function(evt) {
                that.onError(evt);
            };
        },
        disconnect : function() {
            websocket.close();
        },
        onOpen : function() {
            output("CONNECTED");
            state = states.CONNECTED;
        },
        onClose : function() {
            output("DISCONNECTED");
            state = states.DISCONNECTED;
        },
        onMessage : function(evt) {
            output("RECEIVED: " + evt.data);
        },
        onError : function(evt) {
            output("ERROR: " + evt.data);
            state = states.ERROR;
        },

        /**
         * Sends message via web socket
         *
         * @param txt {String} message to be sent
         * @returns {Boolean} true if successfully sent message, false otherwise
         */
        send : function(txt) {
            if (state === states.CONNECTED) {
                output("SEND: " + txt);
                websocket.send(txt);
                return true;
            } else {
                console.error("Unable to send message");
                return false;
            }
        }

    };
}();
// connects with WS/WSS server
tizenWebSocket.connect(
    function() {
    // sends Hello message only when connected
    tizenWebSocket.send('Hello');
    }
);

 

b)Web 存储

此示例应用程序演示如何使用 Web 存储功能。 用户可以在名单中添加和删除好友。 也可以清除列表。 示例应用程序使用四个基本的本地存储操作: 添加项目、读取和列出所有项目、删除项目,和清除整个本地存储。 在下面的示例中,2 个项目被添加到本地存储并显示。

var item = { name : "Tom"};
var key = (new Date()).getTime();
localStorage.setItem(key, JSON.stringify(item));
var item = { name : "Carol" };
var key = (new Date()).getTime();
localStorage.setItem(key, JSON.stringify(item));

for ( var i = 0; i < localStorage.length; i++) {
    var key = localStorage.key(i);
    var element = $.parseJSON(localStorage.getItem(key));
    console.log(element);
}

 

c)Web 工作者

Web 工作者示例实时计算质数。 每当计算新的质数并将其传递到主要事件循环时,相应的 DOM 元素便被更新。 介绍这个数据流是因为 Web 工作者没有权限访问 DOM。 webWorker.js 代码:

this.addEventListener('message', function(msg) {
// in case of any message from main application environment run()
// function is invoked
    run();
}, false);

function run() {
    var n = 1;
    search: while (true) {
        n += 1;
        for ( var i = 2; i <= Math.sqrt(n); i += 1)
            if (n % i == 0)
                continue search;
        // found a prime!
        this.postMessage(n);
    }
}

下面的 JavaScript 代码是主事件循环的代码:

var worker = new Worker('./webWorker.js');
// in this event worker returns data
worker.addEventListener('message', function(msg) {
    console.log(msg.data);
}, false);
// empty message send to worker in order to start calculations
worker.postMessage();

 

d)触摸事件

触控事件识别多少用户手指接触了由用户选定的特定 DOM 元素。 由于触摸事件主要用于支持触摸功能的设备,下面的示例代码在普通的 PC 浏览器上不工作。 为利用触摸事件,开发了特殊的 JavaScript 模块。

touchEvents = function($) {
    var touch;
    return {
        setElement : function(id) {
            touch = document.getElementById(id);
        },
        bindEvents : function() {
            /**
             * Currently there is no possibility to bind touch events with
             * jQuery.bind method so we need to use pure ECMAScript
             * approach.
             */
            touch.addEventListener('touchmove', function(ev) {
                console.log('YES');
            });
            touch.addEventListener('touchstart', function(ev) {
                var touchPoints = ev.targetTouches.length;
                if (touchPoints >= 3) {
                    console.log('3 or more fingers');
                } else {
                    console.log(touchPoints);
                }
            }, false);

            touch.addEventListener('touchend', function(ev) {
                console.log('0 fingers');
                console.log('No');
            }, false);
        }
    }
}($);
// here we add myTouch element to body
$('body').append('
'); // here we attach touch events to element touchEvents.setElement('myTouch');

 

e)多媒体支持

HTML5 视频标签是在 Tizen web 应用程序中嵌入多媒体内容的一项强大的工具。 此示例中,视频文件使用的容器是 MP4。 视频基本流使用 H.264 编解码器编码,而音频基本流使用 AAC 音频编码。 在示例应用程序中,tizenVideo 模块采用 HTML5 视频元素 API 来操作视频。

要嵌入视频内容的 HTML5 代码:

下面的 tizenVideo 模块和示例代码回放上述视频文件。

tizenVideo = function($) {
    var videoInstance;
    var that = this;
    return {
        getVideoInstance : function() {
            return videoInstance;
        },
        setVideoInstance : function(id) {
            videoInstance = document.getElementById(id);
        },
        play : function() {
            videoInstance.play();
        },
        pause : function() {
            videoInstance.pause();
        },
        stop : function() {
            try {
                videoInstance.pause();
                videoInstance.currentTime = 0;
            } catch (e) {
                logger.err("Unable to stop the Video!");
            }
        },
        /**
         * Key binders method
         *
         * @param elements {Object} JSON stores all available keys for which the actions can be hooked
         */
        bind : function(elements) {
            var that = this;
            elements.play.unbind().bind({
                click : function(event) {
                    event.preventDefault();
                    that.play();
                }
            });
            elements.stop.unbind().bind({
                click : function(event) {
                    event.preventDefault();
                    that.stop();
                }
            });
            elements.pause.unbind().bind({
                click : function(event) {
                    event.preventDefault();
                    that.pause();
                }
            });
            elements.fullscreen.unbind().bind({
                click : function(event) {
                    event.preventDefault();
                    that.fullscreen(true);
                }
            });
        },
        /**
         * Method used to turn on/off fullscreen mode for video
         *
         * @param flag {Boolean} If true we turn one fullscreen mode otherwise we turn it off
         */
        fullscreen : function(flag) {
            var that = this;
            if (flag) {
                videoInstance.webkitEnterFullscreen();
                /**
                 * When we enter fullscreen mode we should handle some event to allow user
                 * to leave fullscreen mode, because browser doesn't do it automatically.
                 * We use either swipeLeft or swipeRight for this.
                 */
                $(document).bind('webkitfullscreenchange', function() {
          $('html').bind({
                        swipeleft : function() {
                            logger.info("In FullScreen swipe left");
                            that.fullscreen(false);
                        },
                        swiperight: function() {
                            logger.info("In FullScreen swipe right");
                            that.fullscreen(false);
                        }
                    });
                });
            } else {
                document.webkitCancelFullScreen();
                $('html').unbind();
            }
        },
        /**
         * Method used to set callbacks
         *
         * @param errorCB {Function} Callback invoked in case of playback error
         * @param endCB {Function} Callback invoked in case of playback end
         */
        setCallbacks : function(errorCB, endCB) {
            videoInstance.addEventListener('ended', endCB);
            videoInstance.addEventListener('error', errorCB);
        }

    }
}($);
// here we bind tizenVideo module with video element container
// that has id = video
tizenVideo.setVideoInstance('video');
// starts playback of video content
tizenVideo.play();
提示 Tizen 在 WebKit 浏览器上启动 Web 应用程序。 有专门的方法可用来以全屏模式启动视频播放:videoDOMElement.webkitEnterFullscreen();若要退出全屏模式,开发人员应该使用:document.webkitCancelFullScreen();

请牢记主要区别是对不同的浏览器中的 HTML5 视频标签实现的编码解码器支持。 示例应用程序中的视频文件与 Tizen WebKit web 浏览器兼容,但它也曾经测试可在谷歌 Chrome 21 上启动

4 总结

从上述示例中您可能注意到可以在 Tizen 的 Web 应用程序中以在您的网站上大致相同的方式使用 HTML5 的 API。 我相信,如果你已经创建了一些有趣的 HTML5 网页应用程序,你可以轻松地将它们转换为 Tizen 的 Web 应用程序。

文件附件: