首頁

2013年6月10日 星期一

*Android设计模式--之策略模式 *(建造者模式)&*进行Android单元测试***~!

** *Android设计模式--*
*之策略模式 **~!*(建造者模式)&**
进行Android单元测试***~!

* 1 public abstract class Animation implements Cloneable { 2     Interpolator mInterpolator; 3     // 通过set方法注入    
4     public void
setInterpolator(Interpolator i) { 5          mInterpolator = i; 6      } 7   8     public boolean getTransformation(long currentTime,

Transformation outTransformation) { 9         // ... ... 10         // 具体调用
11         final float interpolatedTime =
mInterpolator.getInterpolation

(normalizedTime); 12         applyTransformation(interpolatedTime, outTransformation); 13        // ... ...
14
    } 15   16      // 缺省实现,是个小技巧,顺便提下,这个不是重点
17      protected void
ensureInterpolator() { 18          if (mInterpolator == null) { 19              mInterpolator = new AccelerateDecelerateInterpolator(); 20          } 21      } 22   23 }                                  *


*策略模式其实特别简单(听到这句话,
大家是不是心里一下子放松了?)。
比如排序,官方告诉大家我这里有一个
排序的接口ISort的sort()方法,然后民间
各尽其能,实现这个
排序的方法:冒泡,快速,堆等等。
这些方法就是“不同的策略”。
然后,某个模块下,需要一个排序方法,
但是暂时不能指定具体的sort方法
(出于扩展的考虑),就需 要使
用ISort接口了。
最后,具体什么场景下,传入什么具体的
sort方法,实现灵活的排序。
这就是策略模式!
下面,我们分析Android中的动画是如何使
用策略模式的。
1. 意图
定义一系列的算法,把它们一个个封装起来,
并且使它们可互相替换。
策略模式使得算法可独立于使用它的
客户而变化。
2. 结构图和代码
Animation不同动画的实现,主要是依
靠Interpolator的不同实现而变。
  
定义接口Interpolator:
复制代码
 1 package android.animation; 
 2   
 3 /** 
 4  * A time interpolator defines the rate 
of change of an animation. This allows 
animations 
 5  * to have non-linear motion, such as 
acceleration and deceleration. 
 6  */ 7 public interface Interpolator { 
 8   
 9     /** 
10      * Maps a value representing the 
elapsed fraction of an animation to a value 
that represents 
11      * the interpolated fraction. This 
interpolated value is then multiplied by 
the change in 
12      * value of an animation to derive 
the animated value at the current elapsed 
animation time. 
13      * 
14      * @param input A value between 0 
and 1.0 indicating our current point 
15      *        in the animation where 0 
represents the start and 1.0 represents 
16      *        the end 
17      * @return The interpolation value. 
This value can be more than 1.0 for 
18      *         interpolators which 
overshoot their targets, or less than 0 for 
19      *         interpolators that 
undershoot their targets. 
20      */21     float getInterpolation(float input); 
22 }
复制代码
我们以AccelerateInterpolator为例,实现
具体的策略,代码如下:
复制代码
 1 package android.view.animation; 
 2   
 3 import android.content.Context; 
 4 import android.content.res.TypedArray; 
 5 import android.util.AttributeSet; 
 6   
 7 /** 
 8  * An interpolator where the rate of 
change starts out slowly and 
 9  * and then accelerates. 
10  * 
11  */12 public class AccelerateInterpolator 
implements Interpolator { 
13     private final float mFactor; 
14     private final double mDoubleFactor; 
15   
16     public AccelerateInterpolator() { 
17         mFactor = 1.0f; 
18         mDoubleFactor = 2.0; 
19     } 
20   
21     /** 
22      * Constructor 
23      * 
24      * @param factor Degree to which the 
animation should be eased. Seting 
25      *        factor to 1.0f produces a 
y=x^2 parabola. Increasing factor above 
26      *        1.0f  exaggerates the 
ease-in effect (i.e., it starts even 
27      *        slower and ends evens faster) 
28      */29     public AccelerateInterpolator 
(float factor) { 
30         mFactor = factor; 
31         mDoubleFactor = 2 * mFactor; 
32     } 
33   
34     public AccelerateInterpolator 
(Context context, AttributeSet attrs) { 
35         TypedArray a = 
36             context.obtainStyledAttributes 
(attrs, com.android.internal.R.styleable. 
AccelerateInterpolator); 
37   
38         mFactor = a.getFloat 
(com.android.internal.R.styleable.
AccelerateInterpolator_factor, 1.0f); 
39         mDoubleFactor = 2 * mFactor; 
40   
41         a.recycle(); 
42     } 
43   
44     public float getInterpolation 
(float input) { 
45         if (mFactor == 1.0f) { 
46             return input * input; 
47         } else { 
48             return (float)Math.pow(input,
 mDoubleFactor); 
49         } 
50     } 
51 }
复制代码
其他的Interpolator实现在此不列举了。
如何在Animation模块实现不同的动画呢?
在这里我想提一个应用很广的概念:
依赖注入。
在Animation模块里实现不同的动画,就是
需要我们把各个Interpolator以父类或者接
口的形式注入进去。
注入的方法一般是构造函数,set方法,
注释等等。
我们看看animation类是怎么做的:
策略模式其实就是多态的一个淋漓精
致的体现。
3. 效果
(1).行为型模式
(2).消除了一些if...else...的条件语句
(3).客户可以对实现进行选择,但是客户必须
要了解这个不同策略的实现(这句话好像是
废话,总而言之,客户需要学习成本)
(4).代码注释中提到了缺省实现,可以让客
户不了解策略,也能实现默认的策略
(5).注入的方式有多种:构造函数,set方法
,注释。配置解析等等  *

{{*如何进行Android单元测试*
*
  1. Menifest.xml中加入:
    <application>中加入:
    <uses-library android:name="android.test.runner" />
    <application>外面加入:
    <uses-permission android:name="android.
  2. permission.RUN_
  3. INSTRUMENTATION" />
    <instrumentation android:name="android.test.
  4. InstrumentationTestRunner" android:targetPackage="name.feisky.android.test"
    android:label="Test for my app"/>
  5. 编写单元测试代码:必须继承自AndroidTestCase
    package name.feisky.android.test;
     
    import android.test.AndroidTestCase;
    import junit.framework.Assert;
     
    public class MyTest extends AndroidTestCase {
    private static final String Tag="MyTest";
     
    public void testSave() throws Throwable
    {
    int i=4+8;
    Assert.assertEquals(5,i);
    }
     
    public void testSomethingElse() throws Throwable {
    Assert.assertTrue(1 + 1 == 12);
    }
     
    }

执行测IntelliJ中:
      

  1.  
     
    eclipse中:右键 run as Android JUnit Test
    命令行工具:
    adb shell am instrument -w name.feisky.
  2. android.test/android.test.
  3. InstrumentationTestRunner
       
也可以新建一个测试项目进行测试
 
  1. New > Project > Android > Android Test Project.

  1. 添加测试用例类
    添加新类,基类设置
  2. android.test.ActivityInstrumentationTestCase2<HelloAndroid>
  3. 添加构造函数
    添加setUp()方法,这个方法在所有的测试之前进行
  4. 变量和测试环境的初始化。
    @Override
        protected void setUp() throws Exception {
            super.setUp();
            mActivity = this.getActivity();
            mView = (TextView) mActivity.findViewById(com.example.helloandroid.R.id.textview);
            resourceString = mActivity.getString(com.example.helloandroid.R.string.hello);
        }
  5. 添加testPreconditions()方法,检查初始化环境,
  6. 只执行一次
    public void testPreconditions() {
          assertNotNull(mView);
        }
  7. 添加单元测试
    public void testText() {
          assertEquals(resourceString,(String)mView.getText());
        }
  8. 测试 Run As... > Android JUnit Test
  9. *
    {{*Android设计模式--- 
      (之生成器模式  (建造者模式)*
    *
    建造者模式把构造和表示分离开,根据客
    户需求生产一个相应的对象。
    本来呢,我们根据Builder接口实现不同
    的具体的ConcreteBuilder,就可生产
    不同的对象了。
    但是,下面例子的只有一个Builder,
    所以也没有接口Builder,也没有其他的ConcreteBuilder。
    但是我今天要讲的例子太简单,简单到
    都不觉得是建造者模式,但是又有建造
    者模式的感觉。
    1. 意图
    将一个复杂对象的构建和它的表示分离,
    使得同样的创建过程可以创建不同的表示。
    2.结构图和代码
    android中大量的使用对话框组件,
    它的调用方法就是构建,拼接,表示。

    Builder通过setTitle(),setMessage(),
    setIcon()等方法在create()中构造出一个AlertDialogInstance对象。
    然后客户可以把把AlertDialogInstance
    对象show出去。
    针对这个例子,我有必要通过扩展一下,
    以正建造者模式之名。
    如何扩展?
    (1).创建其他的ConcreteBuilder
    (2).创建其他的ElseDialog
    (3).第1,2步决定了我们最好创建一个
    抽象的Builder
    (4).创建一个Context,把builder注入
    进去,生产不同的Dialog
    (或者其他UI)对象。
    3.效果
    (1).创建型模式
    (2).可以生产不同的Dialog,也可以生产
    其他的UI,生产的Product可以是差别很
    大的,所以也没必要为Product定义
    抽象父类。
    *                    *
          &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&

        ***Linux+Apache+PHP**+MySQL服务器环境(CentOS篇) *

        ***Linux+Apache+PHP**
        +MySQL服务器环境(CentOS篇) *

        *CentOS(Community ENTerprise Operating System)是Linux发行版
        之一,它是来自于Red Hat Enterprise Linux依照开放源代码规定释出
        的源代码所编译而成。CentOS是架构LAMP
        (Linux+Apache+PHP+MySQL)的理想操作系统,具有较高的稳定性。
        本文以CentOS为例介绍linux系统下yum安装Apache+PHP+MySQL的方法*

        *2.准备工作

        2.1.登录服务器

        登录远程服务器,如果您的服务器在本地
        并安装有桌面环境,也可以直接打开服务
        器桌面,进入终端管理器。
        在windows下Putty是一款出色的liunx远程登
        录工具,打开界面如下
         
         在图中黄色框中填入服务器ip,点击打开,
        之后提示输入用户名和密码,验证成功后完
        成登录服务器。
         2.2.配置源和更新系统软件

        2.2.1.定义非官方yum库

        官方提供的软件是当前的稳定版本,但不是
        最新版本,为了更好的运行dedecms,我们需要
        一些非官方的yum源。
        /RPM-GPG-KEY-jlitka
        vi /etc/yum.repos.d/utterramblings.repo
        添加以下内容
        [utterramblings]
        name=Jason's Utter Ramblings Repo
        baseurl=http://www.jasonlitka.com/media
        /EL$releasever/$basearch/
        enabled=1
        gpgcheck=1
        gpgkey=http://www.jasonlitka.com/media/
        RPM-GPG-KEY-jlitka
        [注]vim编辑器修改文件的方法请自行百度之
         2.2.2.更新系统
        yum update
        yum upgrade
         2.2.3.检查系统软件
        检查当前系统是否已经安装了
        apache 和 mysql
        yum list installed | grep httpd
        rpm -qa | grep httpd
        yum list installed | grep mysql
        rpm -qa | grep mysql
        如果已经存在,请先卸载

        2.3.创建目录

        在这里我们约定各数据存放目录如下
        网站数据   /www/htdocs
        日志目录   /www/log
        数据库文件 /www/mysql
        运行以下命令完成目录创建
        mkdir /www/mysql
        mkdir /www/htdocs
        mkdir /www/log/php
        mkdir /www/log/mysql
        添加apache和mysql用户
        useradd -s /sbin/nologin -M apache
        useradd -s /sbin/nologin -M mysql
        创建了目录之后还需要改变目录属主和
        用户组,apache和mysql才能完成读写操作
        chown -R apache:apache /www/htdocs
        chown -R mysql:mysql /www/mysql
        chown -R apache:apache /www/log/php
        chown -R mysql:mysql /www/log/mysql

        3.安装与配置*

        *3.1. yum 安装 Apache + PHP + MySQL
        yum -y install gcc gcc-c++ autoconf make 
         aclocal libtool expat-devel libxml2-devel 
        httpd php php-devel mysql mysql-server 
        mysql-devel libevent libevent-devel mageMagick 
        ImageMagick-devel php-mysql mod_ssl mod_perl mod_auth_mysql php-mcrypt php-gd php-xml 
        php-mcrypt php-mbstring php-ldap php-pear 
         php-xmlrpc php-pecl-memcache mysql-
        connector-odbc libdbi-dbd-mysql php-
        eaccelerator*
        *3.2.配置php
        vi /etc/php.ini
        请根据自己的情况修改,这里只列出部分
        需要注意的设置
        post_max_size = 32M
        memory_limit = 256M
        allow_url_fopen = On
        upload_max_filesize = 32M
        upload_tmp_dir = /var/tmp
        log_errors = On
        error_reporting = E_ALL & ~E_NOTICE |
        E_STRICT
        display_errors = Off
        error_log = /www/log/php/php_error.log
        magic_quotes_gpc = On*
        *3.3. 配置apache
        先给默认配置文件做个备份
        cp /etc/httpd/conf/httpd.conf /etc/httpd/
        conf/httpd.conf.bak
        编辑配置
        vi /etc/httpd/conf/httpd.conf
        根据自己的需要进行修改
        DocumentRoot "/www/htdocs"  # 修改为
        默认网站主目录
        NameVirtualHost *:80
        如果安装GBK版本dedecms出现乱码,可能
        需要注释掉这个参数
        #AddDefaultCharset UTF-8
        启动apache服务
        service httpd start
        检查apache是否正常,打开浏览器,输入 
        http://localhost,如果看到默认apache test page
        页面,即表示成功启动。*
        *3.4.配置mysql
        系统已经自动安装好了mysql,但我们需要
        做些简单的修改和优化,配置数据库文件
        和日志存放位置,才能启动。
        在 /usr/share/mysql/目录下有多个my-开头
        的cnf文件,我们可以针对我们自己的情况
        选择一个使用,我们这里选择my-medium.cnf
        把它复制到/etc目录里
        cp /usr/share/mysql/my-medium.cnf /etc/my.cnf
        编辑
        vi /etc/my.cnf
        修改以下配置,在原有的基础上修改,
        没有的选项就添加
        [client]
        port = 3306
        socket = /var/lib/mysql/mysql.sock
        default-character-set = utf8
        [mysqld]
        user = mysql
        datadir = /www/mysql
        log-error = /www/log/mysql/mysql_error.log
        log-bin=/www/log/mysql/mysql-bin
        expire_logs_days=7
        character-set-server = utf8
        --skip-external-locking
        启动mysql
        service mysqld start
        系统会自动安装初始数据库,然后启动,
        如果有错误,请查看/www/log/mysql
        /mysql_error.log里的错误信息
        设置mysql root用户密码
        mysql
        UPDATE mysql.user SET password =
        PASSWORD('你的密码') WHERE user = 'root';
        FLUSH PRIVILEGES;
        exit;
        +++++++++++++++++
        删除mysql一些无用的账号信息,root mysql只
        允许本地链接 安全设置。
        +++++++++++++++++ *
        *4.优化设置*
        *

        4.1.安全设置,禁用 PHP 的敏感函数

        vi /etc/php.ini
        取消disable_functions前的#,改为
        disable_functions = exec,shell_exec,system,popen,escapeshellcmd,
        escapeshellarg,gzuncompress,proc_open,proc_
        get_status,show_source,gzinflate

        4.2.开启gzip压缩

        gzip压缩可以减少服务器流量,但也会增
        加cpu资源消耗,是否要开启你需要
        根据情况决定
        vi /etc/httpd/conf/httpd.conf
        LoadModule deflate_module modules/
        mod_deflate.so
        <IfModule mod_deflate.c>
        DeflateCompressionLevel 6
        AddOutputFilterByType DEFLATE text/
        html text/plain text/xml application/x-httpd-php
        AddOutputFilter DEFLATE js css
        </IfModule>          *
        *5.建立网站*
        *
        创建网站目录
        mkdir /www/htdocs/demo
        更改以下网站目录的属主和属组
        chown -R apache:apache /www/htdocs/demo
        配置虚拟主机配置
        vi /etc/httpd/conf/httpd.conf
        在最后添加
        <VirtualHost *:80>
        ServerName hacktea8.com
        ServerAlias www.hacktea8.com
        DocumentRoot /www/htdocs/demo
        </VirtualHost>
        重启apache 
        service httpd restart
        +++++++++++++++
        本地测试 需要将域名与IP对应  写在本
        地hosts文件
        +++++++++++++++
        创建数据库
        mysql -u root -p
        create database demo; #demo为要创建的
        数据库名
        exit;
        环境搭建已经全部完成了,下面您只需要
        把Web网站程序上传到/www/htdocs/demo,
        并把您的域名解析到您的服务器ip,即可
        完成Web网站的安装,本教程到此结束。*
        &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&

        **使用HTML5开发))~WebApp性能注意点*!~

        ****使用HTML5开发))~WebApp性能注意点*!~ 

        *PhoneGap HTML5 应用简介
        PhoneGap是一个   
        用基于HTML,CSS
        和JavaScript的,   
        创建移动跨平台移
        动应用程序的快速
        开发平台。它使开
        发者能够利用iPhone,
        Android,Palm,
        Symbian,WP7,Bada
        和Blackberry智能
        手机的核心功能——包括地理定位,加速器,
        联系人,声音和振动等,此外PhoneGap拥有
        丰富的插件,可以以此扩展无限的功能。
        PhoneGap是免费的,但是它需要特定平台提供
        的附加软件,例如iPhone的iPhone SDK,
        Android的Android SDK等,也可以和DW5.5配
        套开发。使用PhoneGap只比为每个平台分别 
        建立应用程序好一点点,因为虽然基本代码是
        一样的,但是你仍然需要为每个平台分别  
        编译应用程序。*

        *PhoneGap WebApp分析
        我们分析了目前Google play, 安卓市场,豌豆荚
        市场,机锋市场的下载量前300名的应用,以及
        每个分类的前50名的应用进行分析,发现以下 
        7个应用采用了PhoneGap开发:
        **
        *来自国内市场的有5个应用.当然,还有更多的 
        纯HTML5应用程序没有计算在内,也没有计算 
        来自iOS的phoneGap应用。*

        *分析工具WAPA介绍
        我们将上述的PhoneGap应用全部使用了WAPA 
        进行分析,WAPA是Web Application Performance
        Analyzer(Web应用性能分析器)的简称,其来源于
        Intel软件与服务部门全球合作伙伴关系事业  
        部HTML5应用团队的创新项目。旨在给开发者 
        提供如何编写高性能HTML5应用程序提供 
        代码级别的建议*

        *WAPA对HTML5应用分析过程如图所示*
        **

        *1.    首先解包目标Web应用的安装包;
        2.    接下来解析相应的源代码文件(.html, .js. .css)
        3.    如果是JS文件,则生成相应的语法树;如果是 
        html和CSS文件,则静态解析文件;
        4.    将解析后的文件或者语法树和WAPA中预置 
        的优化规则进行匹配和识别;
        5.    根据匹配和识别的结果生成相应的report,
        供开发者选择**

        *我们对目前采用PhoneGap开发的App使用 
        WAPA分析之后,得出一些通用性的结论,
        提供给开发者,供大家在开发PhoneGap App时参考*

        *性能注意点介绍
        经过WAPA优化规则的分析,我们得到了在
        PhoneGap开发中性能优化的一系列的通用性
        性能问题点,经过分析之后,以下六条规则
        是在PhoneGap App中经常遇到的性能可以
        得到优化的点:
        *
        *1.      将for循环条件语句中的.length属性存入
        一个局部变量
        该规则是指:在使用循环的时候,要尽量避免
        使用for in, 除非是在一个不明确的对象里面,
        需要迭代其内部对象。如果已经知道其结构和
        内容数据类型,避免使用for in。在循环中,
        将i.length存储为局部变量,可以提高for循环的
        效率。从下列三个算法的测试结果即可看出 **

        *算法一,使用for in,:
        var i=0
        for (i in geo){
               document.write("The country is " +
        geo[i] +"<br />")
        }
        运行时间结果是最长的,即最没有效率的:(24ms)*

        *算法二,for循环
        for (var i=0 ; i < geo.length; i++){
               document.write("The country is " +
        geo[i] +"<br />")
        }
        运行时间结果,比较有效率(17ms)*

        *算法三 for循环,将i.length存储为局部变量
        for (var i=0, len=geo.length; i < len; i++){
               document.write("The country is " +
        geo[i] +"<br />")
        }
        运行时间结果,最高效。(14ms)*

        *2.      用className属性取代其他style属性
        在给静态的DOM元素添加样式的时候,有以下
        三种写法,分别是系列的.css()、单独.css() 
        写法,或者使用.addClass()方法,给元素添加
        类名之后,在CSS文件中,添加样式**
        *下图是我们在不同平台测试出来的结果,分别
        对应不用的Web Runtime,在移动手机端,
        结论是一样的 *
        **
        *读者可以通过下面的链接亲自感受一下上述三种
        写法带来的性能差异:http://jsperf.com/class-ywq*

        *3.      appendChild()的部分使用document 
        fragments来修改DOM元素
        当我们需要对DOM元素进行一系列操作时,
        可以通过document fragments来减少重绘和重排
        的次数。它可以在当前DOM之外构建一个子树
        ,对齐进行修改之后,再把它拷贝回文档 *
        *其具体使用示例代码如下:
        * var fragment = document.createDocumentFragment();
        appendDataToElment(fragment, data);
        document.getElementById("mylist").appendChild(fragment);  *

        *4.      CSS 中将 2D的CSS变化转化为 3D的CSS
        变换CSS的变换正在变得越来越强大,3D的
        CSS变换已经能够非常完整地支持GPU硬件加速
        ,而传统的2D CSS转换仍然无法使用GPU进行
        加速,导致的结果就是2D的CSS转换比3D CSS转
        换还要慢。我们建议开发者,将2D的CSS变换更
        改为Z轴为0的3D CSS转换,以便充分利用GPU的
        硬件特性 *

        *5.      在HTML文档中,将inline的 JavaScript
        代码转化为独立的JavaScript文件 
        虽然JavaScript是动态解释执行的语言,绝大
        多数的Web Runtime为了提高JavaScript的解释
        执行时间,都会将JavaScript进行预编译为一个
        中间态的文件。WebKit,IE10等都不例外。
        但是HTML文档中的JavaScript代码是无法被预
        编译为中间态文件的,这会显著减低执行效率
        和时间,所以我们强烈建议PhoneGap的开发
        人员将HTML中的JavaScript代码剥离出来,
        放入单独的JavaScript文件中 *

        *6.      由于脚本的阻塞特性,将JavaScript脚本放
        在文件的最底端以及成组加载 
        由于每个<script>标签在下载时都会阻塞页面
        解析的过程,所以限制页面<script>总数也可以
        改善性能。所以成组加载JavaScript脚本可以
        提升页面整体性能,这个规则不仅对内联脚本
        有效,对外部脚本同样适用  **

        #*原因是在于每个HTTP 请求都会产生额外的性能
        负担,下载一个100KB的脚本远比下载4个25KB 
        的脚本要快*#

        *同时将页面和页面初始化无关的JavaScript文件 
        放在页面的最低端进行加载都可以提高性能*

        *结论
        随着HTML5的井喷式发展,使用PhoneGap开发
        的本地应用程序也将会越来越多。性能问题是 
        广大开发者最为关心的一个使用HTML5开发 
        App的担忧。本文分析和总结了目前市面上的 
        PhoneGap 应用程序,使用WAPA工具对其进行 
        了性能分析,得出六点PhoneGap开发应用程序 
        经常出现的性能优化点。供广大PhoneGap  
         HTML5开发者参考 *index CSS*
        *
        
        
        
        
         
        新增說明文字
        






        
        
















        /*  Licensed to the Apache Software Foundation (ASF) under one
          or more contributor license agreements.
         See the NOTICE file
          distributed with this work for
        additional information
          regarding copyright ownership. 
        The ASF licenses this file
          to you under the Apache License,
        Version 2.0 (the
          "License");
        you may not use this file
        except in compliance
          with the License.
         You may obtain a copy of the License at
          Unless required by
        applicable law or agreed to in writing,
         
        software distributed under the License is distributed on an
          "AS IS" BASIS,
        WITHOUT WARRANTIES OR CONDITIONS OF ANY
          KIND,
         either express or implied.  See the License for the
          specific language governing
        permissions and limitations

         under the License.
        */
        body {
          background-color:#F6F4F2;

         font-family:"Helvetica Neue", Helvetica, Arial, sans-serif;
          font-size:16px;
        }
        h1, ul,
         li {
          margin:0px;
          padding:0px;
        }
        #header
        {
          background-color:#515151;
          background:#515151 -webkit-gradient(
            linear,
            left top,
            left bottom,
           
        color-stop(0.2, #515151),
            color-stop(0.8, #302F2D)
          );
          background:-moz-linear-gradient
        (center bottom , #515151 20%, #747474 80%);

         border-top:1px solid #919192;
          height:32px;
          left:0px;
          position:fixed;
          top:0px;
          width:100%;
         
        z-index:1;
        }
        #subheader {
          background-color:#CBCBCB;

         background:-webkit-gradient(linear,
            left top,
            left bottom,
            color-stop(0.0, #F9F9F9),
          
         color-stop(1.0, #CBCBCB)
          );
          background:-moz-linear-gradient
        (center bottom , #CBCBCB 0%, #F9F9F9 100%);
          border-top:1px solid #383A3C;
         
        border-bottom:1px solid #919395;
          height:32px;
          left:0px;
         
        position:fixed;
          top:32px;
          width:100%;
          z-index:1;
        }
        #sidebar
         {
          background-color:#ECEAE7;
          bottom:0px;
          left:0px;
          overflow:auto;

         padding:20px 40px 0px 0px;
          position:fixed;
          text-align:right;
          top:66px;
         
        width:180px;
          z-index:1;
        }
        #scrollable
         {
          bottom:0px;
          left:220px;
          position:fixed;
          overflow:auto;
          right:0px;
          top:64px;
        }
        #content
        {
        /*  top:64px;*/
        /*  bottom:0px;*/
        /*  right:0px;*/
        /*
          left:220px;*/
        /*
          margin:64px auto 0px 220px;*/
         
        margin:20px 60px;
        /*  position:absolute;*/
        /*  overflow:auto;*/
         
        z-index:0;
        }
        #header h1,
        #header h1 a,
        #subheader h1 {
          color:#F6F4F2;
          font-size:18px;
          font-weight:normal;
         
        line-height:32px;
          margin:0px;
          text-align:center;
          text-shadow:0px -1px 1px #222222;
        }
        #header h1 a strong
        {
          font-weight:bold;
        }
        #header h1 {
          text-align:left;
          margin-left:20px;
        }
        #subheader h1
        {
          color:#000000;
          text-
        shadow:#FFFFFF 0px 1px 0px;
        }
        #header small,
        #subheader small
        {
          color:#EFEFEF;
          font-size:14px;
          line-height:32px;
          position:absolute;
          top:0px;
          right:20px;
          text-shadow:-1px 1px 1px #666666;
        }
        #sidebar .vertical_divider
         {
          background-color:#CCCCCC;
          bottom:0px;
         
        border-right:1px solid #FFFFFF;
          position:absolute;
          top:0px;
          right:0px;
          width:1px;
        }
        #sidebar h1
        {
          color:#000000;
          font-size:18px;
          padding:0px;
          margin:30px 0px;
          font-weight:normal;
          text-shadow:#FFFFFF 0px 1px 0px;
        }
        #sidebar ul,
        #sidebar li
         {
          margin:0px;
          padding:0px;
        }
        #sidebar li,
        #sidebar li a {
          color:#767573;
          font-size:14px;
          list-style:none;
          margin:15px 0px;
          text-shadow:#FFFFFF 0px 1px 1px;
        }
        #sidebar li a
        {
          -webkit-transition:color .15s ease-out;
          -moz-transition:color .15s ease-out;
          -o-transition:color .15s ease-out;
        }
        #sidebar li a:hover
         {
          color:#242220;
          -webkit-transition:color .15s ease-in;
          -moz-transition:color .15s ease-in;
          -o-transition:color .15s ease-in;
        }

        #otherbar
         {
          display:none;
        }
        #content
        {
          font-size:13px;
          line-height:160%;
          max-width:750px;
        }
        #content h1
        {
          border-bottom:2px solid;
          font-size:2em;
          font-weight:normal;
          margin:2.0em 0px 1.3em 0px;
          padding-bottom:0.6em;
        }
        #content h2 {
          color:#242220;
          font-size:1.4em;
          font-weight:bold;
          margin:1.3em 0px 0.8em 0px;
          text-shadow:#FFFFFF 0px 1px 1px;
        }
        #content h3
         {
          font-size:1.1em;
          font-weight:bold;
          margin:0.8em 0px 0.5em 0px;
          text-shadow:#FFFFFF 0px 1px 1px;
        }
        hr
         {
          display:none;
          border:none;
          margin:40px 0px;
          border-top:1px solid #CCCCCC;
          border-bottom:1px solid #FFFFFF;
        }
        p,blockquote,pre,ul
         {
          margin:1em 0px;
        }
        h2:after,
        h3:after
         {
         content: ":";
        }
        blockquote
         {
          color:#767573;
         font-style:normal;
          margin-left:35px;
          padding-left:20px;
         position:relative;
         text-shadow:#FFFFFF 0px 1px 0px;
        }
        blockquote code
         {
         font-style: normal;
        }
        blockquote p
         {
          padding:10px 0px;
        }
        blockquote::before
         {
          font-style: normal;
          content: '\201C';
          font-size: 450%;
          font-family:Georgia, Palatino,
         'Times New Roman', Times;;
          position: absolute;
          left: -25px;
          top:0.3em;
          color: #E0E0E0;
        }
        ul
         {
          margin-left:40px;
        }
        ul > li {
         list-style:disc;
         list-style-position:outside;
        }
        ul ul
         {
          margin-bottom:0.5em;
          margin-top:0.5em;
        }

        code
         {
         font-family:"DejaVu", "Monaco", "Courier New", "Courier";
         font-size:90%;
         padding:2px 4px;
         white-space:pre-wrap;;
        }
        pre
         {
        /*    border:1px solid #CCCCCC;*/
            background:#F2F0EE;
            -webkit-border-radius:11px;
            -moz-border-radius:11px;
            border-radius:11px;
            display:block;
            line-height:110%;
            margin:1.5em 0px 3em 0px;
            padding:15px 20px;
            white-space:pre-wrap;
        }
        pre code {
          background:none;
         border:none;
         font-size:11px;
         padding:0px;
        }
        a[href] {
        /*  color:inherit;*/
          color:#F06433;
          text-decoration:none;
          text-shadow:#FFF 0px 1px 0px;
        }
        a[href]:hover
        {
          color:#d0410f;
        }
        .prettyprint a[href],
        .prettyprint a[href]
         span {
          text-decoration:underline;
          text-shadow:none;
        }
        .prettyprint a[href]
         :hover,
        .prettyprint a[href]
         span :hover {
          text-decoration:none;
        }
        code a[href]
         {
          color:inherit;
        /*
          border-bottom:1px dotted #000000;*/
          text-decoration:underline;
        }
        code a[href]:hover {
          color:inherit;
          text-decoration:none;
        }
        a[href].external:after {
         content: "*";
         font-style: super;
         opacity: .5;
        }
        #index {
         -webkit-column-width: 235px;
         -webkit-column-rule-width: 5px;
         -moz-column-width: 235px;
         -moz-column-rule-width: 5px;
         column-width: 235px;
         column-rule-width: 5px;
        }
        #index h2:after,
        #index h3:after
         {
          content:"";
        }
        #index h2
         {
          margin:0px;
          padding:0px;
        }
        #index
         {
          padding: 10px 1px;
        }
        #index ul
         {
         margin:0px 0px 30px 0px;
         padding:0;
        }
        #index ul li
         {
         list-style: none;
        }
        #index ul li a {
        }
        #home h1
         {
          border-bottom:1px solid #919395;
          padding-bottom:20px;
          margin:30px 0px;
        }
        #home h2
         {
          font-weight:normal;
          margin:0px 0px 10px 0px;
          padding:0px;
        }
        #home h2:after
         {
          content:'';
        }
        #home h2
         a {
          text-shadow:#FFFFFF 0px 1px 1px;
        }
        #home span {
          color:#8B8078;
          font-size:14px;
          text-shadow:#FFFFFF 0px 1px 0px;
        }
        #home ul {
          float:left;
          margin:0px;
          padding:0px;
        }
        #home ul li {
          float:left;
          height:120px;
          list-style:none;
        *

        moblie CSS *
        *
        /* Licensed to the Apache Software Foundation (ASF) under one
          or more contributor license agreements.
         See the NOTICE file
          distributed with this work for additional information
          regarding copyright ownership.  The ASF licenses this file
          to you under the Apache License, Version 2.0
         (the
          "License"); you may not use this file except in compliance
          with the License.  You may obtain a copy of the License at

          Unless required by applicable law or agreed to in writing,
          software distributed under the License is distributed on an
          "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
          KIND, either express or implied.  See the License for the
          specific language governing permissions and limitations
          under the License.
        */
        body {
          margin:0px;
          padding:0px;
        }
        #header
         {
          position:static;
        }
        #header h1 {
          margin:0px;
          text-align:center;
        }
        #subheader
         {
          position:static;
          text-align:center;
        }
        #subheader h1
         {
          display:none;
        }
        #subheader small
         {
          position:static;
        }
        #sidebar
         {
          display:none;
        }
        #scrollable {
          position:static;
        }
        #content
         {
          margin:0px;
          max-width:none;
          padding:10px;
          position:static;
        }
        #home,
        #index
         {
          margin:0px 10px;
        }
        #home h1,
        #index h2
         {
          border:none;
          color:#CCCCCC;
          font-size:20px;
          font-weight:bold;
          margin:10px 0px;
          padding:0px;
          text-shadow:#FFFFFF 0px 1px 0px;
        }
        #home h2 a,
        #index ul li a
         {
          text-shadow:#FFFFFF 0px 1px 1px;
        }
        #home ul,
        #index ul
         {
          background-color:#F9F9F9;
          border:1px solid #CCCED0;
          -moz-border-radius:6px;
          -webkit-border-radius:6px;
          border-radius:6px;
          display:block;
          margin:0px 0px 20px 0px;
          padding:0px;
          float:none;
        }
        #home ul li,
        #index ul li
         {
          border-bottom:1px solid #CCCED0;
          display:block;
          float:none;
          height:100%;
          margin:0px;
          padding:0px;
          width:100%;
        }
        #home ul li:last-child,
        #index ul li:last-child
         {
          border-bottom:none;
        }
        #home li h2
         {
          margin:0px;
          padding:0px;
        }
        #home li h2 a,
        #index li a
         {
          background:url(arrow.png) no-repeat 100% 50%;
          color:#66686A;
          display:block;
          font-size:16px;
          font-weight:normal;
          margin:0px;
          padding:10px 20px;
        }
        #home li span
         {
          display:none;
        }
        #index {
         -webkit-column-width: auto;
         -webkit-column-rule-width: auto;
         -moz-column-width: auto;
         -moz-column-rule-width: auto;
         column-width: auto;
         column-rule-width: auto;
        }                                              *


        &&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&&